@joymerrevent/porters-connect 0.2.1 → 0.4.0

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,40 @@
5
5
 
6
6
  ## [Unreleased]
7
7
 
8
+ ## [0.4.0] - 2026-06-27
9
+
10
+ ### Added
11
+
12
+ - **Read クエリ面の拡充**(F-2 / ADR-0038・ADR-0005 R-5)。データ系の `search` / `searchAll` が次を受けます。
13
+ - `order` — 並び順 `[{ 項目: "asc" | "desc" }]`(数値・日時・System 型のみ)。
14
+ - `keywords` — テキスト項目の AND キーワード検索(`string[]`・カンマ込み 100 文字まで。超過は送信前に `PortersConfigError`)。
15
+ - `itemstate` — `"existing"`(既定)/ `"deleted"` / `"all"`。削除 API 非提供下で**削除済みデータを読む唯一の手段**
16
+ (`condition` は `P_Id` / `P_UpdateDate` / `P_UpdatedBy` に限定・実行時ガード/更新日 90 日以内は PORTERS 側が自動付与)。
17
+ - 新規 export 型 `Condition` / `Order` / `ItemState` / `SearchQuery`。
18
+
19
+ ### Changed
20
+
21
+ - **(破壊的)`condition` を型安全化**。`{ "Person.P_Name:part": "山田" }`(loose な `Record<string,string>`)から
22
+ **`{ P_Name: { part: "山田" } }`**(項目の Data Type が許す演算子だけを受ける型付き形・ADR-0038 案1a)へ変更。
23
+ 日時の値は ISO 8601(UTC `…Z`)で渡すと PORTERS 形式へ自動変換。**pre-1.0 のため minor**。
24
+ - 移行: キーを `"Alias:suffix"` から**接頭辞なしの項目名**へ、値を `{ suffix: 値 }` へ。
25
+ 例 `{ "Person.P_Id:eq": "1" }` → `{ P_Id: { eq: 1 } }`。テキスト項目は `eq` 不可(`part` / `full`)。
26
+
27
+ ## [0.3.0] - 2026-06-23
28
+
29
+ ### Added
30
+
31
+ - **OAuth 公開面 `porters.auth.*`**(ADR-0007 SD-3/SD-6 / ADR-0034・F-1)。初回のブラウザ権限付与とトークン運用を補助します。
32
+ - `authorizationUrl(opts)` / `revokeUrl(opts)` — ブラウザの `code` / `remove` グラント URL を生成(App Secret は URL に出さない)。
33
+ - `exchangeAuthorizationCode(code)` — redirect の `?code=` をトークンに交換し内部保存(成功時 `void`・失敗時 throw)。
34
+ - `clearTokens()` — ローカルの cache + トークンストアを破棄。
35
+ - `ensureAuthenticated()` / `getToken()` — トークンのウォームアップ/取得(Refresh Token は返さない)。カスタム auth ストラテジでも動作。
36
+ - カスタムストラテジ下では credential 依存メソッドが `PortersConfigError`。新規 export 型 `AuthApi` / `AuthorizationUrlOptions` / `RevokeUrlOptions`。利用手順は [docs/guide/oauth.md][oauth-guide]。
37
+
38
+ ### Fixed
39
+
40
+ - `PortersClientOptions.partition` の JSDoc 誤記(「overridable per call」)を訂正。per-call 上書きは未対応・予定(ADR-0033)で、partition は構築時に固定です(実行時の挙動変更なし)。
41
+
8
42
  ## [0.2.1] - 2026-06-22
9
43
 
10
44
  メンテナンスリリース。**公開 API・実行コードの変更はありません**(`src/` 変更なし)。
@@ -63,9 +97,12 @@
63
97
  - **配布**: ESM / Node.js 18+ / 型定義同梱 / MIT。`X-P-ConnectAPI-Version: 2` を既定送信(PORTERS 8.x・9.x 想定)。
64
98
 
65
99
  [guide]: docs/guide/error-handling.md
100
+ [oauth-guide]: docs/guide/oauth.md
66
101
  [kac]: https://keepachangelog.com/en/1.1.0/
67
102
  [semver]: https://semver.org/
68
- [unreleased]: https://github.com/Joymerrevent/porters-connect/compare/v0.2.1...HEAD
103
+ [unreleased]: https://github.com/Joymerrevent/porters-connect/compare/v0.4.0...HEAD
104
+ [0.4.0]: https://github.com/Joymerrevent/porters-connect/compare/v0.3.0...v0.4.0
105
+ [0.3.0]: https://github.com/Joymerrevent/porters-connect/compare/v0.2.1...v0.3.0
69
106
  [0.2.1]: https://github.com/Joymerrevent/porters-connect/compare/v0.2.0...v0.2.1
70
107
  [0.2.0]: https://github.com/Joymerrevent/porters-connect/compare/v0.1.1...v0.2.0
71
108
  [0.1.1]: https://github.com/Joymerrevent/porters-connect/compare/v0.1.0...v0.1.1
package/README.md CHANGED
@@ -29,7 +29,7 @@ XML レスポンスを型付きオブジェクトに変換し、独自仕様の
29
29
  1. **PORTERS 契約 + Connect API オプション契約**。ホスト名・App ID・App Secret が通知されます。
30
30
  2. **初回のみブラウザで権限付与**(人手・1 回)。`response_type=code` で対象 Company DB の権限を付与します。
31
31
  これを済ませれば、以降はライブラリが `code_direct`(サーバ間・ブラウザ不要)で無人運用できます。
32
- 詳細は [認証 API のフロー][auth-flow]を参照。
32
+ 手順は [OAuth 認証ガイド][oauth-guide] を参照(API 仕様は [認証 API のフロー][auth-flow])。
33
33
 
34
34
  ## インストール
35
35
 
@@ -59,9 +59,10 @@ const porters = new PortersClient({
59
59
  partition: 123, // Partition(Company DB)Id
60
60
  });
61
61
 
62
- // 検索(最大 200 件/ページ)
62
+ // 検索(最大 200 件/ページ)。condition は項目の Data Type ごとに型付き
63
63
  const page = await porters.candidate.search({
64
- condition: { "Person.P_Name:part": "山田" }, // 部分一致
64
+ condition: { P_Name: { part: "山田" } }, // テキストは part(部分一致)/ full(完全一致)
65
+ order: [{ P_UpdateDate: "desc" }], // 並び順(数値・日時・System のみ)
65
66
  count: 50,
66
67
  });
67
68
  console.log(page.total, page.items.length);
@@ -72,7 +73,7 @@ console.log(one?.P_Name);
72
73
 
73
74
  // 全件を自動ページング(200 件刻み)
74
75
  for await (const c of porters.candidate.searchAll({
75
- condition: { "Person.P_Prefecture:eq": "東京都" },
76
+ condition: { P_Prefecture: { full: "東京都" } },
76
77
  })) {
77
78
  // c は 1 件ずつ
78
79
  }
@@ -137,6 +138,22 @@ new PortersClient({ host, appId, appSecret, partition, tokenStore });
137
138
 
138
139
  `transport`(HTTP 注入)や `auth`(独自 `TokenProvider`)も差し替え可能です。
139
140
 
141
+ ### 初回の権限付与(`porters.auth.*`)
142
+
143
+ 初回だけは人手でブラウザでの権限付与が必要です(「前提」を参照)。ライブラリは認可 URL の生成と `code` 交換を補助します。
144
+
145
+ ```ts
146
+ // 1) 認可 URL を生成 → ユーザーのブラウザで開く(ログイン → 承諾)
147
+ const url = porters.auth.authorizationUrl({
148
+ redirectUrl: "https://app.example.com/porters/callback",
149
+ });
150
+
151
+ // 2) redirect で戻る ?code= を交換(30 秒以内)。以後は透過運用に乗る
152
+ await porters.auth.exchangeAuthorizationCode(code);
153
+ ```
154
+
155
+ > 起動時確認 `ensureAuthenticated()`、利用終了 `revokeUrl()` + `clearTokens()`、カスタムストラテジ時の挙動など `porters.auth.*` の全手順は [OAuth 認証ガイド][oauth-guide] にまとめています。
156
+
140
157
  ## リソースと操作
141
158
 
142
159
  すべてのデータ系リソースは同じ形のアクセサを持ちます。
@@ -156,16 +173,21 @@ new PortersClient({ host, appId, appSecret, partition, tokenStore });
156
173
  - `create(input)` → 採番された **id(number)**。
157
174
  - `update(id, input)` → その **id**。
158
175
 
159
- **検索クエリ**(`query`)の主なキー:
176
+ **検索クエリ**(`query`)の主なキー(すべて型安全。**項目の Data Type が許す演算子だけ**を受けます):
160
177
 
161
178
  - `field`:取得する項目(接頭辞付き alias の配列。例 `["Person.P_Id", "Person.P_Name"]`)。
162
179
  **省略するとカタログ上の全項目を既定取得**します(PORTERS は field 未指定だと主キーのみ返すため、
163
180
  ライブラリが既定 field を補います)。`field: []`(空配列)を渡すと API 仕様どおり**主キーのみ**を返します(件数取得など)。
164
- - `condition`:検索条件。`{ "[Alias]:[suffix]": "値" }` 形式。`suffix` は型ごとに
165
- `eq`/`gt`/`ge`/`le`/`lt`(数値・日時)、`part`/`full`(テキスト)、`or`/`and`(Option)。
181
+ - `condition`:検索条件。`{ 項目: { 演算子: 値 } }` 形式(複数項目は AND)。演算子は Data Type ごとに
182
+ `eq`/`gt`/`ge`/`le`/`lt`(数値・日時・Id)、`part`/`full`(テキスト)、`or`/`and`(Option・参照/ユーザー型は ID)。
183
+ **日時の値は ISO 8601(UTC `…Z`)**で渡すと PORTERS 形式へ自動変換します。
184
+ - `order`:並び順。`[{ 項目: "asc" | "desc" }]`(数値・日時・System 型のみ)。
185
+ - `keywords`:テキスト項目のキーワード AND 検索(`string[]`・カンマ込み **100 文字まで**)。
186
+ - `itemstate`:`"existing"`(既定)/ `"deleted"` / `"all"`。削除済みデータの取得。
166
187
  - `count`(1–200・既定 10)、`start`(0 始まり)。
167
188
 
168
- > **削除 API はありません**(PORTERS 仕様)。`delete()` メソッドは提供しません。削除済みは検索の状態フィルタで扱います。
189
+ > **削除 API はありません**(PORTERS 仕様)。`delete()` メソッドは提供しません。削除済みは `itemstate: "deleted"` で読みます
190
+ > (`condition` は `P_Id` / `P_UpdateDate` / `P_UpdatedBy` に限られ、更新日は 90 日以内)。
169
191
 
170
192
  ### マスタ Read(読み取り専用)
171
193
 
@@ -341,6 +363,7 @@ try {
341
363
  [coc]: ./CODE_OF_CONDUCT.md
342
364
  [issues]: https://github.com/Joymerrevent/porters-connect/issues
343
365
  [auth-flow]: ./docs/reference/authentication-api/README.md
366
+ [oauth-guide]: ./docs/guide/oauth.md
344
367
  [error-handling]: ./docs/guide/error-handling.md
345
368
  [sandbox]: ./examples/offline-sandbox.ts
346
369
  [adr]: ./docs/adr/README.md
package/dist/index.d.ts CHANGED
@@ -75,6 +75,54 @@ type MockTransportOptions = {
75
75
  */
76
76
  declare const createMockTransport: (handler: MockHandler, options?: MockTransportOptions) => Transport;
77
77
 
78
+ /** OAuth scope string: `<resource>_r` (read) or `<resource>_w` (write). */
79
+ type Scope = `${string}_r` | `${string}_w`;
80
+ /** A PORTERS partition (Company DB) id. */
81
+ type PartitionId = number;
82
+
83
+ /** Shared options for the browser `code` / `remove` OAuth URLs (oauth.md). */
84
+ type AuthorizationUrlOptions = {
85
+ /** Registered Redirect URL the browser returns to (required for code/remove). */
86
+ redirectUrl: string;
87
+ /** Scopes to grant/remove; defaults to the client's configured `scopes`. */
88
+ scopes?: Scope[];
89
+ /** Opaque value echoed back on redirect (e.g. CSRF defense). */
90
+ state?: string;
91
+ };
92
+ /** Options for the `remove` (de-authorization) browser URL. */
93
+ type RevokeUrlOptions = AuthorizationUrlOptions;
94
+ /**
95
+ * The `porters.auth.*` surface (ADR-0007 SD-3/SD-6). The initial per-Company-DB grant
96
+ * needs a human to open {@link AuthApi.authorizationUrl} in a browser and consent; the
97
+ * library only builds the URL and exchanges the returned `code`. Day-to-day token
98
+ * acquisition/refresh stays transparent (the default strategy), so most callers never
99
+ * touch this surface.
100
+ */
101
+ type AuthApi = {
102
+ /** Build the browser `code`-grant URL to open for the initial permission grant. */
103
+ authorizationUrl(opts: AuthorizationUrlOptions): string;
104
+ /**
105
+ * Exchange a redirect `?code=` for tokens and save them into the default strategy.
106
+ * Resolves `void` on success (tokens are stored internally — inspect via
107
+ * {@link AuthApi.getToken}); throws on failure: {@link PortersConfigError} (missing
108
+ * credentials / custom strategy), `PortersAuthError` (token-endpoint error or expired
109
+ * code), or `PortersNetworkError`.
110
+ */
111
+ exchangeAuthorizationCode(code: string): Promise<void>;
112
+ /**
113
+ * Build the browser `remove`-grant URL to open for server-side de-authorization.
114
+ * PORTERS has no server-to-server removal, so completing it stays a browser step;
115
+ * pair with {@link AuthApi.clearTokens} to drop the local copy.
116
+ */
117
+ revokeUrl(opts: RevokeUrlOptions): string;
118
+ /** Forget cached + stored tokens locally. Does not de-authorize server-side. */
119
+ clearTokens(): Promise<void>;
120
+ /** Acquire a token now (startup fail-fast / warm-up); throws if auth is unavailable. */
121
+ ensureAuthenticated(): Promise<void>;
122
+ /** Return the current valid Access Token (debug). The Refresh Token is never exposed. */
123
+ getToken(): Promise<string>;
124
+ };
125
+
78
126
  type DataType = "System[Id]" | "Number" | "DateTime" | "System[DateTime]" | "Date" | "Age" | "SinglelineText" | "MultilineText" | "Mail" | "Telephone" | "URL" | "User" | "Option" | "System[Reference]";
79
127
  /** A referenced User (Read is nested; Write is `User.P_Id` only). */
80
128
  type UserRef = {
@@ -113,7 +161,75 @@ type ResourcePage<F extends FieldCatalog> = {
113
161
  start: number;
114
162
  };
115
163
 
116
- type SearchQuery = {
164
+ /** Comparable ops for numeric Ids (System[Id]); `or` matches a set of Resource Ids (`P_Id:or=1:2`). */
165
+ type IdCondition = {
166
+ gt?: number;
167
+ ge?: number;
168
+ eq?: number;
169
+ le?: number;
170
+ lt?: number;
171
+ or?: number[];
172
+ };
173
+ /** Comparable ops for Number. */
174
+ type NumberCondition = {
175
+ gt?: number;
176
+ ge?: number;
177
+ eq?: number;
178
+ le?: number;
179
+ lt?: number;
180
+ };
181
+ /** Comparable ops for date/time fields. Values are ISO 8601 (UTC `…Z`); normalised to PORTERS on send. */
182
+ type TemporalCondition = {
183
+ gt?: string;
184
+ ge?: string;
185
+ eq?: string;
186
+ le?: string;
187
+ lt?: string;
188
+ };
189
+ /** Text match. `full` = exact, `part` = substring (PORTERS default). */
190
+ type TextCondition = {
191
+ full?: string;
192
+ part?: string;
193
+ };
194
+ /** Option-select match; values are option aliases (e.g. `Option.P_SE`), OR/AND-joined. */
195
+ type OptionCondition = {
196
+ or?: string[];
197
+ and?: string[];
198
+ };
199
+ /** Link/reference match by id (User / System[Reference]): `eq` one id, or OR/AND a set of ids. */
200
+ type ReferenceCondition = {
201
+ eq?: number;
202
+ or?: number[];
203
+ and?: number[];
204
+ };
205
+ /** The condition-operator object a field of Data Type `D` accepts. */
206
+ type ConditionFor<D extends DataType> = D extends "System[Id]" ? IdCondition : D extends "Number" ? NumberCondition : D extends "DateTime" | "System[DateTime]" | "Date" | "Age" ? TemporalCondition : D extends "SinglelineText" | "MultilineText" | "Mail" | "Telephone" | "URL" ? TextCondition : D extends "Option" ? OptionCondition : D extends "User" | "System[Reference]" ? ReferenceCondition : never;
207
+ /**
208
+ * A typed search condition over a catalog: each field maps to the operator object its Data Type
209
+ * allows (ADR-0038 案1a). Multiple fields are AND-joined (reference). Unknown aliases / wrong
210
+ * operators are type errors. Custom `U_`/`A_` fields are not in the catalog — condition on them via
211
+ * a cast (the encoder passes unknown aliases through as raw scalars, like read/write).
212
+ */
213
+ type Condition<F extends FieldCatalog> = {
214
+ [K in keyof F]?: ConditionFor<F[K]>;
215
+ };
216
+ type OrderableDataType = "System[Id]" | "System[DateTime]" | "Number" | "DateTime" | "Date" | "Age";
217
+ type OrderableKeys<F extends FieldCatalog> = {
218
+ [K in keyof F]: F[K] extends OrderableDataType ? K : never;
219
+ }[keyof F];
220
+ /**
221
+ * Sort spec: an ordered list of `{ field: "asc" | "desc" }`, encoded in array (then key) order. Only
222
+ * orderable Data Types (Number/Date/DateTime/Age/System) are accepted (reference).
223
+ */
224
+ type Order<F extends FieldCatalog> = Array<Partial<Record<OrderableKeys<F>, "asc" | "desc">>>;
225
+ /**
226
+ * Which delete state to read. Omitting (or `existing`) reads live data; `deleted`/`all` read deleted
227
+ * records — the only way to read deleted data, since there is no delete API. When `deleted`/`all`,
228
+ * condition is restricted to `P_Id` / `P_UpdateDate` / `P_UpdatedBy` and PORTERS auto-adds a
229
+ * "updated within 90 days" filter (`P_UpdateDate` = the delete time, `P_UpdatedBy` = the last editor).
230
+ */
231
+ type ItemState = "existing" | "deleted" | "all";
232
+ type SearchQuery<F extends FieldCatalog = FieldCatalog> = {
117
233
  /**
118
234
  * Output fields as prefixed aliases (e.g. `Person.P_Name`). **Omit** to fetch every catalogued
119
235
  * field by default (ADR-0020): PORTERS returns only the primary key for a fieldless request, so
@@ -121,10 +237,21 @@ type SearchQuery = {
121
237
  * API-native "primary key only" response (e.g. counting). A non-empty list is sent verbatim.
122
238
  */
123
239
  field?: string[];
124
- condition?: Record<string, string>;
240
+ /** Typed AND-conditions; each field's operators derive from its Data Type (ADR-0038). */
241
+ condition?: Condition<F>;
242
+ /** Sort order; orderable Data Types only (Number/Date/DateTime/Age/System). */
243
+ order?: Order<F>;
244
+ /**
245
+ * Keyword AND-search over text fields (MultilineText/SinglelineText/Mail/URL; Telephone digits
246
+ * only). OR is not supported. Max 100 characters including commas — guarded before send.
247
+ */
248
+ keywords?: string[];
249
+ /** Delete-state filter (default `existing`). `deleted`/`all` restrict `condition` — see {@link ItemState}. */
250
+ itemstate?: ItemState;
125
251
  count?: number;
126
252
  start?: number;
127
253
  };
254
+
128
255
  type WritableKeys<F extends FieldCatalog> = {
129
256
  [K in keyof F]: F[K] extends WritableDataType ? K : never;
130
257
  }[keyof F];
@@ -142,9 +269,9 @@ type UpdateInput<F extends FieldCatalog> = {
142
269
  [K in WritableKeys<F>]?: WriteValueOf<F[K]> | null;
143
270
  };
144
271
  type Resource<F extends FieldCatalog, Req extends keyof F> = {
145
- search(query?: SearchQuery): Promise<ResourcePage<F>>;
272
+ search(query?: SearchQuery<F>): Promise<ResourcePage<F>>;
146
273
  /** Auto-paginating search: yields every matching record (200 per page). */
147
- searchAll(query?: Omit<SearchQuery, "count" | "start">): AsyncIterable<ReadRecord<F>>;
274
+ searchAll(query?: Omit<SearchQuery<F>, "count" | "start">): AsyncIterable<ReadRecord<F>>;
148
275
  get(id: number): Promise<ReadRecord<F> | undefined>;
149
276
  /** Create one record; resolves to the newly assigned id. */
150
277
  create(input: CreateInput<F, Req>): Promise<number>;
@@ -176,7 +303,7 @@ declare const REQUIRED_ON_CREATE$4: readonly ["P_Owner"];
176
303
  /** A decoded Candidate: known `P_` fields, each requested field `value | null`. */
177
304
  type Candidate = ReadRecord<typeof FIELDS$8>;
178
305
  type CandidatePage = ResourcePage<typeof FIELDS$8>;
179
- type CandidateSearchQuery = SearchQuery;
306
+ type CandidateSearchQuery = SearchQuery<typeof FIELDS$8>;
180
307
  /** Fields for `create`: `P_Owner` is required; `P_Id` / system timestamps are not settable. */
181
308
  type CandidateCreateInput = CreateInput<typeof FIELDS$8, (typeof REQUIRED_ON_CREATE$4)[number]>;
182
309
  /** Fields for `update`: all optional (`null` omits, `""` clears a text field). */
@@ -224,7 +351,7 @@ declare const REQUIRED_ON_CREATE$3: readonly ["P_Owner", "P_Client", "P_Recruite
224
351
  /** A decoded Job: known `P_` fields, each requested field `value | null`. */
225
352
  type Job = ReadRecord<typeof FIELDS$7>;
226
353
  type JobPage = ResourcePage<typeof FIELDS$7>;
227
- type JobSearchQuery = SearchQuery;
354
+ type JobSearchQuery = SearchQuery<typeof FIELDS$7>;
228
355
  /** Fields for `create`: `P_Owner` required; `P_Id` / system timestamps are not settable. */
229
356
  type JobCreateInput = CreateInput<typeof FIELDS$7, (typeof REQUIRED_ON_CREATE$3)[number]>;
230
357
  /** Fields for `update`: all optional (`null` omits, `""` clears a text field). */
@@ -256,7 +383,7 @@ declare const REQUIRED_ON_CREATE$2: readonly ["P_Owner"];
256
383
  /** A decoded Client (company): known `P_` fields, each requested field `value | null`. */
257
384
  type Client = ReadRecord<typeof FIELDS$6>;
258
385
  type ClientPage = ResourcePage<typeof FIELDS$6>;
259
- type ClientSearchQuery = SearchQuery;
386
+ type ClientSearchQuery = SearchQuery<typeof FIELDS$6>;
260
387
  /** Fields for `create`: `P_Owner` required; `P_Id` / system timestamps are not settable. */
261
388
  type ClientCreateInput = CreateInput<typeof FIELDS$6, (typeof REQUIRED_ON_CREATE$2)[number]>;
262
389
  /** Fields for `update`: all optional (`null` omits, `""` clears a text field). */
@@ -289,7 +416,7 @@ declare const REQUIRED_ON_CREATE$1: readonly ["P_Owner", "P_Client", "P_Recruite
289
416
  * requested field `value | null`. */
290
417
  type Process = ReadRecord<typeof FIELDS$5>;
291
418
  type ProcessPage = ResourcePage<typeof FIELDS$5>;
292
- type ProcessSearchQuery = SearchQuery;
419
+ type ProcessSearchQuery = SearchQuery<typeof FIELDS$5>;
293
420
  /** Fields for `create`: `P_Owner` required; `P_Id` / system timestamps are not settable. */
294
421
  type ProcessCreateInput = CreateInput<typeof FIELDS$5, (typeof REQUIRED_ON_CREATE$1)[number]>;
295
422
  /** Fields for `update`: all optional (`null` omits, `""` clears a text field). */
@@ -334,7 +461,7 @@ declare const REQUIRED_ON_CREATE: readonly ["P_Owner", "P_Candidate"];
334
461
  * `value | null`. */
335
462
  type Resume = ReadRecord<typeof FIELDS$4>;
336
463
  type ResumePage = ResourcePage<typeof FIELDS$4>;
337
- type ResumeSearchQuery = SearchQuery;
464
+ type ResumeSearchQuery = SearchQuery<typeof FIELDS$4>;
338
465
  /** Fields for `create`: `P_Owner` required; `P_Id` / system timestamps are not settable. */
339
466
  type ResumeCreateInput = CreateInput<typeof FIELDS$4, (typeof REQUIRED_ON_CREATE)[number]>;
340
467
  /** Fields for `update`: all optional (`null` omits, `""` clears a text field). */
@@ -577,11 +704,6 @@ type CustomFor<C extends DeclaredCatalogs, K extends CustomFieldResource> = K ex
577
704
  */
578
705
  declare const defineFields: <D extends FieldDecls>(decls: D) => DefinedFields<DeclaredCatalogsOf<D>>;
579
706
 
580
- /** OAuth scope string: `<resource>_r` (read) or `<resource>_w` (write). */
581
- type Scope = `${string}_r` | `${string}_w`;
582
- /** A PORTERS partition (Company DB) id. */
583
- type PartitionId = number;
584
-
585
707
  /** Options for constructing a {@link PortersClient}. `C` is inferred from `fields` (ADR-0023). */
586
708
  type PortersClientOptions<C extends DeclaredCatalogs = EmptyCatalog> = {
587
709
  /**
@@ -592,7 +714,7 @@ type PortersClientOptions<C extends DeclaredCatalogs = EmptyCatalog> = {
592
714
  appId?: string;
593
715
  appSecret?: string;
594
716
  scopes?: Scope[];
595
- /** Default partition; overridable per call (ADR-0008). */
717
+ /** Partition (Company DB) used for every call. Per-call override is not yet supported (planned — see ADR-0033). */
596
718
  partition?: PartitionId;
597
719
  /** Custom auth strategy; defaults to the transparent code_direct strategy. */
598
720
  auth?: TokenProvider;
@@ -620,6 +742,8 @@ declare class PortersClient<C extends DeclaredCatalogs = EmptyCatalog> {
620
742
  readonly process: ProcessResource<CustomFor<C, "process">>;
621
743
  readonly resume: ResumeResource<CustomFor<C, "resume">>;
622
744
  readonly attachment: AttachmentResource;
745
+ /** OAuth surface: initial browser grant, token warm-up/inspection, local revoke (ADR-0007/0034). */
746
+ readonly auth: AuthApi;
623
747
  /** Master Read: accessible partitions (ADR-0021/0022). */
624
748
  readonly partition: PartitionResource;
625
749
  /** Master Read: users, plus `current()` self-identification (ADR-0021/0022). */
@@ -681,4 +805,4 @@ declare const bytesToBase64: (bytes: Uint8Array) => string;
681
805
  /** Decode a Base64 string back to raw bytes. */
682
806
  declare const base64ToBytes: (b64: string) => Uint8Array;
683
807
 
684
- export { type Attachment, type AttachmentCreate, type AttachmentPage, type AttachmentResource, type AttachmentSearchQuery, type AttachmentUpdate, type Candidate, type CandidateCreateInput, type CandidatePage, type CandidateResource, type CandidateSearchQuery, type CandidateUpdateInput, type Client, type ClientCreateInput, type ClientPage, type ClientResource, type ClientSearchQuery, type ClientUpdateInput, type CustomDataType, type DefinedFields, type ErrorCategory, type Field, type FieldBuilder, type FieldDecls, type FieldDef, type FieldPage, type FieldResource, type FieldSearchQuery, type FieldValue, type GetAccessTokenOptions, type Job, type JobCreateInput, type JobPage, type JobResource, type JobSearchQuery, type JobUpdateInput, type MockHandler, type MockReply, type MockTransportOptions, type Option, type OptionResource, type OptionSearchQuery, type Partition, type PartitionId, type PartitionPage, type PartitionResource, type PartitionSearchQuery, PortersAuthError, PortersClient, type PortersClientOptions, PortersConfigError, PortersError, type PortersErrorContext, type PortersErrorOptions, PortersNetworkError, PortersResourceError, type Process, type ProcessCreateInput, type ProcessPage, type ProcessResource, type ProcessSearchQuery, type ProcessUpdateInput, type ResourceType, type Resume, type ResumeCreateInput, type ResumePage, type ResumeResource, type ResumeSearchQuery, type ResumeUpdateInput, type Scope, type StoredTokens, type TokenProvider, type TokenStore, type Transport, type TransportRequest, type TransportResponse, type User, type UserPage, type UserRef, type UserResource, type UserSearchQuery, base64ToBytes, bytesToBase64, createMockTransport, defineFields };
808
+ export { type Attachment, type AttachmentCreate, type AttachmentPage, type AttachmentResource, type AttachmentSearchQuery, type AttachmentUpdate, type AuthApi, type AuthorizationUrlOptions, type Candidate, type CandidateCreateInput, type CandidatePage, type CandidateResource, type CandidateSearchQuery, type CandidateUpdateInput, type Client, type ClientCreateInput, type ClientPage, type ClientResource, type ClientSearchQuery, type ClientUpdateInput, type Condition, type CustomDataType, type DefinedFields, type ErrorCategory, type Field, type FieldBuilder, type FieldDecls, type FieldDef, type FieldPage, type FieldResource, type FieldSearchQuery, type FieldValue, type GetAccessTokenOptions, type ItemState, type Job, type JobCreateInput, type JobPage, type JobResource, type JobSearchQuery, type JobUpdateInput, type MockHandler, type MockReply, type MockTransportOptions, type Option, type OptionResource, type OptionSearchQuery, type Order, type Partition, type PartitionId, type PartitionPage, type PartitionResource, type PartitionSearchQuery, PortersAuthError, PortersClient, type PortersClientOptions, PortersConfigError, PortersError, type PortersErrorContext, type PortersErrorOptions, PortersNetworkError, PortersResourceError, type Process, type ProcessCreateInput, type ProcessPage, type ProcessResource, type ProcessSearchQuery, type ProcessUpdateInput, type ResourceType, type Resume, type ResumeCreateInput, type ResumePage, type ResumeResource, type ResumeSearchQuery, type ResumeUpdateInput, type RevokeUrlOptions, type Scope, type SearchQuery, type StoredTokens, type TokenProvider, type TokenStore, type Transport, type TransportRequest, type TransportResponse, type User, type UserPage, type UserRef, type UserResource, type UserSearchQuery, base64ToBytes, bytesToBase64, createMockTransport, defineFields };