更新内核,删除部分不常用驱动

This commit is contained in:
2016-07-16 20:07:06 +08:00
parent 87533013c6
commit 152f8bf165
13 changed files with 20 additions and 1554 deletions

View File

@@ -19,6 +19,9 @@ use think\Route;
class Url
{
// 生成URL地址的root
protected static $root;
/**
* URL生成 支持路由反射
* @param string $url URL表达式
@@ -113,7 +116,7 @@ class Url
// 检测域名
$domain = self::parseDomain($url, $domain);
// URL组装
$url = $domain . Request::instance()->root() . '/' . ltrim($url, '/');
$url = $domain . (self::$root ?: Request::instance()->root()) . '/' . ltrim($url, '/');
return $url;
}
@@ -316,4 +319,11 @@ class Url
{
Cache::rm('think_route_map');
}
}
// 指定当前生成URL地址的root
public static function root($root)
{
self::$root = $root;
Request::instance()->root($root);
}
}

View File

@@ -1,94 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\cache\driver;
use think\Cache;
use think\Exception;
/**
* Apc缓存驱动
* @author liu21st <liu21st@gmail.com>
*/
class Apc
{
protected $options = [
'expire' => 0,
'prefix' => '',
];
/*****************************
需要支持apc_cli模式
******************************/
/**
* 架构函数
* @param array $options 缓存参数
* @throws Exception
* @access public
*/
public function __construct($options = [])
{
if (!function_exists('apc_cache_info')) {
throw new \BadFunctionCallException('not support: Apc');
}
if (!empty($options)) {
$this->options = array_merge($this->options, $options);
}
}
/**
* 读取缓存
* @access public
* @param string $name 缓存变量名
* @return mixed
*/
public function get($name)
{
return apc_fetch($this->options['prefix'] . $name);
}
/**
* 写入缓存
* @access public
* @param string $name 缓存变量名
* @param mixed $value 存储数据
* @param integer $expire 有效时间(秒)
* @return bool
*/
public function set($name, $value, $expire = null)
{
if (is_null($expire)) {
$expire = $this->options['expire'];
}
$name = $this->options['prefix'] . $name;
return apc_store($name, $value, $expire);
}
/**
* 删除缓存
* @access public
* @param string $name 缓存变量名
* @return bool|\string[]
*/
public function rm($name)
{
return apc_delete($this->options['prefix'] . $name);
}
/**
* 清除缓存
* @access public
* @return bool
*/
public function clear()
{
return apc_clear_cache('user');
}
}

View File

@@ -1,763 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\cache\driver;
use think\Cache;
/**
* Secache缓存驱动
* @author liu21st <liu21st@gmail.com>
*/
class Secache
{
protected $handler = null;
protected $options = [
'project' => '',
'path' => '',
'expire' => 0,
'prefix' => '',
];
/**
* 架构函数
* @param array $options 缓存参数
* @access public
*/
public function __construct($options = [])
{
if (!empty($options)) {
$this->options = array_merge($this->options, $options);
}
if (substr($this->options['path'], -1) != '/') {
$this->options['path'] .= '/';
}
$this->handler = new SecacheClient;
$this->handler->workat($this->options['path'] . $this->options['project']);
}
/**
* 读取缓存
* @access public
* @param string $name 缓存变量名
* @return mixed
*/
public function get($name)
{
$name = $this->options['prefix'] . $name;
$key = md5($name);
$this->handler->fetch($key, $return);
return $return;
}
/**
* 写入缓存
* @access public
* @param string $name 缓存变量名
* @param mixed $value 存储数据
* @param integer $expire 有效时间(秒)
* @return boolean
*/
public function set($name, $value)
{
$name = $this->options['prefix'] . $name;
$key = md5($name);
return $this->handler->store($key, $value);
}
/**
* 删除缓存
* @access public
* @param string $name 缓存变量名
* @return boolen
*/
public function rm($name)
{
$name = $this->options['prefix'] . $name;
$key = md5($name);
return $this->handler->delete($key);
}
/**
* 清除缓存
* @access public
* @return boolen
*/
public function clear()
{
return $this->handler->_format(true);
}
}
if (!defined('SECACHE_SIZE')) {
define('SECACHE_SIZE', '15M');
}
class SecacheClient
{
public $idx_node_size = 40;
public $data_base_pos = 262588; //40+20+24*16+16*16*16*16*4;
public $schema_item_size = 24;
public $header_padding = 20; //保留空间 放置php标记防止下载
public $info_size = 20; //保留空间 4+16 maxsize|ver
//40起 添加20字节保留区域
public $idx_seq_pos = 40; //id 计数器节点地址
public $dfile_cur_pos = 44; //id 计数器节点地址
public $idx_free_pos = 48; //id 空闲链表入口地址
public $idx_base_pos = 444; //40+20+24*16
public $min_size = 10240; //10M最小值
public $schema_struct = array('size', 'free', 'lru_head', 'lru_tail', 'hits', 'miss');
public $ver = '$Rev: 3 $';
public $name = '系统默认缓存(文件型)';
public function workat($file)
{
$this->_file = $file . '.php';
$this->_bsize_list = array(
512 => 10,
3 << 10 => 10,
8 << 10 => 10,
20 << 10 => 4,
30 << 10 => 2,
50 << 10 => 2,
80 << 10 => 2,
96 << 10 => 2,
128 << 10 => 2,
224 << 10 => 2,
256 << 10 => 2,
512 << 10 => 1,
1024 << 10 => 1,
);
$this->_node_struct = array(
'next' => array(0, 'V'),
'prev' => array(4, 'V'),
'data' => array(8, 'V'),
'size' => array(12, 'V'),
'lru_right' => array(16, 'V'),
'lru_left' => array(20, 'V'),
'key' => array(24, 'H*'),
);
if (!file_exists($this->_file)) {
$this->create();
} else {
$this->_rs = fopen($this->_file, 'rb+') || $this->triggerError('Can\'t open the cachefile: ' . realpath($this->_file), E_USER_ERROR);
$this->_seek($this->header_padding);
$info = unpack('V1max_size/a*ver', fread($this->_rs, $this->info_size));
if ($info['ver'] != $this->ver) {
$this->_format(true);
} else {
$this->max_size = $info['max_size'];
}
}
$this->idx_node_base = $this->data_base_pos + $this->max_size;
$this->_block_size_list = array_keys($this->_bsize_list);
sort($this->_block_size_list);
return true;
}
public function create()
{
$this->_rs = fopen($this->_file, 'wb+') || $this->triggerError('Can\'t open the cachefile: ' . realpath($this->_file), E_USER_ERROR);
fseek($this->_rs, 0);
fputs($this->_rs, '<' . '?php exit()?' . '>');
return $this->_format();
}
public function _puts($offset, $data)
{
if ($offset < $this->max_size * 1.5) {
$this->_seek($offset);
return fputs($this->_rs, $data);
} else {
$this->triggerError('Offset over quota:' . $offset, E_USER_ERROR);
}
}
public function _seek($offset)
{
return fseek($this->_rs, $offset);
}
public function clear()
{
return $this->_format(true);
}
public function fetch($key, &$return)
{
$locked = false;
if ($this->lock(false)) {
$locked = true;
}
if ($this->search($key, $offset)) {
$info = $this->_get_node($offset);
$schema_id = $this->_get_size_schema_id($info['size']);
if (false === $schema_id) {
if ($locked) {
$this->unlock();
}
return false;
}
$this->_seek($info['data']);
$data = fread($this->_rs, $info['size']);
$return = unserialize($data);
if (false === $return) {
if ($locked) {
$this->unlock();
}
return false;
}
if ($locked) {
$this->_lru_push($schema_id, $info['offset']);
$this->_set_schema($schema_id, 'hits', $this->_get_schema($schema_id, 'hits') + 1);
return $this->unlock();
} else {
return true;
}
} else {
if ($locked) {
$this->unlock();
}
return false;
}
}
/**
* lock
* 如果flock不管用请继承本类并重载此方法
*
* @param mixed $is_block 是否阻塞
* @access public
* @return bool
*/
public function lock($is_block, $whatever = false)
{
return flock($this->_rs, $is_block ? LOCK_EX : LOCK_EX + LOCK_NB);
}
/**
* unlock
* 如果flock不管用请继承本类并重载此方法
*
* @access public
* @return bool
*/
public function unlock()
{
return flock($this->_rs, LOCK_UN);
}
public function delete($key, $pos = false)
{
if ($pos || $this->search($key, $pos)) {
if ($info = $this->_get_node($pos)) {
//删除data区域
if ($info['prev']) {
$this->_set_node($info['prev'], 'next', $info['next']);
$this->_set_node($info['next'], 'prev', $info['prev']);
} else {
//改入口位置
$this->_set_node($info['next'], 'prev', 0);
$this->_set_node_root($key, $info['next']);
}
$this->_free_dspace($info['size'], $info['data']);
$this->_lru_delete($info);
$this->_free_node($pos);
return $info['prev'];
}
}
return false;
}
public function store($key, $value)
{
if ($this->lock(true)) {
//save data
$data = serialize($value);
$size = strlen($data);
//get list_idx
$has_key = $this->search($key, $list_idx_offset);
$schema_id = $this->_get_size_schema_id($size);
if (false === $schema_id) {
$this->unlock();
return false;
}
if ($has_key) {
$hdseq = $list_idx_offset;
$info = $this->_get_node($hdseq);
if ($this->_get_size_schema_id($info['size']) == $schema_id) {
$dataoffset = $info['data'];
} else {
//破掉原有lru
$this->_lru_delete($info);
if (!($dataoffset = $this->_dalloc($schema_id))) {
$this->unlock();
return false;
}
$this->_free_dspace($info['size'], $info['data']);
$this->_set_node($hdseq, 'lru_left', 0);
$this->_set_node($hdseq, 'lru_right', 0);
}
$this->_set_node($hdseq, 'size', $size);
$this->_set_node($hdseq, 'data', $dataoffset);
} else {
if (!($dataoffset = $this->_dalloc($schema_id))) {
$this->unlock();
return false;
}
$hdseq = $this->_alloc_idx(array(
'next' => 0,
'prev' => $list_idx_offset,
'data' => $dataoffset,
'size' => $size,
'lru_right' => 0,
'lru_left' => 0,
'key' => $key,
));
if ($list_idx_offset > 0) {
$this->_set_node($list_idx_offset, 'next', $hdseq);
} else {
$this->_set_node_root($key, $hdseq);
}
}
if ($dataoffset > $this->max_size) {
$this->triggerError('alloc datasize:' . $dataoffset, E_USER_WARNING);
return false;
}
$this->_puts($dataoffset, $data);
$this->_set_schema($schema_id, 'miss', $this->_get_schema($schema_id, 'miss') + 1);
$this->_lru_push($schema_id, $hdseq);
$this->unlock();
return true;
} else {
$this->triggerError("Couldn't lock the file !", E_USER_WARNING);
return false;
}
}
/**
* search
* 查找指定的key
* 如果找到节点则$pos=节点本身 返回true
* 否则 $pos=树的末端 返回false
*
* @param mixed $key
* @access public
* @return mixed
*/
public function search($key, &$pos)
{
return $this->_get_pos_by_key($this->_get_node_root($key), $key, $pos);
}
public function _get_size_schema_id($size)
{
foreach ($this->_block_size_list as $k => $block_size) {
if ($size <= $block_size) {
return $k;
}
}
return false;
}
public function _parse_str_size($str_size, $default)
{
if (preg_match('/^([0-9]+)\s*([gmk]|)$/i', $str_size, $match)) {
switch (strtolower($match[2])) {
case 'g':
if ($match[1] > 1) {
$this->triggerError('Max cache size 1G', E_USER_ERROR);
}
$size = $match[1] << 30;
break;
case 'm':
$size = $match[1] << 20;
break;
case 'k':
$size = $match[1] << 10;
break;
default:
$size = $match[1];
}
if ($size <= 0) {
$this->triggerError('Error cache size ' . $this->max_size, E_USER_ERROR);
return false;
} elseif ($size < 10485760) {
return 10485760;
} else {
return $size;
}
} else {
return $default;
}
}
public function _format($truncate = false)
{
if ($this->lock(true, true)) {
if ($truncate) {
$this->_seek(0);
ftruncate($this->_rs, $this->idx_node_base);
}
$this->max_size = $this->_parse_str_size(SECACHE_SIZE, 15728640); //default:15m
$this->_puts($this->header_padding, pack('V1a*', $this->max_size, $this->ver));
ksort($this->_bsize_list);
$ds_offset = $this->data_base_pos;
$i = 0;
foreach ($this->_bsize_list as $size => $count) {
//将预分配的空间注册到free链表里
$count *= min(3, floor($this->max_size / 10485760));
$next_free_node = 0;
for ($j = 0; $j < $count; $j++) {
$this->_puts($ds_offset, pack('V', $next_free_node));
$next_free_node = $ds_offset;
$ds_offset += intval($size);
}
$code = pack(str_repeat('V1', count($this->schema_struct)), $size, $next_free_node, 0, 0, 0, 0);
$this->_puts(60 + $i * $this->schema_item_size, $code);
$i++;
}
$this->_set_dcur_pos($ds_offset);
$this->_puts($this->idx_base_pos, str_repeat("\0", 262144));
$this->_puts($this->idx_seq_pos, pack('V', 1));
$this->unlock();
return true;
} else {
$this->triggerError("Couldn't lock the file !", E_USER_ERROR);
return false;
}
}
public function _get_node_root($key)
{
$this->_seek(hexdec(substr($key, 0, 4)) * 4 + $this->idx_base_pos);
$a = fread($this->_rs, 4);
list(, $offset) = unpack('V', $a);
return $offset;
}
public function _set_node_root($key, $value)
{
return $this->_puts(hexdec(substr($key, 0, 4)) * 4 + $this->idx_base_pos, pack('V', $value));
}
public function _set_node($pos, $key, $value)
{
if (!$pos) {
return false;
}
if (isset($this->_node_struct[$key])) {
return $this->_puts($pos * $this->idx_node_size + $this->idx_node_base + $this->_node_struct[$key][0], pack($this->_node_struct[$key][1], $value));
} else {
return false;
}
}
public function _get_pos_by_key($offset, $key, &$pos)
{
if (!$offset) {
$pos = 0;
return false;
}
$info = $this->_get_node($offset);
if ($info['key'] == $key) {
$pos = $info['offset'];
return true;
} elseif ($info['next'] && $info['next'] != $offset) {
return $this->_get_pos_by_key($info['next'], $key, $pos);
} else {
$pos = $offset;
return false;
}
}
public function _lru_delete($info)
{
if ($info['lru_right']) {
$this->_set_node($info['lru_right'], 'lru_left', $info['lru_left']);
} else {
$this->_set_schema($this->_get_size_schema_id($info['size']), 'lru_tail', $info['lru_left']);
}
if ($info['lru_left']) {
$this->_set_node($info['lru_left'], 'lru_right', $info['lru_right']);
} else {
$this->_set_schema($this->_get_size_schema_id($info['size']), 'lru_head', $info['lru_right']);
}
return true;
}
public function _lru_push($schema_id, $offset)
{
$lru_head = $this->_get_schema($schema_id, 'lru_head');
$lru_tail = $this->_get_schema($schema_id, 'lru_tail');
if ((!$offset) || ($lru_head == $offset)) {
return;
}
$info = $this->_get_node($offset);
$this->_set_node($info['lru_right'], 'lru_left', $info['lru_left']);
$this->_set_node($info['lru_left'], 'lru_right', $info['lru_right']);
$this->_set_node($offset, 'lru_right', $lru_head);
$this->_set_node($offset, 'lru_left', 0);
$this->_set_node($lru_head, 'lru_left', $offset);
$this->_set_schema($schema_id, 'lru_head', $offset);
if (0 == $lru_tail) {
$this->_set_schema($schema_id, 'lru_tail', $offset);
} elseif ($lru_tail == $offset && $info['lru_left']) {
$this->_set_schema($schema_id, 'lru_tail', $info['lru_left']);
}
return true;
}
public function _get_node($offset)
{
$this->_seek($offset * $this->idx_node_size + $this->idx_node_base);
$info = unpack('V1next/V1prev/V1data/V1size/V1lru_right/V1lru_left/H*key', fread($this->_rs, $this->idx_node_size));
$info['offset'] = $offset;
return $info;
}
public function _lru_pop($schema_id)
{
if ($node = $this->_get_schema($schema_id, 'lru_tail')) {
$info = $this->_get_node($node);
if (!$info['data']) {
return false;
}
$this->delete($info['key'], $info['offset']);
if (!$this->_get_schema($schema_id, 'free')) {
$this->triggerError('pop lru,But nothing free...', E_USER_ERROR);
}
return $info;
} else {
return false;
}
}
public function _dalloc($schema_id, $lru_freed = false)
{
if ($free = $this->_get_schema($schema_id, 'free')) {
//如果lru里有链表
$this->_seek($free);
list(, $next) = unpack('V', fread($this->_rs, 4));
$this->_set_schema($schema_id, 'free', $next);
return $free;
} elseif ($lru_freed) {
$this->triggerError('Bat lru poped freesize', E_USER_ERROR);
return false;
} else {
$ds_offset = $this->_get_dcur_pos();
$size = $this->_get_schema($schema_id, 'size');
if ($size + $ds_offset > $this->max_size) {
if ($info = $this->_lru_pop($schema_id)) {
return $this->_dalloc($schema_id, $info);
} else {
$this->triggerError('Can\'t alloc dataspace', E_USER_ERROR);
return false;
}
} else {
$this->_set_dcur_pos($ds_offset + $size);
return $ds_offset;
}
}
}
public function _get_dcur_pos()
{
$this->_seek($this->dfile_cur_pos);
list(, $ds_offset) = unpack('V', fread($this->_rs, 4));
return $ds_offset;
}
public function _set_dcur_pos($pos)
{
return $this->_puts($this->dfile_cur_pos, pack('V', $pos));
}
public function _free_dspace($size, $pos)
{
if ($pos > $this->max_size) {
$this->triggerError('free dspace over quota:' . $pos, E_USER_ERROR);
return false;
}
$schema_id = $this->_get_size_schema_id($size);
if ($free = $this->_get_schema($schema_id, 'free')) {
$this->_puts($free, pack('V1', $pos));
} else {
$this->_set_schema($schema_id, 'free', $pos);
}
$this->_puts($pos, pack('V1', 0));
}
public function _dfollow($pos, &$c)
{
$c++;
$this->_seek($pos);
list(, $next) = unpack('V1', fread($this->_rs, 4));
if ($next) {
return $this->_dfollow($next, $c);
} else {
return $pos;
}
}
public function _free_node($pos)
{
$this->_seek($this->idx_free_pos);
list(, $prev_free_node) = unpack('V', fread($this->_rs, 4));
$this->_puts($pos * $this->idx_node_size + $this->idx_node_base, pack('V', $prev_free_node) . str_repeat("\0", $this->idx_node_size - 4));
return $this->_puts($this->idx_free_pos, pack('V', $pos));
}
public function _alloc_idx($data)
{
$this->_seek($this->idx_free_pos);
list(, $list_pos) = unpack('V', fread($this->_rs, 4));
if ($list_pos) {
$this->_seek($list_pos * $this->idx_node_size + $this->idx_node_base);
list(, $prev_free_node) = unpack('V', fread($this->_rs, 4));
$this->_puts($this->idx_free_pos, pack('V', $prev_free_node));
} else {
$this->_seek($this->idx_seq_pos);
list(, $list_pos) = unpack('V', fread($this->_rs, 4));
$this->_puts($this->idx_seq_pos, pack('V', $list_pos + 1));
}
return $this->_create_node($list_pos, $data);
}
public function _create_node($pos, $data)
{
$this->_puts($pos * $this->idx_node_size + $this->idx_node_base
, pack('V1V1V1V1V1V1H*', $data['next'], $data['prev'], $data['data'], $data['size'], $data['lru_right'], $data['lru_left'], $data['key']));
return $pos;
}
public function _set_schema($schema_id, $key, $value)
{
$info = array_flip($this->schema_struct);
return $this->_puts(60 + $schema_id * $this->schema_item_size + $info[$key] * 4, pack('V', $value));
}
public function _get_schema($id, $key)
{
$info = array_flip($this->schema_struct);
$this->_seek(60 + $id * $this->schema_item_size);
unpack('V1' . implode('/V1', $this->schema_struct), fread($this->_rs, $this->schema_item_size));
$this->_seek(60 + $id * $this->schema_item_size + $info[$key] * 4);
list(, $value) = unpack('V', fread($this->_rs, 4));
return $value;
}
public function _all_schemas()
{
$schema = [];
for ($i = 0; $i < 16; $i++) {
$this->_seek(60 + $i * $this->schema_item_size);
$info = unpack('V1' . implode('/V1', $this->schema_struct), fread($this->_rs, $this->schema_item_size));
if ($info['size']) {
$info['id'] = $i;
$schema[$i] = $info;
} else {
return $schema;
}
}
}
public function schemaStatus()
{
$return = [];
foreach ($this->_all_schemas() as $k => $schemaItem) {
if ($schemaItem['free']) {
$this->_dfollow($schemaItem['free'], $schemaItem['freecount']);
}
$return[] = $schemaItem;
}
return $return;
}
public function status(&$curBytes, &$totalBytes)
{
$totalBytes = $curBytes = 0;
$hits = $miss = 0;
$schemaStatus = $this->schemaStatus();
$totalBytes = $this->max_size;
$freeBytes = $this->max_size - $this->_get_dcur_pos();
foreach ($schemaStatus as $schema) {
$freeBytes += $schema['freecount'] * $schema['size'];
$miss += $schema['miss'];
$hits += $schema['hits'];
}
$curBytes = $totalBytes - $freeBytes;
$return[] = array('name' => '缓存命中', 'value' => $hits);
$return[] = array('name' => '缓存未命中', 'value' => $miss);
return $return;
}
public function triggerError($errstr, $errno)
{
triggerError($errstr, $errno);
}
}

View File

@@ -1,67 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\cache\driver;
use think\Cache;
/**
* 测试缓存类
* @author liu21st <liu21st@gmail.com>
*/
class Test
{
/**
* 读取缓存
* @access public
* @param string $name 缓存变量名
* @return mixed
*/
public function get($name)
{
return false;
}
/**
* 写入缓存
* @access public
* @param string $name 缓存变量名
* @param mixed $value 存储数据
* @param int $expire 有效时间 0为永久
* @return boolean
*/
public function set($name, $value, $expire = null)
{
return true;
}
/**
* 删除缓存
* @access public
* @param string $name 缓存变量名
* @return boolean
*/
public function rm($name)
{
return true;
}
/**
* 清除缓存
* @access public
* @return boolean
*/
public function clear()
{
return true;
}
}

View File

@@ -1,70 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK IT ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006-2014 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\controller;
use think\App;
use think\Loader;
/**
* ThinkPHP Hprose控制器类
*/
abstract class Hprose
{
protected $allowMethodList = '';
protected $crossDomain = false;
protected $P3P = false;
protected $get = true;
protected $debug = false;
/**
* 架构函数
* @access public
*/
public function __construct()
{
//控制器初始化
if (method_exists($this, '_initialize')) {
$this->_initialize();
}
//导入类库
Loader::import('vendor.Hprose.HproseHttpServer');
//实例化HproseHttpServer
$server = new \HproseHttpServer();
if ($this->allowMethodList) {
$methods = $this->allowMethodList;
} else {
$methods = get_class_methods($this);
$methods = array_diff($methods, ['__construct', '__call', '_initialize']);
}
$server->addMethods($methods, $this);
if (App::$debug || $this->debug) {
$server->setDebugEnabled(true);
}
// Hprose设置
$server->setCrossDomainEnabled($this->crossDomain);
$server->setP3PEnabled($this->P3P);
$server->setGetEnabled($this->get);
// 启动server
$server->start();
}
/**
* 魔术方法 有不存在的操作的时候执行
* @access public
* @param string $method 方法名
* @param array $args 参数
* @return mixed
*/
public function __call($method, $args)
{}
}

View File

@@ -1,47 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK IT ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006-2014 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\controller;
use think\Loader;
/**
* ThinkPHP JsonRPC控制器类
*/
abstract class Jsonrpc
{
/**
* 架构函数
* @access public
*/
public function __construct()
{
//控制器初始化
if (method_exists($this, '_initialize')) {
$this->_initialize();
}
//导入类库
Loader::import('vendor.jsonrpc.jsonRPCServer');
// 启动server
\jsonRPCServer::handle($this);
}
/**
* 魔术方法 有不存在的操作的时候执行
* @access public
* @param string $method 方法名
* @param array $args 参数
* @return mixed
*/
public function __call($method, $args)
{}
}

View File

@@ -1,65 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK IT ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006-2014 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\controller;
use think\App;
use think\Loader;
/**
* ThinkPHP RPC控制器类
*/
abstract class Rpc
{
protected $allowMethodList = '';
protected $debug = false;
/**
* 架构函数
* @access public
*/
public function __construct()
{
//控制器初始化
if (method_exists($this, '_initialize')) {
$this->_initialize();
}
//导入类库
Loader::import('vendor.phprpc.phprpc_server');
//实例化phprpc
$server = new \PHPRPC_Server();
if ($this->allowMethodList) {
$methods = $this->allowMethodList;
} else {
$methods = get_class_methods($this);
$methods = array_diff($methods, ['__construct', '__call', '_initialize']);
}
$server->add($methods, $this);
if (App::$debug || $this->debug) {
$server->setDebugMode(true);
}
$server->setEnableGZIP(true);
$server->start();
echo $server->comment();
}
/**
* 魔术方法 有不存在的操作的时候执行
* @access public
* @param string $method 方法名
* @param array $args 参数
* @return mixed
*/
public function __call($method, $args)
{}
}

View File

@@ -369,7 +369,7 @@ abstract class Builder
protected function parseDateTime($value, $key, $options = [])
{
// 获取时间字段类型
$type = $this->query->getTableInfo('', 'type');
$type = $this->query->getTableInfo($options['table'], 'type');
if (isset($options['field_type'][$key])) {
$info = $options['field_type'][$key];
} elseif (isset($type[$key])) {

View File

@@ -1,87 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\db\builder;
use think\Db;
use think\db\Builder;
/**
* Oracle数据库驱动
*/
class Oracle extends Builder
{
protected $selectSql = 'SELECT * FROM (SELECT thinkphp.*, rownum AS numrow FROM (SELECT %DISTINCT% %FIELD% FROM %TABLE%%JOIN%%WHERE%%GROUP%%HAVING%%ORDER%) thinkphp ) %LIMIT%%COMMENT%';
/**
* limit
* @access public
* @return string
*/
public function parseLimit($limit)
{
$limitStr = '';
if (!empty($limit)) {
$limit = explode(',', $limit);
if (count($limit) > 1) {
$limitStr = "(numrow>" . $limit[0] . ") AND (numrow<=" . ($limit[0] + $limit[1]) . ")";
} else {
$limitStr = "(numrow>0 AND numrow<=" . $limit[0] . ")";
}
}
return $limitStr ? ' WHERE ' . $limitStr : '';
}
/**
* 设置锁机制
* @access protected
* @param bool|false $lock
* @return string
*/
protected function parseLock($lock = false)
{
if (!$lock) {
return '';
}
return ' FOR UPDATE NOWAIT ';
}
/**
* 字段和表名处理
* @access protected
* @param string $key
* @return string
*/
protected function parseKey($key)
{
$key = trim($key);
if (strpos($key, '$.') && false === strpos($key, '(')) {
// JSON字段支持
list($field, $name) = explode($key, '$.');
$key = $field . '."' . $name . '"';
}
return $key;
}
/**
* 随机排序
* @access protected
* @return string
*/
protected function parseRand()
{
return 'DBMS_RANDOM.value';
}
}

View File

@@ -1,174 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: weianguo <366958903@qq.com>
// +----------------------------------------------------------------------
namespace think\db\connector;
use PDO;
use think\db\Connection;
use think\Log;
use think\Db;
use think\Exception;
use think\exception\PDOException;
/**
* firebird数据库驱动
*/
class Firebird extends Connection
{
/**
* 解析pdo连接的dsn信息
* @access public
* @param array $config 连接信息
* @return string
*/
protected function parseDsn($config)
{
$dsn = 'firebird:dbname=' . $config['hostname'].'/'.$config['hostport'].':'.$config['database'];
return $dsn;
}
/**
* 取得数据表的字段信息
* @access public
* @param string $tableName
* @return array
*/
public function getFields($tableName)
{
$this->initConnect(true);
list($tableName) = explode(' ', $tableName);
$sql= 'SELECT TRIM(RF.RDB$FIELD_NAME) AS FIELD,RF.RDB$DEFAULT_VALUE AS DEFAULT1,RF.RDB$NULL_FLAG AS NULL1,TRIM(T.RDB$TYPE_NAME) || \'(\' || F.RDB$FIELD_LENGTH || \')\' as TYPE FROM RDB$RELATION_FIELDS RF LEFT JOIN RDB$FIELDS F ON (F.RDB$FIELD_NAME = RF.RDB$FIELD_SOURCE) LEFT JOIN RDB$TYPES T ON (T.RDB$TYPE = F.RDB$FIELD_TYPE) WHERE RDB$RELATION_NAME=UPPER(\'' . $tableName . '\') AND T.RDB$FIELD_NAME = \'RDB$FIELD_TYPE\' ORDER By RDB$FIELD_POSITION';
$result = $this->linkID->query($sql);
$info = [];
if ($result) {
foreach ($result as $key => $val) {
$info[$val[0]] = array(
'name' => $val[0],
'type' => $val[3],
'notnull' => ($val[2]==1),
'default' => $val[1],
'primary' => false,
'autoinc' => false,
);
}
}
//获取主键
$sql = 'select TRIM(b.rdb$field_name) as field_name from rdb$relation_constraints a join rdb$index_segments b on a.rdb$index_name=b.rdb$index_name where a.rdb$constraint_type=\'PRIMARY KEY\' and a.rdb$relation_name=UPPER(\'' . $tableName . '\')';
$rs_temp = $this->linkID->query($sql);
foreach ($rs_temp as $row) {
$info[$row[0]]['primary'] = true;
}
return $this->fieldCase($info);
}
/**
* 取得数据库的表信息
* @access public
* @param string $dbName
* @return array
*/
public function getTables($dbName = '')
{
$sql = 'SELECT DISTINCT RDB$RELATION_NAME FROM RDB$RELATION_FIELDS WHERE RDB$SYSTEM_FLAG=0';
$result = $this->query($sql);
$info = [];
foreach ($result as $key => $val) {
$info[$key] = trim(current($val));
}
return $info;
}
/**
* 执行语句
* @access public
* @param string $sql sql指令
* @param array $bind 参数绑定
* @param boolean $getLastInsID 是否获取自增ID
* @param string $sequence 自增序列名
* @return int
* @throws BindParamException
* @throws PDOException
*/
public function execute($sql, $bind = [], $getLastInsID = false, $sequence = null)
{
$this->initConnect(true);
if (!$this->linkID) {
return false;
}
// 根据参数绑定组装最终的SQL语句
$this->queryStr = $this->getRealSql($sql, $bind);
//释放前次的查询结果
if (!empty($this->PDOStatement)) {
$this->free();
}
$bind=array_map(function($v){
return array_map(function($v2){
return mb_convert_encoding($v2,'gbk','utf-8');},$v);
},$bind);
Db::$executeTimes++;
try {
// 调试开始
$this->debug(true);
// 预处理
$this->PDOStatement = $this->linkID->prepare(mb_convert_encoding($sql,'gbk','utf-8'));
// 参数绑定操作
$this->bindValue($bind);
// 执行语句
$result = $this->PDOStatement->execute();
// 调试结束
$this->debug(false);
$this->numRows = $this->PDOStatement->rowCount();
return $this->numRows;
} catch (\PDOException $e) {
throw new PDOException($e, $this->config, $this->queryStr);
}
}
/**
* 启动事务
* @access public
* @return bool|null
*/
public function startTrans()
{
$this->initConnect(true);
if (!$this->linkID) {
return false;
}
++$this->transTimes;
if (1 == $this->transTimes) {
$this->linkID->setAttribute(\PDO::ATTR_AUTOCOMMIT,false);
$this->linkID->beginTransaction();
} elseif ($this->transTimes > 1 && $this->supportSavepoint()) {
$this->linkID->exec(
$this->parseSavepoint('trans' . $this->transTimes)
);
}
}
/**
* SQL性能分析
* @access protected
* @param string $sql
* @return array
*/
protected function getExplain($sql)
{
return [];
}
}

View File

@@ -1,162 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace think\db\connector;
use PDO;
use think\Db;
use think\db\Connection;
/**
* Oracle数据库驱动
*/
class Oracle extends Connection
{
/**
* 解析pdo连接的dsn信息
* @access protected
* @param array $config 连接信息
* @return string
*/
protected function parseDsn($config)
{
$dsn = 'oci:dbname=';
if (!empty($config['hostname'])) {
// Oracle Instant Client
$dsn .= '//' . $config['hostname'] . ($config['hostport'] ? ':' . $config['hostport'] : '') . '/';
}
$dsn .= $config['database'];
if (!empty($config['charset'])) {
$dsn .= ';charset=' . $config['charset'];
}
return $dsn;
}
/**
* 执行语句
* @access public
* @param string $sql sql指令
* @param array $bind 参数绑定
* @param boolean $getLastInsID 是否获取自增ID
* @param string $sequence 序列名
* @return integer
* @throws \Exception
* @throws \think\Exception
*/
public function execute($sql, $bind = [], $getLastInsID = false, $sequence = null)
{
$this->initConnect(true);
if (!$this->linkID) {
return false;
}
// 根据参数绑定组装最终的SQL语句
$this->queryStr = $this->getRealSql($sql, $bind);
$flag = false;
if (preg_match("/^\s*(INSERT\s+INTO)\s+(\w+)\s+/i", $sql, $match)) {
if (is_null($sequence)) {
$sequence = Config::get("db_sequence_prefix") . str_ireplace(Config::get("database.prefix"), "", $match[2]);
}
$flag = (boolean) $this->query("SELECT * FROM all_sequences WHERE sequence_name='" . strtoupper($sequence) . "'");
}
//释放前次的查询结果
if (!empty($this->PDOStatement)) {
$this->free();
}
Db::$executeTimes++;
try {
// 记录开始执行时间
$this->debug(true);
$this->PDOStatement = $this->linkID->prepare($sql);
// 参数绑定操作
$this->bindValue($bind);
$result = $this->PDOStatement->execute();
$this->debug(false);
$this->numRows = $this->PDOStatement->rowCount();
if ($flag || preg_match("/^\s*(INSERT\s+INTO|REPLACE\s+INTO)\s+/i", $sql)) {
$this->lastInsID = $this->linkID->lastInsertId();
if ($getLastInsID) {
return $this->lastInsID;
}
}
return $this->numRows;
} catch (\PDOException $e) {
throw new \think\Exception($this->getError());
}
}
/**
* 取得数据表的字段信息
* @access public
* @param string $tableName
* @return array
*/
public function getFields($tableName)
{
$this->initConnect(true);
list($tableName) = explode(' ', $tableName);
$sql = "select a.column_name,data_type,DECODE (nullable, 'Y', 0, 1) notnull,data_default, DECODE (A .column_name,b.column_name,1,0) pk from all_tab_columns a,(select column_name from all_constraints c, all_cons_columns col where c.constraint_name = col.constraint_name and c.constraint_type = 'P' and c.table_name = '" . strtoupper($tableName) . "' ) b where table_name = '" . strtoupper($tableName) . "' and a.column_name = b.column_name (+)";
$pdo = $this->linkID->query($sql);
$result = $pdo->fetchAll(PDO::FETCH_ASSOC);
$info = [];
if ($result) {
foreach ($result as $key => $val) {
$val = array_change_key_case($val);
$info[$val['column_name']] = [
'name' => $val['column_name'],
'type' => $val['data_type'],
'notnull' => $val['notnull'],
'default' => $val['data_default'],
'primary' => $val['pk'],
'autoinc' => $val['pk'],
];
}
}
return $this->fieldCase($info);
}
/**
* 取得数据库的表信息(暂时实现取得用户表信息)
* @access public
* @param string $dbName
* @return array
*/
public function getTables($dbName = '')
{
$pdo = $this->linkID->query("select table_name from all_tables");
$result = $pdo->fetchAll(PDO::FETCH_ASSOC);
$info = [];
foreach ($result as $key => $val) {
$info[$key] = current($val);
}
return $info;
}
/**
* SQL性能分析
* @access protected
* @param string $sql
* @return array
*/
protected function getExplain($sql)
{
return [];
}
protected function supportSavepoint()
{
return true;
}
}

View File

@@ -640,14 +640,16 @@ class Relation
$id = $data->$relationFk;
}
// 删除中间表数据
$pk = $this->parent->getPk();
$pivot[$this->localKey] = $this->parent->$pk;
$pivot[$this->foreignKey] = is_array($id) ? ['in', $id] : $id;
$query = clone $this->parent->db();
$pk = $this->parent->getPk();
$pivot[$this->localKey] = $this->parent->$pk;
if (isset($id)) {
$pivot[$this->foreignKey] = is_array($id) ? ['in', $id] : $id;
}
$query = clone $this->parent->db();
$query->table($this->middle)->where($pivot)->delete();
// 删除关联表数据
if ($relationDel) {
if (isset($id) && $relationDel) {
$model = $this->model;
$model::destroy($id);
}

View File

@@ -1,17 +0,0 @@
<?php
// +----------------------------------------------------------------------
// | ThinkPHP [ WE CAN DO IT JUST THINK ]
// +----------------------------------------------------------------------
// | Copyright (c) 2006~2016 http://thinkphp.cn All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: liu21st <liu21st@gmail.com>
// +----------------------------------------------------------------------
namespace {%namespace%};
class {%className%} {%extend%}
{
{%content%}
}