Skip to content

Commit 564ffaf

Browse files
committed
feat: Introduce middleware priority system with a default of 100 and range validation, updating related classes and tests.
1 parent 98c6011 commit 564ffaf

File tree

8 files changed

+39
-13
lines changed

8 files changed

+39
-13
lines changed

CHANGELOG.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,14 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8-
## [0.13.2] - 2026-03-24
8+
## [0.14.0] - 2026-03-24
9+
10+
### Breaking Changes
11+
- Middleware default priority changed from `0` to `100` per PROTOCOL_SPEC §11.2. Middleware without explicit priority will now execute before priority-0 middleware.
912

1013
### Added
1114
- **Middleware priority**`Middleware` base class now accepts `priority: number` (default 0). Higher priority executes first; equal priority preserves registration order. `BeforeMiddleware` and `AfterMiddleware` adapters also accept `priority`.
15+
- **Priority range validation**`RangeError` thrown for values outside 0-1000
1216

1317
## [0.13.1] - 2026-03-22
1418

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "apcore-js",
3-
"version": "0.13.2",
3+
"version": "0.14.0",
44
"description": "AI-Perceivable Core — schema-driven module standard",
55
"type": "module",
66
"main": "./dist/index.js",

src/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,4 +160,4 @@ export type { UsageRecord, CallerUsageSummary, HourlyBucket, ModuleUsageSummary,
160160
export { TraceContext } from './trace-context.js';
161161
export type { TraceParent } from './trace-context.js';
162162

163-
export const VERSION = '0.13.2';
163+
export const VERSION = '0.14.0';

src/middleware/adapters.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ export type AfterCallback = (
2121
export class BeforeMiddleware extends Middleware {
2222
private _callback: BeforeCallback;
2323

24-
constructor(callback: BeforeCallback, priority: number = 0) {
24+
constructor(callback: BeforeCallback, priority: number = 100) {
2525
super(priority);
2626
this._callback = callback;
2727
}
@@ -38,7 +38,7 @@ export class BeforeMiddleware extends Middleware {
3838
export class AfterMiddleware extends Middleware {
3939
private _callback: AfterCallback;
4040

41-
constructor(callback: AfterCallback, priority: number = 0) {
41+
constructor(callback: AfterCallback, priority: number = 100) {
4242
super(priority);
4343
this._callback = callback;
4444
}

src/middleware/base.ts

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,12 @@ export class Middleware {
1111
*/
1212
readonly priority: number;
1313

14-
constructor(priority: number = 0) {
14+
constructor(priority: number = 100) {
15+
if (priority < 0 || priority > 1000) {
16+
throw new RangeError(
17+
`priority must be between 0 and 1000, got ${priority}`,
18+
);
19+
}
1520
this.priority = priority;
1621
}
1722

src/middleware/logging.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ export class LoggingMiddleware extends Middleware {
3131
logOutputs?: boolean;
3232
logErrors?: boolean;
3333
}) {
34-
super();
34+
super(700);
3535
this._logger = options?.logger ?? defaultLogger;
3636
this._logInputs = options?.logInputs ?? true;
3737
this._logOutputs = options?.logOutputs ?? true;

tests/test-logging-middleware.test.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,13 @@ describe('LoggingMiddleware', () => {
128128
});
129129
});
130130

131+
describe('priority', () => {
132+
it('has priority 700 (logging range)', () => {
133+
const mw = new LoggingMiddleware();
134+
expect(mw.priority).toBe(700);
135+
});
136+
});
137+
131138
describe('defaults', () => {
132139
it('uses default logger when none provided', () => {
133140
const mw = new LoggingMiddleware();

tests/test-middleware-manager.test.ts

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ function makeContext(): Context {
1010
class TaggingMiddleware extends Middleware {
1111
readonly tag: string;
1212

13-
constructor(tag: string, priority: number = 0) {
13+
constructor(tag: string, priority: number = 100) {
1414
super(priority);
1515
this.tag = tag;
1616
}
@@ -205,10 +205,10 @@ describe('MiddlewareManager', () => {
205205
expect(result['trail']).toBe('FirstSecondThird');
206206
});
207207

208-
it('default priority (0) middleware is ordered after explicit priority', () => {
208+
it('lower priority middleware is ordered after higher priority', () => {
209209
const mgr = new MiddlewareManager();
210-
mgr.add(new TaggingMiddleware('Default'));
211-
mgr.add(new TaggingMiddleware('Prioritized', 1));
210+
mgr.add(new TaggingMiddleware('Default', 100));
211+
mgr.add(new TaggingMiddleware('Prioritized', 101));
212212
const ctx = makeContext();
213213
const [result] = mgr.executeBefore('mod.test', { trail: '' }, ctx);
214214
expect(result['trail']).toBe('PrioritizedDefault');
@@ -225,9 +225,19 @@ describe('MiddlewareManager', () => {
225225
expect(result['trail']).toBe('LowMidHigh');
226226
});
227227

228-
it('Middleware base class defaults to priority 0', () => {
228+
it('Middleware base class defaults to priority 100', () => {
229229
const mw = new Middleware();
230-
expect(mw.priority).toBe(0);
230+
expect(mw.priority).toBe(100);
231+
});
232+
233+
it('throws RangeError for priority below 0', () => {
234+
expect(() => new Middleware(-1)).toThrow(RangeError);
235+
expect(() => new Middleware(-1)).toThrow('priority must be between 0 and 1000');
236+
});
237+
238+
it('throws RangeError for priority above 1000', () => {
239+
expect(() => new Middleware(1001)).toThrow(RangeError);
240+
expect(() => new Middleware(1001)).toThrow('priority must be between 0 and 1000');
231241
});
232242

233243
it('snapshot reflects priority-sorted order', () => {

0 commit comments

Comments
 (0)