Skip to content

Commit 3ee4690

Browse files
committed
Add missing Authors API endpoints and CLAUDE.md
1 parent 63ee91a commit 3ee4690

5 files changed

Lines changed: 304 additions & 4 deletions

File tree

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"@arcxp/sdk-ts": minor
3+
---
4+
5+
Add missing Authors API endpoints: getAuthor, createAuthor, updateAuthor, getConfiguration. Expand ListAuthorsParams with full filter support.
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
---
2+
name: sdk-creator
3+
description: ArcXP SDK TypeScript contribution assistant. Use when the user wants to contribute to the ArcXP SDK, add API endpoints, fetch OpenAPI specs, or work on arcxp-sdk-ts.
4+
---
5+
6+
# ArcXP SDK Contribution Assistant
7+
8+
You help developers contribute to the ArcXP SDK TypeScript project.
9+
10+
## Fetching API Specs
11+
12+
When you need an OpenAPI specification for an ArcXP API, use `WebFetch` to retrieve it from the URLs below. Pass the prompt: "Return the full JSON content as-is."
13+
14+
| API | URL |
15+
| ---------------- | --------------------------------------------------------------------------------------------- |
16+
| subscription | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/subs-apis.json` |
17+
| migration_center | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/mc-v3.json` |
18+
| content_api | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/content-api.json` |
19+
| ifx | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/ifx/admin/prod/swagger.json` |
20+
| draft | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/prod.draft.json` |
21+
| settings | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/arc-settings.json` |
22+
| photo | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/arc-anglerfish.json` |
23+
| tags | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/tags.json` |
24+
| video | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/video-center.json` |
25+
| identity | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/subs-apis.json` |
26+
| authors | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/authors.json` |
27+
| contentops | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/contentops-api.json` |
28+
| preview | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/preview-api.json` |
29+
| site | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/site-api.json` |
30+
| video_center | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/video-center.json` |
31+
| websked | `https://alc-swagger-template.s3.amazonaws.com/docs/swagger/arc-products/websked.json` |
32+
33+
## Project Structure
34+
35+
- **APIs:** Located under `./src/api/`
36+
Each API directory contains:
37+
- `index.ts` - API implementation class (extends `AbstractAPIClient`)
38+
- `types.ts` - Request/response object types (specific to each endpoint)
39+
40+
- **Global Types:** Located under `./types/*.ts`
41+
- Generated from **ANS (ArcXP Native Schema)**
42+
- Contain common entities (e.g. `AStory`, `AnImage`, etc.)
43+
44+
## Type Handling
45+
46+
- **Parameters**
47+
- Always define params types **locally** in the API's `types.ts`. Use `Params` (Query params) or `Payload` (POST request data) suffix for the type name.
48+
- Example: `GetStoryParams` in `./src/api/stories/types.ts`.
49+
50+
- **Responses**
51+
- First, check `./types/*.ts` for a matching global type (`AStory`, `AnImage`, ...).
52+
- If it exists - import and use it.
53+
- If it doesn't exist - define a local type in the API's `types.ts`.
54+
55+
- **Unclear specs**
56+
- If the spec only provides a simple marker like `{ "type": "story" }` - look for a global type (e.g. `AStory`).
57+
- If still not clear, confirm with the user which type to use.
58+
59+
- **Do not duplicate type definitions.**
60+
61+
## Implementation Guidelines
62+
63+
- Before proceeding fetch an OpenAPI schema and identify what's missing
64+
- **Follow existing structure and style.**
65+
- **Do not overwrite existing implementations.**
66+
- Write code like a **senior developer**: Concise, ESM-based, consistent naming conventions. Keep APIs predictable and clean.
67+
68+
## Example Endpoint
69+
70+
```ts
71+
async getStory(params: GetStoryParams): Promise<AStory> {
72+
const { data } = await this.client.get('/stories', { params });
73+
return data;
74+
}
75+
```
76+
77+
- `GetStoryParams` - defined locally in `./types.ts` (under `stories/`).
78+
- `AStory` - imported from global `../../types.ts`.
79+
80+
## Changeset
81+
82+
After making changes, create a changeset file manually in the `.changeset/` folder:
83+
84+
1. Create a file named after the feature, e.g. `.changeset/add-bulk-get-stories.md`
85+
2. Use this format:
86+
87+
```md
88+
---
89+
'@arcxp/sdk-ts': minor
90+
---
91+
92+
Add bulkGetStories method to Content API
93+
```
94+
95+
- Set the bump type (`patch`, `minor`, or `major`) as appropriate
96+
- Write a short description of what changed

CLAUDE.md

Lines changed: 118 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,118 @@
1+
# CLAUDE.md
2+
3+
## Project Overview
4+
5+
ArcXP SDK for TypeScript — a strongly typed wrapper around ArcXP REST APIs. ESM-only, published as `@code.store/arcxp-sdk-ts`.
6+
7+
## Tech Stack
8+
9+
- **Runtime:** Node.js >= 22
10+
- **Package Manager:** pnpm >= 10
11+
- **Language:** TypeScript (strict mode, ESM with `.js` extensions in imports)
12+
- **Build:** Rollup (outputs ESM + CJS)
13+
- **Linter/Formatter:** Biome (single quotes, trailing commas, semicolons, 120 line width, spaces)
14+
- **Tests:** Vitest + nock for HTTP mocking
15+
- **Changesets:** `@changesets/cli` for versioning
16+
17+
## Commands
18+
19+
| Task | Command |
20+
|------|---------|
21+
| Type-check | `tsc --noEmit` |
22+
| Build | `pnpm build` |
23+
| Test | `pnpm test` |
24+
| Lint + fix | `pnpm lint` |
25+
| Format | `pnpm format` |
26+
| Check (biome) | `pnpm check` |
27+
28+
Always run `tsc --noEmit` after making changes to verify types.
29+
30+
## Project Structure
31+
32+
```
33+
src/
34+
api/ # API client implementations
35+
abstract-api.ts # Base class (ArcAbstractAPI) all API clients extend
36+
index.ts # ArcAPI factory — registers all API clients
37+
<api-name>/
38+
index.ts # API class (extends ArcAbstractAPI)
39+
types.ts # Request params / response types for this API
40+
types/ # Global ANS types (AStory, AnImage, etc.) — auto-generated, do not edit manually
41+
tests/ # Test files (*.test.ts)
42+
utils/ # Shared utilities
43+
.changeset/ # Changeset files for versioning
44+
```
45+
46+
## Contributing API Endpoints
47+
48+
### Workflow
49+
50+
1. **Fetch the OpenAPI spec** for the target API using the `sdk-creator` skill (it has URLs for all ArcXP APIs).
51+
2. **Read existing code** in `src/api/<api-name>/` before changing anything.
52+
3. **Identify missing endpoints** by comparing the spec to the implementation.
53+
4. **Implement** following the patterns below, then type-check with `tsc --noEmit`.
54+
5. **Create a changeset** in `.changeset/` (see below).
55+
56+
### API Implementation Pattern
57+
58+
Each API client extends `ArcAbstractAPI` and is registered in `src/api/index.ts`.
59+
60+
```ts
61+
// src/api/example/index.ts
62+
import { ArcAbstractAPI, type ArcAPIOptions } from '../abstract-api.js';
63+
import type { GetThingParams, CreateThingPayload, Thing } from './types.js';
64+
65+
export class ArcExample extends ArcAbstractAPI {
66+
constructor(options: ArcAPIOptions) {
67+
super({ ...options, apiPath: 'example' });
68+
}
69+
70+
async getThing(params: GetThingParams): Promise<Thing> {
71+
const { data } = await this.client.get<Thing>('/v1/things', { params });
72+
return data;
73+
}
74+
75+
async createThing(payload: CreateThingPayload): Promise<Thing> {
76+
const { data } = await this.client.post<Thing>('/v1/things', payload);
77+
return data;
78+
}
79+
}
80+
```
81+
82+
### Type Conventions
83+
84+
- **Params types** (query params): suffix with `Params` — e.g. `ListAuthorsParams`. Define in the API's local `types.ts`.
85+
- **Payload types** (POST body): suffix with `Payload` — e.g. `CreateAuthorPayload`. Define in the API's local `types.ts`.
86+
- **Response types**: check `src/types/` for existing global ANS types first. Only define locally if no global type exists.
87+
- **Do not duplicate types** that already exist globally.
88+
89+
### Changeset
90+
91+
After making changes, create a file in `.changeset/` named after the feature:
92+
93+
```md
94+
---
95+
"@arcxp/sdk-ts": minor
96+
---
97+
98+
Add getAuthor and createAuthor methods to Author API
99+
```
100+
101+
Use `patch` for fixes, `minor` for new endpoints/features, `major` for breaking changes.
102+
103+
## Code Style Rules
104+
105+
- ESM imports with `.js` extensions (e.g. `'../abstract-api.js'`)
106+
- Use `type` keyword for type-only imports
107+
- Single quotes, semicolons, trailing commas (es5), arrow parens always
108+
- Indent with spaces (2), max line width 120
109+
- No unused variables or imports (enforced by biome)
110+
- Keep methods concise — destructure `{ data }` from axios response and return directly
111+
- Name methods clearly: `getX`, `listX`, `createX`, `updateX`, `deleteX`
112+
113+
## Things to Avoid
114+
115+
- Do not edit files in `src/types/` — these are auto-generated from ANS schemas
116+
- Do not overwrite existing endpoint implementations without being asked
117+
- Do not add dependencies without explicit approval
118+
- Do not use `any` unless truly unavoidable (biome allows it but prefer proper types)

src/api/author/index.ts

Lines changed: 29 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,45 @@
11
import { ArcAbstractAPI, type ArcAPIOptions } from '../abstract-api.js';
2-
import type { ListAuthorsParams, ListAuthorsResponse } from './types.js';
2+
import type {
3+
AuthorANS,
4+
AuthorConfigurationResponse,
5+
CreateAuthorPayload,
6+
GetAuthorParams,
7+
ListAuthorsParams,
8+
ListAuthorsResponse,
9+
UpdateAuthorPayload,
10+
} from './types.js';
311

412
export class ArcAuthor extends ArcAbstractAPI {
513
constructor(options: ArcAPIOptions) {
614
super({ ...options, apiPath: 'author' });
715
}
816

17+
async getAuthor(params: GetAuthorParams): Promise<AuthorANS> {
18+
const { data } = await this.client.get<AuthorANS>('/v1/author-service', { params });
19+
return data;
20+
}
21+
922
async listAuthors(params?: ListAuthorsParams): Promise<ListAuthorsResponse> {
10-
const { data } = await this.client.get('/v2/author-service', { params });
23+
const { data } = await this.client.get<ListAuthorsResponse>('/v2/author-service', { params });
24+
return data;
25+
}
1126

27+
async createAuthor(payload: CreateAuthorPayload): Promise<AuthorANS> {
28+
const { data } = await this.client.post<AuthorANS>('/v2/author-service', payload);
1229
return data;
1330
}
1431

15-
async delete(userId: string): Promise<void> {
16-
const { data } = await this.client.delete(`/v2/author-service/${userId}`);
32+
async updateAuthor(id: string, payload: UpdateAuthorPayload): Promise<AuthorANS> {
33+
const { data } = await this.client.post<AuthorANS>(`/v2/author-service/${id}`, payload);
34+
return data;
35+
}
36+
37+
async deleteAuthor(id: string): Promise<void> {
38+
await this.client.delete(`/v2/author-service/${id}`);
39+
}
1740

41+
async getConfiguration(): Promise<AuthorConfigurationResponse> {
42+
const { data } = await this.client.get<AuthorConfigurationResponse>('/v1/configuration');
1843
return data;
1944
}
2045
}

src/api/author/types.ts

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,12 @@
11
export type ListAuthorsParams = Partial<{
2+
sort_by: 'lastName' | 'last_updated_date';
3+
order: 'asc' | 'desc';
4+
byline: string;
5+
email: string;
6+
firstName: string;
7+
lastName: string;
8+
slug: string;
9+
include_inactive: boolean;
210
limit: number;
311
last: string;
412
}>;
@@ -9,6 +17,36 @@ export type ListAuthorsResponse = {
917
last?: string;
1018
};
1119

20+
export type CreateAuthorPayload = Omit<AuthorANS, 'last_updated_date'>;
21+
22+
export type UpdateAuthorPayload = Partial<Omit<AuthorANS, '_id' | 'last_updated_date'>>;
23+
24+
export type GetAuthorParams = {
25+
_id: string;
26+
};
27+
28+
export type AuthorConfigurationResponse = {
29+
q_results: AuthorFieldConfig[];
30+
count: number;
31+
limit: number;
32+
offset: number;
33+
total_count: number;
34+
};
35+
36+
export type AuthorFieldConfig = {
37+
_id: string;
38+
key: string;
39+
label?: string;
40+
type?: string;
41+
required?: boolean;
42+
hidden?: boolean;
43+
placeholder?: string;
44+
default?: string;
45+
max?: number;
46+
versionAdded?: number;
47+
picklist_options?: { value: string; label: string }[];
48+
};
49+
1250
export type AuthorANS = {
1351
type: 'author';
1452
_id: string;
@@ -18,10 +56,15 @@ export type AuthorANS = {
1856
slug: string;
1957
email: string;
2058
image?: string;
59+
url?: string;
60+
middleName?: string;
61+
suffix?: string;
2162
affiliations?: string;
2263
author_type?: string;
2364
education?: { name: string }[];
2465
awards?: { name: string }[];
66+
books?: { title: string; url?: string; publisher?: string }[];
67+
podcasts?: { name?: string; url?: string; download_url?: string }[];
2568
bio_page?: string;
2669
bio?: string;
2770
longBio?: string;
@@ -31,9 +74,22 @@ export type AuthorANS = {
3174
location?: string;
3275
role?: string;
3376
expertise?: string;
77+
languages?: string;
78+
beat?: string;
3479
personal_website?: string;
3580
twitter?: string;
3681
facebook?: string;
3782
linkedin?: string;
83+
youtube?: string;
84+
tumblr?: string;
85+
pinterest?: string;
86+
soundcloud?: string;
87+
instagram?: string;
88+
rss?: string;
89+
snapchat?: string;
90+
whatsapp?: string;
91+
medium?: string;
92+
reddit?: string;
93+
last_updated_date?: string;
3894
status?: boolean;
3995
};

0 commit comments

Comments
 (0)