Init
This commit is contained in:
@@ -0,0 +1,4 @@
|
||||
output/
|
||||
logs/
|
||||
node_modules/
|
||||
.env
|
||||
@@ -0,0 +1,67 @@
|
||||
"use strict";
|
||||
// from crepesr
|
||||
// logger
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
exports.VerboseLevel = void 0;
|
||||
require("colorts/lib/string");
|
||||
var VerboseLevel;
|
||||
(function (VerboseLevel) {
|
||||
VerboseLevel[VerboseLevel["NONE"] = 0] = "NONE";
|
||||
VerboseLevel[VerboseLevel["WARNS"] = 1] = "WARNS";
|
||||
VerboseLevel[VerboseLevel["ALL"] = 2] = "ALL";
|
||||
VerboseLevel[VerboseLevel["VERBL"] = 3] = "VERBL";
|
||||
VerboseLevel[VerboseLevel["VERBH"] = 4] = "VERBH";
|
||||
})(VerboseLevel || (exports.VerboseLevel = VerboseLevel = {}));
|
||||
class Logger {
|
||||
constructor(name = 'CLIENT', color = 'blue') {
|
||||
this.name = name;
|
||||
this.color = color;
|
||||
this.name = name;
|
||||
this.color = color;
|
||||
}
|
||||
getDate() {
|
||||
return new Date().toLocaleTimeString();
|
||||
}
|
||||
raw(...args) {
|
||||
// @ts-ignore - Element implicitly has an 'any' type because index expression is not of type 'number'
|
||||
console.log(`[${this.getDate().white.bold}] <${this.name[this.color].bold}>`, ...args);
|
||||
}
|
||||
log(...args) {
|
||||
this.raw(...args);
|
||||
}
|
||||
trail(...args) {
|
||||
console.log(`\t↳ ${args.join(' ').gray}`);
|
||||
}
|
||||
error(e, stack = true) {
|
||||
if (typeof e === 'string')
|
||||
e = new Error(e);
|
||||
console.log(`[${this.getDate().white.bold}] ${`ERROR<${this.name}>`.bgRed.bold}`, e.message);
|
||||
if (e.stack && stack)
|
||||
this.trail(e.stack);
|
||||
}
|
||||
warn(...args) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.WARNS)
|
||||
return;
|
||||
console.log(`[${this.getDate().white.bold}] ${`WARN<${this.name}>`.bgYellow.bold}`, ...args);
|
||||
}
|
||||
debug(...args) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.ALL)
|
||||
return;
|
||||
console.log(`[${this.getDate().white.bold}] ${`DEBUG<${this.name}>`.bgBlue.bold}`, ...args);
|
||||
this.trail(new Error().stack.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
verbL(...args) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.VERBL)
|
||||
return;
|
||||
console.log(`[${this.getDate().white.bold}] ${`VERBL<${this.name}>`.bgCyan.bold}`, ...args);
|
||||
this.trail(new Error().stack.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
verbH(...args) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.VERBH)
|
||||
return;
|
||||
console.log(`[${this.getDate().white.bold}] ${`VERBH<${this.name}>`.bgCyan.bold}`, ...args);
|
||||
this.trail(new Error().stack.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
}
|
||||
Logger.VERBOSE_LEVEL = 1;
|
||||
exports.default = Logger;
|
||||
+16
@@ -0,0 +1,16 @@
|
||||
async function Token() {
|
||||
const { MatrixAuth } = require('matrix-bot-sdk')
|
||||
|
||||
// This will be the URL where clients can reach your homeserver. Note that this might be different
|
||||
// from where the web/chat interface is hosted. The server must support password registration without
|
||||
// captcha or terms of service (public servers typically won't work).
|
||||
const homeserverUrl = "https://chat.sob.moe";
|
||||
|
||||
const auth = new MatrixAuth(homeserverUrl);
|
||||
// sobu: mk_sob_relEKA1axmA
|
||||
// sob: mk_sob_relA3cDmA3
|
||||
const client = await auth.passwordLogin("sobu", "mk_sob_relEKA1axmA");
|
||||
|
||||
console.log("\n\n")
|
||||
console.log("Copy this access token to your bot's config: ", client.accessToken);
|
||||
};Token()
|
||||
generated
+2844
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"name": "matrix-sob",
|
||||
"version": "1.0.0",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"clean": "rimraf output/",
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"quick": "npm run clean && tsc && node ./output/src/index.js"
|
||||
},
|
||||
"author": "",
|
||||
"license": "ISC",
|
||||
"description": "",
|
||||
"dependencies": {
|
||||
"colorts": "^0.1.63",
|
||||
"dotenv": "^16.5.0",
|
||||
"matrix-bot-sdk": "^0.7.1",
|
||||
"node-pager": "^0.3.6",
|
||||
"rimraf": "^6.0.1",
|
||||
"tree-kill": "^1.2.2",
|
||||
"typescript": "^5.8.3",
|
||||
"winston": "^3.17.0"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"syncToken": "s20307_514091_162_46420_7870_32_844_11065_0_7",
|
||||
"filter": null,
|
||||
"appserviceUsers": {},
|
||||
"appserviceTransactions": {},
|
||||
"kvStore": {}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
import { AutojoinRoomsMixin, MatrixClient, SimpleFsStorageProvider } from "matrix-bot-sdk";
|
||||
import Logger from "./util/Logger";
|
||||
import { StrawberryFilling } from "./types/Cheesecake";
|
||||
const csc = new Logger("Strawberry Cheesecake", 'red')
|
||||
import { cd, commands, handleCommand } from ".";
|
||||
require('dotenv').config()
|
||||
|
||||
var homeServer = process.env.homeserver
|
||||
|
||||
var accessToken: any = process.env.token
|
||||
var storage: SimpleFsStorageProvider
|
||||
|
||||
var client: MatrixClient = null;
|
||||
|
||||
export function BakeStrawberryCheesecake(): StrawberryFilling {
|
||||
client = null;
|
||||
csc.log('Baking strawberry cheesecake...')
|
||||
storage = new SimpleFsStorageProvider('session.json')
|
||||
cd.quiet('Started Matrix Client.')
|
||||
client = new MatrixClient(homeServer, accessToken, storage);
|
||||
client.start()
|
||||
csc.log(`Baked strawberry cheesecake. Serving cake.`)
|
||||
AutojoinRoomsMixin.setupOnClient(client);
|
||||
client.on("room.message", handleCommand);
|
||||
return GetStrawberryCheesecake()
|
||||
}
|
||||
|
||||
export function GetStrawberryCheesecake(): StrawberryFilling {
|
||||
return {
|
||||
accessToken: accessToken,
|
||||
stomach: storage,
|
||||
cake: client
|
||||
}
|
||||
}
|
||||
|
||||
export async function RebakeStrawberryCheesecake() {
|
||||
csc.log('Eating strawberry cheesecake!')
|
||||
await client.stop();
|
||||
client = null;
|
||||
setTimeout(async () => {
|
||||
BakeStrawberryCheesecake();
|
||||
AutojoinRoomsMixin.setupOnClient(client);
|
||||
await client.start()
|
||||
csc.log(`Cinnamon reports a command amount of ${commands.length}`)
|
||||
csc.log('Connection reset! Cake is served once more with an ID of ' + await client.getUserId())
|
||||
client.on("room.message", handleCommand);
|
||||
}, 7000)
|
||||
}
|
||||
|
||||
export function EatStrawberryCheesecake() {
|
||||
client.stop()
|
||||
client = null
|
||||
csc.log('Ate strawberry cheesecake.')
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
import { MatrixClient } from "matrix-bot-sdk";
|
||||
import { CommandData } from "./types/Command";
|
||||
import Logger from "./util/Logger";
|
||||
const c = new Logger("Cinnamon")
|
||||
|
||||
import fs from 'fs';
|
||||
require('dotenv').config()
|
||||
|
||||
var commands: string[] = []
|
||||
// Grab all the command files from the commands directory you created earlier
|
||||
|
||||
export function CinnamonInit(): string[] {
|
||||
const commandFiles = fs
|
||||
.readdirSync(process.cwd() + "/output/src/commands")
|
||||
.filter((file: any) => file.endsWith('.js'))
|
||||
|
||||
for (let file = 0; file < commandFiles.length; file++) {
|
||||
const cmd = commandFiles[file];
|
||||
commands.push(cmd)
|
||||
c.log(`Cinnamon found: ${cmd}`)
|
||||
}
|
||||
return commands
|
||||
}
|
||||
|
||||
export async function Cinnamon(client: MatrixClient, roomId: string, event: any, userInput: any) {
|
||||
try {
|
||||
var CommandMatched = false
|
||||
var CommandFile = ""
|
||||
if (userInput.startsWith('sob!')) {
|
||||
c.quiet("Cinnamon was called.")
|
||||
c.quiet(`Cinnamon input: ${userInput}`)
|
||||
for (let cmd = 0; cmd < commands.length; cmd++) {
|
||||
const command: string = commands[cmd];
|
||||
if (userInput.trim().split(" ")[0] === `sob!${command.replace('.js', '')}`) {
|
||||
CommandMatched = true
|
||||
CommandFile = command
|
||||
}
|
||||
}
|
||||
c.quiet(`Match? ${CommandMatched}`)
|
||||
|
||||
if (CommandMatched && CommandFile) {
|
||||
c.quiet(`${process.cwd()}/output/src/commands/${CommandFile}`)
|
||||
c.quiet(`File exists? ${fs.existsSync(`${process.cwd()}/output/src/commands/${CommandFile}`)}`)
|
||||
const TheCommandItself: CommandData = require(`${process.cwd()}/output/src/commands/${CommandFile}`).default
|
||||
|
||||
if (TheCommandItself) {
|
||||
await client.sendMessage(roomId, {
|
||||
msgtype: "m.text",
|
||||
body: (await TheCommandItself.execute(client, roomId, event, userInput)).toString()
|
||||
});
|
||||
c.quiet(`Cinnamon executed ${TheCommandItself.name}.`)
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (err) {
|
||||
c.error(`Cinnamon caught an error: ${err}`)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,129 @@
|
||||
import { MatrixClient } from "matrix-bot-sdk";
|
||||
import { CommandData } from "../types/Command";
|
||||
import { commands, StrawberryCheesecake } from "..";
|
||||
import Logger from "../util/Logger";
|
||||
import { cd } from "..";
|
||||
import { EatStrawberryCheesecake, RebakeStrawberryCheesecake } from "../Cheesecake";
|
||||
import { run } from "../console_commands/update";
|
||||
|
||||
export var dbg = {
|
||||
sessionIsForDebugging: true,
|
||||
targetEvent: 'none',
|
||||
roomId: 'none'
|
||||
};
|
||||
|
||||
export const Command: CommandData = {
|
||||
name: 'dbg',
|
||||
description: 'Debug command.',
|
||||
usage: false,
|
||||
execute: async (client: MatrixClient, roomId: string, event: any, userInput: any) => {
|
||||
userInput = userInput.replace('sob!dbg ', '')
|
||||
cd.quiet(`Tt ${userInput}`)
|
||||
var args: string[] = userInput.split(' ')
|
||||
if (args[0] && event.sender === "@maki:chat.sob.moe") {
|
||||
switch (args[0].toLowerCase()) {
|
||||
case 'cinnamon':
|
||||
var out = `Cinnamon found:\n\n`
|
||||
for (let i = 0; i < commands.length; i++) {
|
||||
const cmdName = commands[i];
|
||||
cd.quiet('Cinnamon found ' + cmdName)
|
||||
out = `${out}${cmdName},\n`
|
||||
}
|
||||
return `${out}`
|
||||
case 'strawberrycheesecake':
|
||||
if (args[1] && typeof (args[1]) === 'string') {
|
||||
switch (args[1].toLowerCase()) {
|
||||
case 'rebake':
|
||||
RebakeStrawberryCheesecake();
|
||||
return "Rebaked strawberry cheesecake!"
|
||||
case 'eat':
|
||||
client.sendMessage(roomId, {
|
||||
msgtype: "m.text",
|
||||
body: 'Eating strawberry cheesecake.'
|
||||
})
|
||||
EatStrawberryCheesecake();
|
||||
return 'Ate strawberry cheesecake.'
|
||||
case 'updaterecipe':
|
||||
client.sendMessage(roomId, {
|
||||
msgtype: "m.text",
|
||||
body: 'Updating recipe...'
|
||||
})
|
||||
StrawberryCheesecake.cake.stop()
|
||||
setTimeout(() => run('npm run quick'), 7000)
|
||||
default:
|
||||
return 'What do I do with the strawberry cheesecake?'
|
||||
}
|
||||
} else return 'Invalid arguments.'
|
||||
case 'eval':
|
||||
if (args[0].toLowerCase() === "eval") {
|
||||
args.splice(0, 1)
|
||||
var result = args.join(' ')
|
||||
const showRawOutput = result.includes(";;;raw")
|
||||
result = result.replace(';;;raw', '')
|
||||
try {
|
||||
let evaled = eval(result)
|
||||
cd.quiet(`Evaled ${evaled}`)
|
||||
if (!showRawOutput) {
|
||||
result = result.replaceAll(process.env.token, "\"[token\"").replaceAll('client.token', '\"[token]\"').replaceAll('process.env.token', '\"[token]\"');
|
||||
|
||||
//Convert evaled into a JSON String if it is an Object
|
||||
if (typeof evaled === "object") evaled = JSON.stringify(evaled);
|
||||
|
||||
//Do this if evaled is anything else other than a number, text, or true/false
|
||||
if (typeof evaled !== "number" && typeof evaled !== "string" && typeof evaled !== "boolean") evaled = `Output could not be converted to text (output was of type: ${typeof evaled}).`;
|
||||
evaled = evaled.toString().replaceAll(process.env.token.toString(), "[token]")
|
||||
result = result.toString().replaceAll(process.env.token, "[token]").replaceAll('client.token', '[token]').replaceAll('process.env.token', '[token]');
|
||||
}
|
||||
return `${showRawOutput ? "Raw e" : "E"}valuation result:\n${evaled}`
|
||||
} catch (err) {
|
||||
return `${showRawOutput ? "Raw e" : "E"}valuation result:\n${err}`
|
||||
}
|
||||
}
|
||||
default:
|
||||
if (!args[0]) {
|
||||
dbg.sessionIsForDebugging = true;
|
||||
dbg.targetEvent = event.event_id
|
||||
dbg.roomId = roomId
|
||||
return 'Debugging event where sob!dbg was used.'
|
||||
} else {
|
||||
switch (args[0]) {
|
||||
case 'target':
|
||||
if (args[1] && dbg.targetEvent === "none")
|
||||
dbg.targetEvent = args[1]
|
||||
break;
|
||||
case 'room':
|
||||
if (args[1] && dbg.roomId === "none")
|
||||
dbg.roomId = args[1]
|
||||
break;
|
||||
case 'reset':
|
||||
dbg.roomId = 'none'
|
||||
dbg.sessionIsForDebugging = false
|
||||
dbg.targetEvent = 'none'
|
||||
return 'Reset.'
|
||||
}
|
||||
switch (args[2]) {
|
||||
case 'target':
|
||||
if (args[3] && dbg.targetEvent === "none")
|
||||
dbg.targetEvent = args[3]
|
||||
break;
|
||||
case 'room':
|
||||
if (args[3] && dbg.roomId === "none")
|
||||
dbg.roomId = args[3]
|
||||
break;
|
||||
}
|
||||
if (dbg.roomId === 'none')
|
||||
dbg.roomId = roomId
|
||||
if (dbg.targetEvent === 'none')
|
||||
dbg.targetEvent = event.event_id
|
||||
dbg.sessionIsForDebugging = true
|
||||
return `Set ${dbg.targetEvent} as the target event and ${dbg.roomId} as the room id. Now debugging.`
|
||||
}
|
||||
}
|
||||
} else if (event.sender !== "@maki:chat.sob.moe") {
|
||||
return 'No permission to do this!'
|
||||
} else
|
||||
return 'No arguments provided!'
|
||||
}
|
||||
}
|
||||
|
||||
export default Command
|
||||
@@ -0,0 +1,62 @@
|
||||
import { MatrixClient, RoomEvent } from "matrix-bot-sdk";
|
||||
import { CommandData } from "../types/Command";
|
||||
|
||||
export const Command: CommandData = {
|
||||
name: 'delete',
|
||||
description: 'Deletes/redacts a set amount of messages.',
|
||||
usage: false,
|
||||
execute: async (client: MatrixClient, roomId: string, event: any, userInput: any) => {
|
||||
//await client.replyNotice(roomId, event, "😭");
|
||||
userInput = userInput.replace(`sob!${Command.name} `, '')
|
||||
var args = userInput.split(' ')
|
||||
try {
|
||||
if (args[0]) {
|
||||
var reason = ""
|
||||
if (args[1])
|
||||
reason = args[1]
|
||||
var times = parseInt(args[0])
|
||||
var RecentFew = await getRecentMessages(client, roomId, times)
|
||||
|
||||
if (RecentFew.length > 1) {
|
||||
for (let i = 0; i < times; i++) {
|
||||
console.log(`Cleared ${i} times total of ${times}`)
|
||||
const event: RoomEvent = RecentFew[i];
|
||||
console.log(`This: ${event.eventId}`)
|
||||
await client.redactEvent(roomId, event.eventId, reason)
|
||||
}
|
||||
}
|
||||
return `Tried redacting ${times} time(s).`
|
||||
}
|
||||
return `Invalid usage of command. ${userInput}`
|
||||
} catch (err) {
|
||||
return `${err}`
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function getRecentMessages(client: MatrixClient, roomId: string, count: number) {
|
||||
const messages = [];
|
||||
let fromToken = (await client.doRequest("GET", "/_matrix/client/v3/sync?timeout=0")).next_batch;
|
||||
|
||||
while (messages.length < count) {
|
||||
const res = await client.doRequest("GET", `/_matrix/client/v3/rooms/${encodeURIComponent(roomId)}/messages`, {
|
||||
dir: "b",
|
||||
from: fromToken,
|
||||
limit: 50, // Can adjust this
|
||||
filter: JSON.stringify({ types: ["m.room.message"] }),
|
||||
});
|
||||
// @ts-ignore
|
||||
const filtered = res.chunk.filter(e => e.type === "m.room.message");
|
||||
for (const msg of filtered) {
|
||||
messages.push(msg);
|
||||
if (messages.length === count) return messages; // ✅ Return immediately
|
||||
}
|
||||
|
||||
if (!res.end || res.chunk.length === 0) break; // No more messages to paginate
|
||||
fromToken = res.end;
|
||||
}
|
||||
|
||||
return messages; // May contain fewer than `count` if not enough messages
|
||||
}
|
||||
|
||||
export default Command
|
||||
@@ -0,0 +1,35 @@
|
||||
import { MatrixClient } from "matrix-bot-sdk";
|
||||
import { CommandData } from "../types/Command";
|
||||
import Logger from "../util/Logger";
|
||||
import { cd } from "..";
|
||||
|
||||
export const Command: CommandData = {
|
||||
name: 'repeat',
|
||||
description: 'w...',
|
||||
usage: false,
|
||||
execute: async (client: MatrixClient, roomId: string, event: any, userInput: any) => {
|
||||
//await client.replyNotice(roomId, event, "😭");
|
||||
userInput = userInput.replace('sob!repeat ', '')
|
||||
var initial: string[] = userInput.split(';;;') // initial[0]: text to spam
|
||||
|
||||
try {
|
||||
if (initial[1] === "@") {
|
||||
var times = parseInt(initial[2])
|
||||
cd.quiet(`Times: ${times.toString()}`)
|
||||
for (let i = 0; i < times; i++) {
|
||||
if (i != (times - 1))
|
||||
await client.sendMessage(roomId, {
|
||||
msgtype: "m.text",
|
||||
body: initial[0],
|
||||
})
|
||||
}
|
||||
return initial[0]
|
||||
}
|
||||
return initial[0]
|
||||
} catch (err) {
|
||||
return err.toString()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export default Command
|
||||
@@ -0,0 +1,14 @@
|
||||
import { MatrixClient } from "matrix-bot-sdk";
|
||||
import { CommandData } from "../types/Command";
|
||||
|
||||
export const Command: CommandData = {
|
||||
name: 'sob',
|
||||
description: 'sob...',
|
||||
usage: false,
|
||||
execute: async (client: MatrixClient, roomId: string, event: any, userInput: any) => {
|
||||
//await client.replyNotice(roomId, event, "😭");
|
||||
return "😭"
|
||||
}
|
||||
}
|
||||
|
||||
export default Command
|
||||
@@ -0,0 +1,10 @@
|
||||
export const metadata = {
|
||||
name: 'clear',
|
||||
description: "Clears the console.",
|
||||
usage: false,
|
||||
aliases: ["cls"]
|
||||
}
|
||||
|
||||
export function Main(args: Array<string>) {
|
||||
return '$clear'
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
import { cd, StrawberryCheesecake } from ".."
|
||||
import { BakeStrawberryCheesecake, RebakeStrawberryCheesecake } from "../Cheesecake"
|
||||
|
||||
export const metadata = {
|
||||
name: 'debug',
|
||||
description: "Debug commands.",
|
||||
usage: false,
|
||||
aliases: ["dbg"]
|
||||
}
|
||||
|
||||
export async function Main(args: Array<string>) {
|
||||
if (!args[0]) {
|
||||
cd.log(`No arguments supplied.`)
|
||||
return ``
|
||||
} else {
|
||||
switch (args[0]) {
|
||||
case 'bake':
|
||||
BakeStrawberryCheesecake();
|
||||
return 0;
|
||||
case 'reset':
|
||||
RebakeStrawberryCheesecake();
|
||||
return 0
|
||||
case 'eat':
|
||||
StrawberryCheesecake.cake.stop();
|
||||
return 'Ate strawberry cheesecake. Client shouldn\'t be active anymore.'
|
||||
default:
|
||||
return 'Unknown argument supplied.'
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
import Logger from "../util/Logger";
|
||||
const c = new Logger("CLIENT/echo.js")
|
||||
import 'colorts/lib/string'
|
||||
|
||||
export const metadata = {
|
||||
name: "echo",
|
||||
description: "Repeats text.",
|
||||
usage: `echo ${"<input text>"["bold"]}`,
|
||||
aliases: false
|
||||
}
|
||||
|
||||
export function Main(args: Array<string>) {
|
||||
return args.join(' ')
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
import { cd } from "..";
|
||||
import { ConsoleCommandData } from "../types/Command";
|
||||
|
||||
export const metadata: ConsoleCommandData = {
|
||||
name: "eval",
|
||||
description: "Evaluates JavaScript code.",
|
||||
usage: `eval ${'<code>'['bold']}`,
|
||||
aliases: ["do"]
|
||||
}
|
||||
|
||||
export function Main(args: string[]) {
|
||||
let result = ""
|
||||
result = args.join(" ")
|
||||
|
||||
const showRawOutput = result.includes("--raw") || result.includes("-r")
|
||||
result = result.replace('--raw', '').replace('-r', '')
|
||||
let evaled = eval(result)
|
||||
|
||||
if (!showRawOutput) {
|
||||
result = result.replaceAll(process.env.token, "\"[token\"").replaceAll('client.token', '\"[token]\"').replaceAll('process.env.token', '\"[token]\"');
|
||||
|
||||
//Convert evaled into a JSON String if it is an Object
|
||||
if (typeof evaled === "object") evaled = JSON.stringify(evaled);
|
||||
|
||||
//Do this if evaled is anything else other than a number, text, or true/false
|
||||
if (typeof evaled !== "number" && typeof evaled !== "string" && typeof evaled !== "boolean") evaled = `Output could not be converted to text (output was of type: ${typeof evaled}).`;
|
||||
evaled = evaled.toString().replaceAll(process.env.token.toString(), "[token]")
|
||||
result = result.toString().replaceAll(process.env.token, "[token]").replaceAll('client.token', '[token]').replaceAll('process.env.token', '[token]');
|
||||
}
|
||||
cd.log(`Evaled ${evaled}`)
|
||||
return `${showRawOutput ? "Raw e" : "E"}valuation result:\n${evaled}`
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
import Logger from "../util/Logger"
|
||||
var c = new Logger("CLIENT/exit.js")
|
||||
import 'colorts/lib/string'
|
||||
import treeKill from "tree-kill"
|
||||
export const metadata = {
|
||||
name: "exit",
|
||||
description: "Ends this process.",
|
||||
usage: `exit ${"<exitcode>"["italic"]}`,
|
||||
aliases: [ "stop" ]
|
||||
}
|
||||
|
||||
export function Main(args: Array<string>) {
|
||||
var code: number | boolean = Number.parseInt(args[0]) || false // the default is set to 1 for rebuild processes
|
||||
|
||||
c.log(code ? `Exiting process with exitcode ${code}.` : `Killing this process tree (${process.pid}).`)
|
||||
if (!code)
|
||||
treeKill(process.pid)
|
||||
else
|
||||
process.exit(parseInt(code.toString()))
|
||||
return 'Have a nice day!'
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
import Logger from "../util/Logger";
|
||||
const cm = new Logger("CLIENT/help.js")
|
||||
import fs from 'fs'
|
||||
import 'colorts/lib/string'
|
||||
import { ConsoleCommandData } from "../types/Command";
|
||||
|
||||
export const metadata = {
|
||||
name: "help",
|
||||
description: "Returns a list of usable commands / usage of a command.",
|
||||
usage: `help ${"<command name>"["italic"]}`,
|
||||
aliases: false
|
||||
}
|
||||
|
||||
export function Main(args: Array<string>) {
|
||||
const cmdname = args[0]
|
||||
const cwd = process.cwd();
|
||||
|
||||
try {
|
||||
if (cmdname) {
|
||||
const metadata: ConsoleCommandData = require(cwd + `/output/src/console_commands/${cmdname.replace('ts', 'js')}`).metadata
|
||||
|
||||
cm.log('Command name: ' + cmdname)
|
||||
cm.log(`Description: ${metadata.description}`)
|
||||
cm.log(`Usage: ${metadata.usage ? metadata.usage : 'No particular arguments.'}`)
|
||||
if (Array.isArray(metadata.aliases) && metadata.aliases.length)
|
||||
cm.log(`Aliases: ${metadata.aliases.join(', ')}`)
|
||||
return 0
|
||||
}
|
||||
} catch {
|
||||
cm.log(`The command ${cmdname} was not found.`)
|
||||
return 0
|
||||
}
|
||||
|
||||
if (!cmdname)
|
||||
try {
|
||||
//var commands = "\n"
|
||||
const commandList = fs.readdirSync(cwd + '/output/src/console_commands')
|
||||
//var processed_commands: number = 0
|
||||
cm.log(`${"Italic text"["italic"]} represent optional arguments, while ${"bold"["bold"]} text represent mandatory arguments.`)
|
||||
cm.log(`Command usage: ${this.metadata.usage}\n`)
|
||||
cm.log("The following commands are available:")
|
||||
|
||||
for (let i = 0; i < commandList.length; i++) {
|
||||
const commandFile = commandList[i];
|
||||
if (commandFile.includes('.map'))
|
||||
""
|
||||
else {
|
||||
//processed_commands++
|
||||
const commandMetadata = require(cwd + `/output/src/console_commands/${commandFile.replace('ts', 'js')}`).metadata
|
||||
const usage = commandMetadata.usage ? commandMetadata.usage : commandFile
|
||||
cm.log(`${commandFile.replace('.js', '')}\t${commandMetadata.description}`)
|
||||
//cm.log(`description: ${commandMetadata.description}`)
|
||||
//cm.log(`usage: ${usage}`)
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
} catch (err) {
|
||||
cm.error("An error occured while running this command: " + err)
|
||||
return 0
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
import Logger, { defaultLogName } from "../util/Logger"
|
||||
const c = new Logger("CLIENT/log.js")
|
||||
import fs from 'fs'
|
||||
const pager = require('node-pager')
|
||||
import 'colorts/lib/string'
|
||||
|
||||
export const metadata = {
|
||||
name: "log",
|
||||
description: "Views the log files.",
|
||||
usage: `log ${'<clear>'["italic"]}`,
|
||||
aliases: false
|
||||
}
|
||||
|
||||
export function Main(args: Array<string>) {
|
||||
c.log(`Using the log file at ${defaultLogName}.`)
|
||||
if (!args[0])
|
||||
fs.readFile(defaultLogName, (err, data) => {
|
||||
if (err) {
|
||||
c.error('Error reading file:\n' + err);
|
||||
return '...';
|
||||
}
|
||||
pager(data.toString('utf8')).then(() => {
|
||||
return 'Done.'
|
||||
});
|
||||
});
|
||||
else if (args[0].toLowerCase() === "clear") {
|
||||
c.clear()
|
||||
return "Cleared."
|
||||
} else if (args[0].toLowerCase() === "debug") { // means a log file was supplied
|
||||
fs.readFile('./logs/' + require('../index').cd.logger.transports[0].filename, (err, data) => {
|
||||
if (err) {
|
||||
c.error('Error reading file:\n' + err);
|
||||
return '...';
|
||||
}
|
||||
pager(data.toString('utf8')).then(() => {
|
||||
return 'Done.'
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
return 'Done.'
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
import Logger from "../util/Logger"
|
||||
var c = new Logger("CLIENT/update.js")
|
||||
import proc, { exec, execSync } from 'child_process'
|
||||
import { ConsoleCommandData } from '../types/Command'
|
||||
import { StrawberryCheesecake } from ".."
|
||||
|
||||
export const metadata: ConsoleCommandData = {
|
||||
name: "update",
|
||||
description: "Rebuilds the application from within this process.",
|
||||
usage: false,
|
||||
aliases: [ "reload", "restart", 're' ]
|
||||
}
|
||||
|
||||
export function run(command: string) {
|
||||
try {
|
||||
execSync(command, { stdio: 'inherit' })
|
||||
} catch (err) {
|
||||
//c.error(`Caught exception while rebuilding the project. E:\n${err}`)
|
||||
process.exit(0) // probably a sigint?
|
||||
}
|
||||
}
|
||||
|
||||
export const Main = async (args: Array<string>) => {
|
||||
c.log(`Rebuilding project.`)
|
||||
StrawberryCheesecake.cake.stop()
|
||||
// assuming you have and use npm already
|
||||
run('npm run quick')
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
export var dateAsOfInitialization = new Date()
|
||||
|
||||
import Logger, { defaultLogName } from "./util/Logger";
|
||||
|
||||
import dotenv from 'dotenv'
|
||||
import { Prompt } from "./util/Prompt";
|
||||
import { Cinnamon, CinnamonInit } from "./Cinnamon";
|
||||
import { BakeStrawberryCheesecake } from "./Cheesecake";
|
||||
import { StrawberryFilling } from "./types/Cheesecake";
|
||||
|
||||
|
||||
dotenv.config()
|
||||
export const cd = new Logger("DEBUGGER", 'cyan', `${new Date().toLocaleDateString('en-us').replaceAll('/', '-')}-DEBUG`)
|
||||
const cm = new Logger("CLIENT/index.ts")
|
||||
export var commands: string[] = []
|
||||
|
||||
console.clear();
|
||||
cm.quiet('\n\nNEW CLIENT!')
|
||||
cm.log("Hi!")
|
||||
|
||||
export const StrawberryCheesecake: StrawberryFilling = BakeStrawberryCheesecake()
|
||||
|
||||
// Now that everything is set up, start the bot. This will start the sync loop and run until killed.
|
||||
StrawberryCheesecake.cake.start().then(async () => {
|
||||
cm.log("Cheesecake is to be served! Cake ID is " + await StrawberryCheesecake.cake.getUserId())
|
||||
cm.log(`Logs will be printed at ${defaultLogName}.`)
|
||||
cm.log(`-----------------------------------------------------`)
|
||||
commands = CinnamonInit()
|
||||
cm.log(`Cinnamon reports a command amount of ${commands.length}`)
|
||||
cm.log(`-----------------------------------------------------`)
|
||||
cm.log("Enter \"help\" for a list of console commands.")
|
||||
process.stdout.write(`\x1b]0;MTRXC as ${await StrawberryCheesecake.cake.getUserId()}\x07`);
|
||||
Prompt()
|
||||
});
|
||||
|
||||
// This is the command handler we registered a few lines up
|
||||
export async function handleCommand(roomId: string, event: any) {
|
||||
// Don't handle unhelpful events (ones that aren't text messages, are redacted, or sent by us)
|
||||
if (event['content']?.['msgtype'] !== 'm.text') return;
|
||||
if (event['sender'] === await StrawberryCheesecake.cake.getUserId()) return;
|
||||
|
||||
// Check to ensure that the `!hello` command is being run
|
||||
const UserInput = event['content']['body'];
|
||||
//cm.log("Handle Command")
|
||||
if (UserInput)
|
||||
await Cinnamon(StrawberryCheesecake.cake, roomId, event, UserInput)
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
import { MatrixClient, SimpleFsStorageProvider } from "matrix-bot-sdk";
|
||||
|
||||
export interface StrawberryFilling {
|
||||
accessToken: string,
|
||||
stomach: SimpleFsStorageProvider,
|
||||
cake: MatrixClient
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
import { MatrixClient } from "matrix-bot-sdk"
|
||||
|
||||
export interface ConsoleCommandData {
|
||||
name: string,
|
||||
description: string,
|
||||
usage: string | boolean,
|
||||
aliases?: string[] // should be boolean but makes issues
|
||||
}
|
||||
|
||||
export interface CommandData {
|
||||
name: string,
|
||||
description: string,
|
||||
usage: string | boolean,
|
||||
aliases?: string[], // should be boolean but makes issues
|
||||
execute?: (client: MatrixClient, roomId: string, event: any, userInput: any) => Promise<string>; // the string is its final output!
|
||||
}
|
||||
@@ -0,0 +1,156 @@
|
||||
// from crepesr
|
||||
// logger
|
||||
|
||||
|
||||
import 'colorts/lib/string';
|
||||
import fs from 'fs'
|
||||
|
||||
export enum VerboseLevel {
|
||||
NONE = 0, // No logging except for errors
|
||||
WARNS = 1, // Log warns
|
||||
ALL = 2, // Warns and (useless) debug
|
||||
VERBL = 3, // Warns, debug and verbose
|
||||
VERBH = 4, // Warns, debug, verbose and very verbose (thanks copilot this is so funny)
|
||||
}
|
||||
|
||||
type Color = 'red' | 'green' | 'yellow' | 'blue' | 'magenta' | 'cyan' | 'white' | 'gray' | 'black' | 'italic' | 'bold' | 'underline' | 'strikethrough' | 'inverse' | 'bgRed' | 'bgGreen' | 'bgYellow' | 'bgBlue' | 'bgMagenta' | 'bgCyan' | 'bgWhite' | 'bgBlack' | 'bgGray' | 'bgItalic';
|
||||
|
||||
import { createLogger, transports, format } from 'winston';
|
||||
import { dateAsOfInitialization } from '../index.js';
|
||||
|
||||
export var defaultLogName = `./logs/${new Date().getFullYear()}-${new Date().getMonth() + 1}-${new Date().getDay() + 1}.log`
|
||||
|
||||
export default class Logger {
|
||||
public static VERBOSE_LEVEL: VerboseLevel = 3;
|
||||
private constructorLogFile = ''
|
||||
public logger = createLogger({
|
||||
format: format.combine(
|
||||
format.timestamp(),
|
||||
format.printf(({ }) => ``)
|
||||
),
|
||||
|
||||
transports: [
|
||||
new transports.File({ filename: defaultLogName })
|
||||
]
|
||||
});
|
||||
constructor(public name: string = 'CLIENT', public color: Color = 'blue', public logName: string = `default`) {
|
||||
this.name = name;
|
||||
this.color = color;
|
||||
if (logName === "default") {
|
||||
this.logName = defaultLogName
|
||||
this.constructorLogFile = defaultLogName
|
||||
} else {
|
||||
this.logName = logName
|
||||
this.constructorLogFile = logName
|
||||
this.logger.destroy()
|
||||
this.logger = createLogger({
|
||||
format: format.combine(
|
||||
format.timestamp(),
|
||||
format.printf(({ }) => ``)
|
||||
),
|
||||
|
||||
transports: [
|
||||
new transports.File({ filename: `./logs/${this.constructorLogFile}` })
|
||||
]
|
||||
});
|
||||
this.raw(`New ctm logger logging at ${(this.logger.transports as any)[0].filename}`)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public getDate(): string {
|
||||
return new Date().toLocaleTimeString();
|
||||
}
|
||||
|
||||
// clears log file, not stdout!!
|
||||
public clear() {
|
||||
fs.truncateSync(defaultLogName, 0)
|
||||
}
|
||||
|
||||
private raw(...args: string[]) {
|
||||
// @ts-ignore - Element implicitly has an 'any' type because index expression is not of type 'number'
|
||||
console.log(`[${this.getDate().white.bold}] <${this.name[this.color].bold}>`, ...args);
|
||||
}
|
||||
|
||||
public quiet(...args: string[]) {
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] <${this.name}> ${message}`;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
}
|
||||
|
||||
public plain(...args: string[]) {
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `${message}`;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
console.log(...args)
|
||||
}
|
||||
|
||||
public log(...args: string[]) {
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] <${this.name}> ${message}`;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
this.raw(...args);
|
||||
}
|
||||
|
||||
public trail(...args: any[]) {
|
||||
var returnValue = `\t↳ ${args.join(' ').gray}`
|
||||
console.log(returnValue);
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
//@ts-ignore
|
||||
return returnValue;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
}
|
||||
|
||||
public error(e: Error | string, stack: boolean = true) {
|
||||
if (typeof e === 'string') e = new Error(e);
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] ERROR<${this.name}> ${message}`;
|
||||
});
|
||||
this.logger.error(e)
|
||||
console.log(`[${this.getDate().white.bold}] ${`ERROR<${this.name}>`.bgRed.bold}`, e.message);
|
||||
if (e.stack && stack) this.trail(e.stack);
|
||||
}
|
||||
|
||||
public warn(...args: string[]) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.WARNS) return;
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] <${this.name}> ${message}`;
|
||||
});
|
||||
this.logger.warn(...args as [string, ...string[]])
|
||||
console.log(`[${this.getDate().white.bold}] ${`WARN<${this.name}>`.bgYellow.bold}`, ...args);
|
||||
}
|
||||
|
||||
public debug(...args: any) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.ALL) return;
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] ${`DEBUG<${this.name}>`} ${message}`;
|
||||
});
|
||||
this.logger.debug(...args as [string, ...string[]])
|
||||
console.log(`[${this.getDate().white.bold}] ${`DEBUG<${this.name}>`.bgBlue.bold}`, ...args);
|
||||
this.trail(new Error().stack!.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
|
||||
public verbL(...args: any) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.VERBL) return;
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] ${`VERBL<${this.name}>`} ${message}`;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
console.log(`[${this.getDate().white.bold}] ${`VERBL<${this.name}>`.bgCyan.bold}`, ...args);
|
||||
this.trail(new Error().stack!.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
|
||||
public verbH(...args: any) {
|
||||
if (Logger.VERBOSE_LEVEL < VerboseLevel.VERBH) return;
|
||||
this.logger.format = format.printf(({ message }) => {
|
||||
return `[${this.getDate()}] ${`VERBH<${this.name}>`} ${message}`;
|
||||
});
|
||||
this.logger.info(...args as [string, ...string[]])
|
||||
console.log(`[${this.getDate().white.bold}] ${`VERBH<${this.name}>`.bgCyan.bold}`, ...args);
|
||||
this.trail(new Error().stack!.split('\n').slice(2).join('\n'));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,145 @@
|
||||
// import from jtw 🤤
|
||||
// all log comments here r for debug dont remove
|
||||
|
||||
|
||||
import readline from 'readline'
|
||||
import Logger from './Logger'
|
||||
import { ConsoleCommandData } from '../types/Command'
|
||||
import fs from 'fs'
|
||||
|
||||
var c = new Logger("COMMAND", "yellow")
|
||||
|
||||
const rl = readline.createInterface({
|
||||
input: process.stdin as unknown as NodeJS.ReadableStream,
|
||||
output: process.stdout as unknown as NodeJS.WritableStream
|
||||
})
|
||||
|
||||
const originalWrite = process.stdout.write.bind(process.stdout)
|
||||
let inWritePatch = false
|
||||
|
||||
process.stdout.write = (chunk: any, encoding?: any, cb?: any) => {
|
||||
if (inWritePatch) {
|
||||
// Don't recurse
|
||||
return originalWrite(chunk, encoding, cb)
|
||||
}
|
||||
|
||||
inWritePatch = true
|
||||
|
||||
try {
|
||||
readline.clearLine(process.stdout as unknown as NodeJS.WritableStream, 0)
|
||||
readline.cursorTo(process.stdout as unknown as NodeJS.WritableStream, 0)
|
||||
|
||||
const result = originalWrite(chunk, encoding, cb)
|
||||
|
||||
rl.prompt(true)
|
||||
return result
|
||||
} finally {
|
||||
inWritePatch = false
|
||||
}
|
||||
}
|
||||
|
||||
// helper
|
||||
export function splitStr(q: string): Array<string> {
|
||||
return q.split(" ")
|
||||
}
|
||||
|
||||
// clears last printed line
|
||||
// right now this just prints another line...
|
||||
export function removeLine() {
|
||||
readline.moveCursor(process.stdout as unknown as NodeJS.WritableStream, 0, -1)
|
||||
readline.clearLine(process.stdout as unknown as NodeJS.WritableStream, 1)
|
||||
}
|
||||
|
||||
// repeat
|
||||
export function Prompt() {
|
||||
rl.prompt()
|
||||
|
||||
rl.once("line", async (cmd) => {
|
||||
if (!cmd.trim()) {
|
||||
Prompt()
|
||||
} else {
|
||||
await HandlePrompt(splitStr(cmd.trim()))
|
||||
Prompt()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
export const Clear: string = "$clear"
|
||||
export var CommandAliases: ConsoleCommandData[] = []
|
||||
export var CommandFiles: string[] = []
|
||||
export var AllFilesProcessed: boolean = false
|
||||
export var AllAliasesProcessed: boolean = false
|
||||
|
||||
export async function HandlePrompt(args: Array<string>) {
|
||||
let inputName = args[0].toLowerCase()
|
||||
let cmdArgs: Array<string> = args.slice(1)
|
||||
let error = false
|
||||
c.log(`${process.cwd()}`)
|
||||
try {
|
||||
let cs = new Logger(`CLIENT/${inputName}.js+resp`)
|
||||
c.log(`${inputName} ${cmdArgs.join(' ')}`)
|
||||
const directoryPath = process.cwd() + '/output/src/console_commands'; // Replace with your directory path
|
||||
|
||||
try {
|
||||
const files = fs.readdirSync(directoryPath, 'utf-8');
|
||||
//c.log(`HI ${files[0]}`)
|
||||
if (!AllFilesProcessed)
|
||||
for (let i = 0; i < files.length; i++) {
|
||||
var file = files[i]
|
||||
let check = true
|
||||
for (var file2 in CommandFiles)
|
||||
if (file2.includes(file))
|
||||
check = false
|
||||
|
||||
if (!file.includes('.map') && check) {
|
||||
//c.log(file)
|
||||
CommandFiles.push(file.replace(".ts", ".js"))
|
||||
//c.log(`${file}`)
|
||||
}
|
||||
}
|
||||
AllFilesProcessed = true
|
||||
//c.log(CommandFiles.length.toString() + " CommandFile")
|
||||
|
||||
} catch (err) {
|
||||
console.error('Error reading directory:', err);
|
||||
}
|
||||
if (!AllAliasesProcessed)
|
||||
for (let i = 0; i < CommandFiles.length; i++) {
|
||||
var CommandFile = CommandFiles[i]
|
||||
const file: ConsoleCommandData = require(`${process.cwd()}/output/src/console_commands/${CommandFile}`).metadata
|
||||
//c.log(file.name)
|
||||
if (file.aliases)
|
||||
CommandAliases.push(file)
|
||||
AllAliasesProcessed = true
|
||||
}
|
||||
for (let i = 0; i < CommandAliases.length; i++) {
|
||||
const cmd = CommandAliases[i];
|
||||
|
||||
if (cmd.aliases) {
|
||||
//c.log('checked aaa')
|
||||
for (let i = 0; i < cmd.aliases.length; i++) {
|
||||
var alias = cmd.aliases[i]
|
||||
//c.log(alias)
|
||||
if (alias.includes(inputName))
|
||||
inputName = cmd.name
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//c.log(CommandAliases.length.toString() + " Alias")
|
||||
let response = await require(`${process.cwd()}/output/src/console_commands/${inputName}.js`).Main(cmdArgs)
|
||||
|
||||
if (response === Clear)
|
||||
console.clear()
|
||||
else if (response == 0 || response == 1)
|
||||
"" // do nothing, an error occured.
|
||||
else
|
||||
cs.log(response)
|
||||
} catch (err) {
|
||||
//@ts-ignore
|
||||
if (err.toString().includes("Cannot find module"))
|
||||
c.log(`Command ${inputName} not found.`)
|
||||
else
|
||||
c.error(`${err}`)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"target": "esnext",
|
||||
"module": "NodeNext",
|
||||
"sourceMap": true,
|
||||
"experimentalDecorators": true,
|
||||
"rootDir": "./",
|
||||
"outDir": "output",
|
||||
"strict": true,
|
||||
"moduleResolution":"nodenext",
|
||||
"noImplicitAny": true,
|
||||
"esModuleInterop": true,
|
||||
"noImplicitThis": false,
|
||||
"resolveJsonModule":true,
|
||||
"strictNullChecks":false,
|
||||
"noImplicitReturns":false,
|
||||
"skipLibCheck": true
|
||||
},
|
||||
"exclude": ["node_modules"]
|
||||
}
|
||||
Reference in New Issue
Block a user