From 498c7cbec2bbc23c59465f2df3c7713b683ad0b3 Mon Sep 17 00:00:00 2001
From: xiaojunnuo <xiaojunnuo@qq.com>
Date: Fri, 27 Aug 2021 17:00:13 +0800
Subject: [PATCH] =?UTF-8?q?perf:=20=E8=BF=9C=E7=A8=8B=E9=85=8D=E7=BD=AE?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 packages/core/src/config.js                   | 67 ++++++++++++++++++-
 packages/core/src/config/index.js             |  2 +-
 .../src/config/remote_config.json5}           |  0
 packages/gui/src/bridge/api/backend.js        |  2 +
 4 files changed, 67 insertions(+), 4 deletions(-)
 rename packages/{gui/extra/config_remote.json5 => core/src/config/remote_config.json5} (100%)

diff --git a/packages/core/src/config.js b/packages/core/src/config.js
index 08685b51..177953d3 100644
--- a/packages/core/src/config.js
+++ b/packages/core/src/config.js
@@ -3,8 +3,9 @@ const Shell = require('./shell')
 const lodash = require('lodash')
 const defConfig = require('./config/index.js')
 const JSON5 = require('json5').default
-
-console.log('JSON5', JSON5)
+const request = require('request')
+const path = require('path')
+const log = require('./utils/util.log')
 let configTarget = lodash.cloneDeep(defConfig)
 
 function get () {
@@ -24,6 +25,13 @@ function _deleteDisabledItem (target) {
 const getDefaultConfigBasePath = function () {
   return get().server.setting.userBasePath
 }
+function _getRemoteSavePath () {
+  const dir = getDefaultConfigBasePath()
+  if (!fs.existsSync(dir)) {
+    fs.mkdirSync(dir)
+  }
+  return path.join(dir, 'remote_config.json5')
+}
 function _getConfigPath () {
   const dir = getDefaultConfigBasePath()
   if (!fs.existsSync(dir)) {
@@ -33,6 +41,9 @@ function _getConfigPath () {
 }
 
 function doMerge (defObj, newObj) {
+  if (newObj == null) {
+    return defObj
+  }
   const defObj2 = { ...defObj }
   const newObj2 = {}
   for (const key in newObj) {
@@ -69,11 +80,60 @@ function doMerge (defObj, newObj) {
   })
   return newObj2
 }
-
+let timer
 const configApi = {
+  startAutoDownloadRemoteConfig () {
+    if (timer != null) {
+      clearInterval(timer)
+    }
+    const download = async () => {
+      await configApi.downloadRemoteConfig()
+      configApi.reload()
+    }
+    download()
+    setInterval(download, 24 * 60 * 60 * 1000) // 1天
+  },
+  downloadRemoteConfig () {
+    if (get().app.remoteConfig.enabled !== true) {
+      return
+    }
+    const remoteConfigUrl = get().app.remoteConfig.url
+    // eslint-disable-next-line handle-callback-err
+    return new Promise((resolve, reject) => {
+      log.info('下载远程配置:', remoteConfigUrl)
+      request(remoteConfigUrl, (error, response, body) => {
+        if (error) {
+          log.error('下载远程配置失败', error)
+          reject(error)
+          return
+        }
+        if (response && response.statusCode === 200) {
+          fs.writeFileSync(_getRemoteSavePath(), body)
+          resolve()
+        } else {
+          const message = '下载远程配置失败:' + response.message + ',code:' + response.statusCode
+          log.error(message)
+          reject(new Error(message))
+        }
+      })
+    })
+  },
+  readRemoteConfig () {
+    if (get().app.remoteConfig.enabled !== true) {
+      return {}
+    }
+    const path = _getRemoteSavePath()
+    if (fs.existsSync()) {
+      const file = fs.readFileSync(path)
+      log.info('读取合并远程配置文件:', path)
+      return JSON5.parse(file.toString())
+    }
+    return {}
+  },
   /**
    * 保存自定义的 config
    * @param newConfig
+   * @param remoteConfig //远程配置
    */
   save (newConfig) {
     // 对比默认config的异同
@@ -113,6 +173,7 @@ const configApi = {
       }
     }
     lodash.mergeWith(merged, clone, customizer)
+    lodash.mergeWith(merged, configApi.readRemoteConfig(), customizer)
     lodash.mergeWith(merged, newConfig, customizer)
     _deleteDisabledItem(merged)
     configTarget = merged
diff --git a/packages/core/src/config/index.js b/packages/core/src/config/index.js
index 07345817..eec59622 100644
--- a/packages/core/src/config/index.js
+++ b/packages/core/src/config/index.js
@@ -17,7 +17,7 @@ module.exports = {
     },
     remoteConfig: {
       enabled: true,
-      url: 'https://gitee.com/docmirror/dev-sidecar/raw/master/packages/gui/extra/config_remote.json5'
+      url: 'https://gitee.com/docmirror/dev-sidecar/raw/master/packages/core/src/config/remote_config.json5'
     }
   },
   server: {
diff --git a/packages/gui/extra/config_remote.json5 b/packages/core/src/config/remote_config.json5
similarity index 100%
rename from packages/gui/extra/config_remote.json5
rename to packages/core/src/config/remote_config.json5
diff --git a/packages/gui/src/bridge/api/backend.js b/packages/gui/src/bridge/api/backend.js
index cc33892c..b9b339cb 100644
--- a/packages/gui/src/bridge/api/backend.js
+++ b/packages/gui/src/bridge/api/backend.js
@@ -150,6 +150,8 @@ export default {
 
     // 合并用户配置
     DevSidecar.api.config.reload()
+    // 开启自动下载远程配置
+    DevSidecar.api.config.startAutoDownloadRemoteConfig()
     // 启动所有
     localApi.startup()
   },