rpgmaker-mz-mcp 1.0.0
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/LICENSE +21 -0
- package/README.md +425 -0
- package/dist/events/commandBuilders.d.ts +405 -0
- package/dist/events/commandBuilders.d.ts.map +1 -0
- package/dist/events/commandBuilders.js +554 -0
- package/dist/events/commandBuilders.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +105 -0
- package/dist/index.js.map +1 -0
- package/dist/registry.d.ts +81 -0
- package/dist/registry.d.ts.map +1 -0
- package/dist/registry.js +49 -0
- package/dist/registry.js.map +1 -0
- package/dist/tiles/autotile.d.ts +65 -0
- package/dist/tiles/autotile.d.ts.map +1 -0
- package/dist/tiles/autotile.js +201 -0
- package/dist/tiles/autotile.js.map +1 -0
- package/dist/tiles/catalog/dungeon.d.ts +16 -0
- package/dist/tiles/catalog/dungeon.d.ts.map +1 -0
- package/dist/tiles/catalog/dungeon.js +765 -0
- package/dist/tiles/catalog/dungeon.js.map +1 -0
- package/dist/tiles/catalog/index.d.ts +78 -0
- package/dist/tiles/catalog/index.d.ts.map +1 -0
- package/dist/tiles/catalog/index.js +115 -0
- package/dist/tiles/catalog/index.js.map +1 -0
- package/dist/tiles/catalog/inside.d.ts +16 -0
- package/dist/tiles/catalog/inside.d.ts.map +1 -0
- package/dist/tiles/catalog/inside.js +765 -0
- package/dist/tiles/catalog/inside.js.map +1 -0
- package/dist/tiles/catalog/outside.d.ts +16 -0
- package/dist/tiles/catalog/outside.d.ts.map +1 -0
- package/dist/tiles/catalog/outside.js +799 -0
- package/dist/tiles/catalog/outside.js.map +1 -0
- package/dist/tiles/catalog/overworld.d.ts +16 -0
- package/dist/tiles/catalog/overworld.d.ts.map +1 -0
- package/dist/tiles/catalog/overworld.js +585 -0
- package/dist/tiles/catalog/overworld.js.map +1 -0
- package/dist/tiles/catalog/sf.d.ts +16 -0
- package/dist/tiles/catalog/sf.d.ts.map +1 -0
- package/dist/tiles/catalog/sf.js +1313 -0
- package/dist/tiles/catalog/sf.js.map +1 -0
- package/dist/tiles/paint.d.ts +20 -0
- package/dist/tiles/paint.d.ts.map +1 -0
- package/dist/tiles/paint.js +65 -0
- package/dist/tiles/paint.js.map +1 -0
- package/dist/tiles/png.d.ts +11 -0
- package/dist/tiles/png.d.ts.map +1 -0
- package/dist/tiles/png.js +180 -0
- package/dist/tiles/png.js.map +1 -0
- package/dist/tiles/tileCodec.d.ts +95 -0
- package/dist/tiles/tileCodec.d.ts.map +1 -0
- package/dist/tiles/tileCodec.js +186 -0
- package/dist/tiles/tileCodec.js.map +1 -0
- package/dist/tiles/tileFlags.d.ts +98 -0
- package/dist/tiles/tileFlags.d.ts.map +1 -0
- package/dist/tiles/tileFlags.js +129 -0
- package/dist/tiles/tileFlags.js.map +1 -0
- package/dist/tiles/tilegeom.d.ts +29 -0
- package/dist/tiles/tilegeom.d.ts.map +1 -0
- package/dist/tiles/tilegeom.js +111 -0
- package/dist/tiles/tilegeom.js.map +1 -0
- package/dist/tiles/transparency.d.ts +22 -0
- package/dist/tiles/transparency.d.ts.map +1 -0
- package/dist/tiles/transparency.js +59 -0
- package/dist/tiles/transparency.js.map +1 -0
- package/dist/tools/actorTools.d.ts +48 -0
- package/dist/tools/actorTools.d.ts.map +1 -0
- package/dist/tools/actorTools.js +154 -0
- package/dist/tools/actorTools.js.map +1 -0
- package/dist/tools/allTools.d.ts +8 -0
- package/dist/tools/allTools.d.ts.map +1 -0
- package/dist/tools/allTools.js +56 -0
- package/dist/tools/allTools.js.map +1 -0
- package/dist/tools/assetTools.d.ts +113 -0
- package/dist/tools/assetTools.d.ts.map +1 -0
- package/dist/tools/assetTools.js +97 -0
- package/dist/tools/assetTools.js.map +1 -0
- package/dist/tools/batchTools.d.ts +3 -0
- package/dist/tools/batchTools.d.ts.map +1 -0
- package/dist/tools/batchTools.js +138 -0
- package/dist/tools/batchTools.js.map +1 -0
- package/dist/tools/battleTools.d.ts +72 -0
- package/dist/tools/battleTools.d.ts.map +1 -0
- package/dist/tools/battleTools.js +322 -0
- package/dist/tools/battleTools.js.map +1 -0
- package/dist/tools/catalogTools.d.ts +3 -0
- package/dist/tools/catalogTools.d.ts.map +1 -0
- package/dist/tools/catalogTools.js +134 -0
- package/dist/tools/catalogTools.js.map +1 -0
- package/dist/tools/classTools.d.ts +85 -0
- package/dist/tools/classTools.d.ts.map +1 -0
- package/dist/tools/classTools.js +279 -0
- package/dist/tools/classTools.js.map +1 -0
- package/dist/tools/commonEventTools.d.ts +32 -0
- package/dist/tools/commonEventTools.d.ts.map +1 -0
- package/dist/tools/commonEventTools.js +150 -0
- package/dist/tools/commonEventTools.js.map +1 -0
- package/dist/tools/eventCommandTools.d.ts +37 -0
- package/dist/tools/eventCommandTools.d.ts.map +1 -0
- package/dist/tools/eventCommandTools.js +893 -0
- package/dist/tools/eventCommandTools.js.map +1 -0
- package/dist/tools/eventPageTools.d.ts +112 -0
- package/dist/tools/eventPageTools.d.ts.map +1 -0
- package/dist/tools/eventPageTools.js +597 -0
- package/dist/tools/eventPageTools.js.map +1 -0
- package/dist/tools/itemTools.d.ts +82 -0
- package/dist/tools/itemTools.d.ts.map +1 -0
- package/dist/tools/itemTools.js +380 -0
- package/dist/tools/itemTools.js.map +1 -0
- package/dist/tools/listTools.d.ts +58 -0
- package/dist/tools/listTools.d.ts.map +1 -0
- package/dist/tools/listTools.js +99 -0
- package/dist/tools/listTools.js.map +1 -0
- package/dist/tools/mapTools.d.ts +270 -0
- package/dist/tools/mapTools.d.ts.map +1 -0
- package/dist/tools/mapTools.js +1066 -0
- package/dist/tools/mapTools.js.map +1 -0
- package/dist/tools/moveTools.d.ts +43 -0
- package/dist/tools/moveTools.d.ts.map +1 -0
- package/dist/tools/moveTools.js +240 -0
- package/dist/tools/moveTools.js.map +1 -0
- package/dist/tools/objectTools.d.ts +12 -0
- package/dist/tools/objectTools.d.ts.map +1 -0
- package/dist/tools/objectTools.js +221 -0
- package/dist/tools/objectTools.js.map +1 -0
- package/dist/tools/paintTools.d.ts +3 -0
- package/dist/tools/paintTools.d.ts.map +1 -0
- package/dist/tools/paintTools.js +134 -0
- package/dist/tools/paintTools.js.map +1 -0
- package/dist/tools/pluginScanTools.d.ts +22 -0
- package/dist/tools/pluginScanTools.d.ts.map +1 -0
- package/dist/tools/pluginScanTools.js +119 -0
- package/dist/tools/pluginScanTools.js.map +1 -0
- package/dist/tools/pluginTools.d.ts +11 -0
- package/dist/tools/pluginTools.d.ts.map +1 -0
- package/dist/tools/pluginTools.js +63 -0
- package/dist/tools/pluginTools.js.map +1 -0
- package/dist/tools/projectTools.d.ts +11 -0
- package/dist/tools/projectTools.d.ts.map +1 -0
- package/dist/tools/projectTools.js +74 -0
- package/dist/tools/projectTools.js.map +1 -0
- package/dist/tools/skillTools.d.ts +83 -0
- package/dist/tools/skillTools.d.ts.map +1 -0
- package/dist/tools/skillTools.js +369 -0
- package/dist/tools/skillTools.js.map +1 -0
- package/dist/tools/stateTools.d.ts +28 -0
- package/dist/tools/stateTools.d.ts.map +1 -0
- package/dist/tools/stateTools.js +161 -0
- package/dist/tools/stateTools.js.map +1 -0
- package/dist/tools/systemTools.d.ts +86 -0
- package/dist/tools/systemTools.d.ts.map +1 -0
- package/dist/tools/systemTools.js +342 -0
- package/dist/tools/systemTools.js.map +1 -0
- package/dist/tools/tileTools.d.ts +9 -0
- package/dist/tools/tileTools.d.ts.map +1 -0
- package/dist/tools/tileTools.js +34 -0
- package/dist/tools/tileTools.js.map +1 -0
- package/dist/tools/tileTransparency.d.ts +40 -0
- package/dist/tools/tileTransparency.d.ts.map +1 -0
- package/dist/tools/tileTransparency.js +156 -0
- package/dist/tools/tileTransparency.js.map +1 -0
- package/dist/tools/tilesetTools.d.ts +23 -0
- package/dist/tools/tilesetTools.d.ts.map +1 -0
- package/dist/tools/tilesetTools.js +209 -0
- package/dist/tools/tilesetTools.js.map +1 -0
- package/dist/tools/validationTools.d.ts +50 -0
- package/dist/tools/validationTools.d.ts.map +1 -0
- package/dist/tools/validationTools.js +229 -0
- package/dist/tools/validationTools.js.map +1 -0
- package/dist/utils/commit.d.ts +62 -0
- package/dist/utils/commit.d.ts.map +1 -0
- package/dist/utils/commit.js +119 -0
- package/dist/utils/commit.js.map +1 -0
- package/dist/utils/fileHandler.d.ts +49 -0
- package/dist/utils/fileHandler.d.ts.map +1 -0
- package/dist/utils/fileHandler.js +137 -0
- package/dist/utils/fileHandler.js.map +1 -0
- package/dist/utils/records.d.ts +8 -0
- package/dist/utils/records.d.ts.map +1 -0
- package/dist/utils/records.js +10 -0
- package/dist/utils/records.js.map +1 -0
- package/dist/utils/types.d.ts +465 -0
- package/dist/utils/types.d.ts.map +1 -0
- package/dist/utils/types.js +5 -0
- package/dist/utils/types.js.map +1 -0
- package/dist/validation/assets.d.ts +53 -0
- package/dist/validation/assets.d.ts.map +1 -0
- package/dist/validation/assets.js +198 -0
- package/dist/validation/assets.js.map +1 -0
- package/dist/validation/createRefs.d.ts +37 -0
- package/dist/validation/createRefs.d.ts.map +1 -0
- package/dist/validation/createRefs.js +89 -0
- package/dist/validation/createRefs.js.map +1 -0
- package/dist/validation/eventCommands.d.ts +70 -0
- package/dist/validation/eventCommands.d.ts.map +1 -0
- package/dist/validation/eventCommands.js +273 -0
- package/dist/validation/eventCommands.js.map +1 -0
- package/dist/validation/gate.d.ts +56 -0
- package/dist/validation/gate.d.ts.map +1 -0
- package/dist/validation/gate.js +50 -0
- package/dist/validation/gate.js.map +1 -0
- package/dist/validation/moveCommands.d.ts +31 -0
- package/dist/validation/moveCommands.d.ts.map +1 -0
- package/dist/validation/moveCommands.js +123 -0
- package/dist/validation/moveCommands.js.map +1 -0
- package/dist/validation/pluginCommands.d.ts +83 -0
- package/dist/validation/pluginCommands.d.ts.map +1 -0
- package/dist/validation/pluginCommands.js +134 -0
- package/dist/validation/pluginCommands.js.map +1 -0
- package/dist/validation/pluginManifest.d.ts +67 -0
- package/dist/validation/pluginManifest.d.ts.map +1 -0
- package/dist/validation/pluginManifest.js +199 -0
- package/dist/validation/pluginManifest.js.map +1 -0
- package/dist/validation/references.d.ts +57 -0
- package/dist/validation/references.d.ts.map +1 -0
- package/dist/validation/references.js +314 -0
- package/dist/validation/references.js.map +1 -0
- package/package.json +67 -0
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { EventCommand } from '../utils/types.js';
|
|
2
|
+
import { ValidationWarning } from './eventCommands.js';
|
|
3
|
+
/**
|
|
4
|
+
* Event command code for an RPG Maker MZ plugin command. On disk a 357 command is
|
|
5
|
+
* `{ code: 357, indent, parameters: [pluginName, commandName, label, args] }`:
|
|
6
|
+
* - parameters[0] — plugin filename without `.js` (e.g. `TextPicture`)
|
|
7
|
+
* - parameters[1] — the registered command key the plugin listens for
|
|
8
|
+
* - parameters[2] — the editor's display label (cosmetic; the engine ignores it)
|
|
9
|
+
* - parameters[3] — an args object `{ name: value }`; the editor stores every
|
|
10
|
+
* value as a string (structs/arrays are JSON-stringified into that string).
|
|
11
|
+
* `command357` only reads [0], [1] and [3]; [2] is purely for the editor's list.
|
|
12
|
+
*/
|
|
13
|
+
export declare const PLUGIN_COMMAND_CODE = 357;
|
|
14
|
+
/** Spec for a single plugin-command argument. */
|
|
15
|
+
export interface PluginArgSpec {
|
|
16
|
+
name: string;
|
|
17
|
+
required?: boolean;
|
|
18
|
+
description?: string;
|
|
19
|
+
/** The editor's display label (`@text`), when scanned from a plugin source. */
|
|
20
|
+
text?: string;
|
|
21
|
+
/** The arg's declared `@type` (number, common_event, struct<X>, …), when scanned. */
|
|
22
|
+
type?: string;
|
|
23
|
+
/** The arg's `@default`, when scanned. */
|
|
24
|
+
default?: string;
|
|
25
|
+
}
|
|
26
|
+
/** Spec for one registered plugin command. */
|
|
27
|
+
export interface PluginCommandSpec {
|
|
28
|
+
/** Display label the editor shows (parameters[2]); defaults to the command key. */
|
|
29
|
+
label?: string;
|
|
30
|
+
description?: string;
|
|
31
|
+
args?: PluginArgSpec[];
|
|
32
|
+
}
|
|
33
|
+
/** A plugin's registry entry: a description plus its known commands. */
|
|
34
|
+
export interface PluginSpec {
|
|
35
|
+
description?: string;
|
|
36
|
+
commands: Record<string, PluginCommandSpec>;
|
|
37
|
+
/**
|
|
38
|
+
* Whether `js/plugins.js` has the plugin turned on. Only set by the project
|
|
39
|
+
* scanner — a built-in allowlist entry leaves it undefined (unknown), so only an
|
|
40
|
+
* explicit `false` is ever reported.
|
|
41
|
+
*/
|
|
42
|
+
enabled?: boolean;
|
|
43
|
+
}
|
|
44
|
+
/** A plugin registry: plugin filename (no `.js`) → its spec. */
|
|
45
|
+
export type PluginRegistry = Record<string, PluginSpec>;
|
|
46
|
+
/**
|
|
47
|
+
* Curated allowlist of known community/official plugin commands, keyed by plugin
|
|
48
|
+
* filename → command key. Deliberately **not** exhaustive — it is a starter set
|
|
49
|
+
* meant to grow. Its only job is to turn a specific plugin command from opaque
|
|
50
|
+
* params into something `create_plugin_command` can validate (required args
|
|
51
|
+
* present, no stray args) and label the way the editor would. A plugin command
|
|
52
|
+
* that isn't listed here is still built fine — it just passes through with a soft
|
|
53
|
+
* "not in the allowlist" warning (warn-by-default, mirroring unknown event codes).
|
|
54
|
+
*/
|
|
55
|
+
export declare const PLUGIN_COMMAND_REGISTRY: PluginRegistry;
|
|
56
|
+
/**
|
|
57
|
+
* Look up a plugin command spec, or `undefined` if the plugin/command is unlisted.
|
|
58
|
+
* `registry` defaults to the built-in allowlist; the tools pass a project-scanned
|
|
59
|
+
* registry merged over it (see `tools/pluginScanTools.ts`).
|
|
60
|
+
*/
|
|
61
|
+
export declare function lookupPluginCommand(pluginName: string, commandName: string, registry?: PluginRegistry): PluginCommandSpec | undefined;
|
|
62
|
+
/**
|
|
63
|
+
* Normalize a plugin-command args object into the exact on-disk shape the editor
|
|
64
|
+
* writes: every value is a string. Scalars are stringified; objects/arrays (plugin
|
|
65
|
+
* "struct" params) are JSON-stringified into a single string. `null`/`undefined`
|
|
66
|
+
* values are dropped. A value that is already a string is left untouched (so a
|
|
67
|
+
* caller may pre-stringify a struct if they prefer).
|
|
68
|
+
*/
|
|
69
|
+
export declare function normalizePluginArgs(args: Record<string, unknown>): Record<string, string>;
|
|
70
|
+
/**
|
|
71
|
+
* Validate a plugin command against the allowlist. Warn-by-default: an unlisted
|
|
72
|
+
* plugin or command yields a single soft warning (its args pass through
|
|
73
|
+
* unchecked); a listed command additionally flags missing required args and stray
|
|
74
|
+
* unknown args. Nothing throws.
|
|
75
|
+
*/
|
|
76
|
+
export declare function validatePluginCommand(pluginName: string, commandName: string, args: Record<string, unknown>, path?: string, registry?: PluginRegistry): ValidationWarning[];
|
|
77
|
+
/**
|
|
78
|
+
* Build the plugin-command event command (code 357) for insertion into an event
|
|
79
|
+
* page via `add_event_command`. `label` defaults to the registry's display label
|
|
80
|
+
* (or the command key). Args are normalized to the editor's string-valued shape.
|
|
81
|
+
*/
|
|
82
|
+
export declare function buildPluginCommand(pluginName: string, commandName: string, args?: Record<string, unknown>, indent?: number, label?: string, registry?: PluginRegistry): EventCommand;
|
|
83
|
+
//# sourceMappingURL=pluginCommands.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pluginCommands.d.ts","sourceRoot":"","sources":["../../src/validation/pluginCommands.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACjD,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAEvD;;;;;;;;;GASG;AACH,eAAO,MAAM,mBAAmB,MAAM,CAAC;AAEvC,iDAAiD;AACjD,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,+EAA+E;IAC/E,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,qFAAqF;IACrF,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,0CAA0C;IAC1C,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,8CAA8C;AAC9C,MAAM,WAAW,iBAAiB;IAChC,mFAAmF;IACnF,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,IAAI,CAAC,EAAE,aAAa,EAAE,CAAC;CACxB;AAED,wEAAwE;AACxE,MAAM,WAAW,UAAU;IACzB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,iBAAiB,CAAC,CAAC;IAC5C;;;;OAIG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,gEAAgE;AAChE,MAAM,MAAM,cAAc,GAAG,MAAM,CAAC,MAAM,EAAE,UAAU,CAAC,CAAC;AAExD;;;;;;;;GAQG;AACH,eAAO,MAAM,uBAAuB,EAAE,cAiBrC,CAAC;AAEF;;;;GAIG;AACH,wBAAgB,mBAAmB,CACjC,UAAU,EAAE,MAAM,EAClB,WAAW,EAAE,MAAM,EACnB,QAAQ,GAAE,cAAwC,GACjD,iBAAiB,GAAG,SAAS,CAE/B;AAED;;;;;;GAMG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAOzF;AAED;;;;;GAKG;AACH,wBAAgB,qBAAqB,CACnC,UAAU,EAAE,MAAM,EAClB,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,IAAI,SAAiD,EACrD,QAAQ,GAAE,cAAwC,GACjD,iBAAiB,EAAE,CAyDrB;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,MAAM,EAClB,WAAW,EAAE,MAAM,EACnB,IAAI,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,EAClC,MAAM,SAAI,EACV,KAAK,CAAC,EAAE,MAAM,EACd,QAAQ,GAAE,cAAwC,GACjD,YAAY,CAQd"}
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Event command code for an RPG Maker MZ plugin command. On disk a 357 command is
|
|
3
|
+
* `{ code: 357, indent, parameters: [pluginName, commandName, label, args] }`:
|
|
4
|
+
* - parameters[0] — plugin filename without `.js` (e.g. `TextPicture`)
|
|
5
|
+
* - parameters[1] — the registered command key the plugin listens for
|
|
6
|
+
* - parameters[2] — the editor's display label (cosmetic; the engine ignores it)
|
|
7
|
+
* - parameters[3] — an args object `{ name: value }`; the editor stores every
|
|
8
|
+
* value as a string (structs/arrays are JSON-stringified into that string).
|
|
9
|
+
* `command357` only reads [0], [1] and [3]; [2] is purely for the editor's list.
|
|
10
|
+
*/
|
|
11
|
+
export const PLUGIN_COMMAND_CODE = 357;
|
|
12
|
+
/**
|
|
13
|
+
* Curated allowlist of known community/official plugin commands, keyed by plugin
|
|
14
|
+
* filename → command key. Deliberately **not** exhaustive — it is a starter set
|
|
15
|
+
* meant to grow. Its only job is to turn a specific plugin command from opaque
|
|
16
|
+
* params into something `create_plugin_command` can validate (required args
|
|
17
|
+
* present, no stray args) and label the way the editor would. A plugin command
|
|
18
|
+
* that isn't listed here is still built fine — it just passes through with a soft
|
|
19
|
+
* "not in the allowlist" warning (warn-by-default, mirroring unknown event codes).
|
|
20
|
+
*/
|
|
21
|
+
export const PLUGIN_COMMAND_REGISTRY = {
|
|
22
|
+
TextPicture: {
|
|
23
|
+
description: 'Official MZ sample plugin — render text as a picture.',
|
|
24
|
+
commands: {
|
|
25
|
+
set: {
|
|
26
|
+
label: 'Set text picture',
|
|
27
|
+
description: 'Set the text drawn by the next Show Picture command.',
|
|
28
|
+
args: [
|
|
29
|
+
{
|
|
30
|
+
name: 'text',
|
|
31
|
+
required: true,
|
|
32
|
+
description: 'The text to render (supports control characters like \\V[n]).',
|
|
33
|
+
},
|
|
34
|
+
],
|
|
35
|
+
},
|
|
36
|
+
},
|
|
37
|
+
},
|
|
38
|
+
};
|
|
39
|
+
/**
|
|
40
|
+
* Look up a plugin command spec, or `undefined` if the plugin/command is unlisted.
|
|
41
|
+
* `registry` defaults to the built-in allowlist; the tools pass a project-scanned
|
|
42
|
+
* registry merged over it (see `tools/pluginScanTools.ts`).
|
|
43
|
+
*/
|
|
44
|
+
export function lookupPluginCommand(pluginName, commandName, registry = PLUGIN_COMMAND_REGISTRY) {
|
|
45
|
+
return registry[pluginName]?.commands[commandName];
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* Normalize a plugin-command args object into the exact on-disk shape the editor
|
|
49
|
+
* writes: every value is a string. Scalars are stringified; objects/arrays (plugin
|
|
50
|
+
* "struct" params) are JSON-stringified into a single string. `null`/`undefined`
|
|
51
|
+
* values are dropped. A value that is already a string is left untouched (so a
|
|
52
|
+
* caller may pre-stringify a struct if they prefer).
|
|
53
|
+
*/
|
|
54
|
+
export function normalizePluginArgs(args) {
|
|
55
|
+
const out = {};
|
|
56
|
+
for (const [key, value] of Object.entries(args)) {
|
|
57
|
+
if (value === undefined || value === null)
|
|
58
|
+
continue;
|
|
59
|
+
out[key] = typeof value === 'object' ? JSON.stringify(value) : String(value);
|
|
60
|
+
}
|
|
61
|
+
return out;
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Validate a plugin command against the allowlist. Warn-by-default: an unlisted
|
|
65
|
+
* plugin or command yields a single soft warning (its args pass through
|
|
66
|
+
* unchecked); a listed command additionally flags missing required args and stray
|
|
67
|
+
* unknown args. Nothing throws.
|
|
68
|
+
*/
|
|
69
|
+
export function validatePluginCommand(pluginName, commandName, args, path = `plugin command ${pluginName}: ${commandName}`, registry = PLUGIN_COMMAND_REGISTRY) {
|
|
70
|
+
const warnings = [];
|
|
71
|
+
const plugin = registry[pluginName];
|
|
72
|
+
if (!plugin) {
|
|
73
|
+
warnings.push({
|
|
74
|
+
path,
|
|
75
|
+
code: PLUGIN_COMMAND_CODE,
|
|
76
|
+
message: `plugin "${pluginName}" is not installed in this project and is not in the known-plugin allowlist (args passed through unchecked)`,
|
|
77
|
+
});
|
|
78
|
+
return warnings;
|
|
79
|
+
}
|
|
80
|
+
// A command on a plugin the editor has switched off never runs at all — a
|
|
81
|
+
// silent no-op that's easy to miss. Only the project scanner sets `enabled`.
|
|
82
|
+
if (plugin.enabled === false) {
|
|
83
|
+
warnings.push({
|
|
84
|
+
path,
|
|
85
|
+
code: PLUGIN_COMMAND_CODE,
|
|
86
|
+
message: `plugin "${pluginName}" is installed but disabled in js/plugins.js — this command will not run until it is enabled in the editor's Plugin Manager`,
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
const spec = plugin.commands[commandName];
|
|
90
|
+
if (!spec) {
|
|
91
|
+
warnings.push({
|
|
92
|
+
path,
|
|
93
|
+
code: PLUGIN_COMMAND_CODE,
|
|
94
|
+
message: `command "${commandName}" is not a known command of plugin "${pluginName}" (args passed through unchecked)`,
|
|
95
|
+
});
|
|
96
|
+
return warnings;
|
|
97
|
+
}
|
|
98
|
+
const known = spec.args ?? [];
|
|
99
|
+
const knownNames = new Set(known.map((a) => a.name));
|
|
100
|
+
for (const arg of known) {
|
|
101
|
+
if (arg.required && !(arg.name in args)) {
|
|
102
|
+
warnings.push({
|
|
103
|
+
path,
|
|
104
|
+
code: PLUGIN_COMMAND_CODE,
|
|
105
|
+
message: `missing required argument "${arg.name}"`,
|
|
106
|
+
});
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
for (const name of Object.keys(args)) {
|
|
110
|
+
if (!knownNames.has(name)) {
|
|
111
|
+
warnings.push({
|
|
112
|
+
path,
|
|
113
|
+
code: PLUGIN_COMMAND_CODE,
|
|
114
|
+
message: `unknown argument "${name}" for ${pluginName}: ${commandName}`,
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
return warnings;
|
|
119
|
+
}
|
|
120
|
+
/**
|
|
121
|
+
* Build the plugin-command event command (code 357) for insertion into an event
|
|
122
|
+
* page via `add_event_command`. `label` defaults to the registry's display label
|
|
123
|
+
* (or the command key). Args are normalized to the editor's string-valued shape.
|
|
124
|
+
*/
|
|
125
|
+
export function buildPluginCommand(pluginName, commandName, args = {}, indent = 0, label, registry = PLUGIN_COMMAND_REGISTRY) {
|
|
126
|
+
const spec = lookupPluginCommand(pluginName, commandName, registry);
|
|
127
|
+
const displayLabel = label ?? spec?.label ?? commandName;
|
|
128
|
+
return {
|
|
129
|
+
code: PLUGIN_COMMAND_CODE,
|
|
130
|
+
indent,
|
|
131
|
+
parameters: [pluginName, commandName, displayLabel, normalizePluginArgs(args)],
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
//# sourceMappingURL=pluginCommands.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pluginCommands.js","sourceRoot":"","sources":["../../src/validation/pluginCommands.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import { PluginRegistry, PluginSpec } from './pluginCommands.js';
|
|
2
|
+
/**
|
|
3
|
+
* Parsers for what an RPG Maker MZ project already tells us about its plugins —
|
|
4
|
+
* the annotation comment block every plugin carries, and the `js/plugins.js`
|
|
5
|
+
* manifest the editor generates. Pure (no I/O) so they can be unit-tested against
|
|
6
|
+
* real plugin sources; the file reading lives in `tools/pluginScanTools.ts`.
|
|
7
|
+
*
|
|
8
|
+
* This is what turns plugin validation from a hand-maintained allowlist into real
|
|
9
|
+
* per-project coverage: the plugin sources ARE the source of truth for which
|
|
10
|
+
* commands exist and what args they take.
|
|
11
|
+
*/
|
|
12
|
+
/** One entry of the `$plugins` array in `js/plugins.js`. */
|
|
13
|
+
export interface PluginManifestEntry {
|
|
14
|
+
name: string;
|
|
15
|
+
status: boolean;
|
|
16
|
+
description?: string;
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Parse `js/plugins.js` — the editor-generated manifest listing which plugins are
|
|
20
|
+
* installed and whether each is **enabled** (`status`). The file is JS
|
|
21
|
+
* (`var $plugins = [ ... ];`) but the array literal itself is JSON, so it's
|
|
22
|
+
* extracted and parsed directly. Fails soft: anything unparseable yields `[]`.
|
|
23
|
+
*/
|
|
24
|
+
export declare function parsePluginsJs(source: string): PluginManifestEntry[];
|
|
25
|
+
/**
|
|
26
|
+
* Extract the body of a plugin's **default-locale** annotation block.
|
|
27
|
+
*
|
|
28
|
+
* A plugin's metadata lives in a `/*:` comment. Localized copies of the same block
|
|
29
|
+
* are tagged (`/*:ja`) and must be skipped — otherwise a Japanese `@text` would win
|
|
30
|
+
* on the official sample plugins, which ship both. Struct definitions
|
|
31
|
+
* (`/*~struct~Name:`) are a different construct and are never matched here.
|
|
32
|
+
*
|
|
33
|
+
* Returns the block's inner text (comment markers still attached), or `null`.
|
|
34
|
+
*/
|
|
35
|
+
export declare function defaultAnnotationBlock(source: string): string | null;
|
|
36
|
+
/**
|
|
37
|
+
* Parse a plugin's source into the same {@link PluginSpec} shape the built-in
|
|
38
|
+
* allowlist uses, reading its `@plugindesc`, `@command`s and their `@arg`s.
|
|
39
|
+
*
|
|
40
|
+
* Annotation grammar (from the official MZ sample plugins): `@command <key>` opens
|
|
41
|
+
* a command; `@arg <name>` opens an argument **of the command above it**; `@text`
|
|
42
|
+
* and `@desc` describe whichever of those is currently open. `@param` (a plugin
|
|
43
|
+
* *parameter*, not a command arg) and `@help` close that scope so their own
|
|
44
|
+
* `@text`/`@desc` don't attach to the last command.
|
|
45
|
+
*
|
|
46
|
+
* **No `required` is ever set:** MZ has no "required argument" annotation, so
|
|
47
|
+
* inferring it (e.g. from a missing `@default`) would only produce false "missing
|
|
48
|
+
* required argument" warnings. Scanned args are validated for *unknown* names only.
|
|
49
|
+
*
|
|
50
|
+
* Returns `null` when the source has no default-locale annotation block.
|
|
51
|
+
*/
|
|
52
|
+
export declare function parsePluginAnnotations(source: string): PluginSpec | null;
|
|
53
|
+
/**
|
|
54
|
+
* Merge a project scan over the curated allowlist.
|
|
55
|
+
*
|
|
56
|
+
* The two registries know different things and neither is a superset:
|
|
57
|
+
* - the **scan** is authoritative on *structure* — which plugins/commands/args
|
|
58
|
+
* actually exist in this project, and each arg's `@type`/`@default`;
|
|
59
|
+
* - the **allowlist** carries knowledge the annotations can't express, above all
|
|
60
|
+
* `required` (MZ has no required-arg annotation).
|
|
61
|
+
*
|
|
62
|
+
* So the scan wins on structure while a curated `required`/`description` is carried
|
|
63
|
+
* across onto the matching arg by name, rather than a whole-plugin overwrite that
|
|
64
|
+
* would silently drop it.
|
|
65
|
+
*/
|
|
66
|
+
export declare function mergePluginRegistries(builtin: PluginRegistry, scanned: PluginRegistry): PluginRegistry;
|
|
67
|
+
//# sourceMappingURL=pluginManifest.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pluginManifest.d.ts","sourceRoot":"","sources":["../../src/validation/pluginManifest.ts"],"names":[],"mappings":"AAAA,OAAO,EAAoC,cAAc,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAEnG;;;;;;;;;GASG;AAEH,4DAA4D;AAC5D,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,OAAO,CAAC;IAChB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,MAAM,GAAG,mBAAmB,EAAE,CAmBpE;AAED;;;;;;;;;GASG;AACH,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAQpE;AAgBD;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,MAAM,GAAG,UAAU,GAAG,IAAI,CAwExE;AAQD;;;;;;;;;;;;GAYG;AACH,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,cAAc,EACvB,OAAO,EAAE,cAAc,GACtB,cAAc,CAwBhB"}
|
|
@@ -0,0 +1,199 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Parse `js/plugins.js` — the editor-generated manifest listing which plugins are
|
|
3
|
+
* installed and whether each is **enabled** (`status`). The file is JS
|
|
4
|
+
* (`var $plugins = [ ... ];`) but the array literal itself is JSON, so it's
|
|
5
|
+
* extracted and parsed directly. Fails soft: anything unparseable yields `[]`.
|
|
6
|
+
*/
|
|
7
|
+
export function parsePluginsJs(source) {
|
|
8
|
+
const start = source.indexOf('[');
|
|
9
|
+
const end = source.lastIndexOf(']');
|
|
10
|
+
if (start === -1 || end === -1 || end < start)
|
|
11
|
+
return [];
|
|
12
|
+
try {
|
|
13
|
+
const parsed = JSON.parse(source.slice(start, end + 1));
|
|
14
|
+
if (!Array.isArray(parsed))
|
|
15
|
+
return [];
|
|
16
|
+
return parsed
|
|
17
|
+
.filter((entry) => !!entry && typeof entry === 'object')
|
|
18
|
+
.filter((entry) => typeof entry.name === 'string')
|
|
19
|
+
.map((entry) => ({
|
|
20
|
+
name: entry.name,
|
|
21
|
+
status: entry.status === true,
|
|
22
|
+
...(typeof entry.description === 'string' ? { description: entry.description } : {}),
|
|
23
|
+
}));
|
|
24
|
+
}
|
|
25
|
+
catch {
|
|
26
|
+
return [];
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Extract the body of a plugin's **default-locale** annotation block.
|
|
31
|
+
*
|
|
32
|
+
* A plugin's metadata lives in a `/*:` comment. Localized copies of the same block
|
|
33
|
+
* are tagged (`/*:ja`) and must be skipped — otherwise a Japanese `@text` would win
|
|
34
|
+
* on the official sample plugins, which ship both. Struct definitions
|
|
35
|
+
* (`/*~struct~Name:`) are a different construct and are never matched here.
|
|
36
|
+
*
|
|
37
|
+
* Returns the block's inner text (comment markers still attached), or `null`.
|
|
38
|
+
*/
|
|
39
|
+
export function defaultAnnotationBlock(source) {
|
|
40
|
+
// Block opener + an optional locale tag + newline, up to the comment terminator.
|
|
41
|
+
const re = /\/\*:([A-Za-z_-]*)[ \t]*\r?\n([\s\S]*?)\*\//g;
|
|
42
|
+
let match;
|
|
43
|
+
while ((match = re.exec(source)) !== null) {
|
|
44
|
+
if (match[1] === '')
|
|
45
|
+
return match[2];
|
|
46
|
+
}
|
|
47
|
+
return null;
|
|
48
|
+
}
|
|
49
|
+
/** Strip the leading ` * ` comment gutter from an annotation-block line. */
|
|
50
|
+
function stripGutter(line) {
|
|
51
|
+
return line.replace(/^[ \t]*\*[ \t]?/, '');
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Parse a plugin's source into the same {@link PluginSpec} shape the built-in
|
|
55
|
+
* allowlist uses, reading its `@plugindesc`, `@command`s and their `@arg`s.
|
|
56
|
+
*
|
|
57
|
+
* Annotation grammar (from the official MZ sample plugins): `@command <key>` opens
|
|
58
|
+
* a command; `@arg <name>` opens an argument **of the command above it**; `@text`
|
|
59
|
+
* and `@desc` describe whichever of those is currently open. `@param` (a plugin
|
|
60
|
+
* *parameter*, not a command arg) and `@help` close that scope so their own
|
|
61
|
+
* `@text`/`@desc` don't attach to the last command.
|
|
62
|
+
*
|
|
63
|
+
* **No `required` is ever set:** MZ has no "required argument" annotation, so
|
|
64
|
+
* inferring it (e.g. from a missing `@default`) would only produce false "missing
|
|
65
|
+
* required argument" warnings. Scanned args are validated for *unknown* names only.
|
|
66
|
+
*
|
|
67
|
+
* Returns `null` when the source has no default-locale annotation block.
|
|
68
|
+
*/
|
|
69
|
+
export function parsePluginAnnotations(source) {
|
|
70
|
+
const block = defaultAnnotationBlock(source);
|
|
71
|
+
if (block === null)
|
|
72
|
+
return null;
|
|
73
|
+
const spec = { commands: {} };
|
|
74
|
+
let context = { kind: 'plugin' };
|
|
75
|
+
for (const raw of block.split(/\r?\n/)) {
|
|
76
|
+
const line = stripGutter(raw);
|
|
77
|
+
const match = /^@(\w+)[ \t]*(.*)$/.exec(line);
|
|
78
|
+
if (!match)
|
|
79
|
+
continue;
|
|
80
|
+
const [, tag, value] = match;
|
|
81
|
+
const trimmed = value.trim();
|
|
82
|
+
switch (tag) {
|
|
83
|
+
case 'plugindesc':
|
|
84
|
+
if (trimmed)
|
|
85
|
+
spec.description = trimmed;
|
|
86
|
+
context = { kind: 'plugin' };
|
|
87
|
+
break;
|
|
88
|
+
case 'command': {
|
|
89
|
+
if (!trimmed)
|
|
90
|
+
break;
|
|
91
|
+
const command = {};
|
|
92
|
+
spec.commands[trimmed] = command;
|
|
93
|
+
context = { kind: 'command', command };
|
|
94
|
+
break;
|
|
95
|
+
}
|
|
96
|
+
case 'arg': {
|
|
97
|
+
if (!trimmed || context.kind === 'plugin' || context.kind === 'other')
|
|
98
|
+
break;
|
|
99
|
+
// An `@arg` belongs to the command above it — which, when the previous
|
|
100
|
+
// context was itself an arg, is still the same command.
|
|
101
|
+
const command = context.kind === 'command' ? context.command : lastCommand(spec);
|
|
102
|
+
if (!command)
|
|
103
|
+
break;
|
|
104
|
+
const arg = { name: trimmed };
|
|
105
|
+
command.args = [...(command.args ?? []), arg];
|
|
106
|
+
context = { kind: 'arg', arg };
|
|
107
|
+
break;
|
|
108
|
+
}
|
|
109
|
+
case 'text':
|
|
110
|
+
if (context.kind === 'command')
|
|
111
|
+
context.command.label = trimmed || undefined;
|
|
112
|
+
else if (context.kind === 'arg')
|
|
113
|
+
context.arg.text = trimmed || undefined;
|
|
114
|
+
break;
|
|
115
|
+
case 'desc':
|
|
116
|
+
if (context.kind === 'command')
|
|
117
|
+
context.command.description = trimmed || undefined;
|
|
118
|
+
else if (context.kind === 'arg')
|
|
119
|
+
context.arg.description = trimmed || undefined;
|
|
120
|
+
break;
|
|
121
|
+
case 'type':
|
|
122
|
+
if (context.kind === 'arg')
|
|
123
|
+
context.arg.type = trimmed || undefined;
|
|
124
|
+
break;
|
|
125
|
+
case 'default':
|
|
126
|
+
if (context.kind === 'arg')
|
|
127
|
+
context.arg.default = trimmed;
|
|
128
|
+
break;
|
|
129
|
+
case 'param':
|
|
130
|
+
case 'help':
|
|
131
|
+
context = { kind: 'other' };
|
|
132
|
+
break;
|
|
133
|
+
default:
|
|
134
|
+
// Any other annotation (@target, @author, @url, @min, @max, @require, …)
|
|
135
|
+
// leaves the current scope open — @min/@max sit inside an @arg.
|
|
136
|
+
break;
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
return spec;
|
|
140
|
+
}
|
|
141
|
+
/** The most recently declared command, so a run of `@arg`s keeps attaching to it. */
|
|
142
|
+
function lastCommand(spec) {
|
|
143
|
+
const keys = Object.keys(spec.commands);
|
|
144
|
+
return keys.length > 0 ? spec.commands[keys[keys.length - 1]] : undefined;
|
|
145
|
+
}
|
|
146
|
+
/**
|
|
147
|
+
* Merge a project scan over the curated allowlist.
|
|
148
|
+
*
|
|
149
|
+
* The two registries know different things and neither is a superset:
|
|
150
|
+
* - the **scan** is authoritative on *structure* — which plugins/commands/args
|
|
151
|
+
* actually exist in this project, and each arg's `@type`/`@default`;
|
|
152
|
+
* - the **allowlist** carries knowledge the annotations can't express, above all
|
|
153
|
+
* `required` (MZ has no required-arg annotation).
|
|
154
|
+
*
|
|
155
|
+
* So the scan wins on structure while a curated `required`/`description` is carried
|
|
156
|
+
* across onto the matching arg by name, rather than a whole-plugin overwrite that
|
|
157
|
+
* would silently drop it.
|
|
158
|
+
*/
|
|
159
|
+
export function mergePluginRegistries(builtin, scanned) {
|
|
160
|
+
const merged = { ...builtin };
|
|
161
|
+
for (const [name, scan] of Object.entries(scanned)) {
|
|
162
|
+
const base = builtin[name];
|
|
163
|
+
if (!base) {
|
|
164
|
+
merged[name] = scan;
|
|
165
|
+
continue;
|
|
166
|
+
}
|
|
167
|
+
const commands = { ...base.commands };
|
|
168
|
+
for (const [key, scanCommand] of Object.entries(scan.commands)) {
|
|
169
|
+
const baseCommand = base.commands[key];
|
|
170
|
+
commands[key] = baseCommand ? mergeCommand(baseCommand, scanCommand) : scanCommand;
|
|
171
|
+
}
|
|
172
|
+
merged[name] = {
|
|
173
|
+
...base,
|
|
174
|
+
...scan,
|
|
175
|
+
commands,
|
|
176
|
+
};
|
|
177
|
+
}
|
|
178
|
+
return merged;
|
|
179
|
+
}
|
|
180
|
+
function mergeCommand(base, scan) {
|
|
181
|
+
return {
|
|
182
|
+
label: scan.label ?? base.label,
|
|
183
|
+
description: scan.description ?? base.description,
|
|
184
|
+
// A scan that found no args at all tells us nothing about them, so the
|
|
185
|
+
// curated list survives; otherwise the scanned list is the real one.
|
|
186
|
+
args: scan.args ? scan.args.map((arg) => mergeArg(base.args ?? [], arg)) : base.args,
|
|
187
|
+
};
|
|
188
|
+
}
|
|
189
|
+
function mergeArg(baseArgs, scan) {
|
|
190
|
+
const base = baseArgs.find((a) => a.name === scan.name);
|
|
191
|
+
if (!base)
|
|
192
|
+
return scan;
|
|
193
|
+
return {
|
|
194
|
+
...scan,
|
|
195
|
+
...(base.required !== undefined ? { required: base.required } : {}),
|
|
196
|
+
description: scan.description ?? base.description,
|
|
197
|
+
};
|
|
198
|
+
}
|
|
199
|
+
//# sourceMappingURL=pluginManifest.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pluginManifest.js","sourceRoot":"","sources":["../../src/validation/pluginManifest.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { Actor, GameClass, Skill, Item, Weapon, Armor, Enemy, Troop, State, CommonEvent, MapEvent, MapInfo, SystemData } from '../utils/types.js';
|
|
2
|
+
/**
|
|
3
|
+
* A single cross-file reference-integrity finding. Like {@link
|
|
4
|
+
* ValidationWarning} this is warn-by-default (it never blocks a write); it tells
|
|
5
|
+
* the caller that one record points at another record that doesn't exist — a
|
|
6
|
+
* dangling id the RPG Maker editor would silently treat as "nothing", producing
|
|
7
|
+
* a subtle runtime bug rather than an error. `category` groups findings by the
|
|
8
|
+
* kind of reference; `path` locates the offending field.
|
|
9
|
+
*/
|
|
10
|
+
export interface ReferenceWarning {
|
|
11
|
+
category: string;
|
|
12
|
+
path: string;
|
|
13
|
+
message: string;
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* The loaded project data the reference linter cross-checks. Every database
|
|
17
|
+
* array is the raw 1-indexed file (slot 0 `null`). `animations` is `null` when
|
|
18
|
+
* `Animations.json` couldn't be loaded, so animation-id checks are skipped
|
|
19
|
+
* rather than flagging every reference. Kept as plain data so {@link
|
|
20
|
+
* checkReferences} stays pure and unit-testable without file I/O.
|
|
21
|
+
*/
|
|
22
|
+
export interface ProjectData {
|
|
23
|
+
mapInfos: (MapInfo | null)[];
|
|
24
|
+
/** Only the maps that loaded, carrying just the id + events the linter needs. */
|
|
25
|
+
maps: Array<{
|
|
26
|
+
id: number;
|
|
27
|
+
events: (MapEvent | null)[];
|
|
28
|
+
}>;
|
|
29
|
+
actors: (Actor | null)[];
|
|
30
|
+
classes: (GameClass | null)[];
|
|
31
|
+
skills: (Skill | null)[];
|
|
32
|
+
items: (Item | null)[];
|
|
33
|
+
weapons: (Weapon | null)[];
|
|
34
|
+
armors: (Armor | null)[];
|
|
35
|
+
enemies: (Enemy | null)[];
|
|
36
|
+
troops: (Troop | null)[];
|
|
37
|
+
states: (State | null)[];
|
|
38
|
+
commonEvents: (CommonEvent | null)[];
|
|
39
|
+
/** `null` = Animations.json unavailable → animation-id checks skipped. */
|
|
40
|
+
animations: (unknown | null)[] | null;
|
|
41
|
+
system: SystemData | null;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Whether `id` names a live entry in a 1-indexed RPG Maker database array (slot
|
|
45
|
+
* 0 is `null`; id === array index). A `0`/negative id, an out-of-range id, or a
|
|
46
|
+
* nulled slot all count as "does not exist". An empty array (a file that failed
|
|
47
|
+
* to load) is treated as "can't verify" — never a match, but callers guard on
|
|
48
|
+
* array length so a failed load doesn't flag every reference.
|
|
49
|
+
*/
|
|
50
|
+
export declare function refExists(arr: readonly (unknown | null)[], id: number): boolean;
|
|
51
|
+
/**
|
|
52
|
+
* Run every cross-file reference check over a loaded project snapshot. Pure and
|
|
53
|
+
* warn-by-default: returns an aggregated list of dangling/cyclic references,
|
|
54
|
+
* empty when everything resolves. See {@link ProjectData} for the input shape.
|
|
55
|
+
*/
|
|
56
|
+
export declare function checkReferences(data: ProjectData): ReferenceWarning[];
|
|
57
|
+
//# sourceMappingURL=references.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"references.d.ts","sourceRoot":"","sources":["../../src/validation/references.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,EACL,SAAS,EACT,KAAK,EACL,IAAI,EACJ,MAAM,EACN,KAAK,EACL,KAAK,EACL,KAAK,EACL,KAAK,EACL,WAAW,EACX,QAAQ,EACR,OAAO,EACP,UAAU,EAEX,MAAM,mBAAmB,CAAC;AAE3B;;;;;;;GAOG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;;;;;GAMG;AACH,MAAM,WAAW,WAAW;IAC1B,QAAQ,EAAE,CAAC,OAAO,GAAG,IAAI,CAAC,EAAE,CAAC;IAC7B,iFAAiF;IACjF,IAAI,EAAE,KAAK,CAAC;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,CAAC,QAAQ,GAAG,IAAI,CAAC,EAAE,CAAA;KAAE,CAAC,CAAC;IACzD,MAAM,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IACzB,OAAO,EAAE,CAAC,SAAS,GAAG,IAAI,CAAC,EAAE,CAAC;IAC9B,MAAM,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IACzB,KAAK,EAAE,CAAC,IAAI,GAAG,IAAI,CAAC,EAAE,CAAC;IACvB,OAAO,EAAE,CAAC,MAAM,GAAG,IAAI,CAAC,EAAE,CAAC;IAC3B,MAAM,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IACzB,OAAO,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IAC1B,MAAM,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IACzB,MAAM,EAAE,CAAC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC;IACzB,YAAY,EAAE,CAAC,WAAW,GAAG,IAAI,CAAC,EAAE,CAAC;IACrC,0EAA0E;IAC1E,UAAU,EAAE,CAAC,OAAO,GAAG,IAAI,CAAC,EAAE,GAAG,IAAI,CAAC;IACtC,MAAM,EAAE,UAAU,GAAG,IAAI,CAAC;CAC3B;AAYD;;;;;;GAMG;AACH,wBAAgB,SAAS,CAAC,GAAG,EAAE,SAAS,CAAC,OAAO,GAAG,IAAI,CAAC,EAAE,EAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE/E;AA6TD;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,WAAW,GAAG,gBAAgB,EAAE,CASrE"}
|