@cyanheads/brapi-mcp-server 0.4.5 → 0.4.6

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.
Files changed (57) hide show
  1. package/CLAUDE.md +1 -1
  2. package/README.md +1 -1
  3. package/changelog/0.4.x/0.4.6.md +26 -0
  4. package/dist/mcp-server/tools/definitions/brapi-find-germplasm.tool.d.ts +7 -1
  5. package/dist/mcp-server/tools/definitions/brapi-find-germplasm.tool.d.ts.map +1 -1
  6. package/dist/mcp-server/tools/definitions/brapi-find-germplasm.tool.js +11 -2
  7. package/dist/mcp-server/tools/definitions/brapi-find-germplasm.tool.js.map +1 -1
  8. package/dist/mcp-server/tools/definitions/brapi-find-images.tool.d.ts +7 -1
  9. package/dist/mcp-server/tools/definitions/brapi-find-images.tool.d.ts.map +1 -1
  10. package/dist/mcp-server/tools/definitions/brapi-find-images.tool.js +11 -2
  11. package/dist/mcp-server/tools/definitions/brapi-find-images.tool.js.map +1 -1
  12. package/dist/mcp-server/tools/definitions/brapi-find-locations.tool.d.ts +7 -1
  13. package/dist/mcp-server/tools/definitions/brapi-find-locations.tool.d.ts.map +1 -1
  14. package/dist/mcp-server/tools/definitions/brapi-find-locations.tool.js +11 -2
  15. package/dist/mcp-server/tools/definitions/brapi-find-locations.tool.js.map +1 -1
  16. package/dist/mcp-server/tools/definitions/brapi-find-observations.tool.d.ts +7 -1
  17. package/dist/mcp-server/tools/definitions/brapi-find-observations.tool.d.ts.map +1 -1
  18. package/dist/mcp-server/tools/definitions/brapi-find-observations.tool.js +11 -2
  19. package/dist/mcp-server/tools/definitions/brapi-find-observations.tool.js.map +1 -1
  20. package/dist/mcp-server/tools/definitions/brapi-find-studies.tool.d.ts +7 -1
  21. package/dist/mcp-server/tools/definitions/brapi-find-studies.tool.d.ts.map +1 -1
  22. package/dist/mcp-server/tools/definitions/brapi-find-studies.tool.js +11 -2
  23. package/dist/mcp-server/tools/definitions/brapi-find-studies.tool.js.map +1 -1
  24. package/dist/mcp-server/tools/definitions/brapi-find-variables.tool.d.ts +7 -1
  25. package/dist/mcp-server/tools/definitions/brapi-find-variables.tool.d.ts.map +1 -1
  26. package/dist/mcp-server/tools/definitions/brapi-find-variables.tool.js +11 -2
  27. package/dist/mcp-server/tools/definitions/brapi-find-variables.tool.js.map +1 -1
  28. package/dist/mcp-server/tools/definitions/brapi-find-variants.tool.d.ts +7 -1
  29. package/dist/mcp-server/tools/definitions/brapi-find-variants.tool.d.ts.map +1 -1
  30. package/dist/mcp-server/tools/definitions/brapi-find-variants.tool.js +11 -2
  31. package/dist/mcp-server/tools/definitions/brapi-find-variants.tool.js.map +1 -1
  32. package/dist/mcp-server/tools/definitions/index.d.ts +42 -7
  33. package/dist/mcp-server/tools/definitions/index.d.ts.map +1 -1
  34. package/dist/mcp-server/tools/shared/find-helpers.d.ts +10 -6
  35. package/dist/mcp-server/tools/shared/find-helpers.d.ts.map +1 -1
  36. package/dist/mcp-server/tools/shared/find-helpers.js +16 -5
  37. package/dist/mcp-server/tools/shared/find-helpers.js.map +1 -1
  38. package/dist/services/brapi-dialect/brapi-test-dialect.d.ts +19 -8
  39. package/dist/services/brapi-dialect/brapi-test-dialect.d.ts.map +1 -1
  40. package/dist/services/brapi-dialect/brapi-test-dialect.js +139 -11
  41. package/dist/services/brapi-dialect/brapi-test-dialect.js.map +1 -1
  42. package/dist/services/brapi-dialect/cassavabase-dialect.d.ts +2 -2
  43. package/dist/services/brapi-dialect/cassavabase-dialect.d.ts.map +1 -1
  44. package/dist/services/brapi-dialect/cassavabase-dialect.js +13 -40
  45. package/dist/services/brapi-dialect/cassavabase-dialect.js.map +1 -1
  46. package/dist/services/brapi-dialect/singularizing-dialect.d.ts +47 -0
  47. package/dist/services/brapi-dialect/singularizing-dialect.d.ts.map +1 -0
  48. package/dist/services/brapi-dialect/singularizing-dialect.js +63 -0
  49. package/dist/services/brapi-dialect/singularizing-dialect.js.map +1 -0
  50. package/dist/services/brapi-dialect/spec-dialect.d.ts +7 -5
  51. package/dist/services/brapi-dialect/spec-dialect.d.ts.map +1 -1
  52. package/dist/services/brapi-dialect/spec-dialect.js +8 -6
  53. package/dist/services/brapi-dialect/spec-dialect.js.map +1 -1
  54. package/dist/services/brapi-dialect/types.d.ts +10 -1
  55. package/dist/services/brapi-dialect/types.d.ts.map +1 -1
  56. package/package.json +1 -1
  57. package/server.json +3 -3
@@ -0,0 +1,63 @@
1
+ /**
2
+ * @fileoverview Generic factory for dialects that translate BrAPI v2.1 plural
3
+ * filter keys (`studyDbIds`, `germplasmDbIds`, …) to the v2.0 singular forms
4
+ * the upstream actually honors. Used by both the SGN/Breedbase family
5
+ * (`cassavabase-dialect`) and the BrAPI Community Test Server
6
+ * (`brapi-test-dialect`) — the two share an identical translation engine but
7
+ * carry different per-endpoint mappings, drop lists, and search-route flags,
8
+ * so the data lives in each dialect module while the engine lives here.
9
+ *
10
+ * @module services/brapi-dialect/singularizing-dialect
11
+ */
12
+ const EMPTY_DROP_SET = new Set();
13
+ /**
14
+ * Build a `BrapiDialect` whose `adaptGetFilters` translates plural v2.1 filter
15
+ * names to the configured singulars, drops blacklisted keys, and downcasts
16
+ * multi-value arrays to the first element with a loud warning (the v2.0 GET
17
+ * surface can't express multi-value filters; the agent should re-call per
18
+ * value or use a curated tool that paginates).
19
+ */
20
+ export function createSingularizingDialect(config) {
21
+ const adaptGetFilters = (endpoint, filters) => {
22
+ const mapping = config.pluralToSingular[endpoint] ?? {};
23
+ const droppedSet = config.droppedFilters?.[endpoint] ?? EMPTY_DROP_SET;
24
+ const out = {};
25
+ const warnings = [];
26
+ const dropped = [];
27
+ for (const [key, value] of Object.entries(filters)) {
28
+ if (value === undefined)
29
+ continue;
30
+ if (droppedSet.has(key)) {
31
+ dropped.push(key);
32
+ warnings.push(`${config.label} dialect: dropped filter '${key}' — this server does not honor it. Adjust the query or omit the filter.`);
33
+ continue;
34
+ }
35
+ const target = mapping[key];
36
+ if (!target) {
37
+ out[key] = value;
38
+ continue;
39
+ }
40
+ if (Array.isArray(value)) {
41
+ if (value.length === 0)
42
+ continue;
43
+ out[target] = value[0];
44
+ if (value.length > 1) {
45
+ warnings.push(`${config.label} dialect: '${key}' downcast to '${target}'; only the first value (${JSON.stringify(value[0])}) was sent — this server's GET /${endpoint} accepts a single value per filter, not arrays. Run separate calls for the other values, or use a curated tool that paginates over them.`);
46
+ }
47
+ }
48
+ else {
49
+ out[target] = value;
50
+ }
51
+ }
52
+ return { filters: out, dropped, warnings };
53
+ };
54
+ return {
55
+ id: config.id,
56
+ adaptGetFilters,
57
+ ...(config.disabledSearchEndpoints !== undefined && {
58
+ disabledSearchEndpoints: config.disabledSearchEndpoints,
59
+ }),
60
+ ...(config.notes !== undefined && { notes: config.notes }),
61
+ };
62
+ }
63
+ //# sourceMappingURL=singularizing-dialect.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"singularizing-dialect.js","sourceRoot":"","sources":["../../../src/services/brapi-dialect/singularizing-dialect.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AA+BH,MAAM,cAAc,GAAwB,IAAI,GAAG,EAAE,CAAC;AAEtD;;;;;;GAMG;AACH,MAAM,UAAU,0BAA0B,CAAC,MAAkC;IAC3E,MAAM,eAAe,GAAG,CACtB,QAAgB,EAChB,OAA0C,EACvB,EAAE;QACrB,MAAM,OAAO,GAAG,MAAM,CAAC,gBAAgB,CAAC,QAAQ,CAAC,IAAI,EAAE,CAAC;QACxD,MAAM,UAAU,GAAG,MAAM,CAAC,cAAc,EAAE,CAAC,QAAQ,CAAC,IAAI,cAAc,CAAC;QACvE,MAAM,GAAG,GAA4B,EAAE,CAAC;QACxC,MAAM,QAAQ,GAAa,EAAE,CAAC;QAC9B,MAAM,OAAO,GAAa,EAAE,CAAC;QAE7B,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC;YACnD,IAAI,KAAK,KAAK,SAAS;gBAAE,SAAS;YAClC,IAAI,UAAU,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC;gBACxB,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;gBAClB,QAAQ,CAAC,IAAI,CACX,GAAG,MAAM,CAAC,KAAK,6BAA6B,GAAG,yEAAyE,CACzH,CAAC;gBACF,SAAS;YACX,CAAC;YACD,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC;YAC5B,IAAI,CAAC,MAAM,EAAE,CAAC;gBACZ,GAAG,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC;gBACjB,SAAS;YACX,CAAC;YACD,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;gBACzB,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;oBAAE,SAAS;gBACjC,GAAG,CAAC,MAAM,CAAC,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;gBACvB,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;oBACrB,QAAQ,CAAC,IAAI,CACX,GAAG,MAAM,CAAC,KAAK,cAAc,GAAG,kBAAkB,MAAM,4BAA4B,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,mCAAmC,QAAQ,0IAA0I,CAClS,CAAC;gBACJ,CAAC;YACH,CAAC;iBAAM,CAAC;gBACN,GAAG,CAAC,MAAM,CAAC,GAAG,KAAK,CAAC;YACtB,CAAC;QACH,CAAC;QAED,OAAO,EAAE,OAAO,EAAE,GAAG,EAAE,OAAO,EAAE,QAAQ,EAAE,CAAC;IAC7C,CAAC,CAAC;IAEF,OAAO;QACL,EAAE,EAAE,MAAM,CAAC,EAAE;QACb,eAAe;QACf,GAAG,CAAC,MAAM,CAAC,uBAAuB,KAAK,SAAS,IAAI;YAClD,uBAAuB,EAAE,MAAM,CAAC,uBAAuB;SACxD,CAAC;QACF,GAAG,CAAC,MAAM,CAAC,KAAK,KAAK,SAAS,IAAI,EAAE,KAAK,EAAE,MAAM,CAAC,KAAK,EAAE,CAAC;KAC3D,CAAC;AACJ,CAAC"}
@@ -1,10 +1,12 @@
1
1
  /**
2
2
  * @fileoverview The default `spec` dialect — passes filters through verbatim.
3
- * Used for any server that implements BrAPI v2.1 query-string filters as
4
- * specified (the BrAPI Community Test Server, modern PIPPA / GnpIS / Reference
5
- * Server deployments). Selected when no server-specific dialect matches the
6
- * detected `serverInfo.serverName`, or when an operator pins
7
- * `BRAPI_<ALIAS>_DIALECT=spec` to override detection.
3
+ * Used for servers that implement BrAPI v2.1 query-string filters as
4
+ * specified (modern PIPPA / GnpIS / Reference Server deployments). Selected
5
+ * when no server-specific dialect matches the detected `serverInfo.serverName`,
6
+ * or when an operator pins `BRAPI_<ALIAS>_DIALECT=spec` to override detection.
7
+ *
8
+ * Note: the BrAPI Community Test Server is intentionally **not** spec-shaped
9
+ * for GET filters — see `brapi-test-dialect.ts`.
8
10
  *
9
11
  * @module services/brapi-dialect/spec-dialect
10
12
  */
@@ -1 +1 @@
1
- {"version":3,"file":"spec-dialect.d.ts","sourceRoot":"","sources":["../../../src/services/brapi-dialect/spec-dialect.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAE/C,eAAO,MAAM,WAAW,EAAE,YAKzB,CAAC"}
1
+ {"version":3,"file":"spec-dialect.d.ts","sourceRoot":"","sources":["../../../src/services/brapi-dialect/spec-dialect.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAE/C,eAAO,MAAM,WAAW,EAAE,YAKzB,CAAC"}
@@ -1,17 +1,19 @@
1
1
  /**
2
2
  * @fileoverview The default `spec` dialect — passes filters through verbatim.
3
- * Used for any server that implements BrAPI v2.1 query-string filters as
4
- * specified (the BrAPI Community Test Server, modern PIPPA / GnpIS / Reference
5
- * Server deployments). Selected when no server-specific dialect matches the
6
- * detected `serverInfo.serverName`, or when an operator pins
7
- * `BRAPI_<ALIAS>_DIALECT=spec` to override detection.
3
+ * Used for servers that implement BrAPI v2.1 query-string filters as
4
+ * specified (modern PIPPA / GnpIS / Reference Server deployments). Selected
5
+ * when no server-specific dialect matches the detected `serverInfo.serverName`,
6
+ * or when an operator pins `BRAPI_<ALIAS>_DIALECT=spec` to override detection.
7
+ *
8
+ * Note: the BrAPI Community Test Server is intentionally **not** spec-shaped
9
+ * for GET filters — see `brapi-test-dialect.ts`.
8
10
  *
9
11
  * @module services/brapi-dialect/spec-dialect
10
12
  */
11
13
  export const specDialect = {
12
14
  id: 'spec',
13
15
  adaptGetFilters(_endpoint, filters) {
14
- return { filters: { ...filters }, warnings: [] };
16
+ return { filters: { ...filters }, dropped: [], warnings: [] };
15
17
  },
16
18
  };
17
19
  //# sourceMappingURL=spec-dialect.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"spec-dialect.js","sourceRoot":"","sources":["../../../src/services/brapi-dialect/spec-dialect.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAIH,MAAM,CAAC,MAAM,WAAW,GAAiB;IACvC,EAAE,EAAE,MAAM;IACV,eAAe,CAAC,SAAS,EAAE,OAAO;QAChC,OAAO,EAAE,OAAO,EAAE,EAAE,GAAG,OAAO,EAAE,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;IACnD,CAAC;CACF,CAAC"}
1
+ {"version":3,"file":"spec-dialect.js","sourceRoot":"","sources":["../../../src/services/brapi-dialect/spec-dialect.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAIH,MAAM,CAAC,MAAM,WAAW,GAAiB;IACvC,EAAE,EAAE,MAAM;IACV,eAAe,CAAC,SAAS,EAAE,OAAO;QAChC,OAAO,EAAE,OAAO,EAAE,EAAE,GAAG,OAAO,EAAE,EAAE,OAAO,EAAE,EAAE,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;IAChE,CAAC;CACF,CAAC"}
@@ -18,9 +18,18 @@
18
18
  * Result of adapting a filter map for a specific endpoint. `filters` is the
19
19
  * wire-shape map (what gets serialized into the URL); `warnings` are
20
20
  * operator-facing notes about lossy conversions (multi-value array downcast,
21
- * filters dropped because the server doesn't honor them, etc.).
21
+ * filters dropped because the server doesn't honor them, etc.). `dropped` is
22
+ * the structured list of input keys that were removed entirely so callers can
23
+ * detect "agent intended to scope, dialect couldn't honor it" without parsing
24
+ * warning strings.
22
25
  */
23
26
  export interface DialectAdaptation {
27
+ /**
28
+ * Input filter keys the dialect dropped entirely (server doesn't honor them
29
+ * in any form). Each dropped key also produces a human-readable entry in
30
+ * `warnings`. Empty when nothing was dropped.
31
+ */
32
+ dropped: readonly string[];
24
33
  filters: Record<string, unknown>;
25
34
  warnings: string[];
26
35
  }
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/services/brapi-dialect/types.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH;;;;;GAKG;AACH,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED;;;;;GAKG;AACH,MAAM,WAAW,YAAY;IAC3B;;;;;;;;;OASG;IACH,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,GAAG,iBAAiB,CAAC;IACjG;;;;;;;;;OASG;IACH,QAAQ,CAAC,uBAAuB,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC;IACvD,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB;;;;OAIG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;CACpC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/services/brapi-dialect/types.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH;;;;;;;;GAQG;AACH,MAAM,WAAW,iBAAiB;IAChC;;;;OAIG;IACH,OAAO,EAAE,SAAS,MAAM,EAAE,CAAC;IAC3B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED;;;;;GAKG;AACH,MAAM,WAAW,YAAY;IAC3B;;;;;;;;;OASG;IACH,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,GAAG,iBAAiB,CAAC;IACjG;;;;;;;;;OASG;IACH,QAAQ,CAAC,uBAAuB,CAAC,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC;IACvD,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB;;;;OAIG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;CACpC"}
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@cyanheads/brapi-mcp-server",
3
3
  "mcpName": "io.github.cyanheads/brapi-mcp-server",
4
- "version": "0.4.5",
4
+ "version": "0.4.6",
5
5
  "description": "BrAPI v2.1 MCP server — studies, germplasm, observations, genotypes, images, and pedigrees.",
6
6
  "author": "Casey Hand @cyanheads (https://github.com/cyanheads/brapi-mcp-server#readme)",
7
7
  "type": "module",
package/server.json CHANGED
@@ -6,14 +6,14 @@
6
6
  "url": "https://github.com/cyanheads/brapi-mcp-server",
7
7
  "source": "github"
8
8
  },
9
- "version": "0.4.5",
9
+ "version": "0.4.6",
10
10
  "packages": [
11
11
  {
12
12
  "registryType": "npm",
13
13
  "registryBaseUrl": "https://registry.npmjs.org",
14
14
  "identifier": "@cyanheads/brapi-mcp-server",
15
15
  "runtimeHint": "bun",
16
- "version": "0.4.5",
16
+ "version": "0.4.6",
17
17
  "packageArguments": [
18
18
  { "type": "positional", "value": "run" },
19
19
  { "type": "positional", "value": "start:stdio" }
@@ -49,7 +49,7 @@
49
49
  "registryBaseUrl": "https://registry.npmjs.org",
50
50
  "identifier": "@cyanheads/brapi-mcp-server",
51
51
  "runtimeHint": "bun",
52
- "version": "0.4.5",
52
+ "version": "0.4.6",
53
53
  "packageArguments": [
54
54
  { "type": "positional", "value": "run" },
55
55
  { "type": "positional", "value": "start:http" }