From 9749393cc01d32d9b630a0b2760fba509f88a311 Mon Sep 17 00:00:00 2001
From: printempw
Date: Sun, 3 Apr 2016 21:49:19 +0800
Subject: [PATCH] added auto-updating
---
.gitignore | 2 +-
admin/adduser.php | 4 +-
admin/customize.php | 4 +-
admin/index.php | 4 +-
admin/manage.php | 4 +-
admin/options.php | 4 +-
admin/update.php | 132 +++---------------
libraries/Option.class.php | 3 +-
libraries/Updater.class.php | 37 ++++-
libraries/Utils.class.php | 63 +++++++--
setup/index.php | 6 +-
setup/tables.sql | 9 +-
setup/update.php | 74 ++++++++++
.../update-from-2.3.3-to-2.3.4.php | 9 +-
.../update-from-2.3.4-to-2.4.php | 22 +++
templates/admin/check.tpl.php | 87 ++++++++++++
templates/admin/download.tpl.php | 60 ++++++++
templates/admin/footer.tpl.php | 16 +++
18 files changed, 388 insertions(+), 152 deletions(-)
create mode 100644 setup/update.php
rename setup/{ => update_scripts}/update-from-2.3.3-to-2.3.4.php (56%)
create mode 100644 setup/update_scripts/update-from-2.3.4-to-2.4.php
create mode 100644 templates/admin/check.tpl.php
create mode 100644 templates/admin/download.tpl.php
create mode 100644 templates/admin/footer.tpl.php
diff --git a/.gitignore b/.gitignore
index 26255d6b..f44e9624 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,3 +1,3 @@
textures/*
config.php
-.phpintel/
+setup/update_cache/*
diff --git a/admin/adduser.php b/admin/adduser.php
index 1e8b3c74..33e31f58 100644
--- a/admin/adduser.php
+++ b/admin/adduser.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-19 21:00:58
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 07:55:53
+ * @Last Modified time: 2016-04-03 20:58:33
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
@@ -111,4 +111,4 @@ function add() {
}
EOT;
-View::show('footer', $data); ?>
+View::show('admin/footer', $data); ?>
diff --git a/admin/customize.php b/admin/customize.php
index 79278c91..597169a5 100644
--- a/admin/customize.php
+++ b/admin/customize.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-19 14:34:21
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 11:27:05
+ * @Last Modified time: 2016-04-03 20:58:26
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
@@ -241,4 +241,4 @@ $('#color-submit').click(function() {
});
EOT;
-View::show('footer', $data); ?>
+View::show('admin/footer', $data); ?>
diff --git a/admin/index.php b/admin/index.php
index ee3de3b4..9fe407c3 100644
--- a/admin/index.php
+++ b/admin/index.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-02-03 14:39:50
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 07:59:57
+ * @Last Modified time: 2016-04-03 20:58:22
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
@@ -55,4 +55,4 @@ $db = new Database\Database('users');
+View::show('admin/footer'); ?>
diff --git a/admin/manage.php b/admin/manage.php
index f92eddcd..9a45c1dd 100644
--- a/admin/manage.php
+++ b/admin/manage.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-06 14:19:20
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 07:55:53
+ * @Last Modified time: 2016-04-03 20:58:13
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
@@ -26,4 +26,4 @@ $('#page-select').on('change', function() {
EOT;
if (isset($_GET['show']))
$data['script'] .= '';
-View::show('footer', $data); ?>
+View::show('admin/footer', $data); ?>
diff --git a/admin/options.php b/admin/options.php
index b3c692ef..f15c56ea 100644
--- a/admin/options.php
+++ b/admin/options.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-18 22:50:25
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 15:09:33
+ * @Last Modified time: 2016-04-03 20:58:06
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
@@ -200,4 +200,4 @@ $db = new Database\Database('users');
+View::show('admin/footer'); ?>
diff --git a/admin/update.php b/admin/update.php
index 888c1a4e..5bd2a0f3 100644
--- a/admin/update.php
+++ b/admin/update.php
@@ -3,123 +3,27 @@
* @Author: printempw
* @Date: 2016-03-27 15:03:40
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 07:55:54
+ * @Last Modified time: 2016-04-03 21:05:51
*/
require "../libraries/session.inc.php";
if (!$user->is_admin) Utils::redirect('../index.php?msg=看起来你并不是管理员');
+$action = isset($_GET['action']) ? $_GET['action'] : "";
+
+$updater = new Updater(Option::get('current_version'));
+
+if ($action == "check" && $updater->newVersionAvailable()) {
+ exit(json_encode([
+ 'new_version_available' => true,
+ 'latest_version' => $updater->latest_version
+ ]));
+}
+
View::show('admin/header', array('page_title' => "检查更新"));
-$db = new Database\Database('users');
-?>
-
-
-
-
-
-
-
-
-
-
-
-
- newVersionAvailable()): ?>
-
有更新可用。
-
-
-
- | 最新版本: |
-
- vlatest_version; ?>
- |
-
-
- | 当前版本: |
-
- vcurrent_version; ?>
- |
-
-
- | 发布时间: |
-
- update_time; ?>
- |
-
-
- | 更新日志: |
-
- getUpdateInfo()['releases'][$updater->latest_version]['release_note']); ?>
- |
-
-
- | 下载地址: |
-
- @GitHub
- |
-
-
-
-
-
已更新至最新版本。
-
-
-
- | 当前版本: |
-
- vcurrent_version; ?>
- |
-
-
- | 发布时间: |
-
- getUpdateInfo()['releases'][$updater->current_version]['release_time']); ?>
- |
-
-
-
-
-
-
-
-
+if ($action == "download") {
+ View::show('admin/download');
+} else {
+ View::show('admin/check');
+}
-
-
-
-
-
1. 下载新版源码
-
2. 完全覆盖旧版目录
-
3. 运行 /setup/update-from-2.3.3-to-2.3.4.php
-
4. 升级完成
-
-
-
-
-
-
-
自动升级正在开发中,开发者现在忙于应考,可能要过几个星期才能发布。
-
-
-
-
-
-
-
-
-
+View::show('admin/footer'); ?>
diff --git a/libraries/Option.class.php b/libraries/Option.class.php
index be844192..cd193f19 100644
--- a/libraries/Option.class.php
+++ b/libraries/Option.class.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-18 14:02:12
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-02 22:50:19
+ * @Last Modified time: 2016-04-03 21:47:08
*/
use Database\Database;
@@ -27,6 +27,7 @@ class Option
public static function add($key, $value) {
$db = new Database('options');
+ if (self::has($key)) return true;
return $db->insert(['option_name' => $key, 'option_value' => $value]);
}
diff --git a/libraries/Updater.class.php b/libraries/Updater.class.php
index 46bb27df..88b6f5e6 100644
--- a/libraries/Updater.class.php
+++ b/libraries/Updater.class.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-27 15:16:22
* @Last Modified by: printempw
- * @Last Modified time: 2016-03-27 16:26:07
+ * @Last Modified time: 2016-04-03 21:15:23
*/
class Updater
@@ -13,10 +13,13 @@ class Updater
public $update_time = "";
- public $update_url = "https://work.prinzeugen.net/update.json";
+ public $update_url = "";
+
+ public $update_info = null;
function __construct($current_version) {
$this->current_version = $current_version;
+ $this->update_url = Option::get('update_url');
}
public function getUpdateInfo() {
@@ -27,8 +30,8 @@ class Updater
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$result = curl_exec($ch);
curl_close($ch);
-
- return json_decode($result, true);
+ $this->update_info = json_decode($result, true);
+ return $this->update_info;
}
public function checkUpdate() {
@@ -37,6 +40,32 @@ class Updater
$this->update_time = date('Y-m-d H:i:s', $info['update_time']);
}
+ public function downloadUpdate($silent = true) {
+ $release_url = $this->update_info['releases'][$this->latest_version]['release_url'];
+ $ch = curl_init();
+ curl_setopt($ch, CURLOPT_URL, $release_url);
+ curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+ curl_setopt($ch, CURLOPT_HEADER, 0);
+ curl_setopt($ch, CURLOPT_USERAGENT, $_SERVER['HTTP_USER_AGENT']);
+
+ if (!$silent) echo "正在下载更新包:$release_url
";
+ $file = curl_exec($ch);
+ if (!$silent) echo "下载完成。
";
+ curl_close($ch);
+
+ $update_cache = BASE_DIR."/setup/update_cache/";
+ if (!is_dir($update_cache)) mkdir($update_cache);
+
+ $zip_path = $update_cache."update_".time().".zip";
+
+ if (file_put_contents($zip_path, $file) === false) {
+ Utils::removeDir(BASE_DIR.'/setup/update_cache/');
+ return false;
+
+ }
+ return $zip_path;
+ }
+
/**
* Check if a new version is available
*
diff --git a/libraries/Utils.class.php b/libraries/Utils.class.php
index f5848196..3c36cac1 100644
--- a/libraries/Utils.class.php
+++ b/libraries/Utils.class.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-01-16 23:01:33
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 10:58:15
+ * @Last Modified time: 2016-04-03 21:44:11
*/
class Utils
@@ -38,13 +38,28 @@ class Utils
* @return $bool
*/
public static function remove($filename) {
- if(file_exists($filename)) {
- if (!unlink($filename)) {
- self::raise(-1, "删除 $filename 的时候出现了奇怪的问题。。请联系作者");
- } else {
- return true;
+ if (file_exists($filename)) {
+ return unlink($filename);
+ }
+ }
+
+ public static function removeDir($dir) {
+ $resource = opendir($dir);
+ $size = 0;
+ while($filename = @readdir($resource)) {
+ if ($filename != "." && $filename != "..") {
+ $path = $dir.$filename;
+ if (is_dir($path)) {
+ // recursion
+ self::removeDir($path."/");
+ } else {
+ unlink($path);
+ }
}
}
+ closedir($resource);
+
+ return rmdir($dir);
}
/**
@@ -56,7 +71,7 @@ class Utils
public static function getDirSize($dir) {
$resource = opendir($dir);
$size = 0;
- while($filename = readdir($resource)) {
+ while($filename = @readdir($resource)) {
if ($filename != "." && $filename != "..") {
$path = $dir.$filename;
if (is_dir($path)) {
@@ -95,6 +110,33 @@ class Utils
return $file_num;
}
+ /**
+ * Copy directory recursively
+ *
+ * @param string $source
+ * @param string $dest
+ * @return bool
+ */
+ public static function copyDir($source, $dest) {
+ if(!is_dir($source)) return false;
+ if(!is_dir($dest)) mkdir($dest, 0777, true);
+
+ $handle = dir($source);
+
+ while($entry = $handle->read()) {
+ if ($entry != "." && $entry != "..") {
+ if (is_dir($source.'/'.$entry)) {
+ // recursion
+ self::copyDir($source.'/'.$entry, $dest.'/'.$entry);
+ } else {
+ @copy($source.'/'.$entry, $dest.'/'.$entry);
+ // echo $source.'/'.$entry." => ".$dest.'/'.$entry."
";
+ }
+ }
+ }
+ return true;
+ }
+
/**
* Simple SQL injection protection
*
@@ -184,8 +226,11 @@ class Utils
* @param string $url
* @return null
*/
- public static function redirect($url) {
- header('Location: '.$url);
+ public static function redirect($url, $use_js = false) {
+ if ($use_js)
+ echo "";
+ else
+ header('Location: '.$url);
}
}
diff --git a/setup/index.php b/setup/index.php
index a4ad4f27..1b28fd4d 100644
--- a/setup/index.php
+++ b/setup/index.php
@@ -3,7 +3,7 @@
* @Author: printempw
* @Date: 2016-03-27 13:30:00
* @Last Modified by: printempw
- * @Last Modified time: 2016-04-03 16:16:57
+ * @Last Modified time: 2016-04-03 19:23:11
*/
// Sanity check
@@ -44,9 +44,7 @@ $step = isset($_GET['step']) ? $_GET['step'] : 1;
connect_error): ?>
MySQL 连接错误
diff --git a/setup/tables.sql b/setup/tables.sql
index 00f675df..ee1ce3f3 100644
--- a/setup/tables.sql
+++ b/setup/tables.sql
@@ -2,7 +2,7 @@
* @Author: printempw
* @Date: 2016-04-03 16:22:11
* @Last Modified by: printempw
-* @Last Modified time: 2016-04-03 17:14:53
+* @Last Modified time: 2016-04-03 21:22:18
*/
CREATE TABLE IF NOT EXISTS `{$prefix}users` (
@@ -33,7 +33,7 @@ INSERT INTO `{$prefix}options` (`option_name`, `option_value`) VALUES
('user_can_register', '1'),
('user_default_skin', ''),
('regs_per_ip', '2'),
-('upload_max_size', '10'),
+('upload_max_size', '1024'),
('api_type', '0'),
('announcement', '这是默认的公告~'),
('data_adapter', ''),
@@ -44,7 +44,8 @@ INSERT INTO `{$prefix}options` (`option_name`, `option_value`) VALUES
('data_column_ip', 'ip'),
('color_scheme', 'skin-blue'),
('home_pic_url', './assets/images/bg.jpg'),
-('google_font_cdn', ''),
+('google_font_cdn', 'moefont'),
('custom_css', ''),
-('custom_js', '');
+('custom_js', ''),
+('update_url', 'https://work.prinzeugen.net/update.json');
diff --git a/setup/update.php b/setup/update.php
new file mode 100644
index 00000000..96e4bc4a
--- /dev/null
+++ b/setup/update.php
@@ -0,0 +1,74 @@
+
+
+
+
+
+
+
+Blessing Skin Server 升级程序
+
+
+
+Blessing Skin Server
+newVersionAvailable()): ?>
+并没有可用的更新
+当前版本:vcurrent_version; ?>
+返回首页
+
+非法访问
+下载完更新后再来吧
+检查更新
+
+还差一小步
+我们需要先升级下数据库。点击下一步以继续。
+下一步
+
+升级数据库
+数据库升级成功。欢迎使用 Blessing Skin Server v{$updater->current_version}!
"
+?>
+进入首页
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ newVersionAvailable()): ?>
+
有更新可用。
+
+
+
+ | 最新版本: |
+
+ vlatest_version; ?>
+ |
+
+
+ | 当前版本: |
+
+ vcurrent_version; ?>
+ |
+
+
+ | 发布时间: |
+
+ update_time; ?>
+ |
+
+
+ | 更新日志: |
+
+ getUpdateInfo()['releases'][$updater->latest_version]['release_note']); ?>
+ |
+
+
+ | 下载地址: |
+
+ @GitHub
+ |
+
+
+
+
+
+
已更新至最新版本。
+
+
+
+ | 当前版本: |
+
+ vcurrent_version; ?>
+ |
+
+
+ | 发布时间: |
+
+ getUpdateInfo()['releases'][$updater->current_version]['release_time']); ?>
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/templates/admin/download.tpl.php b/templates/admin/download.tpl.php
new file mode 100644
index 00000000..5a36f71a
--- /dev/null
+++ b/templates/admin/download.tpl.php
@@ -0,0 +1,60 @@
+
+
+
+
+
+
+
+
+
newVersionAvailable()) {
+
+ $zip_path = $updater->downloadUpdate(false);
+
+ if ($zip_path === false) {
+ exit('
无法下载更新包。
');
+ }
+
+ $zip = new ZipArchive();
+ $extract_dir = BASE_DIR."/setup/update_cache/{$updater->latest_version}";
+ if ($zip->open($zip_path) === true) {
+ echo "
正在解压更新包
";
+ $zip->extractTo($extract_dir);
+ } else {
+ exit('
更新包解压缩失败。
');
+ }
+ $zip->close();
+
+ if (Utils::copyDir($extract_dir, BASE_DIR) !== true) {
+ Utils::removeDir(BASE_DIR.'/setup/update_cache/');
+ exit('无法覆盖文件。');
+ } else {
+ echo "
正在覆盖文件
";
+ Utils::removeDir(BASE_DIR.'/setup/update_cache/');
+ echo "
正在清理
";
+ }
+
+ echo "
更新完成。
";
+
+ $_SESSION['downloaded_version'] = $updater->latest_version;
+
+ } else {
+ Utils::redirect('update.php', true);
+ } ?>
+
+
+
+
+
+
diff --git a/templates/admin/footer.tpl.php b/templates/admin/footer.tpl.php
new file mode 100644
index 00000000..89312d5d
--- /dev/null
+++ b/templates/admin/footer.tpl.php
@@ -0,0 +1,16 @@
+
+$(document).ready(function() {
+ $.getJSON('update.php?action=check', function(data) {
+ if (data.new_version_available == true)
+ $('[href="update.php"]').append('v'+data.latest_version+'');
+ })
+});
+
+EOT;
+
+View::show('footer', $data);