Conversation
…query params and metadata protocol
The simulateBrowser mock handlers had three categories of issues:
1. GET /data/:object ignored query parameters (top, skip, sort, select, filter).
Added parseQueryOptions() to parse URL search params and pass them to ql.find().
2. Metadata type/list endpoints used SchemaRegistry directly, missing runtime types
(agent, tool) registered via MetadataService. Now uses protocol service which
merges both SchemaRegistry and MetadataService data.
3. Metadata object list endpoint returned a plain object instead of the expected
{ type: 'object', items: [...] } format. Now uses protocol.getMetaItems().
Agent-Logs-Url: https://github.com/objectstack-ai/framework/sessions/91f259ad-90cc-408e-a96c-056b04824a93
Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
There was a problem hiding this comment.
Pull request overview
Fixes Studio CI failures by making the simulateBrowser MSW mock behave closer to the real ObjectStack HTTP API, especially for queryable data endpoints and protocol-compliant metadata endpoints.
Changes:
- Added query-string parsing for
GET /api/v1/data/:objectand passed the parsed options intoql.find(...). - Switched metadata mocks (
/api/v1/meta*) to use theprotocolservice (getMetaTypes/getMetaItems/getMetaItem) so runtime-registered metadata types/items are included. - Documented the fix in the Studio changelog.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.
| File | Description |
|---|---|
| apps/studio/src/mocks/simulateBrowser.ts | Adds parseQueryOptions() and updates MSW handlers to use query options for data find and protocol-backed metadata endpoints. |
| apps/studio/CHANGELOG.md | Adds a patch note describing the simulateBrowser mock handler fixes. |
| try { query.orderBy = JSON.parse(val); } catch { | ||
| query.orderBy = val.split(',').map((s: string) => s.trim()); |
There was a problem hiding this comment.
parseQueryOptions() maps the sort query param to query.orderBy as a string array when the value is comma-separated (e.g. "-created_at"). EngineQueryOptions.orderBy is an array of SortNode objects ({ field, order }), and the in-memory driver’s applySort() ignores string items, so sorting won’t be applied for the common sort=-field form sent by ObjectStackClient.data.find(). Convert string tokens into SortNode objects (handle leading '-' for desc) instead of returning raw strings.
| try { query.orderBy = JSON.parse(val); } catch { | |
| query.orderBy = val.split(',').map((s: string) => s.trim()); | |
| try { | |
| query.orderBy = JSON.parse(val); | |
| } catch { | |
| query.orderBy = val | |
| .split(',') | |
| .map((s: string) => s.trim()) | |
| .filter(Boolean) | |
| .map((token: string) => ({ | |
| field: token.startsWith('-') ? token.slice(1) : token, | |
| order: token.startsWith('-') ? 'desc' : 'asc', | |
| })); |
| case 'filter': | ||
| case '$filter': | ||
| try { Object.assign(where, JSON.parse(val)); } catch { /* ignore malformed */ } | ||
| break; |
There was a problem hiding this comment.
filter is JSON-parsed and merged into where via Object.assign(where, JSON.parse(val)). When the client sends an AST/array filter (it serializes arrays into the filter param), this produces a { "0": ..., "1": ... } object rather than a valid where condition, so filtering will silently fail. If the parsed value is an array (or already a FilterCondition shape), assign it to query.where directly rather than merging into an object.
| default: | ||
| // Individual key-value filter params (e.g. id=abc) | ||
| where[key] = val; | ||
| break; |
There was a problem hiding this comment.
ObjectStackClient.data.find() can send aggregations (JSON) and groupBy (comma-separated) query params, but parseQueryOptions() currently treats unknown params as field filters and puts them into where. This breaks aggregation queries by turning control params into WHERE conditions. Add explicit parsing/forwarding for these keys (or explicitly ignore them) so they don’t end up in where.
Summary
Fixes all 9 failing tests in
@objectstack/studio#test(CI run #24456193896) by correcting thesimulateBrowserMSW mock handlers inapps/studio/src/mocks/simulateBrowser.ts.Root Causes & Fixes
1. Data endpoint ignored query parameters (4 test failures)
Tests:
api.test.ts(3 tests),api-discovery.test.ts(1 test)The
GET /data/:objecthandler calledql.find(params.object)without passing any query options. The client sendstop,skip,sort,select, and filter parameters, but all were ignored — returning all records instead of the filtered/paginated subset.Fix: Added
parseQueryOptions()helper that parses URL search params into ObjectQLEngineQueryOptions(limit,offset,orderBy,fields,where), and passes them toql.find().2. Metadata types endpoint missing runtime types (2 test failures)
Tests:
verify-metadata.test.ts— "should include agent/tool in metadata types"The
GET /metahandler usedql.registry.getRegisteredTypes()which only returns SchemaRegistry types (package,data,app,object), missing runtime types (agent,tool, etc.) registered byAIServicePluginviaMetadataService.Fix: Now uses
protocol.getMetaTypes()which merges both SchemaRegistry and MetadataService types.3. Metadata items endpoint only queried SchemaRegistry (2 test failures)
Tests:
verify-metadata.test.ts— "should list registered agents/tools"The
GET /meta/:typehandler usedql.registry.listItems(type)which only returns SchemaRegistry items. Agents and tools are registered in MetadataService, not SchemaRegistry.Fix: Now uses
protocol.getMetaItems({ type })which queries both registries.4. Object list endpoint returned wrong format (1 test failure)
Test:
verify-metadata.test.ts— "should fetch list of objects"The
GET /meta/objecthandler returnedql.getObjects()(which doesn't exist, defaulting to{}) instead of the spec-compliant{ type: 'object', items: [...] }format.Fix: Now uses
protocol.getMetaItems({ type: 'object' })which returns the correct format.Verification