<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
/**
* CodeIgniter
*
* An open source application development framework for PHP 5.1.6 or newer
*
* @package CodeIgniter
* @author ExpressionEngine Dev Team
* @copyright Copyright (c) 2008 - 2011, EllisLab, Inc.
* @license http://codeigniter.com/user_guide/license.html
* @link http://codeigniter.com
* @since Version 1.0
* @filesource
*/
// ------------------------------------------------------------------------
/**
* Initialize the database
* 初始化数据库类
*
* @category Database
* @author ExpressionEngine Dev Team
* @link http://codeigniter.com/user_guide/database/
* @param string 确定是否应使用或不活动记录
* @param bool Determines if active record should be used or not
*/
function &DB($params = '', $active_record_override = NULL)
{
// Load the DB config file if a DSN string wasn't passed
// 加载DB的配置文件,如果不获通过的DSN字符串
// $params必须为字符串,并且没有'://'字符
if (is_string($params) AND strpos($params, '://') === FALSE)
{
// Is the config file in the environment folder?
// 环境“文件夹中的config文件?
if ( ! defined('ENVIRONMENT') OR ! file_exists($file_path = APPPATH.'config/'.ENVIRONMENT.'/database.php'))
{
if ( ! file_exists($file_path = APPPATH.'config/database.php'))
{
show_error('The configuration file database.php does not exist.配置文件database.php中不存在');
}
}
//加载指定配置文件
include($file_path);
//如果$db数组为空值或者不存在
if ( ! isset($db) OR count($db) == 0)
{
show_error('No database connection settings were found in the database config file.没有数据库连接设置数据库配置文件中发现。');
}
if ($params != '')
{
$active_group = $params;
}
if ( ! isset($active_group) OR ! isset($db[$active_group]))
{
show_error('You have specified an invalid database connection group.你指定了无效的数据库连接组');
}
$params = $db[$active_group];
}
elseif (is_string($params)) //如果为字符串
{
/* parse the URL from the DSN string
* Database settings can be passed as discreet
* parameters or as a data source name in the first
* parameter. DSNs must have this prototype:
* $dsn = 'driver://username:password@hostname/database';
*/
/*从DSN字符串解析URL
*数据库设置可以通过谨慎
*参数或数据源名称在第一
*参数。 DSN中必须有这样的原型:
* $ DSN='司机://用户名:密码@主机名/数据库“;
*/
//parse_url 本函数解析一个 URL 并返回一个关联数组,包含在 URL 中出现的各种组成部分。
if (($dns = @parse_url($params)) === FALSE)
{
show_error('Invalid DB Connection String 无效的DB连接字符串');
}
$params = array(
'dbdriver' => $dns['scheme'], //数据库类型
'hostname' => (isset($dns['host'])) ? rawurldecode($dns['host']) : '', //服务器地址
'username' => (isset($dns['user'])) ? rawurldecode($dns['user']) : '', //用户名
'password' => (isset($dns['pass'])) ? rawurldecode($dns['pass']) : '', //密码
'database' => (isset($dns['path'])) ? rawurldecode(substr($dns['path'], 1)) : ''
); //数据库名称
// were additional config items set?
// 额外的配置项是设置?
//额外的配置项是设置?
if (isset($dns['query']))
{
//parse_str() 将查询字会串解析到变量中
//parse_str("id=23&name=John%20Adams",$myArray);
//print_r($myArray);
/*
Array
(
[id] => 23
[name] => John Adams
)
*/
parse_str($dns['query'], $extra);
foreach ($extra as $key => $val)
{
// booleans please
//如果值为true
if (strtoupper($val) == "TRUE")
{
$val = TRUE;
}
elseif (strtoupper($val) == "FALSE")
{
$val = FALSE;
}
$params[$key] = $val;
//将一些扩展值放入到$params数组中去
}
}
}
// No DB specified yet? Beat them senseless...
// 没有设置数据库类型
if ( ! isset($params['dbdriver']) OR $params['dbdriver'] == '')
{
show_error('You have not selected a database type to connect to.您没有选择连接到数据库类型');
}
// Load the DB classes. Note: Since the active record class is optional
// we need to dynamically create a class that extends proper parent class
// based on whether we're using the active record class or not.
// Kudos to Paul for discovering this clever use of eval()
//加载的DB类。注:由于活动记录类是可选
//我们需要动态创建一个类,扩展适当的父类
//根据我们是否使用活动记录类或不。
//荣誉保罗发现这个聪明的使用eval()
if ($active_record_override !== NULL)
{
$active_record = $active_record_override;
}
require_once(BASEPATH.'database/DB_driver.php');
if ( ! isset($active_record) OR $active_record == TRUE)
{
require_once(BASEPATH.'database/DB_active_rec.php');
if ( ! class_exists('CI_DB'))
{
eval('class CI_DB extends CI_DB_active_record { }');
//eval()函数把字符串按照php代码来计算
//该字符串必须是合法的php代码,且必须以分号结尾
//如果没有在代码字符串中调用return语句,则返回null,如果代码中存在解析错误,则eval()函数返回false
}
}
else
{
if ( ! class_exists('CI_DB'))
{
eval('class CI_DB extends CI_DB_driver { }');
}
}
require_once(BASEPATH.'database/drivers/'.$params['dbdriver'].'/'.$params['dbdriver'].'_driver.php');
// Instantiate the DB adapter 实例DB适配器
$driver = 'CI_DB_'.$params['dbdriver'].'_driver';
$DB = new $driver($params);
if ($DB->autoinit == TRUE) //autoinit 是指初始化的意思吗?
{
$DB->initialize();
}
if (isset($params['stricton']) && $params['stricton'] == TRUE)
{
//sql_mode好像是
/*
数值列中的插入操作受SQL模式的影响,它是由sql_mode系统变量控制的(请参见1.8.2节,“选择SQL模式”)。下面介绍了严格模式(由STRICT_ALL_TABLES或STRICT_TRANS_TABLES模式值选择)和RROR_FOR_DIVISION_BY_ZERO。要想打开所有限制,可简单地使用TRADITIONAL模式,它包含严格模式和ERROR_FOR_DIVISION_BY_ZERO:
mysql> SET SQL_MODE='TRADITIONAL';
如果将数值插入具有准确类型的列(DECIMAL或整数),如果值在列允许的范围内,将以准确值形式插入数值。
如果数值在其小数部分有过多位,将执行四舍五入操作并给出告警。关于四舍五入的具体介绍,请参见四舍五入一节。
如果数值在其整数部分有过多位,数值过大,并将按下述方式处理:
· 如果未启用严格模式,该数值将被截短为最近的合法值,并发出警告。
· 如果启用了严格模式,将给出溢出错误。
不检测下溢,因而下溢处理是不确定的。
默认情况下,除0操作会导致NULL结果,不产生告警。启用了ERROR_FOR_DIVISION_BY_ZERO SQL模式后,MySQL会以不同方式处理除0问题:
· 如果未启用严格模式,发出警告。
· 如果启用了严格模式,将禁止包含除0操作的插入和更新,并给出错误。
换句话讲,对于包含执行除0操作的表达式的插入和更新,将被当作错误对待,但除了严格模式外还需要ERROR_FOR_DIVISION_BY_ZERO。
*/
$DB->query('SET SESSION sql_mode="STRICT_ALL_TABLES"');
}
return $DB;
}
/* End of file DB.php */
/* Location: ./system/database/DB.php */