Skip to content

Commit c5e3948

Browse files
Claudehotlong
andauthored
fix: resolve CI test failures in spec and objectql packages
- Fix spec test: update test expectation to account for defaultDatasource being added during validation - Fix objectql SchemaRegistry mock: add missing getObjectOwner method to test mock - Fix objectql engine: use object FQN when calling getObjectOwner to ensure correct ownership lookup - Fix objectql datasource-mapping tests: rename SchemaRegistry.clear() to reset() and engine.create() to insert() Agent-Logs-Url: https://github.com/objectstack-ai/framework/sessions/ecd04cb1-085f-40cc-be05-b236c08a82eb Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
1 parent ea55ea8 commit c5e3948

File tree

6 files changed

+85
-11
lines changed

6 files changed

+85
-11
lines changed

content/docs/references/api/auth-endpoints.mdx

Lines changed: 55 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,8 @@ the canonical API contract.
2424
## TypeScript Usage
2525

2626
```typescript
27-
import { AuthEndpoint } from '@objectstack/spec/api';
28-
import type { AuthEndpoint } from '@objectstack/spec/api';
27+
import { AuthEndpoint, AuthFeaturesConfig, AuthProviderInfo, EmailPasswordConfigPublic, GetAuthConfigResponse } from '@objectstack/spec/api';
28+
import type { AuthEndpoint, AuthFeaturesConfig, AuthProviderInfo, EmailPasswordConfigPublic, GetAuthConfigResponse } from '@objectstack/spec/api';
2929

3030
// Validate data
3131
const result = AuthEndpoint.parse(data);
@@ -51,3 +51,56 @@ const result = AuthEndpoint.parse(data);
5151

5252
---
5353

54+
## AuthFeaturesConfig
55+
56+
### Properties
57+
58+
| Property | Type | Required | Description |
59+
| :--- | :--- | :--- | :--- |
60+
| **twoFactor** | `boolean` || Two-factor authentication enabled |
61+
| **passkeys** | `boolean` || Passkey/WebAuthn support enabled |
62+
| **magicLink** | `boolean` || Magic link login enabled |
63+
| **organization** | `boolean` || Multi-tenant organization support enabled |
64+
65+
66+
---
67+
68+
## AuthProviderInfo
69+
70+
### Properties
71+
72+
| Property | Type | Required | Description |
73+
| :--- | :--- | :--- | :--- |
74+
| **id** | `string` || Provider ID (e.g., google, github, microsoft) |
75+
| **name** | `string` || Display name (e.g., Google, GitHub) |
76+
| **enabled** | `boolean` || Whether this provider is enabled |
77+
78+
79+
---
80+
81+
## EmailPasswordConfigPublic
82+
83+
### Properties
84+
85+
| Property | Type | Required | Description |
86+
| :--- | :--- | :--- | :--- |
87+
| **enabled** | `boolean` || Whether email/password auth is enabled |
88+
| **disableSignUp** | `boolean` | optional | Whether new user registration is disabled |
89+
| **requireEmailVerification** | `boolean` | optional | Whether email verification is required |
90+
91+
92+
---
93+
94+
## GetAuthConfigResponse
95+
96+
### Properties
97+
98+
| Property | Type | Required | Description |
99+
| :--- | :--- | :--- | :--- |
100+
| **emailPassword** | `Object` || Email/password authentication config |
101+
| **socialProviders** | `Object[]` || Available social/OAuth providers |
102+
| **features** | `Object` || Enabled authentication features |
103+
104+
105+
---
106+

content/docs/references/kernel/manifest.mdx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ const result = Manifest.parse(data);
6161
| :--- | :--- | :--- | :--- |
6262
| **id** | `string` | ✅ | Unique package identifier (reverse domain style) |
6363
| **namespace** | `string` | optional | Short namespace identifier for metadata scoping (e.g. "crm", "todo") |
64+
| **defaultDatasource** | `string` | ✅ | Default datasource for all objects in this package |
6465
| **version** | `string` | ✅ | Package version (semantic versioning) |
6566
| **type** | `Enum<'plugin' \| 'ui' \| 'driver' \| 'server' \| 'app' \| 'theme' \| 'agent' \| 'objectql' \| 'module' \| 'gateway' \| 'adapter'>` | ✅ | Type of package |
6667
| **name** | `string` | ✅ | Human-readable package name |

packages/objectql/src/datasource-mapping.test.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ describe('DatasourceMapping', () => {
3535

3636
beforeEach(() => {
3737
engine = new ObjectQL();
38-
SchemaRegistry.clear();
38+
SchemaRegistry.reset();
3939
});
4040

4141
it('should route objects by namespace', async () => {
@@ -62,7 +62,7 @@ describe('DatasourceMapping', () => {
6262
);
6363

6464
// Test that it uses memory driver
65-
const result = await engine.create('account', { name: 'Test Account' });
65+
const result = await engine.insert('account', { name: 'Test Account' });
6666
expect(result).toBeDefined();
6767
expect(result.name).toBe('Test Account');
6868
});
@@ -91,7 +91,7 @@ describe('DatasourceMapping', () => {
9191
'own'
9292
);
9393

94-
const result = await engine.create('sys_user', { username: 'admin' });
94+
const result = await engine.insert('sys_user', { username: 'admin' });
9595
expect(result).toBeDefined();
9696
});
9797

@@ -119,7 +119,7 @@ describe('DatasourceMapping', () => {
119119
);
120120

121121
// Should use turso (priority 50) not memory (priority 100)
122-
const result = await engine.create('account', { name: 'Test' });
122+
const result = await engine.insert('account', { name: 'Test' });
123123
expect(result).toBeDefined();
124124
});
125125

@@ -147,7 +147,7 @@ describe('DatasourceMapping', () => {
147147
);
148148

149149
// Should use memory (default)
150-
const result = await engine.create('task', { title: 'Do something' });
150+
const result = await engine.insert('task', { title: 'Do something' });
151151
expect(result).toBeDefined();
152152
});
153153

@@ -175,7 +175,7 @@ describe('DatasourceMapping', () => {
175175
);
176176

177177
// Should use turso (explicit) not memory (mapping)
178-
const result = await engine.create('account', { name: 'Test' });
178+
const result = await engine.insert('account', { name: 'Test' });
179179
expect(result).toBeDefined();
180180
});
181181
});

packages/objectql/src/engine.test.ts

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,26 @@ import type { IDataDriver } from '@objectstack/spec/contracts';
66
// Mock the SchemaRegistry to avoid side effects between tests
77
vi.mock('./registry', () => {
88
const mockObjects = new Map();
9+
const mockContributors = new Map();
910
return {
1011
SchemaRegistry: {
1112
getObject: vi.fn((name) => mockObjects.get(name)),
1213
resolveObject: vi.fn((name) => mockObjects.get(name)),
1314
registerObject: vi.fn((obj, packageId, namespace, ownership, priority) => {
1415
const fqn = namespace ? `${namespace}__${obj.name}` : obj.name;
1516
mockObjects.set(fqn, { ...obj, name: fqn });
17+
// Also track contributors for getObjectOwner
18+
if (!mockContributors.has(fqn)) {
19+
mockContributors.set(fqn, []);
20+
}
21+
const contributors = mockContributors.get(fqn);
22+
contributors.push({ packageId, namespace, ownership, priority, definition: obj });
1623
return fqn;
1724
}),
25+
getObjectOwner: vi.fn((fqn) => {
26+
const contributors = mockContributors.get(fqn);
27+
return contributors?.find(c => c.ownership === 'own');
28+
}),
1829
registerNamespace: vi.fn(),
1930
registerKind: vi.fn(),
2031
registerItem: vi.fn(),
@@ -25,7 +36,10 @@ vi.mock('./registry', () => {
2536
enabled: true,
2637
installedAt: new Date().toISOString(),
2738
})),
28-
reset: vi.fn(() => mockObjects.clear()),
39+
reset: vi.fn(() => {
40+
mockObjects.clear();
41+
mockContributors.clear();
42+
}),
2943
metadata: {
3044
get: vi.fn(() => mockObjects) // Expose for verification if needed
3145
}

packages/objectql/src/engine.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -618,7 +618,9 @@ export class ObjectQL implements IDataEngine {
618618
}
619619

620620
// 3. Check package's defaultDatasource
621-
const owner = SchemaRegistry.getObjectOwner(objectName);
621+
// Use the object's FQN name (from getObject) for ownership lookup
622+
const fqn = object?.name || objectName;
623+
const owner = SchemaRegistry.getObjectOwner(fqn);
622624
if (owner?.packageId) {
623625
const manifest = this.manifests.get(owner.packageId);
624626
if (manifest?.defaultDatasource && manifest.defaultDatasource !== 'default') {

packages/spec/src/stack.test.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -430,8 +430,12 @@ describe('defineStack', () => {
430430
const result = defineStack(config);
431431
// Default is now strict=true, so result is validated and is a different object reference
432432
expect(result).not.toBe(config); // Validation creates new object
433-
expect(result).toEqual(config); // But content is the same
433+
// Validation may add defaults like defaultDatasource
434434
expect(result.manifest).toBeDefined();
435+
expect(result.manifest.id).toBe(baseManifest.id);
436+
expect(result.manifest.name).toBe(baseManifest.name);
437+
expect(result.manifest.version).toBe(baseManifest.version);
438+
expect(result.manifest.type).toBe(baseManifest.type);
435439
});
436440

437441
it('should return config as-is when strict is false', () => {

0 commit comments

Comments
 (0)