在github上发现了个不错的项目
https://github.com/chaegumi/cxpcms

我一直还说着要做一个管理框架来着,有人做了就拿下看看
结果在本地配置好之后,一直都登录提示验证码错误,这个倒是开始怀疑人生了

1 验证码错误?

反复确认了Captcha.php里生成的和我输入的是一致的
然后确认对比流程,发现提交的是对的,但本地读取的是空值
另外查看session目录的文件,每次访问都产生新的session文件
说明session会话根本没有跟踪到,每次访问都是当做新用户看待,所以比对失败

2 那为什么每次都是新的session呢?

CI根据cookie里的ci_session值作为session_id
做了个简单的页面,打印cookie和session,每次这两个值都在变
另外做了个原生页面的,这个值是不会变的

3 那肯定是CI的问题

直接查看文件
system/libraries/Session/Session.php
检查session的处理流程:

    print_r($_COOKIE);
    echo $this->_config['cookie_name'].'//'.$this->_sid_regexp.'//';
    if (isset($_COOKIE[$this->_config['cookie_name']])
      && (
        ! is_string($_COOKIE[$this->_config['cookie_name']])
        OR ! preg_match('#\A'.$this->_sid_regexp.'\z#', $_COOKIE[$this->_config['cookie_name']])
      )
    )
    {
      echo 'del//';
      unset($_COOKIE[$this->_config['cookie_name']]);
    }


调试起来发现,总是进入del的流程,cookie被删掉了
导致后面会重新设置cookie
很明显是这个导致的
preg_match('#\A'.$this->_sid_regexp.'\z#', $_COOKIE[$this->_config['cookie_name']]


4 表达式在做什么

    if (PHP_VERSION_ID < 70100)
    {
      if ((int) ini_get('session.hash_function') === 0)
      {
        ini_set('session.hash_function', 1);
        ini_set('session.hash_bits_per_character', $bits_per_character = 4);
      }
      else
      {
        $bits_per_character = (int) ini_get('session.hash_bits_per_character');
      }
    }
    elseif ((int) ini_get('session.sid_length') < 40 && ($bits_per_character = (int) ini_get('session.sid_bits_per_character')) === 4)
    {
      ini_set('session.sid_length', 40);
    }

    switch ($bits_per_character)
    {
      case 4:
        $this->_sid_regexp = '[0-9a-f]{40,}';
        break;
      case 5:
        $this->_sid_regexp = '[0-9a-v]{40,}';
        break;
      case 6:
        $this->_sid_regexp = '[0-9a-zA-Z,-]{40,}';
        break;
    }


我们看到表达式是 [0-9a-f]{40,} 而cookie长度是26个字符,所以总是不能符合要求
打印出来配置,发现也一直是26,ini_set也不起作用

5 如何修复

我们看到新版本的CI已经修复了这个问题
    // Yes, 4,5,6 are the only known possible values as of 2016-10-27
    switch ($bits_per_character)
    {
      case 4:
        $this->_sid_regexp = '[0-9a-f]';
        break;
      case 5:
        $this->_sid_regexp = '[0-9a-v]';
        break;
      case 6:
        $this->_sid_regexp = '[0-9a-zA-Z,-]';
        break;
    }


简单升级替换system文件夹即可解决

项目更新在 https://github.com/hqlulu/cxpcms


原创内容如转载请注明:来自 阿权的书房
收藏本文到网摘
发表评论
AD
表情
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
打开HTML 打开UBB 打开表情 隐藏
昵称   密码   游客无需密码
网址   电邮   [注册]
               

验证码 不区分大小写
 

阅读推荐

服务器相关推荐

开发相关推荐

应用软件推荐