hackmud-script-manager 0.19.0-fa82f73 → 0.19.1-003b022

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/pull.js CHANGED
@@ -1 +1,11 @@
1
- import{copyFilePersistent as t}from"@samual/lib/copyFilePersistent";import{resolve as r}from"path";const pull=async(s,a,i)=>{const[o,e]=i.split(".");if(!o||!e)throw new Error('`script` argument must be in "user.name" format');await t(r(a,o,"scripts",`${e}.js`),r(s,o,`${e}.js`))};export{pull as default,pull};
1
+ import { copyFilePersistent } from "@samual/lib/copyFilePersistent"
2
+ import { resolve } from "path"
3
+ const pull = async (sourceFolderPath, hackmudPath, script) => {
4
+ const [user, name] = script.split(".")
5
+ if (!user || !name) throw Error('`script` argument must be in "user.name" format')
6
+ await copyFilePersistent(
7
+ resolve(hackmudPath, user, "scripts", name + ".js"),
8
+ resolve(sourceFolderPath, user, name + ".js")
9
+ )
10
+ }
11
+ export { pull as default, pull }
package/push.js CHANGED
@@ -1 +1,269 @@
1
- import{DynamicMap as e}from"@samual/lib/DynamicMap";import{countHackmudCharacters as t}from"@samual/lib/countHackmudCharacters";import{writeFilePersistent as r}from"@samual/lib/writeFilePersistent";import{readdir as i,readFile as a}from"fs/promises";import{resolve as s,extname as o,basename as n}from"path";import{supportedExtensions as p}from"./constants.js";import{processScript as m}from"./processScript/index.js";import"@babel/generator";import"@babel/parser";import"@babel/plugin-proposal-decorators";import"@babel/plugin-proposal-destructuring-private";import"@babel/plugin-proposal-explicit-resource-management";import"@babel/plugin-transform-class-properties";import"@babel/plugin-transform-class-static-block";import"@babel/plugin-transform-exponentiation-operator";import"@babel/plugin-transform-json-strings";import"@babel/plugin-transform-logical-assignment-operators";import"@babel/plugin-transform-nullish-coalescing-operator";import"@babel/plugin-transform-numeric-separator";import"@babel/plugin-transform-object-rest-spread";import"@babel/plugin-transform-optional-catch-binding";import"@babel/plugin-transform-optional-chaining";import"@babel/plugin-transform-private-property-in-object";import"@babel/plugin-transform-unicode-sets-regex";import"@babel/traverse";import"@babel/types";import"@rollup/plugin-babel";import"@rollup/plugin-commonjs";import"@rollup/plugin-json";import"@rollup/plugin-node-resolve";import"@samual/lib/assert";import"prettier";import"rollup";import"./processScript/minify.js";import"@samual/lib/spliceString";import"acorn";import"terser";import"./processScript/shared.js";import"./processScript/postprocess.js";import"./processScript/preprocess.js";import"import-meta-resolve";import"./processScript/transform.js";import"@samual/lib/clearObject";const push=async(l,c,{scripts:f=["*.*"],onPush:u=(()=>{}),minify:g=!0,mangleNames:b=!1,forceQuineCheats:d}={})=>{const h=new e((e=>new Set)),w=new Set,$=new Set;let y=!1;for(const e of f){const[t,r]=e.split(".");t&&"*"!=t?r&&"*"!=r?h.get(t).add(r):w.add(t):r&&"*"!=r?$.add(r):y=!0}const S=new e((e=>new Set)),P=[],j=new e((e=>new Set));let N;if($.size||y){const e=await i(s(c),{withFileTypes:!0}),t=new Set([...(N=await i(s(l),{withFileTypes:!0})).filter((e=>e.isDirectory())).map((e=>e.name)),...e.filter((e=>e.isDirectory())).map((e=>e.name)),...e.filter((e=>e.isFile()&&e.name.endsWith(".key"))).map((e=>e.name.slice(0,-4))),...h.keys(),...w]);if(y)for(const e of t)w.add(e);else for(const e of t){const t=h.get(e);for(const e of $)t.add(e)}}return await Promise.all([...w].map((async e=>{await i(s(l,e),{withFileTypes:!0}).then((async i=>{await Promise.all(i.map((async i=>{if(i.name.endsWith(".d.ts"))return;const f=o(i.name);if(i.isFile()&&p.includes(f)){const o=n(i.name,f),p=s(l,e,i.name),{script:h}=await m(await a(p,{encoding:"utf-8"}),{minify:g,scriptUser:e,scriptName:o,filePath:p,mangleNames:b,forceQuineCheats:d}),w={file:`${e}/${i.name}`,users:[e],minLength:t(h),error:void 0};j.get(e).add(o),P.push(w),await r(s(c,e,`scripts/${o}.js`),h),u(w)}})))}),(e=>{if("ENOENT"!=e.code)throw e}))}))),await Promise.all([...h].map((async([e,i])=>{w.has(e)||await Promise.all([...i].map((async i=>{let o,n,f;for(const t of p)try{n=`${i}${t}`,o=await a(f=s(l,e,n),{encoding:"utf-8"});break}catch{}if(o){const{script:a}=await m(o,{minify:g,scriptUser:e,scriptName:i,filePath:f,mangleNames:b,forceQuineCheats:d}),p={file:`${e}/${n}`,users:[e],minLength:t(a),error:void 0};P.push(p),await r(s(c,e,"scripts",`${i}.js`),a),u(p)}else S.get(i).add(e)})))}))),await(w.size?Promise.all((N||await i(s(l),{withFileTypes:!0})).map((async e=>{if(e.name.endsWith(".d.ts"))return;const i=o(e.name);if(!e.isFile()||!p.includes(i))return;const f=n(e.name,i),h=[...w,...S.get(f)].filter((e=>!j.get(e).has(f)));if(!h.length)return;const $=Math.floor(Math.random()*2**52).toString(36).padStart(11,"0"),y=s(l,e.name),{script:N}=await m(await a(y,{encoding:"utf-8"}),{minify:g,scriptUser:!0,scriptName:f,uniqueID:$,filePath:y,mangleNames:b,forceQuineCheats:d}),C={file:e.name,users:h,minLength:t(N),error:void 0};await Promise.all(h.map((e=>r(s(c,e,`scripts/${f}.js`),N.replace(new RegExp(`\\$${$}\\$SCRIPT_USER\\$`,"g"),e).replace(new RegExp(`\\$${$}\\$FULL_SCRIPT_NAME\\$`,"g"),`${e}.${f}`))))),P.push(C),u(C)}))):Promise.all([...S].map((async([e,i])=>{let o,n,f;for(const t of p)try{n=`${e}${t}`,o=await a(f=s(l,n),{encoding:"utf-8"});break}catch{}if(o){const a=Math.floor(Math.random()*2**52).toString(36).padStart(11,"0"),{script:p}=await m(o,{minify:g,scriptUser:!0,scriptName:e,uniqueID:a,filePath:f,mangleNames:b,forceQuineCheats:d}),l={file:n,users:[...i],minLength:t(p),error:void 0};await Promise.all([...i].map((t=>r(s(c,t,`scripts/${e}.js`),p.replace(new RegExp(`\\$${a}\\$SCRIPT_USER\\$`,"g"),t).replace(new RegExp(`\\$${a}\\$FULL_SCRIPT_NAME\\$`,"g"),`${t}.${e}`))))),P.push(l),u(l)}})))),P};export{push as default,push};
1
+ import { Cache } from "@samual/lib/Cache"
2
+ import { countHackmudCharacters } from "@samual/lib/countHackmudCharacters"
3
+ import { readDirectoryWithStats } from "@samual/lib/readDirectoryWithStats"
4
+ import { writeFilePersistent } from "@samual/lib/writeFilePersistent"
5
+ import { readFile } from "fs/promises"
6
+ import { basename, resolve, extname } from "path"
7
+ import { supportedExtensions } from "./constants.js"
8
+ import { processScript } from "./processScript/index.js"
9
+ import "@babel/generator"
10
+ import "@babel/parser"
11
+ import "@babel/plugin-proposal-decorators"
12
+ import "@babel/plugin-proposal-destructuring-private"
13
+ import "@babel/plugin-proposal-explicit-resource-management"
14
+ import "@babel/plugin-transform-class-properties"
15
+ import "@babel/plugin-transform-class-static-block"
16
+ import "@babel/plugin-transform-exponentiation-operator"
17
+ import "@babel/plugin-transform-json-strings"
18
+ import "@babel/plugin-transform-logical-assignment-operators"
19
+ import "@babel/plugin-transform-nullish-coalescing-operator"
20
+ import "@babel/plugin-transform-numeric-separator"
21
+ import "@babel/plugin-transform-object-rest-spread"
22
+ import "@babel/plugin-transform-optional-catch-binding"
23
+ import "@babel/plugin-transform-optional-chaining"
24
+ import "@babel/plugin-transform-private-property-in-object"
25
+ import "@babel/plugin-transform-unicode-sets-regex"
26
+ import "@babel/traverse"
27
+ import "@babel/types"
28
+ import "@rollup/plugin-babel"
29
+ import "@rollup/plugin-commonjs"
30
+ import "@rollup/plugin-json"
31
+ import "@rollup/plugin-node-resolve"
32
+ import "@samual/lib/assert"
33
+ import "prettier"
34
+ import "rollup"
35
+ import "./processScript/minify.js"
36
+ import "@samual/lib/spliceString"
37
+ import "acorn"
38
+ import "terser"
39
+ import "./processScript/shared.js"
40
+ import "./processScript/postprocess.js"
41
+ import "./processScript/preprocess.js"
42
+ import "import-meta-resolve"
43
+ import "./processScript/transform.js"
44
+ import "@samual/lib/clearObject"
45
+ const push = async (
46
+ sourceDirectory,
47
+ hackmudDirectory,
48
+ { scripts = ["*.*"], onPush = () => {}, minify = !0, mangleNames = !1, forceQuineCheats } = {}
49
+ ) => {
50
+ const scriptNamesByUser = new Cache(_user => new Set()),
51
+ wildScriptUsers = new Set(),
52
+ wildUserScripts = new Set()
53
+ let pushEverything = !1
54
+ for (const fullScriptName of scripts) {
55
+ const [user, scriptName] = fullScriptName.split(".")
56
+ user && "*" != user ?
57
+ scriptName && "*" != scriptName ?
58
+ scriptNamesByUser.get(user).add(scriptName)
59
+ : wildScriptUsers.add(user)
60
+ : scriptName && "*" != scriptName ? wildUserScripts.add(scriptName)
61
+ : (pushEverything = !0)
62
+ }
63
+ const usersByGlobalScriptsToPush = new Cache(_user => new Set()),
64
+ allInfo = [],
65
+ scriptNamesAlreadyPushedByUser = new Cache(_user => new Set())
66
+ let sourceDirectoryDirents
67
+ if (wildUserScripts.size || pushEverything) {
68
+ let hackmudDirectoryEntries
69
+ ;[hackmudDirectoryEntries, sourceDirectoryDirents] = await Promise.all([
70
+ readDirectoryWithStats(hackmudDirectory),
71
+ readDirectoryWithStats(sourceDirectory)
72
+ ])
73
+ const allUsers = new Set([
74
+ ...sourceDirectoryDirents.filter(({ stats }) => stats.isDirectory()).map(({ path }) => basename(path)),
75
+ ...hackmudDirectoryEntries.filter(({ stats }) => stats.isDirectory()).map(({ name }) => name),
76
+ ...hackmudDirectoryEntries
77
+ .filter(({ name, stats }) => stats.isFile() && name.endsWith(".key"))
78
+ .map(({ name }) => name.slice(0, -4)),
79
+ ...scriptNamesByUser.keys(),
80
+ ...wildScriptUsers
81
+ ])
82
+ if (pushEverything) for (const user of allUsers) wildScriptUsers.add(user)
83
+ else
84
+ for (const user of allUsers) {
85
+ const scriptNames = scriptNamesByUser.get(user)
86
+ for (const scriptName of wildUserScripts) scriptNames.add(scriptName)
87
+ }
88
+ }
89
+ await Promise.all(
90
+ [...wildScriptUsers].map(async user => {
91
+ await readDirectoryWithStats(resolve(sourceDirectory, user)).then(
92
+ async entries => {
93
+ await Promise.all(
94
+ entries.map(async ({ stats, name, path }) => {
95
+ if (name.endsWith(".d.ts")) return
96
+ const extension = extname(name)
97
+ if (stats.isFile() && supportedExtensions.includes(extension)) {
98
+ const scriptName = basename(name, extension),
99
+ { script: minifiedCode } = await processScript(
100
+ await readFile(path, { encoding: "utf-8" }),
101
+ {
102
+ minify,
103
+ scriptUser: user,
104
+ scriptName,
105
+ filePath: path,
106
+ mangleNames,
107
+ forceQuineCheats
108
+ }
109
+ ),
110
+ info = {
111
+ file: `${user}/${name}`,
112
+ users: [user],
113
+ minLength: countHackmudCharacters(minifiedCode),
114
+ error: void 0
115
+ }
116
+ scriptNamesAlreadyPushedByUser.get(user).add(scriptName)
117
+ allInfo.push(info)
118
+ await writeFilePersistent(
119
+ resolve(hackmudDirectory, user, `scripts/${scriptName}.js`),
120
+ minifiedCode
121
+ )
122
+ onPush(info)
123
+ }
124
+ })
125
+ )
126
+ },
127
+ error => {
128
+ if ("ENOENT" != error.code) throw error
129
+ }
130
+ )
131
+ })
132
+ )
133
+ await Promise.all(
134
+ [...scriptNamesByUser].map(async ([user, scripts]) => {
135
+ wildScriptUsers.has(user) ||
136
+ (await Promise.all(
137
+ [...scripts].map(async scriptName => {
138
+ let code, fileName, filePath
139
+ for (const extension of supportedExtensions)
140
+ try {
141
+ fileName = `${scriptName}${extension}`
142
+ code = await readFile((filePath = resolve(sourceDirectory, user, fileName)), {
143
+ encoding: "utf-8"
144
+ })
145
+ break
146
+ } catch {}
147
+ if (code) {
148
+ const { script: minifiedCode } = await processScript(code, {
149
+ minify,
150
+ scriptUser: user,
151
+ scriptName,
152
+ filePath,
153
+ mangleNames,
154
+ forceQuineCheats
155
+ }),
156
+ info = {
157
+ file: `${user}/${fileName}`,
158
+ users: [user],
159
+ minLength: countHackmudCharacters(minifiedCode),
160
+ error: void 0
161
+ }
162
+ allInfo.push(info)
163
+ await writeFilePersistent(
164
+ resolve(hackmudDirectory, user, "scripts", scriptName + ".js"),
165
+ minifiedCode
166
+ )
167
+ onPush(info)
168
+ } else usersByGlobalScriptsToPush.get(scriptName).add(user)
169
+ })
170
+ ))
171
+ })
172
+ )
173
+ await (wildScriptUsers.size ?
174
+ Promise.all(
175
+ (sourceDirectoryDirents || (await readDirectoryWithStats(sourceDirectory))).map(
176
+ async ({ path, stats, name }) => {
177
+ if (name.endsWith(".d.ts")) return
178
+ const extension = extname(name)
179
+ if (!stats.isFile() || !supportedExtensions.includes(extension)) return
180
+ const scriptName = basename(name, extension),
181
+ usersToPushTo = [...wildScriptUsers, ...usersByGlobalScriptsToPush.get(scriptName)].filter(
182
+ user => !scriptNamesAlreadyPushedByUser.get(user).has(scriptName)
183
+ )
184
+ if (!usersToPushTo.length) return
185
+ const uniqueID = Math.floor(Math.random() * 2 ** 52)
186
+ .toString(36)
187
+ .padStart(11, "0"),
188
+ { script: minifiedCode } = await processScript(await readFile(path, { encoding: "utf-8" }), {
189
+ minify,
190
+ scriptUser: !0,
191
+ scriptName,
192
+ uniqueID,
193
+ filePath: path,
194
+ mangleNames,
195
+ forceQuineCheats
196
+ }),
197
+ info = {
198
+ file: name,
199
+ users: usersToPushTo,
200
+ minLength: countHackmudCharacters(minifiedCode),
201
+ error: void 0
202
+ }
203
+ await Promise.all(
204
+ usersToPushTo.map(user =>
205
+ writeFilePersistent(
206
+ resolve(hackmudDirectory, user, `scripts/${scriptName}.js`),
207
+ minifiedCode
208
+ .replace(RegExp(`\\$${uniqueID}\\$SCRIPT_USER\\$`, "g"), user)
209
+ .replace(
210
+ RegExp(`\\$${uniqueID}\\$FULL_SCRIPT_NAME\\$`, "g"),
211
+ `${user}.${scriptName}`
212
+ )
213
+ )
214
+ )
215
+ )
216
+ allInfo.push(info)
217
+ onPush(info)
218
+ }
219
+ )
220
+ )
221
+ : Promise.all(
222
+ [...usersByGlobalScriptsToPush].map(async ([scriptName, users]) => {
223
+ let code, fileName, filePath
224
+ for (const extension of supportedExtensions)
225
+ try {
226
+ fileName = `${scriptName}${extension}`
227
+ code = await readFile((filePath = resolve(sourceDirectory, fileName)), { encoding: "utf-8" })
228
+ break
229
+ } catch {}
230
+ if (code) {
231
+ const uniqueID = Math.floor(Math.random() * 2 ** 52)
232
+ .toString(36)
233
+ .padStart(11, "0"),
234
+ { script: minifiedCode } = await processScript(code, {
235
+ minify,
236
+ scriptUser: !0,
237
+ scriptName,
238
+ uniqueID,
239
+ filePath,
240
+ mangleNames,
241
+ forceQuineCheats
242
+ }),
243
+ info = {
244
+ file: fileName,
245
+ users: [...users],
246
+ minLength: countHackmudCharacters(minifiedCode),
247
+ error: void 0
248
+ }
249
+ await Promise.all(
250
+ [...users].map(user =>
251
+ writeFilePersistent(
252
+ resolve(hackmudDirectory, user, `scripts/${scriptName}.js`),
253
+ minifiedCode
254
+ .replace(RegExp(`\\$${uniqueID}\\$SCRIPT_USER\\$`, "g"), user)
255
+ .replace(
256
+ RegExp(`\\$${uniqueID}\\$FULL_SCRIPT_NAME\\$`, "g"),
257
+ `${user}.${scriptName}`
258
+ )
259
+ )
260
+ )
261
+ )
262
+ allInfo.push(info)
263
+ onPush(info)
264
+ }
265
+ })
266
+ ))
267
+ return allInfo
268
+ }
269
+ export { push as default, push }
package/syncMacros.js CHANGED
@@ -1 +1,43 @@
1
- import{readdir as e,readFile as t,stat as a,writeFile as s}from"fs/promises";import{extname as o,basename as n,resolve as r}from"path";const syncMacros=async c=>{const m=await e(c,{withFileTypes:!0}),i=new Map,l=[];await Promise.all(m.map((async e=>{if(e.isFile())switch(o(e.name)){case".macros":{const[s,o]=await Promise.all([t(r(c,e.name),{encoding:"utf-8"}).then((e=>e.split("\n"))),a(r(c,e.name)).then((({mtime:e})=>e))]);for(let e=0;e<s.length/2-1;e++){const t=s[2*e],a=i.get(t);(!a||o>a.date)&&i.set(t,{date:o,macro:s[2*e+1]})}}break;case".key":l.push(n(e.name,".key"))}})));let f="",p=0;for(const[e,{macro:t}]of[...i].sort((([e],[t])=>(e>t)-(e<t))))t[0]==t[0].toLowerCase()&&(f+=`${e}\n${t}\n`,p++);for(const e of l)s(r(c,`${e}.macros`),f);return{macrosSynced:p,usersSynced:l.length}};export{syncMacros as default,syncMacros};
1
+ import { readDirectoryWithStats } from "@samual/lib/readDirectoryWithStats"
2
+ import { readFile, stat, writeFile } from "fs/promises"
3
+ import { extname, basename, resolve } from "path"
4
+ const syncMacros = async hackmudPath => {
5
+ const files = await readDirectoryWithStats(hackmudPath),
6
+ macros = new Map(),
7
+ users = []
8
+ await Promise.all(
9
+ files.map(async file => {
10
+ if (file.stats.isFile())
11
+ switch (extname(file.name)) {
12
+ case ".macros":
13
+ {
14
+ const [lines, date] = await Promise.all([
15
+ readFile(resolve(hackmudPath, file.name), { encoding: "utf-8" }).then(file =>
16
+ file.split("\n")
17
+ ),
18
+ stat(resolve(hackmudPath, file.name)).then(({ mtime }) => mtime)
19
+ ])
20
+ for (let index = 0; index < lines.length / 2 - 1; index++) {
21
+ const macroName = lines[2 * index],
22
+ currentMacro = macros.get(macroName)
23
+ ;(!currentMacro || date > currentMacro.date) &&
24
+ macros.set(macroName, { date, macro: lines[2 * index + 1] })
25
+ }
26
+ }
27
+ break
28
+ case ".key":
29
+ users.push(basename(file.name, ".key"))
30
+ }
31
+ })
32
+ )
33
+ let macroFile = "",
34
+ macrosSynced = 0
35
+ for (const [name, { macro }] of [...macros].sort(([a], [b]) => (a > b) - (a < b)))
36
+ if (macro[0] == macro[0].toLowerCase()) {
37
+ macroFile += `${name}\n${macro}\n`
38
+ macrosSynced++
39
+ }
40
+ for (const user of users) writeFile(resolve(hackmudPath, user + ".macros"), macroFile)
41
+ return { macrosSynced, usersSynced: users.length }
42
+ }
43
+ export { syncMacros as default, syncMacros }