reciple 10.0.30 → 10.0.31

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/README.md CHANGED
@@ -55,10 +55,10 @@ Commands:
55
55
 
56
56
  ```bash
57
57
  npx reciple
58
- yarn dlx reciple
58
+ yarn exec reciple
59
59
  pnpx reciple
60
60
  bunx reciple
61
- deno run -A npm:reciple
61
+ deno x reciple
62
62
  ```
63
63
 
64
64
  ## Links
@@ -94,7 +94,7 @@ var CLI = class {
94
94
  (function(_CLI) {
95
95
  _CLI.root = path.join(path.dirname(fileURLToPath(import.meta.url)), "../../../");
96
96
  _CLI.bin = path.join(CLI.root, "dist/bin/reciple.mjs");
97
- _CLI.version = "10.0.30";
97
+ _CLI.version = "10.0.31";
98
98
  function stringifyFlags(flags, command, ignored = []) {
99
99
  let arr = [];
100
100
  for (const [key, value] of Object.entries(flags)) {
@@ -2,7 +2,6 @@ import { Client } from "@reciple/core";
2
2
 
3
3
  //#region src/classes/cli/RuntimeEnvironment.d.ts
4
4
  declare namespace RuntimeEnvironment {
5
- let stopping: boolean;
6
5
  type Type = 'node' | 'deno' | 'bun';
7
6
  function get(): Type | null;
8
7
  function sleep(time: number): Promise<void>;
@@ -4,7 +4,7 @@ import { setTimeout } from "node:timers/promises";
4
4
  //#region src/classes/cli/RuntimeEnvironment.ts
5
5
  let RuntimeEnvironment;
6
6
  (function(_RuntimeEnvironment) {
7
- let stopping = _RuntimeEnvironment.stopping = false;
7
+ let stopping = false;
8
8
  function get() {
9
9
  if ("isBun" in process && process.isBun && process.versions.bun) return "bun";
10
10
  if ("deno" in process.versions && process.versions.deno) return "deno";
@@ -1 +1 @@
1
- {"version":3,"file":"RuntimeEnvironment.mjs","names":[],"sources":["../../../src/classes/cli/RuntimeEnvironment.ts"],"sourcesContent":["import { colors } from '@prtty/prtty';\nimport type { Client } from '@reciple/core';\nimport { setTimeout } from 'node:timers/promises';\n\nexport namespace RuntimeEnvironment {\n export let stopping = false;\n\n export type Type = 'node'|'deno'|'bun';\n\n export function get(): Type|null {\n if ('isBun' in process && process.isBun && process.versions.bun) return 'bun';\n if ('deno' in process.versions && process.versions.deno) return 'deno';\n if (process.versions.node) return 'node';\n\n return null;\n }\n\n export async function sleep(time: number): Promise<void> {\n return setTimeout(time);\n }\n\n export async function handleExitSignal(client: Client, signal: NodeJS.Signals) {\n if (stopping) return;\n\n stopping = true;\n\n client.logger?.warn(`Received exit signal: ${signal}`);\n\n await client.destroy();\n client.eventListeners.unregisterAll();\n\n const signalString = signal === 'SIGINT' ? 'keyboard interrupt' : signal === 'SIGTERM' ? 'terminate' : String(signal);\n\n await sleep(10);\n\n client.logger?.warn(`Process exited: ${colors.yellow(signalString)}`);\n client.logger?.closeFileWriteStream();\n process.exit(0);\n }\n}\n"],"mappings":";;;;AAIO;;CACI,IAAI,0CAAW;CAIf,SAAS,MAAiB;AAC7B,MAAI,WAAW,WAAW,QAAQ,SAAS,QAAQ,SAAS,IAAK,QAAO;AACxE,MAAI,UAAU,QAAQ,YAAY,QAAQ,SAAS,KAAM,QAAO;AAChE,MAAI,QAAQ,SAAS,KAAM,QAAO;AAElC,SAAO;;;CAGJ,eAAe,MAAM,MAA6B;AACrD,SAAO,WAAW,KAAK;;;CAGpB,eAAe,iBAAiB,QAAgB,QAAwB;AAC3E,MAAI,SAAU;AAEd,aAAW;AAEX,SAAO,QAAQ,KAAK,yBAAyB,SAAS;AAEtD,QAAM,OAAO,SAAS;AACtB,SAAO,eAAe,eAAe;EAErC,MAAM,eAAe,WAAW,WAAW,uBAAuB,WAAW,YAAY,cAAc,OAAO,OAAO;AAErH,QAAM,MAAM,GAAG;AAEf,SAAO,QAAQ,KAAK,mBAAmB,OAAO,OAAO,aAAa,GAAG;AACrE,SAAO,QAAQ,sBAAsB;AACrC,UAAQ,KAAK,EAAE;;;mDAEtB"}
1
+ {"version":3,"file":"RuntimeEnvironment.mjs","names":[],"sources":["../../../src/classes/cli/RuntimeEnvironment.ts"],"sourcesContent":["import { colors } from '@prtty/prtty';\nimport type { Client } from '@reciple/core';\nimport { setTimeout } from 'node:timers/promises';\n\nexport namespace RuntimeEnvironment {\n let stopping = false;\n\n export type Type = 'node'|'deno'|'bun';\n\n export function get(): Type|null {\n if ('isBun' in process && process.isBun && process.versions.bun) return 'bun';\n if ('deno' in process.versions && process.versions.deno) return 'deno';\n if (process.versions.node) return 'node';\n\n return null;\n }\n\n export async function sleep(time: number): Promise<void> {\n return setTimeout(time);\n }\n\n export async function handleExitSignal(client: Client, signal: NodeJS.Signals) {\n if (stopping) return;\n\n stopping = true;\n\n client.logger?.warn(`Received exit signal: ${signal}`);\n\n await client.destroy();\n client.eventListeners.unregisterAll();\n\n const signalString = signal === 'SIGINT' ? 'keyboard interrupt' : signal === 'SIGTERM' ? 'terminate' : String(signal);\n\n await sleep(10);\n\n client.logger?.warn(`Process exited: ${colors.yellow(signalString)}`);\n client.logger?.closeFileWriteStream();\n process.exit(0);\n }\n}\n"],"mappings":";;;;AAIO;;CACH,IAAI,WAAW;CAIR,SAAS,MAAiB;AAC7B,MAAI,WAAW,WAAW,QAAQ,SAAS,QAAQ,SAAS,IAAK,QAAO;AACxE,MAAI,UAAU,QAAQ,YAAY,QAAQ,SAAS,KAAM,QAAO;AAChE,MAAI,QAAQ,SAAS,KAAM,QAAO;AAElC,SAAO;;;CAGJ,eAAe,MAAM,MAA6B;AACrD,SAAO,WAAW,KAAK;;;CAGpB,eAAe,iBAAiB,QAAgB,QAAwB;AAC3E,MAAI,SAAU;AAEd,aAAW;AAEX,SAAO,QAAQ,KAAK,yBAAyB,SAAS;AAEtD,QAAM,OAAO,SAAS;AACtB,SAAO,eAAe,eAAe;EAErC,MAAM,eAAe,WAAW,WAAW,uBAAuB,WAAW,YAAY,cAAc,OAAO,OAAO;AAErH,QAAM,MAAM,GAAG;AAEf,SAAO,QAAQ,KAAK,mBAAmB,OAAO,OAAO,aAAa,GAAG;AACrE,SAAO,QAAQ,sBAAsB;AACrC,UAAQ,KAAK,EAAE;;;mDAEtB"}
@@ -26,7 +26,6 @@ declare class ModuleLoader extends EventEmitter<ModuleLoader.Events> {
26
26
  private emitOrThrow;
27
27
  }
28
28
  declare namespace ModuleLoader {
29
- let globby: typeof globby$1 | null;
30
29
  const fileTypes: string[];
31
30
  interface Config {
32
31
  directories?: string[];
@@ -136,7 +136,7 @@ var ModuleLoader = class ModuleLoader extends EventEmitter {
136
136
  }
137
137
  };
138
138
  (function(_ModuleLoader) {
139
- let globby = _ModuleLoader.globby = null;
139
+ let globby = null;
140
140
  _ModuleLoader.fileTypes = [
141
141
  "js",
142
142
  "mjs",
@@ -1 +1 @@
1
- {"version":3,"file":"ModuleLoader.mjs","names":[],"sources":["../../../src/classes/client/ModuleLoader.ts"],"sourcesContent":["import { type Awaitable } from 'discord.js';\nimport path from 'node:path';\nimport { mkdir, readdir, stat } from 'node:fs/promises';\nimport micromatch from 'micromatch';\nimport { globby, isDynamicPattern } from 'globby';\nimport { CommandType, RecipleError, type Client } from '@reciple/core';\nimport type { AnyModule, AnyModuleData } from '../../helpers/types.js';\nimport { recursiveDefaults } from '@reciple/utils';\nimport { BaseModule } from '../modules/BaseModule.js';\nimport { BaseModuleValidator } from '../validation/BaseModuleValidator.js';\nimport { ModuleType } from '../../helpers/constants.js';\nimport { PostconditionModule } from '../modules/PostconditionModule.js';\nimport { PreconditionModule } from '../modules/PreconditionModule.js';\nimport { EventModule } from '../modules/events/EventModule.js';\nimport { MessageCommandModule } from '../modules/commands/MessageCommandModule.js';\nimport { SlashCommandModule } from '../modules/commands/SlashCommandModule.js';\nimport { ContextMenuCommandModule } from '../modules/commands/ContextMenuCommandModule.js';\nimport { CommandModuleValidator } from '../validation/CommandModuleValidator.js';\nimport { EventModuleValidator } from '../validation/EventModuleValidator.js';\nimport { PreconditionModuleValidator } from '../validation/PreconditionModule.js';\nimport { PostconditionModuleValidator } from '../validation/PostconditionModule.js';\nimport type { Logger } from '@prtty/print';\nimport { EventEmitter } from 'node:events';\nimport { colors } from '@prtty/prtty';\n\nexport class ModuleLoader extends EventEmitter<ModuleLoader.Events> {\n public readonly logger: Logger;\n\n constructor(public readonly client: Client) {\n super();\n\n this.logger = this.client.logger.clone({\n label: 'ModuleLoader'\n });\n }\n\n public async findModules(ignoreErrors: boolean = false): Promise<AnyModule[]> {\n const modulePaths = await ModuleLoader.scanForModulePaths(this.client.config?.modules);\n const modules: AnyModule[] = [];\n\n this.emit('modulesResolving', modulePaths);\n\n for (const path of modulePaths) {\n try {\n this.emit('moduleResolving', path);\n const resolved = await ModuleLoader.resolveModuleFromPath(path);\n\n Object.assign(resolved, { client: this.client, __$filepath: path });\n modules.push(resolved);\n\n this.emit('moduleResolved', resolved);\n } catch (error) {\n if (ignoreErrors) continue;\n\n this.emitOrThrow('moduleResolveError', new RecipleError({\n message: `Failed to load module: ${colors.cyan(path)}`,\n cause: error\n }));\n }\n }\n\n this.emit('modulesResolved', modules);\n return modules;\n }\n\n public static async scanForDirectories(config?: Pick<ModuleLoader.Config, 'directories'|'ignore'> & { cwd?: string; createDirectories?: boolean; }) {\n const cwd = config?.cwd ?? process.cwd();\n\n let scanned: string[] = [];\n let directories: string[] = [];\n\n for (const directory of config?.directories ?? []) {\n if (isDynamicPattern(directory, { cwd })) {\n const matches = await globby(directory, {\n cwd,\n ignore: config?.ignore,\n onlyDirectories: true,\n baseNameMatch: true,\n absolute: true\n });\n\n scanned.push(...matches);\n continue;\n }\n\n scanned.push(path.join(cwd, directory));\n }\n\n for (const directory of scanned) {\n const stats = await stat(directory).catch(() => undefined);\n\n if (!stats && config?.createDirectories !== false) {\n await mkdir(directory, { recursive: true });\n }\n\n directories.push(directory);\n }\n\n return directories;\n }\n\n public static async scanForModulePaths(config?: ModuleLoader.Config & { cwd?: string; createDirectories?: boolean; }): Promise<string[]> {\n const directories = await ModuleLoader.scanForDirectories(config);\n\n let modules: string[] = [];\n\n for (const directory of directories) {\n let files = await readdir(directory);\n\n if (config?.ignore?.length) {\n files = micromatch.not(files, config.ignore, {\n cwd: directory,\n matchBase: true,\n dot: true\n });\n }\n\n files = files.map(f => path.join(directory, f));\n\n for (const file of files) {\n if (config?.filter ? !(await config?.filter(file)) : ModuleLoader.fileTypes.every(type => !file.endsWith(`.${type}`))) continue;\n modules.push(file);\n }\n }\n\n if (config?.sort) modules.sort(config.sort);\n\n return modules;\n }\n\n public static async resolveModuleFromPath(filepath: string, options?: { cwd?: string; }): Promise<AnyModule> {\n const stats = await stat(filepath).catch(() => undefined);\n if (!stats) throw new RecipleError(`Module not found: ${filepath}`);\n\n const data = recursiveDefaults<AnyModule|AnyModuleData|undefined>(await import(`file://${path.resolve(options?.cwd ?? process.cwd(), filepath)}`));\n if (BaseModule.isModule(data)) return data;\n\n if (data && 'moduleType' in data) {\n switch (data?.moduleType) {\n case ModuleType.Command:\n CommandModuleValidator.isValid(data);\n switch (data.type) {\n case CommandType.Message: return MessageCommandModule.from(data);\n case CommandType.Slash: return SlashCommandModule.from(data);\n case CommandType.ContextMenu: return ContextMenuCommandModule.from(data);\n default: throw new RecipleError(`Unknown command type from module: ${colors.cyan(filepath)}`);\n }\n case ModuleType.Event:\n EventModuleValidator.isValid(data);\n return EventModule.from(data);\n case ModuleType.Precondition:\n PreconditionModuleValidator.isValid(data);\n return PreconditionModule.from(data);\n case ModuleType.Postcondition:\n PostconditionModuleValidator.isValid(data);\n return PostconditionModule.from(data);\n default:\n BaseModuleValidator.isValid(data);\n return BaseModule.from(data);\n }\n }\n\n BaseModuleValidator.isValid(data);\n return BaseModule.from(data);\n }\n\n public static async resolveSourceDirectories(options: ModuleLoader.ResolveSourceDirectoryOptions): Promise<string[]> {\n const dir = path.isAbsolute(options.baseUrl) ? options.baseUrl : path.resolve(path.join(options.cwd ?? process.cwd(), options.baseUrl));\n\n const root = path.resolve(path.join(dir, options.rootDir));\n const out = path.resolve(path.join(dir, options.outDir));\n\n return options.directories.map(directory => path.resolve(directory).replace(out, root));\n }\n\n private emitOrThrow<K extends keyof Pick<ModuleLoader.Events, 'moduleResolveError'>>(event: K, error: RecipleError) {\n if (this.client.listenerCount(event) > 0) {\n // @ts-expect-error\n return this.emit(event, error);\n }\n\n throw error;\n }\n}\n\nexport namespace ModuleLoader {\n export let globby: typeof import('globby')|null = null;\n\n export const fileTypes = [\n 'js',\n 'mjs',\n 'jsx'\n ];\n\n export interface Config {\n directories?: string[];\n ignore?: string[];\n filter?: (filepath: string) => Awaitable<boolean>;\n sort?: (a: string, b: string) => number;\n }\n\n export interface Events {\n moduleResolveError: [error: RecipleError];\n moduleResolved: [module: AnyModule];\n moduleResolving: [filepath: string];\n modulesResolved: [modules: AnyModule[]];\n modulesResolving: [files: string[]];\n }\n\n export interface ResolveSourceDirectoryOptions {\n directories: string[];\n baseUrl: string;\n rootDir: string;\n outDir: string;\n cwd?: string;\n }\n\n export async function getGlobby(): Promise<typeof import('globby')> {\n if (globby) return globby;\n\n return globby = await import('globby');\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"ModuleLoader.mjs","names":[],"sources":["../../../src/classes/client/ModuleLoader.ts"],"sourcesContent":["import { type Awaitable } from 'discord.js';\nimport path from 'node:path';\nimport { mkdir, readdir, stat } from 'node:fs/promises';\nimport micromatch from 'micromatch';\nimport { globby, isDynamicPattern } from 'globby';\nimport { CommandType, RecipleError, type Client } from '@reciple/core';\nimport type { AnyModule, AnyModuleData } from '../../helpers/types.js';\nimport { recursiveDefaults } from '@reciple/utils';\nimport { BaseModule } from '../modules/BaseModule.js';\nimport { BaseModuleValidator } from '../validation/BaseModuleValidator.js';\nimport { ModuleType } from '../../helpers/constants.js';\nimport { PostconditionModule } from '../modules/PostconditionModule.js';\nimport { PreconditionModule } from '../modules/PreconditionModule.js';\nimport { EventModule } from '../modules/events/EventModule.js';\nimport { MessageCommandModule } from '../modules/commands/MessageCommandModule.js';\nimport { SlashCommandModule } from '../modules/commands/SlashCommandModule.js';\nimport { ContextMenuCommandModule } from '../modules/commands/ContextMenuCommandModule.js';\nimport { CommandModuleValidator } from '../validation/CommandModuleValidator.js';\nimport { EventModuleValidator } from '../validation/EventModuleValidator.js';\nimport { PreconditionModuleValidator } from '../validation/PreconditionModule.js';\nimport { PostconditionModuleValidator } from '../validation/PostconditionModule.js';\nimport type { Logger } from '@prtty/print';\nimport { EventEmitter } from 'node:events';\nimport { colors } from '@prtty/prtty';\n\nexport class ModuleLoader extends EventEmitter<ModuleLoader.Events> {\n public readonly logger: Logger;\n\n constructor(public readonly client: Client) {\n super();\n\n this.logger = this.client.logger.clone({\n label: 'ModuleLoader'\n });\n }\n\n public async findModules(ignoreErrors: boolean = false): Promise<AnyModule[]> {\n const modulePaths = await ModuleLoader.scanForModulePaths(this.client.config?.modules);\n const modules: AnyModule[] = [];\n\n this.emit('modulesResolving', modulePaths);\n\n for (const path of modulePaths) {\n try {\n this.emit('moduleResolving', path);\n const resolved = await ModuleLoader.resolveModuleFromPath(path);\n\n Object.assign(resolved, { client: this.client, __$filepath: path });\n modules.push(resolved);\n\n this.emit('moduleResolved', resolved);\n } catch (error) {\n if (ignoreErrors) continue;\n\n this.emitOrThrow('moduleResolveError', new RecipleError({\n message: `Failed to load module: ${colors.cyan(path)}`,\n cause: error\n }));\n }\n }\n\n this.emit('modulesResolved', modules);\n return modules;\n }\n\n public static async scanForDirectories(config?: Pick<ModuleLoader.Config, 'directories'|'ignore'> & { cwd?: string; createDirectories?: boolean; }) {\n const cwd = config?.cwd ?? process.cwd();\n\n let scanned: string[] = [];\n let directories: string[] = [];\n\n for (const directory of config?.directories ?? []) {\n if (isDynamicPattern(directory, { cwd })) {\n const matches = await globby(directory, {\n cwd,\n ignore: config?.ignore,\n onlyDirectories: true,\n baseNameMatch: true,\n absolute: true\n });\n\n scanned.push(...matches);\n continue;\n }\n\n scanned.push(path.join(cwd, directory));\n }\n\n for (const directory of scanned) {\n const stats = await stat(directory).catch(() => undefined);\n\n if (!stats && config?.createDirectories !== false) {\n await mkdir(directory, { recursive: true });\n }\n\n directories.push(directory);\n }\n\n return directories;\n }\n\n public static async scanForModulePaths(config?: ModuleLoader.Config & { cwd?: string; createDirectories?: boolean; }): Promise<string[]> {\n const directories = await ModuleLoader.scanForDirectories(config);\n\n let modules: string[] = [];\n\n for (const directory of directories) {\n let files = await readdir(directory);\n\n if (config?.ignore?.length) {\n files = micromatch.not(files, config.ignore, {\n cwd: directory,\n matchBase: true,\n dot: true\n });\n }\n\n files = files.map(f => path.join(directory, f));\n\n for (const file of files) {\n if (config?.filter ? !(await config?.filter(file)) : ModuleLoader.fileTypes.every(type => !file.endsWith(`.${type}`))) continue;\n modules.push(file);\n }\n }\n\n if (config?.sort) modules.sort(config.sort);\n\n return modules;\n }\n\n public static async resolveModuleFromPath(filepath: string, options?: { cwd?: string; }): Promise<AnyModule> {\n const stats = await stat(filepath).catch(() => undefined);\n if (!stats) throw new RecipleError(`Module not found: ${filepath}`);\n\n const data = recursiveDefaults<AnyModule|AnyModuleData|undefined>(await import(`file://${path.resolve(options?.cwd ?? process.cwd(), filepath)}`));\n if (BaseModule.isModule(data)) return data;\n\n if (data && 'moduleType' in data) {\n switch (data?.moduleType) {\n case ModuleType.Command:\n CommandModuleValidator.isValid(data);\n switch (data.type) {\n case CommandType.Message: return MessageCommandModule.from(data);\n case CommandType.Slash: return SlashCommandModule.from(data);\n case CommandType.ContextMenu: return ContextMenuCommandModule.from(data);\n default: throw new RecipleError(`Unknown command type from module: ${colors.cyan(filepath)}`);\n }\n case ModuleType.Event:\n EventModuleValidator.isValid(data);\n return EventModule.from(data);\n case ModuleType.Precondition:\n PreconditionModuleValidator.isValid(data);\n return PreconditionModule.from(data);\n case ModuleType.Postcondition:\n PostconditionModuleValidator.isValid(data);\n return PostconditionModule.from(data);\n default:\n BaseModuleValidator.isValid(data);\n return BaseModule.from(data);\n }\n }\n\n BaseModuleValidator.isValid(data);\n return BaseModule.from(data);\n }\n\n public static async resolveSourceDirectories(options: ModuleLoader.ResolveSourceDirectoryOptions): Promise<string[]> {\n const dir = path.isAbsolute(options.baseUrl) ? options.baseUrl : path.resolve(path.join(options.cwd ?? process.cwd(), options.baseUrl));\n\n const root = path.resolve(path.join(dir, options.rootDir));\n const out = path.resolve(path.join(dir, options.outDir));\n\n return options.directories.map(directory => path.resolve(directory).replace(out, root));\n }\n\n private emitOrThrow<K extends keyof Pick<ModuleLoader.Events, 'moduleResolveError'>>(event: K, error: RecipleError) {\n if (this.client.listenerCount(event) > 0) {\n // @ts-expect-error\n return this.emit(event, error);\n }\n\n throw error;\n }\n}\n\nexport namespace ModuleLoader {\n let globby: typeof import('globby')|null = null;\n\n export const fileTypes = [\n 'js',\n 'mjs',\n 'jsx'\n ];\n\n export interface Config {\n directories?: string[];\n ignore?: string[];\n filter?: (filepath: string) => Awaitable<boolean>;\n sort?: (a: string, b: string) => number;\n }\n\n export interface Events {\n moduleResolveError: [error: RecipleError];\n moduleResolved: [module: AnyModule];\n moduleResolving: [filepath: string];\n modulesResolved: [modules: AnyModule[]];\n modulesResolving: [files: string[]];\n }\n\n export interface ResolveSourceDirectoryOptions {\n directories: string[];\n baseUrl: string;\n rootDir: string;\n outDir: string;\n cwd?: string;\n }\n\n export async function getGlobby(): Promise<typeof import('globby')> {\n if (globby) return globby;\n\n return globby = await import('globby');\n }\n}\n"],"mappings":"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"}
@@ -75,6 +75,8 @@ declare class CommandModuleValidator extends Validator {
75
75
  execute: Function;
76
76
  }>>;
77
77
  static resolvable: _sapphire_shapeshift0.UnionValidator<_sapphire_shapeshift0.UndefinedToOptional<{
78
+ toJSON: Function;
79
+ }> | _sapphire_shapeshift0.UndefinedToOptional<{
78
80
  id: string | undefined;
79
81
  moduleType: ModuleType | undefined;
80
82
  onEnable: Function | undefined;
@@ -107,8 +109,6 @@ declare class CommandModuleValidator extends Validator {
107
109
  disabledPreconditions: string[] | undefined;
108
110
  disabledPostconditions: string[] | undefined;
109
111
  execute: Function;
110
- }> | _sapphire_shapeshift0.UndefinedToOptional<{
111
- toJSON: Function;
112
112
  }>>;
113
113
  static isValid(value: unknown): asserts value is AnyCommandModuleData;
114
114
  }
package/dist/package.mjs CHANGED
@@ -1,7 +1,7 @@
1
1
  //#region package.json
2
2
  var package_default = {
3
3
  name: "reciple",
4
- version: "10.0.30",
4
+ version: "10.0.31",
5
5
  license: "LGPL-3.0-only",
6
6
  description: "The CLI for reciple",
7
7
  module: "./dist/index.mjs",
@@ -58,7 +58,7 @@ var package_default = {
58
58
  "@types/micromatch": "^4.0.10",
59
59
  "@types/node": "catalog:",
60
60
  "nodemon": "^3.1.14",
61
- "rolldown": "^1.0.0-rc.5",
61
+ "rolldown": "^1.0.0-rc.6",
62
62
  "typescript": "catalog:"
63
63
  },
64
64
  peerDependencies: {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "reciple",
3
- "version": "10.0.30",
3
+ "version": "10.0.31",
4
4
  "license": "LGPL-3.0-only",
5
5
  "description": "The CLI for reciple",
6
6
  "module": "./dist/index.mjs",
@@ -37,8 +37,8 @@
37
37
  "dependencies": {
38
38
  "@clack/prompts": "^1.0.1",
39
39
  "@dotenvx/dotenvx": "^1.52.0",
40
- "@prtty/print": "^1.1.2",
41
- "@prtty/prtty": "^1.1.1",
40
+ "@prtty/print": "^1.1.3",
41
+ "@prtty/prtty": "^1.1.2",
42
42
  "@reciple/utils": "^10.0.1",
43
43
  "@sapphire/shapeshift": "^4.0.0",
44
44
  "@sapphire/snowflake": "^3.5.5",
@@ -55,9 +55,9 @@
55
55
  "devDependencies": {
56
56
  "@reciple/jsx": "^10.0.8",
57
57
  "@types/micromatch": "^4.0.10",
58
- "@types/node": "^25.3.1",
58
+ "@types/node": "^25.3.2",
59
59
  "nodemon": "^3.1.14",
60
- "rolldown": "^1.0.0-rc.5",
60
+ "rolldown": "^1.0.0-rc.6",
61
61
  "typescript": "^5.9.3"
62
62
  },
63
63
  "peerDependencies": {