|
|
|
|
|
import YAML from 'yaml' |
|
|
import chokidar from 'chokidar' |
|
|
import fs from 'node:fs' |
|
|
import YamlReader from './YamlReader.js' |
|
|
import cfg from '../../../lib/config/config.js' |
|
|
import _ from 'lodash' |
|
|
import { modifyWebSocket } from './WebSocket.js' |
|
|
import { cfgSchema } from '../config/system/cfg_system.js' |
|
|
|
|
|
const Path = process.cwd() |
|
|
const Plugin_Name = 'ws-plugin' |
|
|
const Plugin_Path = `${Path}/plugins/${Plugin_Name}` |
|
|
class Config { |
|
|
constructor() { |
|
|
this.config = {} |
|
|
this.oldConfig = {} |
|
|
|
|
|
this.watcher = { config: {}, defSet: {} } |
|
|
|
|
|
this.initCfg() |
|
|
} |
|
|
|
|
|
|
|
|
initCfg() { |
|
|
let path = `${Plugin_Path}/config/config/` |
|
|
if (!fs.existsSync(path)) fs.mkdirSync(path) |
|
|
let pathDef = `${Plugin_Path}/config/default_config/` |
|
|
const files = fs.readdirSync(pathDef).filter(file => file.endsWith('.yaml')) |
|
|
for (let file of files) { |
|
|
if (!fs.existsSync(`${path}${file}`)) { |
|
|
fs.copyFileSync(`${pathDef}${file}`, `${path}${file}`) |
|
|
} |
|
|
this.watch(`${path}${file}`, file.replace('.yaml', ''), 'config') |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
get masterQQ() { |
|
|
return cfg.masterQQ |
|
|
} |
|
|
|
|
|
|
|
|
get master() { |
|
|
return cfg.master |
|
|
} |
|
|
|
|
|
|
|
|
get blackGroup() { |
|
|
return cfg.getOther().blackGroup |
|
|
} |
|
|
|
|
|
|
|
|
get whiteGroup() { |
|
|
return cfg.getOther().whiteGroup |
|
|
} |
|
|
|
|
|
|
|
|
get heartbeatInterval() { |
|
|
return this.getDefOrConfig('ws-config').heartbeatInterval |
|
|
} |
|
|
|
|
|
|
|
|
get messagePostFormat() { |
|
|
return this.getDefOrConfig('ws-config').messagePostFormat |
|
|
} |
|
|
|
|
|
|
|
|
get servers() { |
|
|
return this.getDefOrConfig('ws-config').servers |
|
|
} |
|
|
|
|
|
get noMsgStart() { |
|
|
return this.getDefOrConfig('msg-config').noMsgStart |
|
|
} |
|
|
|
|
|
get noMsgInclude() { |
|
|
return this.getDefOrConfig('msg-config').noMsgInclude |
|
|
} |
|
|
|
|
|
get howToMaster() { |
|
|
return this.getDefOrConfig('msg-config').howToMaster |
|
|
} |
|
|
|
|
|
|
|
|
get disconnectToMaster() { |
|
|
return this.getDefOrConfig('msg-config').disconnectToMaster |
|
|
} |
|
|
|
|
|
|
|
|
get reconnectToMaster() { |
|
|
return this.getDefOrConfig('msg-config').reconnectToMaster |
|
|
} |
|
|
|
|
|
|
|
|
get firstconnectToMaster() { |
|
|
return this.getDefOrConfig('msg-config').firstconnectToMaster |
|
|
} |
|
|
|
|
|
|
|
|
get msgStoreTime() { |
|
|
return this.getDefOrConfig('msg-config').msgStoreTime |
|
|
} |
|
|
|
|
|
|
|
|
get noGroup() { |
|
|
return this.getDefOrConfig('msg-config').noGroup |
|
|
} |
|
|
|
|
|
|
|
|
get yesGroup() { |
|
|
return this.getDefOrConfig('msg-config').yesGroup |
|
|
} |
|
|
|
|
|
|
|
|
get muteStop() { |
|
|
return this.getDefOrConfig('msg-config').muteStop |
|
|
} |
|
|
|
|
|
|
|
|
get redSendForwardMsgType(){ |
|
|
return this.getDefOrConfig('msg-config').redSendForwardMsgType |
|
|
} |
|
|
|
|
|
|
|
|
get groupAdmin() { |
|
|
return this.getDefOrConfig('notice-config').groupAdmin |
|
|
} |
|
|
|
|
|
|
|
|
get groupDecrease() { |
|
|
return this.getDefOrConfig('notice-config').groupDecrease |
|
|
} |
|
|
|
|
|
|
|
|
get groupIncrease() { |
|
|
return this.getDefOrConfig('notice-config').groupIncrease |
|
|
} |
|
|
|
|
|
|
|
|
get groupBan() { |
|
|
return this.getDefOrConfig('notice-config').groupBan |
|
|
} |
|
|
|
|
|
|
|
|
get friendIncrease() { |
|
|
return this.getDefOrConfig('notice-config').friendIncrease |
|
|
} |
|
|
|
|
|
|
|
|
get groupRecall() { |
|
|
return this.getDefOrConfig('notice-config').groupRecall |
|
|
} |
|
|
|
|
|
|
|
|
get friendRecall() { |
|
|
return this.getDefOrConfig('notice-config').friendRecall |
|
|
} |
|
|
|
|
|
|
|
|
get groupPoke() { |
|
|
return this.getDefOrConfig('notice-config').groupPoke |
|
|
} |
|
|
|
|
|
|
|
|
get friendAdd() { |
|
|
return this.getDefOrConfig('request-config').friendAdd |
|
|
} |
|
|
|
|
|
|
|
|
get groupInvite() { |
|
|
return this.getDefOrConfig('request-config').groupInvite |
|
|
} |
|
|
|
|
|
|
|
|
get groupAdd() { |
|
|
return this.getDefOrConfig('request-config').groupAdd |
|
|
} |
|
|
|
|
|
|
|
|
getDefOrConfig(name) { |
|
|
let def = this.getdefSet(name) |
|
|
let config = this.getConfig(name) |
|
|
return { ...def, ...config } |
|
|
} |
|
|
|
|
|
|
|
|
getdefSet(name) { |
|
|
return this.getYaml('default_config', name) |
|
|
} |
|
|
|
|
|
|
|
|
getConfig(name) { |
|
|
return this.getYaml('config', name) |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
getYaml(type, name) { |
|
|
let file = `${Plugin_Path}/config/${type}/${name}.yaml` |
|
|
let key = `${type}.${name}` |
|
|
|
|
|
if (this.config[key]) return this.config[key] |
|
|
|
|
|
this.config[key] = YAML.parse( |
|
|
fs.readFileSync(file, 'utf8') |
|
|
) |
|
|
|
|
|
this.watch(file, name, type) |
|
|
|
|
|
return this.config[key] |
|
|
} |
|
|
|
|
|
|
|
|
watch(file, name, type = 'default_config') { |
|
|
let key = `${type}.${name}` |
|
|
if (!this.oldConfig[key]) this.oldConfig[key] = _.cloneDeep(this.config[key]) |
|
|
if (this.watcher[key]) return |
|
|
|
|
|
const watcher = chokidar.watch(file) |
|
|
watcher.on('change', path => { |
|
|
delete this.config[key] |
|
|
if (typeof Bot == 'undefined') return |
|
|
logger.mark(`[ws-plugin][修改配置文件][${type}][${name}]`) |
|
|
|
|
|
if (name == 'ws-config') { |
|
|
const oldConfig = this.oldConfig[key] |
|
|
delete this.oldConfig[key] |
|
|
const newConfig = this.getYaml(type, name) |
|
|
const object = this.findDifference(oldConfig, newConfig) |
|
|
|
|
|
for (const key in object) { |
|
|
if (Object.hasOwnProperty.call(object, key)) { |
|
|
const value = object[key]; |
|
|
const arr = key.split('.') |
|
|
if (arr[0] !== 'servers') continue |
|
|
let data = newConfig.servers[arr[1]] |
|
|
if (typeof data === 'undefined') data = oldConfig.servers[arr[1]] |
|
|
const target = { |
|
|
type: null, |
|
|
data |
|
|
} |
|
|
if (typeof value['newValue'] === 'object' && typeof value['oldValue'] === 'undefined') { |
|
|
target.type = 'add' |
|
|
} |
|
|
else if (typeof value['newValue'] === 'undefined' && typeof value['oldValue'] === 'object') { |
|
|
target.type = 'del' |
|
|
} |
|
|
else if (value['newValue'] === true && (value['oldValue'] === false || typeof value['oldValue'] === 'undefined')) { |
|
|
target.type = 'close' |
|
|
} |
|
|
else if (value['newValue'] === false && (value['oldValue'] === true || typeof value['oldValue'] === 'undefined')) { |
|
|
target.type = 'open' |
|
|
} |
|
|
modifyWebSocket(target) |
|
|
} |
|
|
} |
|
|
|
|
|
} |
|
|
}) |
|
|
|
|
|
this.watcher[key] = watcher |
|
|
} |
|
|
|
|
|
getCfgSchemaMap() { |
|
|
let ret = {} |
|
|
_.forEach(cfgSchema, (cfgGroup) => { |
|
|
_.forEach(cfgGroup.cfg, (cfgItem, cfgKey) => { |
|
|
ret[cfgItem.key] = cfgItem |
|
|
cfgItem.cfgKey = cfgKey |
|
|
}) |
|
|
}) |
|
|
return ret |
|
|
} |
|
|
|
|
|
getCfgSchema() { |
|
|
return cfgSchema |
|
|
} |
|
|
|
|
|
getCfg() { |
|
|
let wsconfig = this.getDefOrConfig('ws-config') |
|
|
let msgconfig = this.getDefOrConfig('msg-config') |
|
|
let noticeconfig = this.getDefOrConfig('notice-config') |
|
|
let requestconfig = this.getDefOrConfig('request-config') |
|
|
return { |
|
|
...wsconfig, |
|
|
...msgconfig, |
|
|
...noticeconfig, |
|
|
...requestconfig |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
modify(name, key, value, type = 'config') { |
|
|
let path = `${Plugin_Path}/config/${type}/${name}.yaml` |
|
|
new YamlReader(path).set(key, value) |
|
|
this.oldConfig[key] = _.cloneDeep(this.config[key]) |
|
|
delete this.config[`${type}.${name}`] |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
modifyarr(name, key, value, category = 'add', type = 'config') { |
|
|
let path = `${Plugin_Path}/config/${type}/${name}.yaml` |
|
|
let yaml = new YamlReader(path) |
|
|
if (category == 'add') { |
|
|
yaml.addIn(key, value) |
|
|
} else { |
|
|
let index = yaml.jsonData[key].indexOf(value) |
|
|
yaml.delete(`${key}.${index}`) |
|
|
} |
|
|
} |
|
|
|
|
|
setArr(name, key, item, value, type = 'config') { |
|
|
let path = `${Plugin_Path}/config/${type}/${name}.yaml` |
|
|
let yaml = new YamlReader(path) |
|
|
let arr = yaml.get(key).slice(); |
|
|
arr[item] = value |
|
|
yaml.set(key, arr) |
|
|
} |
|
|
|
|
|
delServersArr(value, name = 'ws-config', type = 'config') { |
|
|
let path = `${Plugin_Path}/config/${type}/${name}.yaml` |
|
|
let yaml = new YamlReader(path) |
|
|
let key = 'servers' |
|
|
|
|
|
let index = yaml.jsonData[key].findIndex(item => item.name === value); |
|
|
yaml.delete(`${key}.${index}`) |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
findDifference(obj1, obj2, parentKey = '') { |
|
|
const result = {}; |
|
|
for (const key in obj1) { |
|
|
const fullKey = parentKey ? `${parentKey}.${key}` : key; |
|
|
if (_.isObject(obj1[key]) && _.isObject(obj2[key])) { |
|
|
const diff = this.findDifference(obj1[key], obj2[key], fullKey); |
|
|
if (!_.isEmpty(diff)) { |
|
|
Object.assign(result, diff); |
|
|
} |
|
|
} else if (!_.isEqual(obj1[key], obj2[key])) { |
|
|
result[fullKey] = { oldValue: obj1[key], newValue: obj2[key] }; |
|
|
} |
|
|
} |
|
|
for (const key in obj2) { |
|
|
if (!obj1.hasOwnProperty(key)) { |
|
|
const fullKey = parentKey ? `${parentKey}.${key}` : key; |
|
|
result[fullKey] = { oldValue: undefined, newValue: obj2[key] }; |
|
|
} |
|
|
} |
|
|
return result; |
|
|
} |
|
|
} |
|
|
export default new Config() |