meocord 4.1.1 → 4.1.2

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/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # meocord
2
2
 
3
+ ## 4.1.2
4
+
5
+ ### Patch Changes
6
+
7
+ - [#454](https://github.com/meocord/meocord/pull/454) [`1f71fe1`](https://github.com/meocord/meocord/commit/1f71fe12b96c339bf3e1f19f714f24ebd8e7e853) Thanks [@l7aromeo](https://github.com/l7aromeo)! - A mock interaction's type guards, such as `isButton()` and `isRepliable()`, and its `inGuild()`, `inCachedGuild()` and `inRawGuild()` keep answering as discord.js does after `resetAllMocks()`. They returned `undefined` after a reset, so a mock made once for several tests, such as in `beforeAll`, failed every type check after the first test in a project that resets between tests, as a generated one does.
8
+
3
9
  ## 4.1.1
4
10
 
5
11
  ### Patch Changes
package/README.md CHANGED
@@ -15,17 +15,17 @@
15
15
 
16
16
  If you know NestJS, the shape will feel familiar.
17
17
 
18
- **Documentation:** [meocord.dev](https://meocord.dev/docs/4.1) · [Getting started](https://meocord.dev/docs/4.1/getting-started) · [API reference](https://meocord.dev/docs/4.1/api) · [Upgrading to 4.1](https://meocord.dev/docs/4.1/migrating) · [Changelog](https://meocord.dev/docs/4.1/changelog)
18
+ **Documentation:** [meocord.dev](https://meocord.dev/docs/latest) · [Getting started](https://meocord.dev/docs/latest/getting-started) · [API reference](https://meocord.dev/docs/latest/api) · [Upgrading to 4.1](https://meocord.dev/docs/latest/migrating) · [Changelog](https://meocord.dev/docs/latest/changelog)
19
19
 
20
20
  ## Features
21
21
 
22
- - **Controllers for every interaction** — [slash commands](https://meocord.dev/docs/4.1/slash-commands) and their subcommands, autocomplete, [buttons, selects and modals](https://meocord.dev/docs/4.1/components) routed by customId, context menus, message commands and reactions, each a decorated method.
23
- - **Message commands** — [commands typed in chat](https://meocord.dev/docs/4.1/message-commands), from a pattern such as `ban {target:member} {reason...?}`: typed params, flags and lists, a usage reply when a message does not fit, and built-in help.
24
- - **A request pipeline** — [guards](https://meocord.dev/docs/4.1/guards) decide whether a handler runs, interceptors wrap it, validation and pipes check its input, [cooldowns](https://meocord.dev/docs/4.1/cooldowns) limit how often it runs, and exception filters decide what the user is told.
22
+ - **Controllers for every interaction** — [slash commands](https://meocord.dev/docs/latest/slash-commands) and their subcommands, autocomplete, [buttons, selects and modals](https://meocord.dev/docs/latest/components) routed by customId, context menus, message commands and reactions, each a decorated method.
23
+ - **Message commands** — [commands typed in chat](https://meocord.dev/docs/latest/message-commands), from a pattern such as `ban {target:member} {reason...?}`: typed params, flags and lists, a usage reply when a message does not fit, and built-in help.
24
+ - **A request pipeline** — [guards](https://meocord.dev/docs/latest/guards) decide whether a handler runs, interceptors wrap it, validation and pipes check its input, [cooldowns](https://meocord.dev/docs/latest/cooldowns) limit how often it runs, and exception filters decide what the user is told.
25
25
  - **Dependency injection** — services, providers and lifecycle hooks, wired into controllers with no manual instantiation.
26
- - **Answers that fit the interaction** — `respond(interaction)` replies, edits or follows up from whatever state the interaction is in, styled by a presenter and a [theme](https://meocord.dev/docs/4.1/theming).
27
- - **Testing without Discord** — `meocord/testing` runs a handler through its whole pipeline, with [mocks](https://meocord.dev/docs/4.1/mocks) for every interaction type.
28
- - **A CLI** — `meocord create`, `build`, `start`, `register` and `generate`, with Rsbuild builds for development and production, sharding, and [self-contained builds](https://meocord.dev/docs/4.1/self-contained-builds) that deploy without `node_modules`.
26
+ - **Answers that fit the interaction** — `respond(interaction)` replies, edits or follows up from whatever state the interaction is in, styled by a presenter and a [theme](https://meocord.dev/docs/latest/theming).
27
+ - **Testing without Discord** — `meocord/testing` runs a handler through its whole pipeline, with [mocks](https://meocord.dev/docs/latest/mocks) for every interaction type.
28
+ - **A CLI** — `meocord create`, `build`, `start`, `register` and `generate`, with Rsbuild builds for development and production, sharding, and [self-contained builds](https://meocord.dev/docs/latest/self-contained-builds) that deploy without `node_modules`.
29
29
 
30
30
  ## Getting started
31
31
 
@@ -38,7 +38,7 @@ cp .env.example .env # then put your bot token in DISCORD_TOKEN
38
38
  npx meocord start --dev # development, restarting on every change
39
39
  ```
40
40
 
41
- The new project comes with a sample of each controller type, a guard, a presenter, a service and a spec for each. [Getting started](https://meocord.dev/docs/4.1/getting-started) walks through it, and [Your first command](https://meocord.dev/docs/4.1/first-command) adds one.
41
+ The new project comes with a sample of each controller type, a guard, a presenter, a service and a spec for each. [Getting started](https://meocord.dev/docs/latest/getting-started) walks through it, and [Your first command](https://meocord.dev/docs/latest/first-command) adds one.
42
42
 
43
43
  ## Example
44
44
 
@@ -77,18 +77,18 @@ export class GreetController {
77
77
  export default class App {}
78
78
  ```
79
79
 
80
- The command's options arrive as the handler's second argument. [Slash commands](https://meocord.dev/docs/4.1/slash-commands) covers options, subcommands and registration.
80
+ The command's options arrive as the handler's second argument. [Slash commands](https://meocord.dev/docs/latest/slash-commands) covers options, subcommands and registration.
81
81
 
82
82
  ## Documentation
83
83
 
84
- Everything else is on [meocord.dev](https://meocord.dev/docs/4.1), for each version:
84
+ Everything else is on [meocord.dev](https://meocord.dev/docs/latest), for each version:
85
85
 
86
- | To | Read |
87
- | ----------------------------------- | --------------------------------------------------------------- |
88
- | Learn MeoCord from the start | [Getting started](https://meocord.dev/docs/4.1/getting-started) |
89
- | Look up a decorator, type or helper | [API reference](https://meocord.dev/docs/4.1/api) |
90
- | Upgrade from 4.0, or from 3.x | [Upgrading](https://meocord.dev/docs/4.1/migrating) |
91
- | See what changed in each release | [Changelog](https://meocord.dev/docs/4.1/changelog) |
86
+ | To | Read |
87
+ | ----------------------------------- | ------------------------------------------------------------------ |
88
+ | Learn MeoCord from the start | [Getting started](https://meocord.dev/docs/latest/getting-started) |
89
+ | Look up a decorator, type or helper | [API reference](https://meocord.dev/docs/latest/api) |
90
+ | Upgrade from 4.0, or from 3.x | [Upgrading](https://meocord.dev/docs/latest/migrating) |
91
+ | See what changed in each release | [Changelog](https://meocord.dev/docs/latest/changelog) |
92
92
 
93
93
  ## Support
94
94
 
@@ -108,28 +108,28 @@ These sections moved to meocord.dev. Their headings stay here so that links from
108
108
 
109
109
  ### Theming
110
110
 
111
- [Theming](https://meocord.dev/docs/4.1/theming) on meocord.dev.
111
+ [Theming](https://meocord.dev/docs/latest/theming) on meocord.dev.
112
112
 
113
113
  ### Themes per server and per user
114
114
 
115
- [Themes per server and per user](https://meocord.dev/docs/4.1/theming#per-server-and-per-user) on meocord.dev.
115
+ [Themes per server and per user](https://meocord.dev/docs/latest/theming#per-server-and-per-user) on meocord.dev.
116
116
 
117
117
  ### Adding tokens of your own
118
118
 
119
- [Adding tokens of your own](https://meocord.dev/docs/4.1/theming#adding-tokens-of-your-own) on meocord.dev.
119
+ [Adding tokens of your own](https://meocord.dev/docs/latest/theming#adding-tokens-of-your-own) on meocord.dev.
120
120
 
121
121
  ### Where calls are counted
122
122
 
123
- [Where calls are counted](https://meocord.dev/docs/4.1/cooldowns#where-calls-are-counted) on meocord.dev.
123
+ [Where calls are counted](https://meocord.dev/docs/latest/cooldowns#where-calls-are-counted) on meocord.dev.
124
124
 
125
125
  ### Store recipes
126
126
 
127
- [Cooldown stores](https://meocord.dev/docs/4.1/recipes/cooldown-stores) on meocord.dev.
127
+ [Cooldown stores](https://meocord.dev/docs/latest/recipes/cooldown-stores) on meocord.dev.
128
128
 
129
129
  ### Stack traces
130
130
 
131
- [Stack traces](https://meocord.dev/docs/4.1/configuration#stack-traces) on meocord.dev.
131
+ [Stack traces](https://meocord.dev/docs/latest/configuration#stack-traces) on meocord.dev.
132
132
 
133
133
  ### Running tests
134
134
 
135
- [Running tests](https://meocord.dev/docs/4.1/testing#running-tests) on meocord.dev.
135
+ [Running tests](https://meocord.dev/docs/latest/testing#running-tests) on meocord.dev.
@@ -1325,13 +1325,10 @@ function createMockInteraction(Class, props) {
1325
1325
  instance[key] = value;
1326
1326
  }
1327
1327
  }
1328
- // Wire each type guard as a mock fn calling the real prototype implementation.
1329
- // Correct by default; overridable per test via .mockReturnValue().
1328
+ // Each type guard runs the real prototype implementation, as the mock's own, so a reset keeps it; a test may override it
1330
1329
  for (const name of TYPE_GUARD_METHODS){
1331
1330
  const method = findPrototypeMethod(instance, name);
1332
- if (method !== null) {
1333
- stubs.set(name, createMockFn().mockImplementation(()=>method.call(instance)));
1334
- }
1331
+ if (method !== null) stubs.set(name, createMockFn(()=>method.call(instance)));
1335
1332
  }
1336
1333
  // Guild checks read the mock's own data, since discord.js resolves `guild` through a client the
1337
1334
  // mock lacks: a guildId is a guild, a guild object with it a cached one, neither a DM. A member
@@ -1344,7 +1341,7 @@ function createMockInteraction(Class, props) {
1344
1341
  inRawGuild: ()=>Boolean(own('guildId') && !own('guild') && hasMember())
1345
1342
  };
1346
1343
  for (const [name, check] of Object.entries(guildChecks)){
1347
- if (findPrototypeMethod(instance, name) !== null) stubs.set(name, createMockFn().mockImplementation(check));
1344
+ if (findPrototypeMethod(instance, name) !== null) stubs.set(name, createMockFn(check));
1348
1345
  }
1349
1346
  // Set up reply state machine for repliable interactions
1350
1347
  const isRepliableMethod = findPrototypeMethod(instance, 'isRepliable');
package/dist/cli.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "schemaVersion": 1,
3
- "meocordVersion": "4.1.1",
3
+ "meocordVersion": "4.1.2",
4
4
  "name": "meocord",
5
5
  "description": "CLI for managing the MeoCord application",
6
6
  "usage": "[options] [command]",
@@ -1,4 +1,4 @@
1
- var version = "4.1.1";
1
+ var version = "4.1.2";
2
2
  var engines = {
3
3
  node: ">=22.13"
4
4
  };
@@ -680,13 +680,10 @@ function createMockInteraction(Class, props) {
680
680
  instance[key] = value;
681
681
  }
682
682
  }
683
- // Wire each type guard as a mock fn calling the real prototype implementation.
684
- // Correct by default; overridable per test via .mockReturnValue().
683
+ // Each type guard runs the real prototype implementation, as the mock's own, so a reset keeps it; a test may override it
685
684
  for (const name of TYPE_GUARD_METHODS){
686
685
  const method = findPrototypeMethod(instance, name);
687
- if (method !== null) {
688
- stubs.set(name, createMockFn().mockImplementation(()=>method.call(instance)));
689
- }
686
+ if (method !== null) stubs.set(name, createMockFn(()=>method.call(instance)));
690
687
  }
691
688
  // Guild checks read the mock's own data, since discord.js resolves `guild` through a client the
692
689
  // mock lacks: a guildId is a guild, a guild object with it a cached one, neither a DM. A member
@@ -699,7 +696,7 @@ function createMockInteraction(Class, props) {
699
696
  inRawGuild: ()=>Boolean(own('guildId') && !own('guild') && hasMember())
700
697
  };
701
698
  for (const [name, check] of Object.entries(guildChecks)){
702
- if (findPrototypeMethod(instance, name) !== null) stubs.set(name, createMockFn().mockImplementation(check));
699
+ if (findPrototypeMethod(instance, name) !== null) stubs.set(name, createMockFn(check));
703
700
  }
704
701
  // Set up reply state machine for repliable interactions
705
702
  const isRepliableMethod = findPrototypeMethod(instance, 'isRepliable');
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "meocord",
3
3
  "description": "Decorator-based framework for Discord bots on discord.js, with dependency injection, guards, a CLI and a testing toolkit.",
4
- "version": "4.1.1",
4
+ "version": "4.1.2",
5
5
  "type": "module",
6
6
  "engines": {
7
7
  "node": ">=22.13"