Просмотр исходного кода

:sparkles: loglevel and datetime

Signed-off-by: LI JIAHAO <lijiahao99131@gmail.com>
LI JIAHAO 6 лет назад
Родитель
Сommit
2aa435dd8d
16 измененных файлов с 146 добавлено и 31 удалено
  1. 2 1
      config.example.json
  2. 4 2
      dist/command.js
  3. 6 6
      dist/cqhttp.js
  4. 48 0
      dist/datetime.js
  5. 7 3
      dist/main.js
  6. 7 2
      dist/twitter.js
  7. 1 1
      dist/webshot.js
  8. 6 3
      src/command.ts
  9. 6 6
      src/cqhttp.ts
  10. 39 0
      src/datetime.js
  11. 9 4
      src/main.ts
  12. 1 0
      src/model.d.ts
  13. 8 2
      src/twitter.ts
  14. 1 1
      src/webshot.ts
  15. 0 0
      src/webshot_test.js
  16. 1 0
      tsconfig.json

+ 2 - 1
config.example.json

@@ -8,5 +8,6 @@
   "twitter_access_token_secret": "",
   "work_interval": 60,
   "webshot_delay": 5000,
-  "lockfile": "subscriber.lock"
+  "lockfile": "subscriber.lock",
+  "loglevel": "info"
 }

+ 4 - 2
dist/command.js

@@ -3,8 +3,9 @@ Object.defineProperty(exports, "__esModule", { value: true });
 const fs = require("fs");
 const log4js = require("log4js");
 const path = require("path");
+const datetime_1 = require("./datetime");
 const logger = log4js.getLogger('command');
-logger.level = 'info';
+logger.level = global.loglevel;
 function sub(chat, args, lock, lockfile) {
     if (args.length === 0) {
         return '找不到要订阅的链接。';
@@ -36,6 +37,7 @@ https://twitter.com/rikakomoe/lists/lovelive`;
         lock.threads[link] = {
             offset: 0,
             subscribers: [],
+            updatedAt: '',
         };
     }
     flag = false;
@@ -78,7 +80,7 @@ function list(chat, args, lock) {
     Object.keys(lock.threads).forEach(key => {
         lock.threads[key].subscribers.forEach(c => {
             if (c.chatID === chat.chatID && c.chatType === chat.chatType)
-                links.push(key);
+                links.push(`${key} ${datetime_1.relativeDate(lock.threads[key].updatedAt)}`);
         });
     });
     return '此聊天中订阅的链接:\n' + links.join('\n');

+ 6 - 6
dist/cqhttp.js

@@ -4,7 +4,7 @@ const CQWebsocket = require("cq-websocket");
 const log4js = require("log4js");
 const helper_1 = require("./helper");
 const logger = log4js.getLogger('cq-websocket');
-logger.level = 'info';
+logger.level = global.loglevel;
 class default_1 {
     constructor(opt) {
         this.retryInterval = 1000;
@@ -63,16 +63,16 @@ class default_1 {
                 }
             });
             this.bot.on('api.send.pre', (type, apiRequest) => {
-                logger.info(`sending request ${type}: ${JSON.stringify(apiRequest)}`);
+                logger.debug(`sending request ${type}: ${JSON.stringify(apiRequest)}`);
             });
             this.bot.on('api.send.post', (type) => {
-                logger.info(`sent request ${type}`);
+                logger.debug(`sent request ${type}`);
             });
             this.bot.on('api.response', (type, result) => {
                 if (result.retcode !== 0)
                     logger.warn(`${type} respond: ${JSON.stringify(result)}`);
                 else
-                    logger.info(`${type} respond: ${JSON.stringify(result)}`);
+                    logger.debug(`${type} respond: ${JSON.stringify(result)}`);
             });
         };
         this.connect = () => {
@@ -84,13 +84,13 @@ class default_1 {
             this.retryInterval *= 2;
             if (this.retryInterval > 300000)
                 this.retryInterval = 300000;
-            logger.info(`retrying in ${this.retryInterval / 1000}s...`);
+            logger.warn(`retrying in ${this.retryInterval / 1000}s...`);
             setTimeout(() => {
                 logger.warn('reconnecting to websocket...');
                 this.connect();
             }, this.retryInterval);
         };
-        logger.info(`init cqwebsocket for ${opt.host}:${opt.port}, with access_token ${opt.access_token}`);
+        logger.warn(`init cqwebsocket for ${opt.host}:${opt.port}, with access_token ${opt.access_token}`);
         this.botInfo = opt;
     }
 }

+ 48 - 0
dist/datetime.js

@@ -0,0 +1,48 @@
+"use strict";
+Object.defineProperty(exports, "__esModule", { value: true });
+function relativeDate(dtstr) {
+    if (!dtstr)
+        return '暂无数据';
+    const dt = new Date(dtstr);
+    const dateTimeStamp = dt.getTime();
+    const minute = 1000 * 60;
+    const hour = minute * 60;
+    const day = hour * 24;
+    const month = day * 30;
+    const now = new Date().getTime();
+    const diffValue = now - dateTimeStamp;
+    if (diffValue < 0) {
+        return;
+    }
+    const monthC = diffValue / month;
+    const weekC = diffValue / (7 * day);
+    const dayC = diffValue / day;
+    const hourC = diffValue / hour;
+    const minC = diffValue / minute;
+    let result;
+    if (monthC > 12) {
+        const y = dt.getFullYear() + ' 年';
+        const m = dt.getMonth() + 1 + ' 月';
+        const d = dt.getDate() + ' 日';
+        result = [y, m, d].join(' ');
+    }
+    else if (monthC >= 1) {
+        result = '' + Math.floor(monthC) + ' 个月前';
+    }
+    else if (weekC >= 1) {
+        result = '' + Math.floor(weekC) + ' 周前';
+    }
+    else if (dayC >= 1) {
+        result = '' + Math.floor(dayC) + ' 天前';
+    }
+    else if (hourC >= 1) {
+        result = '' + Math.floor(hourC) + ' 小时前';
+    }
+    else if (minC >= 1) {
+        result = '' + Math.floor(minC) + ' 分钟前';
+    }
+    else
+        result = '刚刚';
+    return result;
+}
+exports.relativeDate = relativeDate;

+ 7 - 3
dist/main.js

@@ -5,9 +5,6 @@ const commandLineUsage = require("command-line-usage");
 const fs = require("fs");
 const log4js = require("log4js");
 const path = require("path");
-const command_1 = require("./command");
-const cqhttp_1 = require("./cqhttp");
-const twitter_1 = require("./twitter");
 const logger = log4js.getLogger();
 logger.level = 'info';
 const sections = [
@@ -74,6 +71,13 @@ if (config.work_interval === undefined) {
 if (config.webshot_delay === undefined) {
     config.webshot_delay = 5000;
 }
+if (config.loglevel === undefined) {
+    config.loglevel = 'info';
+}
+global.loglevel = config.loglevel;
+const command_1 = require("./command");
+const cqhttp_1 = require("./cqhttp");
+const twitter_1 = require("./twitter");
 let lock;
 if (fs.existsSync(path.resolve(config.lockfile))) {
     try {

+ 7 - 2
dist/twitter.js

@@ -6,7 +6,7 @@ const path = require("path");
 const Twitter = require("twitter");
 const webshot_1 = require("./webshot");
 const logger = log4js.getLogger('twitter');
-logger.level = 'info';
+logger.level = global.loglevel;
 class default_1 {
     constructor(opt) {
         this.work = () => {
@@ -31,6 +31,7 @@ class default_1 {
                 this.work();
                 return;
             }
+            logger.debug(`pulling feed ${lock.feed[lock.workon]}`);
             const promise = new Promise(resolve => {
                 let match = lock.feed[lock.workon].match(/https:\/\/twitter.com\/([^\/]+)\/lists\/([^\/]+)/);
                 if (match) {
@@ -62,6 +63,7 @@ class default_1 {
                 }
             });
             promise.then((tweets) => {
+                logger.debug(`api returned ${JSON.stringify(tweets)} for feed ${lock.feed[lock.workon]}`);
                 if (tweets.length === 0)
                     return;
                 if (lock.threads[lock.feed[lock.workon]].offset === -1) {
@@ -82,7 +84,10 @@ class default_1 {
                         });
                     });
                 }, this.webshotDelay)
-                    .then(() => lock.threads[lock.feed[lock.workon]].offset = tweets[0].id_str);
+                    .then(() => {
+                    lock.threads[lock.feed[lock.workon]].offset = tweets[0].id_str;
+                    lock.threads[lock.feed[lock.workon]].updatedAt = new Date().toString();
+                });
             })
                 .then(() => {
                 lock.workon++;

+ 1 - 1
dist/webshot.js

@@ -6,7 +6,7 @@ const pngjs_1 = require("pngjs");
 const read = require("read-all-stream");
 const webshot = require("webshot");
 const logger = log4js.getLogger('webshot');
-logger.level = 'info';
+logger.level = global.loglevel;
 function renderWebshot(url, height, webshotDelay) {
     const promise = new Promise(resolve => {
         const options = {

+ 6 - 3
src/command.ts

@@ -2,8 +2,10 @@ import * as fs from 'fs';
 import * as log4js from 'log4js';
 import * as path from 'path';
 
+import { relativeDate } from './datetime';
+
 const logger = log4js.getLogger('command');
-logger.level = 'info';
+logger.level = (global as any).loglevel;
 
 function sub(chat: IChat, args: string[], lock: ILock, lockfile: string): string {
   if (args.length === 0) {
@@ -32,6 +34,7 @@ https://twitter.com/rikakomoe/lists/lovelive`;
     lock.threads[link] = {
       offset: 0,
       subscribers: [],
+      updatedAt: '',
     };
   }
   flag = false;
@@ -71,10 +74,10 @@ function list(chat: IChat, args: string[], lock: ILock): string {
   const links = [];
   Object.keys(lock.threads).forEach(key => {
     lock.threads[key].subscribers.forEach(c => {
-      if (c.chatID === chat.chatID && c.chatType === chat.chatType) links.push(key);
+      if (c.chatID === chat.chatID && c.chatType === chat.chatType) links.push(`${key} ${relativeDate(lock.threads[key].updatedAt)}`);
     });
   });
   return '此聊天中订阅的链接:\n' + links.join('\n');
 }
 
-export { sub, list, unsub };
+export {sub, list, unsub};

+ 6 - 6
src/cqhttp.ts

@@ -4,7 +4,7 @@ import * as log4js from 'log4js';
 import command from './helper';
 
 const logger = log4js.getLogger('cq-websocket');
-logger.level = 'info';
+logger.level = (global as any).loglevel;
 
 interface IQQProps {
   access_token: string;
@@ -81,16 +81,16 @@ export default class {
     });
 
     this.bot.on('api.send.pre', (type, apiRequest) => {
-      logger.info(`sending request ${type}: ${JSON.stringify(apiRequest)}`);
+      logger.debug(`sending request ${type}: ${JSON.stringify(apiRequest)}`);
     });
 
     this.bot.on('api.send.post', (type) => {
-      logger.info(`sent request ${type}`);
+      logger.debug(`sent request ${type}`);
     });
 
     this.bot.on('api.response', (type, result) => {
       if (result.retcode !== 0) logger.warn(`${type} respond: ${JSON.stringify(result)}`);
-      else logger.info(`${type} respond: ${JSON.stringify(result)}`);
+      else logger.debug(`${type} respond: ${JSON.stringify(result)}`);
     });
 }
 
@@ -103,7 +103,7 @@ export default class {
   private reconnect = () => {
     this.retryInterval *= 2;
     if (this.retryInterval > 300000) this.retryInterval = 300000;
-    logger.info(`retrying in ${this.retryInterval / 1000}s...`);
+    logger.warn(`retrying in ${this.retryInterval / 1000}s...`);
     setTimeout(() => {
       logger.warn('reconnecting to websocket...');
       this.connect();
@@ -111,7 +111,7 @@ export default class {
   }
 
   constructor(opt: IQQProps) {
-    logger.info(`init cqwebsocket for ${opt.host}:${opt.port}, with access_token ${opt.access_token}`);
+    logger.warn(`init cqwebsocket for ${opt.host}:${opt.port}, with access_token ${opt.access_token}`);
     this.botInfo = opt;
   }
 }

+ 39 - 0
src/datetime.js

@@ -0,0 +1,39 @@
+function relativeDate(dtstr) {
+  if (!dtstr) return '暂无数据';
+  const dt = new Date(dtstr);
+  const dateTimeStamp = dt.getTime();
+  const minute = 1000 * 60;
+  const hour = minute * 60;
+  const day = hour * 24;
+  const month = day * 30;
+  const now = new Date().getTime();
+  const diffValue = now - dateTimeStamp;
+  if (diffValue < 0) {
+    return;
+  }
+  const monthC = diffValue / month;
+  const weekC = diffValue / (7 * day);
+  const dayC = diffValue / day;
+  const hourC = diffValue / hour;
+  const minC = diffValue / minute;
+  let result;
+  if (monthC > 12) {
+    const y = dt.getFullYear() + ' 年';
+    const m = dt.getMonth() + 1 + ' 月';
+    const d = dt.getDate() + ' 日';
+    result = [y, m, d].join(' ');
+  } else if (monthC >= 1) {
+    result = '' + Math.floor(monthC) + ' 个月前';
+  } else if (weekC >= 1) {
+    result = '' + Math.floor(weekC) + ' 周前';
+  } else if (dayC >= 1) {
+    result = '' + Math.floor(dayC) + ' 天前';
+  } else if (hourC >= 1) {
+    result = '' + Math.floor(hourC) + ' 小时前';
+  } else if (minC >= 1) {
+    result = '' + Math.floor(minC) + ' 分钟前';
+  } else result = '刚刚';
+  return result;
+}
+
+export { relativeDate };

+ 9 - 4
src/main.ts

@@ -5,10 +5,6 @@ import * as fs from 'fs';
 import * as log4js from 'log4js';
 import * as path from 'path';
 
-import { list, sub, unsub } from './command';
-import QQBot from './cqhttp';
-import Worker from './twitter';
-
 const logger = log4js.getLogger();
 logger.level = 'info';
 
@@ -81,6 +77,15 @@ if (config.work_interval === undefined) {
 if (config.webshot_delay === undefined) {
   config.webshot_delay = 5000;
 }
+if (config.loglevel === undefined) {
+  config.loglevel = 'info';
+}
+
+(global as any).loglevel = config.loglevel;
+
+import { list, sub, unsub } from './command';
+import QQBot from './cqhttp';
+import Worker from './twitter';
 
 let lock: ILock;
 if (fs.existsSync(path.resolve(config.lockfile))) {

+ 1 - 0
src/model.d.ts

@@ -16,6 +16,7 @@ interface ILock {
     [key: string]:
       {
         offset: number,
+        updatedAt: string,
         subscribers: IChat[],
       }
   }

+ 8 - 2
src/twitter.ts

@@ -19,7 +19,7 @@ interface IWorkerOption {
 }
 
 const logger = log4js.getLogger('twitter');
-logger.level = 'info';
+logger.level = (global as any).loglevel;
 
 export default class {
 
@@ -65,6 +65,8 @@ export default class {
       return;
     }
 
+    logger.debug(`pulling feed ${lock.feed[lock.workon]}`);
+
     const promise = new Promise(resolve => {
       let match = lock.feed[lock.workon].match(/https:\/\/twitter.com\/([^\/]+)\/lists\/([^\/]+)/);
       if (match) {
@@ -94,6 +96,7 @@ export default class {
     });
 
     promise.then((tweets: any) => {
+      logger.debug(`api returned ${JSON.stringify(tweets)} for feed ${lock.feed[lock.workon]}`);
       if (tweets.length === 0) return;
       if (lock.threads[lock.feed[lock.workon]].offset === -1) {
         lock.threads[lock.feed[lock.workon]].offset = tweets[0].id_str;
@@ -112,7 +115,10 @@ export default class {
           });
         });
       }, this.webshotDelay)
-        .then(() => lock.threads[lock.feed[lock.workon]].offset = tweets[0].id_str);
+        .then(() => {
+          lock.threads[lock.feed[lock.workon]].offset = tweets[0].id_str;
+          lock.threads[lock.feed[lock.workon]].updatedAt = new Date().toString();
+        });
 
     })
       .then(() => {

+ 1 - 1
src/webshot.ts

@@ -5,7 +5,7 @@ import * as read from 'read-all-stream';
 import * as webshot from 'webshot';
 
 const logger = log4js.getLogger('webshot');
-logger.level = 'info';
+logger.level = (global as any).loglevel;
 
 function renderWebshot(url: string, height: number, webshotDelay: number): Promise<string> {
   const promise = new Promise<{ data: string, boundary: null | number }>(resolve => {

+ 0 - 0
src/webshot_test.ts → src/webshot_test.js


+ 1 - 0
tsconfig.json

@@ -10,6 +10,7 @@
     "module": "commonjs",
     "target": "es6",
     "noUnusedLocals": true,
+    "allowJs": true,
     "allowSyntheticDefaultImports": true
   }
 }