| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204 | <?phpnamespace app\admin\controller\general;use addons\database\library\Backup;use app\common\controller\Backend;use think\Db;use think\Debug;use think\Exception;use think\exception\PDOException;use ZipArchive;/** * 数据库管理 * * @icon   fa fa-database * @remark 可在线进行一些简单的数据库表优化或修复,查看表结构和数据。也可以进行SQL语句的操作 */class Database extends Backend{    protected $noNeedRight = ['backuplist'];    public function _initialize()    {        if (!config("app_debug")) {            $this->error("数据库管理插件只允许在开发环境下使用");        }        return parent::_initialize();    }    /**     * 查看     */    public function index()    {        $tables_data_length = $tables_index_length = $tables_free_length = $tables_data_count = 0;        $tables = $list = [];        $list = Db::query("SHOW TABLES");        foreach ($list as $key => $row) {            $tables[] = ['name' => reset($row), 'rows' => 0];        }        $data['tables'] = $tables;        $data['saved_sql'] = [];        $this->view->assign($data);        return $this->view->fetch();    }    /**     * SQL查询     */    public function query()    {        $do_action = $this->request->post('do_action');        echo '<style type="text/css">            xmp,body{margin:0;padding:0;line-height:18px;font-size:13px;font-family:"Helvetica Neue", Helvetica, Microsoft Yahei, Hiragino Sans GB, WenQuanYi Micro Hei, sans-serif;}            hr{height:1px;margin:5px 1px;background:#e3e3e3;border:none;}            </style>';        if ($do_action == '') {            exit(__('Invalid parameters'));        }        $tablename = $this->request->post("tablename/a", []);        if (in_array($do_action, array('doquery', 'optimizeall', 'repairall'))) {            $this->$do_action();        } elseif (count($tablename) == 0) {            exit(__('请选中表后再进行操作'));        } else {            foreach ($tablename as $table) {                $this->$do_action($table);                echo "<br />";            }        }    }    private function viewinfo($name)    {        $row = Db::query("SHOW CREATE TABLE `{$name}`");        $row = array_values($row[0]);        $info = $row[1];        echo "<xmp>{$info};</xmp>";    }    private function viewdata($name = '')    {        $sqlquery = "SELECT * FROM `{$name}`";        $this->doquery($sqlquery);    }    private function optimize($name = '')    {        if (Db::execute("OPTIMIZE TABLE `{$name}`")) {            echo __('Optimize table %s done', $name);        } else {            echo __('Optimize table %s fail', $name);        }    }    private function optimizeall($name = '')    {        $list = Db::query("SHOW TABLES");        foreach ($list as $key => $row) {            $name = reset($row);            if (Db::execute("OPTIMIZE TABLE {$name}")) {                echo __('Optimize table %s done', $name);            } else {                echo __('Optimize table %s fail', $name);            }            echo "<br />";        }    }    private function repair($name = '')    {        if (Db::execute("REPAIR TABLE `{$name}`")) {            echo __('Repair table %s done', $name);        } else {            echo __('Repair table %s fail', $name);        }    }    private function repairall($name = '')    {        $list = Db::query("SHOW TABLES");        foreach ($list as $key => $row) {            $name = reset($row);            if (Db::execute("REPAIR TABLE {$name}")) {                echo __('Repair table %s done', $name);            } else {                echo __('Repair table %s fail', $name);            }            echo "<br />";        }    }    private function doquery($sql = null)    {        $sqlquery = $sql ? $sql : $this->request->post('sqlquery');        if ($sqlquery == '') {            exit(__('SQL can not be empty'));        }        $sqlquery = str_replace('__PREFIX__', config('database.prefix'), $sqlquery);        $sqlquery = str_replace("\r", "", $sqlquery);        $sqls = preg_split("/;[ \t]{0,}\n/i", $sqlquery);        $maxreturn = 100;        $r = '';        foreach ($sqls as $key => $val) {            if (trim($val) == '') {                continue;            }            $val = rtrim($val, ';');            $r .= "SQL:<span style='color:green;'>{$val}</span> ";            if (preg_match("/^(select|explain)(.*)/i ", $val)) {                Debug::remark("begin");                $limit = stripos(strtolower($val), "limit") !== false ? true : false;                try {                    $count = Db::execute($val);                    if ($count > 0) {                        $resultlist = Db::query($val . (!$limit && $count > $maxreturn ? ' LIMIT ' . $maxreturn : ''));                    } else {                        $resultlist = [];                    }                } catch (\PDOException $e) {                    continue;                }                Debug::remark("end");                $time = Debug::getRangeTime('begin', 'end', 4);                $usedseconds = __('Query took %s seconds', $time) . "<br />";                if ($count <= 0) {                    $r .= __('Query returned an empty result');                } else {                    $r .= (__('Total:%s', $count) . (!$limit && $count > $maxreturn ? ',' . __('Max output:%s', $maxreturn) : ""));                }                $r = $r . ',' . $usedseconds;                $j = 0;                foreach ($resultlist as $m => $n) {                    $j++;                    if (!$limit && $j > $maxreturn) {                        break;                    }                    $r .= "<hr/>";                    $r .= "<font color='red'>" . __('Row:%s', $j) . "</font><br />";                    foreach ($n as $k => $v) {                        $r = $r . "<font color='blue'>" . htmlentities($k) . ":</font>" . htmlentities($v) . "<br/>\r\n";                    }                }            } else {                try {                    Debug::remark("begin");                    $count = Db::getPdo()->exec($val);                    Debug::remark("end");                } catch (\PDOException $e) {                    continue;                }                $time = Debug::getRangeTime('begin', 'end', 4);                $r .= __('Query affected %s rows and took %s seconds', $count, $time) . "<br />";            }        }        echo $r;    }}
 |