deere-sdk 2.0.0 → 2.1.1

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
@@ -5,6 +5,200 @@ All notable changes to this project will be documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [2.1.1] - 2026-04-14
9
+
10
+ **Patch release completing 2.1.0's intended scope.** 2.1.0 shipped one safe
11
+ facade method — `deere.safe.fieldOperations.listAllWithMeasurements` — against
12
+ a plan that explicitly deferred `list`/`get` variants and silently omitted any
13
+ audit of the rest of the embed surface. A post-ship audit found that the same
14
+ silent-zero bug class was still loaded on TWO other field-operations methods,
15
+ plus the entire equipment and products families. 2.1.1 fixes that.
16
+
17
+ Framing as a patch is technically stretched (2.1.1 adds public API surface,
18
+ which semver-purists would call a minor), but the work here is completing
19
+ 2.1.0's promise to kill the embed footgun in the `fieldOperations` family and
20
+ extending that guarantee to adjacent families where JD's spec documents narrow
21
+ embed enum values. Nothing in 2.1.0 is broken or removed.
22
+
23
+ ### Added
24
+
25
+ - **`deere.safe.fieldOperations.listWithMeasurements(orgId, fieldId, params?)`** —
26
+ paginated single-page variant. Returns `PaginatedResponse<FieldOperationWithMeasurements>`.
27
+ Forces `embed=measurementTypes`, runtime-verifies every operation on the
28
+ returned page carries the `measurementTypes` array, throws `DeereError` on
29
+ contract violation. Same guarantee contract as `listAllWithMeasurements`.
30
+ - **`deere.safe.fieldOperations.getWithMeasurements(operationId, params?)`** —
31
+ single-operation-by-id variant. Returns `FieldOperationIdWithMeasurements`.
32
+ JD treats the list-shape (`FieldOperation`) and get-shape (`FieldOperationId`)
33
+ as separate schemas; 2.1.0's spec patch only covered `FieldOperation`. 2.1.1
34
+ adds a matching patch for `FieldOperationId` so the narrowed return type on
35
+ the single-op path is honest.
36
+ - **`FieldOperationIdWithMeasurements`** — new exported type, the narrowed
37
+ variant of `FieldOperationId`.
38
+ - **`deere.safe.equipment`** (new facade, `SafeEquipmentApi`) — six methods
39
+ wrapping every embed-accepting raw method on `EquipmentApi`:
40
+ `getWithEmbed`, `getEquipmentWithEmbed`, `listEquipmentmodelsWithEmbed`,
41
+ `listEquipmentisgtypesWithEmbed`, `getEquipmentisgtypesWithEmbed`,
42
+ `getEquipmentisgtypes2WithEmbed`. Each method makes the `embed` parameter
43
+ **required at the type level** — TypeScript refuses to compile a call that
44
+ forgets it. Embed values follow JD's documented enums (`devices`, `equipment`,
45
+ `icon`, `pairingDetails`, `offsets`, `capabilities`, `make`, `type`, `isgType`,
46
+ `equipmentModels`, `recordMetadata`).
47
+ - **`deere.safe.products`** (new facade, `SafeProductsApi`) — three methods
48
+ wrapping every embed-accepting raw method on `ProductsApi`: `listWithEmbed`,
49
+ `listAllWithEmbed`, `getWithEmbed`. Embed values are JD's documented enum:
50
+ `documents`, `showMergedProducts`.
51
+ - **Spec patch: `FieldOperationId.measurementTypes`** — mirrors the 2.1.0
52
+ patch on `FieldOperation` so both the list-shape and get-shape carry the
53
+ optional array in the generated types. Added via one new `addProperty` entry
54
+ in `scripts/embed-contracts.yaml`.
55
+
56
+ ### Important scope note — what 2.1.1 does NOT cover
57
+
58
+ Equipment and Products safe facades are **type-level forcing functions only**.
59
+ They require the caller to pass `embed`, but they do NOT narrow the return
60
+ type and do NOT runtime-verify that response fields are populated. The reason:
61
+ we don't yet have empirical wire traces confirming which response fields each
62
+ embed value populates on those endpoints. Without that evidence, any type
63
+ narrowing or runtime assertion would be guessing. 2.1.0's pattern of spec
64
+ patch + narrowed type + runtime verification is deferred for these families
65
+ until `field-mcp/scripts/jd-probe-shapes.ts` captures wire traces for
66
+ equipment and products. Once captured, a future release can tighten the
67
+ wrappers with the same registry-driven mechanism.
68
+
69
+ The following endpoints also take an `embed` parameter but **remain unwrapped
70
+ in 2.1.1** because JD's published OpenAPI spec documents the embed as a bare
71
+ `string` with no enum values — we literally cannot know what values the caller
72
+ should be forced to pass. These endpoints are still raw-only and still expose
73
+ the silent-zero footgun to callers who forget the embed: `boundaries.list`,
74
+ `boundaries.listAll`, `boundaries.listBoundaries`, `clients.list`,
75
+ `clients.listAll`, `clients.get`, `farms.list`, `farms.listAll`, `farms.get`,
76
+ `assets.list`, `assets.listAll`, `assets.get`, `guidance-lines.list`,
77
+ `guidance-lines.listAll`, `guidance-lines.get`, `harvest-id.list`,
78
+ `harvest-id.listAll`, `harvest-id.get`, `operators.list`, `operators.listAll`,
79
+ `operators.get`, `map-layers.list`, `map-layers.listAll`, `users.*`,
80
+ `flags.*`, `fields.*`. A proper audit of these requires both empirical wire
81
+ traces AND a fix-specs patch to tighten the `embed?: string` type to a
82
+ narrow enum, and is tracked as a future work item.
83
+
84
+ ### Migration
85
+
86
+ If FieldMCP (or any other consumer) calls `fieldOperations.list` or
87
+ `fieldOperations.get` and reads measurement data from the response, migrate:
88
+
89
+ ```ts
90
+ // Before — silent data loss if embed is forgotten
91
+ const page = await deere.fieldOperations.list(orgId, fieldId);
92
+ const op = await deere.fieldOperations.get(operationId);
93
+
94
+ // After — guaranteed measurementTypes, throws on contract drift
95
+ const page = await deere.safe.fieldOperations.listWithMeasurements(orgId, fieldId);
96
+ const op = await deere.safe.fieldOperations.getWithMeasurements(operationId);
97
+ ```
98
+
99
+ For equipment and products, the migration is the same pattern but the safe
100
+ wrapper just forces you to pick an embed at compile time:
101
+
102
+ ```ts
103
+ // Raw (compiles, will silently miss fields when you forget embed)
104
+ const equipmentList = await deere.equipment.get();
105
+
106
+ // Safe (refuses to compile unless you pass embed)
107
+ const equipmentList = await deere.safe.equipment.getWithEmbed({ embed: 'devices' });
108
+ ```
109
+
110
+ ### Unchanged
111
+
112
+ - Everything shipped in 2.1.0. `listAllWithMeasurements` is untouched, same
113
+ signature, same guarantee.
114
+ - Raw `FieldOperationsApi`, `EquipmentApi`, `ProductsApi` method signatures.
115
+ - Error hierarchy, URL resolution, HATEOAS mode.
116
+ - The contract registry mechanism and `applyEmbedContracts` patcher.
117
+
118
+ ## [2.1.0] - 2026-04-14
119
+
120
+ **Minor, additive release.** Kills a footgun on `fieldOperations.listAll` by
121
+ introducing a "safe facade" layer (`deere.safe.*`) that forces query params
122
+ John Deere's API requires for a complete response but the raw SDK leaves
123
+ optional. Also adds a contract registry that lets future SDK patches encode
124
+ JD spec gaps in one place instead of across hand-written wrappers.
125
+
126
+ ### Why
127
+
128
+ John Deere's API documents `embed` as an optional query param on
129
+ `GET /organizations/{orgId}/fields/{fieldId}/fieldOperations`, but silently
130
+ omits the `measurementTypes` array on every returned FieldOperation unless
131
+ the request passes `?embed=measurementTypes`. Downstream consumers that
132
+ forget the embed param get objects with zero values for yield, area,
133
+ moisture, application rate, and seeding population — and can't tell "missing
134
+ data" from "real zero" because JD's OpenAPI spec never documents the
135
+ invariant. FieldMCP shipped placeholder data to production three separate
136
+ times because of this exact bug. 2.1.0 makes "forget the embed param"
137
+ syntactically impossible.
138
+
139
+ ### Added
140
+
141
+ - **`deere.safe.fieldOperations.listAllWithMeasurements(orgId, fieldId, params?)`**
142
+ — returns `FieldOperationWithMeasurements[]` (non-optional `measurementTypes`
143
+ array). Forces `embed=measurementTypes` on the outgoing request, and verifies
144
+ every returned operation actually carries the array, throwing `DeereError`
145
+ with the operation id on any contract violation. Empty `measurementTypes: []`
146
+ is valid (the operation has no recorded measurements yet); `undefined` is not
147
+ and fails loudly.
148
+ - **`SafeFacades` class** on `deere.safe` — composition root for safe facades.
149
+ Adding a new safe wrapper means writing a file under `src/safe/` and adding
150
+ one field + one constructor init to `SafeFacades`. The codegen at
151
+ `scripts/generate-sdk.ts` is deliberately kept dumb about what's inside
152
+ `SafeFacades` — it only emits the wire-up, never the contents.
153
+ - **`FieldOperationWithMeasurements`** type — re-exported from the main entry
154
+ for consumers who need to reference the narrowed shape directly.
155
+ - **`scripts/embed-contracts.yaml`** — new registry encoding JD's undocumented
156
+ invariants as a list of OpenAPI schema-patch operations. Consumed at codegen
157
+ time by `scripts/fix-specs.ts`'s `applyEmbedContracts()` transform before
158
+ `openapi-typescript` runs, so the generated types include the
159
+ previously-missing fields with JD's own declared schemas as `$ref` targets.
160
+ - **Generated type `ApplicationProductTotal`** and optional properties
161
+ `FieldOperation.measurementTypes: FieldOperationMeasurement[]` and
162
+ `FieldOperationMeasurementInFullRelease.applicationProductTotals:
163
+ ApplicationProductTotal[]` — produced by the registry patcher and visible to
164
+ both safe-path and raw-path callers.
165
+
166
+ ### Migration
167
+
168
+ Replace raw `listAll` calls that read measurement data with the safe variant:
169
+
170
+ ```ts
171
+ // Before — silently returns FieldOperation objects without measurementTypes
172
+ // unless you remember to pass embed, and the type system doesn't warn you.
173
+ const ops = await deere.fieldOperations.listAll(orgId, fieldId);
174
+ const yield_ = ops[0].measurementTypes; // ← undefined, silent data loss
175
+
176
+ // After — always populated, type-guaranteed, throws clearly on drift
177
+ const ops = await deere.safe.fieldOperations.listAllWithMeasurements(
178
+ orgId,
179
+ fieldId
180
+ );
181
+ const yield_ = ops[0].measurementTypes[0]?.averageYield?.value; // typed, narrowed
182
+ ```
183
+
184
+ Raw `deere.fieldOperations.listAll` still exists and still works — it's the
185
+ right tool for metadata-only callers (calendar UIs, operation listings that
186
+ don't consume measurement data). The raw return type now carries
187
+ `measurementTypes?: FieldOperationMeasurement[]` as an optional field, so
188
+ raw-path consumers can read it when they pass the embed param themselves,
189
+ but with a compile-time nudge that it might be absent.
190
+
191
+ ### Unchanged
192
+
193
+ - `FieldOperationsApi.listAll` signature, behavior, and existing query param
194
+ semantics. No breaking changes.
195
+ - All other generated API classes.
196
+ - Error hierarchy, HATEOAS mode, URL resolution, retry policy.
197
+ - `openapi-typescript` version, generator script structure (aside from the
198
+ three literal-string insertions in `generateMainClass()` that wire up
199
+ `SafeFacades` — see `scripts/generate-sdk.ts` and the `// DO NOT REORDER`
200
+ comment it emits into the generated `deere.ts`).
201
+
8
202
  ## [2.0.0] - 2026-04-13
9
203
 
10
204
  **Major release.** URL resolution is now fully spec-driven. This release fixes
package/README.md CHANGED
@@ -1,3 +1,7 @@
1
+ <p align="center">
2
+ <img src=".github/images/hero.png" alt="deere-sdk">
3
+ </p>
4
+
1
5
  <h1 align="center">deere-sdk</h1>
2
6
 
3
7
  <p align="center">
@@ -59,7 +63,7 @@ import {Deere} from 'deere-sdk';
59
63
 
60
64
  const deere = new Deere({
61
65
  accessToken: 'your-oauth-access-token',
62
- environment: 'sandbox', // or 'production'
66
+ environment: 'sandboxapi', // or 'api' for production
63
67
  });
64
68
 
65
69
  // List all organizations
@@ -98,13 +102,48 @@ This SDK requires an OAuth 2.0 access token from John Deere:
98
102
  <details>
99
103
  <summary><strong>Environments</strong></summary>
100
104
 
101
- | Environment | URL | Use Case |
102
- |--------------|----------------------|----------------------|
103
- | `production` | api.deere.com | Live data |
104
- | `sandbox` | sandboxapi.deere.com | Development |
105
- | `partner` | partnerapi.deere.com | Partner integrations |
106
- | `cert` | apicert.deere.com | Certification |
107
- | `qa` | apiqa.tal.deere.com | QA testing |
105
+ v2.0.0 uses raw John Deere subdomain names as environment values. Pass the subdomain (without `.deere.com`) as `environment`. Default: `sandboxapi`.
106
+
107
+ | Environment | URL | Use Case |
108
+ |------------------|----------------------------|----------------------------------|
109
+ | `api` | api.deere.com | Live production |
110
+ | `sandboxapi` | sandboxapi.deere.com | Development (default) |
111
+ | `partnerapi` | partnerapi.deere.com | Partner production |
112
+ | `apicert` | apicert.deere.com | Production certification |
113
+ | `partnerapicert` | partnerapicert.deere.com | Partner certification |
114
+ | `apiqa.tal` | apiqa.tal.deere.com | QA tier |
115
+ | `partnerapiqa` | partnerapiqa.deere.com | Partner QA |
116
+ | `sandboxapiqa` | sandboxapiqa.deere.com | Sandbox QA |
117
+ | `apidev.tal` | apidev.tal.deere.com | Internal dev tier (rarely used) |
118
+
119
+ Not every spec has servers for every environment. If you pick an environment a given spec doesn't ship (e.g., a production-only spec on `sandboxapi`), the constructor throws `UnsupportedEnvironmentError` with the valid values for that spec.
120
+
121
+ </details>
122
+
123
+ <details>
124
+ <summary><strong>Migrating from v1</strong></summary>
125
+
126
+ v1 accepted friendly environment names. v2.0.0 replaces them with the raw John Deere subdomain names so URL routing comes directly from each spec's OpenAPI `servers` block — no more hardcoded hostname maps.
127
+
128
+ Passing a v1 name to the v2 constructor throws immediately with a migration hint:
129
+
130
+ | v1 (pre-2.0.0) | v2.0.0+ |
131
+ |----------------|----------------|
132
+ | `production` | `api` |
133
+ | `sandbox` | `sandboxapi` |
134
+ | `partner` | `partnerapi` |
135
+ | `cert` | `apicert` |
136
+ | `qa` | `apiqa.tal` |
137
+
138
+ ```typescript
139
+ // v1
140
+ const deere = new Deere({ accessToken, environment: 'sandbox' });
141
+
142
+ // v2.0.0
143
+ const deere = new Deere({ accessToken, environment: 'sandboxapi' });
144
+ ```
145
+
146
+ The SDK now uses separate host subdomains per spec family (e.g., `equipmentapi.deere.com` for machine telemetry, `api.deere.com` for organizations) on the production tier. v1 silently routed everything through `api.deere.com`, which worked for most flows but mis-routed some machine-data endpoints. v2 routes each call to the exact host the spec declares.
108
147
 
109
148
  </details>
110
149
 
@@ -290,14 +329,26 @@ const models = await deere.equipment.listEquipmentmodels({equipmentModelName: '9
290
329
  <summary><strong>Field Operations</strong></summary>
291
330
 
292
331
  ```typescript
293
- // List field operations
294
- const ops = await deere.fieldOperations.list('org-id', 'field-id');
295
-
296
- // Filter by type and season
297
- const harvests = await deere.fieldOperations.list('org-id', 'field-id', {
298
- cropSeason: '2026',
299
- fieldOperationType: 'harvest'
300
- });
332
+ // Prefer the safe facade when you need measurement data (yield, area,
333
+ // moisture, application rate, seeding population). It forces
334
+ // ?embed=measurementTypes on the request and guarantees the returned
335
+ // operations carry a measurementTypes array, throwing a clear error if
336
+ // JD's wire format ever drifts from the documented contract.
337
+ const ops = await deere.safe.fieldOperations.listAllWithMeasurements(
338
+ 'org-id',
339
+ 'field-id'
340
+ );
341
+ const yieldValue = ops[0].measurementTypes[0]?.averageYield?.value;
342
+
343
+ // Filter by type and season — filters forward through to the safe wrapper too.
344
+ const harvests = await deere.safe.fieldOperations.listAllWithMeasurements(
345
+ 'org-id',
346
+ 'field-id',
347
+ { cropSeason: '2026', fieldOperationType: 'harvest' }
348
+ );
349
+
350
+ // Raw API (no forcing) — use when you only need metadata, not measurements.
351
+ const metaOnly = await deere.fieldOperations.list('org-id', 'field-id');
301
352
 
302
353
  // Get operation details
303
354
  const op = await deere.fieldOperations.get('operation-id');
@@ -309,6 +360,17 @@ const shapefile = await deere.fieldOperations.getFieldops('operation-id', {
309
360
  });
310
361
  ```
311
362
 
363
+ **Why `deere.safe.*`?** John Deere's API silently omits the `measurementTypes`
364
+ array on `fieldOperations.listAll` responses unless the request passes
365
+ `?embed=measurementTypes`, and their OpenAPI spec doesn't document that
366
+ invariant. Consumers that forget the embed param get objects with zero values
367
+ for yield, area, moisture, and rate — and can't tell "missing data" from "real
368
+ zero." The safe facade makes that footgun syntactically impossible: you can't
369
+ call `listAllWithMeasurements` without the embed param because the wrapper
370
+ adds it for you, and the returned type guarantees `measurementTypes` is
371
+ present. See `src/safe/` and `scripts/embed-contracts.yaml` for the spec-patch
372
+ machinery that makes the narrowed type honest at the type level.
373
+
312
374
  </details>
313
375
 
314
376
  <details>
@@ -452,7 +514,7 @@ import {DeereClient} from 'deere-sdk';
452
514
 
453
515
  const client = new DeereClient({
454
516
  accessToken: 'your-token',
455
- environment: 'sandbox',
517
+ environment: 'sandboxapi',
456
518
  timeout: 30000, // Request timeout in ms (default: 30000)
457
519
  maxRetries: 3, // Retry attempts (default: 3, set to 0 to disable)
458
520
  });
@@ -470,6 +532,25 @@ for await (const items of client.paginate('/large/collection')) {
470
532
  }
471
533
  ```
472
534
 
535
+ ### fetchUrl — Bearer token hostname guard
536
+
537
+ `DeereClient` exposes `fetchUrl(method, url, body?, options?)` and `followLink(url)` for calling absolute URLs (e.g., HAL `next` page links, externally-discovered URLs). Both **suppress the OAuth Bearer token** on any URL whose hostname is not a trusted `*.deere.com` origin. This prevents accidental token leakage if a HATEOAS response, user-supplied URL, or link cache ever includes a third-party host.
538
+
539
+ ```typescript
540
+ // Bearer token attached (trusted host)
541
+ await client.fetchUrl('GET', 'https://api.deere.com/platform/organizations');
542
+
543
+ // Bearer token SUPPRESSED (untrusted host) — request still goes out, just without Authorization
544
+ await client.fetchUrl('GET', 'https://example.com/some-webhook');
545
+
546
+ // You can opt in explicitly by passing your own Authorization header:
547
+ await client.fetchUrl('GET', 'https://example.com/api', undefined, {
548
+ headers: { Authorization: 'Bearer some-other-token' },
549
+ });
550
+ ```
551
+
552
+ Enable `hateoasDebug: true` to see a `console.warn` whenever a token is suppressed, so you can audit where your HATEOAS graph is pointing.
553
+
473
554
  ---
474
555
 
475
556
  ## HATEOAS Mode
@@ -479,7 +560,7 @@ John Deere requires applications to demonstrate [HATEOAS](https://en.wikipedia.o
479
560
  ```typescript
480
561
  const deere = new Deere({
481
562
  accessToken: 'your-token',
482
- environment: 'sandbox',
563
+ environment: 'sandboxapi',
483
564
  hateoas: true, // Enable HATEOAS link traversal
484
565
  hateoasDebug: true, // Optional: log resolution details
485
566
  });
@@ -499,7 +580,7 @@ import {Deere} from 'deere-sdk';
499
580
  // 1. Create client with HATEOAS enabled
500
581
  const deere = new Deere({
501
582
  accessToken: 'your-oauth-token',
502
- environment: 'sandbox',
583
+ environment: 'sandboxapi',
503
584
  hateoas: true,
504
585
  hateoasDebug: true, // See link resolution in console
505
586
  });
@@ -573,8 +654,23 @@ const deere = new Deere({
573
654
 
574
655
  ### Error Types
575
656
 
657
+ | Error | When it's thrown | Retried? |
658
+ |-------------------------------|-------------------------------------------------------------------|----------|
659
+ | `DeereError` | Base class. Any HTTP error from John Deere (400/404/422/5xx). | Only 5xx |
660
+ | `RateLimitError` | HTTP 429. Only reaches your catch after all retries are exhausted. | Yes |
661
+ | `AuthError` | HTTP 401/403. Refresh your OAuth token. | No |
662
+ | `HateoasError` | HATEOAS link resolution fails (parent fetch errored or no matching link). | No |
663
+ | `UnsupportedEnvironmentError` | Constructor threw because `environment` doesn't match the spec's `servers` block. | N/A (thrown at construction) |
664
+ | `NoServerConfigError` | Constructor threw because a spec has no `servers` block at all. | N/A |
665
+
576
666
  ```typescript
577
- import {DeereError, RateLimitError, AuthError} from 'deere-sdk';
667
+ import {
668
+ DeereError,
669
+ RateLimitError,
670
+ AuthError,
671
+ HateoasError,
672
+ UnsupportedEnvironmentError,
673
+ } from 'deere-sdk';
578
674
 
579
675
  try {
580
676
  const fields = await deere.fields.listAll('org-id');
@@ -585,6 +681,12 @@ try {
585
681
  } else if (error instanceof AuthError) {
586
682
  // Never retried - refresh your token
587
683
  console.log('Token expired - refresh required');
684
+ } else if (error instanceof HateoasError) {
685
+ // HATEOAS link resolution failed (only when hateoas: true)
686
+ console.log(`Link resolution failed on ${error.path}: ${error.message}`);
687
+ } else if (error instanceof UnsupportedEnvironmentError) {
688
+ // Spec doesn't ship this environment — try another from its valid list
689
+ console.log(error.message);
588
690
  } else if (error instanceof DeereError) {
589
691
  console.log(`API error: ${error.status} ${error.message}`);
590
692
  }
@@ -691,6 +793,14 @@ git push --follow-tags
691
793
 
692
794
  CI sees the tag → creates GitHub Release → publishes to npm.
693
795
 
796
+ **Gotcha:** GitHub sometimes does not fire the `push` event for a tag pushed via `git push --follow-tags`, so `release.yml` never auto-triggers. If you don't see a "Create Release" run within a minute of pushing the tag, dispatch it manually:
797
+
798
+ ```bash
799
+ gh workflow run release.yml --ref vX.Y.Z
800
+ ```
801
+
802
+ `release.yml` also accepts `workflow_dispatch`, so this produces an identical run against the tag's commit.
803
+
694
804
  ---
695
805
 
696
806
  ## Disclaimer
@@ -2,7 +2,7 @@
2
2
  * API server configuration per spec — single source of truth for URL resolution.
3
3
  *
4
4
  * @generated by scripts/generate-api-servers.ts — do not edit manually
5
- * Last generated: 2026-04-13T20:34:18.775Z
5
+ * Last generated: 2026-04-14T21:02:00.480Z
6
6
  *
7
7
  * Env coverage matrix (X = supported, - = throws UnsupportedEnvironmentError):
8
8
  *
@@ -2,7 +2,7 @@
2
2
  * API server configuration per spec — single source of truth for URL resolution.
3
3
  *
4
4
  * @generated by scripts/generate-api-servers.ts — do not edit manually
5
- * Last generated: 2026-04-13T20:34:18.775Z
5
+ * Last generated: 2026-04-14T21:02:00.480Z
6
6
  *
7
7
  * Env coverage matrix (X = supported, - = throws UnsupportedEnvironmentError):
8
8
  *
package/dist/deere.d.ts CHANGED
@@ -6,6 +6,7 @@
6
6
  */
7
7
  import { AempApi, AssetsApi, BoundariesApi, ClientsApi, ConnectionManagementApi, CropTypesApi, EquipmentApi, EquipmentMeasurementApi, FarmsApi, FieldOperationsApi, FieldsApi, FilesApi, FlagsApi, GuidanceLinesApi, HarvestIdApi, MachineAlertsApi, MachineDeviceStateReportsApi, MachineEngineHoursApi, MachineHoursOfOperationApi, MachineLocationsApi, MapLayersApi, NotificationsApi, OperatorsApi, OrganizationsApi, PartnershipsApi, ProductsApi, UsersApi, WebhookApi } from './api/index.js';
8
8
  import { DeereClient, type DeereClientConfig } from './client.js';
9
+ import { SafeFacades } from './safe/index.js';
9
10
  /**
10
11
  * John Deere SDK
11
12
  *
@@ -23,6 +24,14 @@ import { DeereClient, type DeereClientConfig } from './client.js';
23
24
  * const orgs = await deere.organizations.listAll();
24
25
  * const farms = await deere.farms.listAll(orgs[0].id);
25
26
  * const fields = await deere.fields.listAll(orgs[0].id);
27
+ *
28
+ * // Safe facades force query params that JD's API requires for a complete
29
+ * // response but the raw SDK leaves optional. See src/safe/ and
30
+ * // scripts/embed-contracts.yaml for the contract invariants they enforce.
31
+ * const ops = await deere.safe.fieldOperations.listAllWithMeasurements(
32
+ * orgs[0].id,
33
+ * fields[0].id
34
+ * );
26
35
  * ```
27
36
  */
28
37
  export declare class Deere {
@@ -84,6 +93,11 @@ export declare class Deere {
84
93
  readonly users: UsersApi;
85
94
  /** webhook API */
86
95
  readonly webhook: WebhookApi;
96
+ /**
97
+ * Safe facades that force query params the raw API leaves optional (e.g.
98
+ * `embed=measurementTypes`). See src/safe/ and scripts/embed-contracts.yaml.
99
+ */
100
+ readonly safe: SafeFacades;
87
101
  constructor(config: DeereClientConfig);
88
102
  }
89
103
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"deere.d.ts","sourceRoot":"","sources":["../src/deere.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"deere.d.ts","sourceRoot":"","sources":["../src/deere.ts"],"names":[],"mappings":"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"}
package/dist/deere.js CHANGED
@@ -6,6 +6,7 @@
6
6
  */
7
7
  import { AempApi, AssetsApi, BoundariesApi, ClientsApi, ConnectionManagementApi, CropTypesApi, EquipmentApi, EquipmentMeasurementApi, FarmsApi, FieldOperationsApi, FieldsApi, FilesApi, FlagsApi, GuidanceLinesApi, HarvestIdApi, MachineAlertsApi, MachineDeviceStateReportsApi, MachineEngineHoursApi, MachineHoursOfOperationApi, MachineLocationsApi, MapLayersApi, NotificationsApi, OperatorsApi, OrganizationsApi, PartnershipsApi, ProductsApi, UsersApi, WebhookApi, } from './api/index.js';
8
8
  import { DeereClient } from './client.js';
9
+ import { SafeFacades } from './safe/index.js';
9
10
  /**
10
11
  * John Deere SDK
11
12
  *
@@ -23,6 +24,14 @@ import { DeereClient } from './client.js';
23
24
  * const orgs = await deere.organizations.listAll();
24
25
  * const farms = await deere.farms.listAll(orgs[0].id);
25
26
  * const fields = await deere.fields.listAll(orgs[0].id);
27
+ *
28
+ * // Safe facades force query params that JD's API requires for a complete
29
+ * // response but the raw SDK leaves optional. See src/safe/ and
30
+ * // scripts/embed-contracts.yaml for the contract invariants they enforce.
31
+ * const ops = await deere.safe.fieldOperations.listAllWithMeasurements(
32
+ * orgs[0].id,
33
+ * fields[0].id
34
+ * );
26
35
  * ```
27
36
  */
28
37
  export class Deere {
@@ -84,6 +93,11 @@ export class Deere {
84
93
  users;
85
94
  /** webhook API */
86
95
  webhook;
96
+ /**
97
+ * Safe facades that force query params the raw API leaves optional (e.g.
98
+ * `embed=measurementTypes`). See src/safe/ and scripts/embed-contracts.yaml.
99
+ */
100
+ safe;
87
101
  constructor(config) {
88
102
  this.client = new DeereClient(config);
89
103
  this.aemp = new AempApi(this.client);
@@ -114,6 +128,12 @@ export class Deere {
114
128
  this.products = new ProductsApi(this.client);
115
129
  this.users = new UsersApi(this.client);
116
130
  this.webhook = new WebhookApi(this.client);
131
+ // DO NOT REORDER: SafeFacades reads generated API fields (e.g.
132
+ // `this.fieldOperations`), so it MUST run AFTER every API field has
133
+ // been initialized above. The runtime guard in SafeFacades' constructor
134
+ // fires loudly if this line ever moves ahead of the generated field
135
+ // inits. See scripts/generate-sdk.ts generateMainClass() for the source.
136
+ this.safe = new SafeFacades(this);
117
137
  }
118
138
  }
119
139
  /**
package/dist/deere.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"deere.js","sourceRoot":"","sources":["../src/deere.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"deere.js","sourceRoot":"","sources":["../src/deere.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -32,5 +32,6 @@ export * from './api/index.js';
32
32
  export type { DeereClientConfig, Environment, Link, PaginatedResponse, RequestOptions, } from './client.js';
33
33
  export { AuthError, createClient, DeereClient, DeereError, HateoasError, RateLimitError, } from './client.js';
34
34
  export { createDeere, Deere } from './deere.js';
35
+ export { type FieldOperationIdWithMeasurements, type FieldOperationWithMeasurements, SafeEquipmentApi, SafeFacades, SafeFieldOperationsApi, SafeProductsApi, } from './safe/index.js';
35
36
  export * as Types from './types/index.js';
36
37
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AAGH,cAAc,gBAAgB,CAAC;AAC/B,YAAY,EACV,iBAAiB,EACjB,WAAW,EACX,IAAI,EACJ,iBAAiB,EACjB,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,OAAO,EACL,SAAS,EACT,YAAY,EACZ,WAAW,EACX,UAAU,EACV,YAAY,EACZ,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAGhD,OAAO,KAAK,KAAK,MAAM,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AAGH,cAAc,gBAAgB,CAAC;AAC/B,YAAY,EACV,iBAAiB,EACjB,WAAW,EACX,IAAI,EACJ,iBAAiB,EACjB,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,OAAO,EACL,SAAS,EACT,YAAY,EACZ,WAAW,EACX,UAAU,EACV,YAAY,EACZ,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAIhD,OAAO,EACL,KAAK,gCAAgC,EACrC,KAAK,8BAA8B,EACnC,gBAAgB,EAChB,WAAW,EACX,sBAAsB,EACtB,eAAe,GAChB,MAAM,iBAAiB,CAAC;AAGzB,OAAO,KAAK,KAAK,MAAM,kBAAkB,CAAC"}
package/dist/index.js CHANGED
@@ -34,6 +34,9 @@ export * from './api/index.js';
34
34
  export { AuthError, createClient, DeereClient, DeereError, HateoasError, RateLimitError, } from './client.js';
35
35
  // Main SDK class
36
36
  export { createDeere, Deere } from './deere.js';
37
+ // Safe facades that force query params the raw API leaves optional.
38
+ // See scripts/embed-contracts.yaml and src/safe/ for context.
39
+ export { SafeEquipmentApi, SafeFacades, SafeFieldOperationsApi, SafeProductsApi, } from './safe/index.js';
37
40
  // OpenAPI Types (for advanced usage)
38
41
  export * as Types from './types/index.js';
39
42
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AAEH,cAAc;AACd,cAAc,gBAAgB,CAAC;AAQ/B,mBAAmB;AACnB,OAAO,EACL,SAAS,EACT,YAAY,EACZ,WAAW,EACX,UAAU,EACV,YAAY,EACZ,cAAc,GACf,MAAM,aAAa,CAAC;AACrB,iBAAiB;AACjB,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAEhD,qCAAqC;AACrC,OAAO,KAAK,KAAK,MAAM,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AAEH,cAAc;AACd,cAAc,gBAAgB,CAAC;AAQ/B,mBAAmB;AACnB,OAAO,EACL,SAAS,EACT,YAAY,EACZ,WAAW,EACX,UAAU,EACV,YAAY,EACZ,cAAc,GACf,MAAM,aAAa,CAAC;AACrB,iBAAiB;AACjB,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAEhD,oEAAoE;AACpE,8DAA8D;AAC9D,OAAO,EAGL,gBAAgB,EAChB,WAAW,EACX,sBAAsB,EACtB,eAAe,GAChB,MAAM,iBAAiB,CAAC;AAEzB,qCAAqC;AACrC,OAAO,KAAK,KAAK,MAAM,kBAAkB,CAAC"}