@pindownai/client-js 1.3.2 → 1.3.3

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/README.md CHANGED
@@ -6,7 +6,7 @@ Requires a **Workspace** plan API key (`pk_…`).
6
6
 
7
7
  ## Features
8
8
 
9
- - Typed **`pin_type` + `pin_config`** for all 27 pin shapes
9
+ - Typed **`pin_type` + `pin_config`** for all 37 pin shapes
10
10
  - Full CRUD + batch + share on `/v1/pins`
11
11
  - ESM + CJS, zero runtime dependencies (native `fetch`)
12
12
 
@@ -36,10 +36,8 @@ const pin = await client.pins.get(created.id)
36
36
  const content = (pin.metadata?.pin_config as MarkdownPinConfig | undefined)?.content
37
37
 
38
38
  await client.pins.update(created.id, {
39
- metadata: {
40
- title: 'My doc (updated)',
41
- pin_config: { content: '# Updated body' },
42
- },
39
+ pin_config: { content: '# Updated body' },
40
+ metadata: { title: 'My doc (updated)' },
43
41
  })
44
42
 
45
43
  await client.pins.delete(created.id)
@@ -64,6 +62,10 @@ Product types: `PRODUCT_PIN_TYPES` (same as `ALL_PIN_TYPES`)
64
62
 
65
63
  ## Helpers
66
64
 
65
+ Use either:
66
+ - `createPin(pinType, input)` / `updatePin(pinId, pinType, input)` for every type, or
67
+ - generated named helpers: `createMarkdown`, `updateMarkdown`, `createTable`, `updateTable`, `createTimeline`, etc.
68
+
67
69
  ```typescript
68
70
  await client.pins.createMarkdown({
69
71
  title: 'Notes',
@@ -87,6 +89,17 @@ await client.pins.createEmbed({
87
89
  url: 'https://www.youtube.com/watch?v=dQw4w9WgXcQ',
88
90
  type: 'youtube',
89
91
  })
92
+
93
+ // Generic helper for any pin_type
94
+ await client.pins.createPin('timeline', {
95
+ title: 'Roadmap timeline',
96
+ items: [{ id: 'm1', title: 'Milestone 1' }],
97
+ })
98
+
99
+ // Generated update helper per type
100
+ await client.pins.updateMarkdown('p-abc123', {
101
+ content: '# Updated via updateMarkdown helper',
102
+ })
90
103
  ```
91
104
 
92
105
  ## Pins API surface
package/dist/index.cjs CHANGED
@@ -1,8 +1,8 @@
1
- 'use strict';var y=class{constructor(e){this.client=e;}async create(e){return this.client.request("POST","/pins",e)}async get(e){return this.client.request("GET",`/pins/${e}`)}async list(e){let i=new URLSearchParams;e?.limit&&i.append("limit",e.limit.toString()),e?.offset&&i.append("offset",e.offset.toString());let n=i.toString(),s=n?`/pins?${n}`:"/pins";return this.client.request("GET",s)}async update(e,i){return this.client.request("PUT",`/pins/${e}`,i)}async delete(e){return this.client.request("DELETE",`/pins/${e}`)}async share(e,i){return this.client.request("POST",`/pins/${e}/share`,i)}async batchGet(e){return this.client.request("POST","/pins/batch/get",{pin_ids:e})}async batchCreate(e){return this.client.request("POST","/pins/batch",{pins:e})}async batchUpdate(e){return this.client.request("PATCH","/pins/batch",{updates:e})}async batchDelete(e){return this.client.request("DELETE","/pins/batch",{pin_ids:e})}async createMarkdown(e){let{content:i,title:n,tags:s,description:a,pin_layout:o,is_public:t,allow_edit:d,require_sign_in:w,allow_comments:b,pending_invites:_}=e;return this.create({pin_type:"markdown",pin_config:{content:i},pin_layout:o,is_public:t,allow_edit:d,require_sign_in:w,allow_comments:b,pending_invites:_,metadata:{title:n,tags:s,description:a}})}async createStatCards(e){let{cards:i,title:n,tags:s,description:a,pin_layout:o,is_public:t}=e;return this.create({pin_type:"stat-cards",pin_config:{cards:i},pin_layout:o,is_public:t,metadata:{title:n,tags:s,description:a}})}async createTable(e){let{columns:i,rows:n,title:s,tags:a,description:o,pin_layout:t,is_public:d}=e;return this.create({pin_type:"table",pin_config:{columns:i,rows:n},pin_layout:t,is_public:d,metadata:{title:s,tags:a,description:o}})}async updateTable(e,i){let{columns:n,rows:s,title:a,tags:o,description:t}=i,d={};return n!==void 0&&(d.columns=n),s!==void 0&&(d.rows=s),this.update(e,{pin_config:d,...a!==void 0||o!==void 0||t!==void 0?{metadata:{...a!==void 0&&{title:a},...o!==void 0&&{tags:o},...t!==void 0&&{description:t}}}:{}})}async createEmbed(e){let{url:i,type:n,title:s,tags:a,description:o,pin_layout:t,is_public:d}=e;return this.create({pin_type:"embed",pin_config:{url:i,type:n},pin_layout:t,is_public:d,metadata:{title:s,tags:a,description:o}})}async createMarkdownLegacy(e,i){return this.createMarkdown({title:e,content:"",...i})}};var p=class extends Error{constructor(e){super(e),this.name="PindownError";}},u=class extends p{constructor(e="Authentication failed"){super(e),this.name="AuthenticationError";}},l=class extends p{constructor(e="Access forbidden"){super(e),this.name="ForbiddenError";}},P=class extends p{constructor(e){super(`${e} not found`),this.name="NotFoundError";}},f=class extends p{constructor(e,i){super(e),this.name="ValidationError",this.details=i;}},g=class extends p{constructor(e="Rate limit exceeded (429 RATE_LIMITED)"){super(e),this.name="RateLimitError";}},c=class extends p{constructor(e,i=500){super(e),this.name="ServerError",this.statusCode=i;}},m=class extends p{constructor(e="Network request failed"){super(e),this.name="NetworkError";}};var C=class{constructor(e){if(!e.apiKey)throw new Error("API key is required");this.config={apiKey:e.apiKey,baseURL:e.baseURL||"https://api.pindown.ai/v1",maxRetries:e.maxRetries??3,timeout:e.timeout??3e4},this.pins=new y(this);}async request(e,i,n){let s=`${this.config.baseURL}${i}`,a={Authorization:`Bearer ${this.config.apiKey}`};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(a["Content-Type"]="application/json");let o={method:e,headers:a,signal:AbortSignal.timeout(this.config.timeout)};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(o.body=JSON.stringify(n));try{let t=await fetch(s,o);return t.ok||await this.handleErrorResponse(t),(await t.json()).data}catch(t){throw t instanceof u||t instanceof l||t instanceof P||t instanceof f||t instanceof g||t instanceof c?t:t instanceof Error&&(t.name==="AbortError"||t.name==="TimeoutError")?new m("Request timeout"):new m(t instanceof Error?t.message:"Network request failed")}}async handleErrorResponse(e){let i;try{i=await e.json();}catch{i={message:e.statusText};}let n=i.error?.message||i.message||"Unknown error";switch(e.status){case 401:throw new u(n);case 403:throw new l(n);case 404:throw new P(n);case 400:case 422:throw new f(n,i.error?.details);case 429:throw new g(n);case 500:case 502:case 503:throw new c(n,e.status);default:throw new c(n,e.status)}}};var x={pin_type:"table",summary:"Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.",required_fields:["columns"],optional_fields:["rows"],fields:[{path:"columns",type:"TableColumn[]",required:true,description:"At least one column. Each column needs id + name (type optional, e.g. text | number)."},{path:"columns[].id",type:"string",required:true,description:"Stable column key used in row.cells."},{path:"columns[].name",type:"string",required:true,description:"Column header label."},{path:"rows",type:"TableRow[]",required:false,description:"Table data. Each row: { id, cells: { [columnId]: value } }."}],example_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Item",col2:1}}]},example_update:{pin_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Updated",col2:42}}]}}},T={table:x,markdown:{pin_type:"markdown",summary:"Rich text / markdown body.",required_fields:[],optional_fields:["content","collaboration"],fields:[{path:"content",type:"string",required:false,description:"Markdown source. Server seeds Yjs when set on create."}],example_config:{content:`# Hello
1
+ 'use strict';var C=["markdown","image","gallery","table","charts","mermaid","code","embed","pdf-viewer","excel-viewer","stat-cards","timeline","json-viewer","json-list","links","qr-code","social-handles","steps","trace","plan","notes","csv-viewer","user-story","chat","intro","mastra","text-media","business-card","video","audio","file-upload","kanban-board","checklist","comparison","calendar","roadmap","realtime-canvas"];[...C];var S={markdown:["content","collaboration"],image:["url","altText","fit"],gallery:["images"],table:["columns","rows"],charts:["chartType","data","xAxis","yAxis"],mermaid:["diagram","code","title"],code:["code","language","filename","title"],embed:["url","type"],"pdf-viewer":["pdf"],"excel-viewer":["excel"],"stat-cards":["cards"],timeline:["mode","items"],"json-viewer":["json","jsonString","title"],"json-list":["json","jsonString"],links:["links"],"qr-code":["url","label"],"social-handles":["title","showLabels","iconSize","handles"],steps:["steps"],trace:["title","live","spans"],plan:["title","status","breadcrumbs","phases"],notes:["notes"],"csv-viewer":["csvText","csvData","fileName"],"user-story":["title","userStory","acceptanceCriteria"],chat:["title","placeholder","linked_pin_id","linked_pin_title"],intro:["heading","subheading"],mastra:["mode","agentId","workflowId"],"text-media":["title","text","subtext","textPosition","mediaType","embedConfig","imageConfig"],"business-card":["sectionTitle","fields","imageConfig","imagePosition"],video:["url","fileId","fileName","mimeType","caption","size"],audio:["url","fileId","fileName","mimeType","caption","size","tracks"],"file-upload":["files","displayMode"],"kanban-board":["columns"],checklist:["title","items"],comparison:["title","left","right","highlightedLines","matches","showVsBadge"],calendar:["weekStartsOn","events"],roadmap:["title","months"],"realtime-canvas":["title","description","roomId"]};function v(t){return t.split("-").map(e=>e.charAt(0).toUpperCase()+e.slice(1)).join("")}function T(t,e){let i=S[t],n={};for(let a of i)a in e&&e[a]!==void 0&&(n[a]=e[a]);return n}function k(t,e){let n=T(t,e),a={title:e.title,tags:e.tags,description:e.description,allow_edit:e.allow_edit,require_sign_in:e.require_sign_in,allow_comments:e.allow_comments};return {pin_type:t,pin_config:n,pin_layout:e.pin_layout,is_public:e.is_public,allow_edit:e.allow_edit,require_sign_in:e.require_sign_in,allow_comments:e.allow_comments,pending_invites:e.pending_invites,metadata:a}}function b(t,e){let n=T(t,e),a=Object.keys(n).length>0,o={...e.metadata??{}};e.title!==void 0&&(o.title=e.title),e.tags!==void 0&&(o.tags=e.tags),e.description!==void 0&&(o.description=e.description);let s=Object.keys(o).length>0;return {...a?{pin_config:n}:{},pin_layout:e.pin_layout,is_public:e.is_public,...s?{metadata:o}:{}}}function x(t){for(let e of C){let i=v(e);t.prototype[`create${i}`]=function(n){return this.createPin(e,n)},t.prototype[`update${i}`]=function(n,a){return this.updatePin(n,e,a)};}}var y=class{constructor(e){this.client=e;}async create(e){return this.client.request("POST","/pins",e)}async createPin(e,i){return this.create(k(e,i))}async get(e){return this.client.request("GET",`/pins/${e}`)}async list(e){let i=new URLSearchParams;e?.limit&&i.append("limit",e.limit.toString()),e?.offset&&i.append("offset",e.offset.toString());let n=i.toString(),a=n?`/pins?${n}`:"/pins";return this.client.request("GET",a)}async update(e,i){return this.client.request("PUT",`/pins/${e}`,i)}async updatePin(e,i,n){return this.update(e,b(i,n))}async delete(e){return this.client.request("DELETE",`/pins/${e}`)}async share(e,i){return this.client.request("POST",`/pins/${e}/share`,i)}async batchGet(e){return this.client.request("POST","/pins/batch/get",{pin_ids:e})}async batchCreate(e){return this.client.request("POST","/pins/batch",{pins:e})}async batchUpdate(e){return this.client.request("PATCH","/pins/batch",{updates:e})}async batchDelete(e){return this.client.request("DELETE","/pins/batch",{pin_ids:e})}async createMarkdown(e){let{content:i,title:n,tags:a,description:o,pin_layout:s,is_public:r,allow_edit:l,require_sign_in:I,allow_comments:R,pending_invites:q}=e;return this.create({pin_type:"markdown",pin_config:{content:i},pin_layout:s,is_public:r,allow_edit:l,require_sign_in:I,allow_comments:R,pending_invites:q,metadata:{title:n,tags:a,description:o}})}async createStatCards(e){let{cards:i,title:n,tags:a,description:o,pin_layout:s,is_public:r}=e;return this.create({pin_type:"stat-cards",pin_config:{cards:i},pin_layout:s,is_public:r,metadata:{title:n,tags:a,description:o}})}async createTable(e){let{columns:i,rows:n,title:a,tags:o,description:s,pin_layout:r,is_public:l}=e;return this.create({pin_type:"table",pin_config:{columns:i,rows:n},pin_layout:r,is_public:l,metadata:{title:a,tags:o,description:s}})}async updateTable(e,i){return this.updatePin(e,"table",i)}async createEmbed(e){let{url:i,type:n,title:a,tags:o,description:s,pin_layout:r,is_public:l}=e;return this.create({pin_type:"embed",pin_config:{url:i,type:n},pin_layout:r,is_public:l,metadata:{title:a,tags:o,description:s}})}async createMarkdownLegacy(e,i){return this.createMarkdown({title:e,content:"",...i})}};x(y);var p=class extends Error{constructor(e){super(e),this.name="PindownError";}},g=class extends p{constructor(e="Authentication failed"){super(e),this.name="AuthenticationError";}},c=class extends p{constructor(e="Access forbidden"){super(e),this.name="ForbiddenError";}},u=class extends p{constructor(e){super(`${e} not found`),this.name="NotFoundError";}},P=class extends p{constructor(e,i){super(e),this.name="ValidationError",this.details=i;}},f=class extends p{constructor(e="Rate limit exceeded (429 RATE_LIMITED)"){super(e),this.name="RateLimitError";}},d=class extends p{constructor(e,i=500){super(e),this.name="ServerError",this.statusCode=i;}},m=class extends p{constructor(e="Network request failed"){super(e),this.name="NetworkError";}};var w=class{constructor(e){if(!e.apiKey)throw new Error("API key is required");this.config={apiKey:e.apiKey,baseURL:e.baseURL||"https://api.pindown.ai/v1",maxRetries:e.maxRetries??3,timeout:e.timeout??3e4},this.pins=new y(this);}async request(e,i,n){let a=`${this.config.baseURL}${i}`,o={Authorization:`Bearer ${this.config.apiKey}`};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(o["Content-Type"]="application/json");let s={method:e,headers:o,signal:AbortSignal.timeout(this.config.timeout)};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(s.body=JSON.stringify(n));try{let r=await fetch(a,s);return r.ok||await this.handleErrorResponse(r),(await r.json()).data}catch(r){throw r instanceof g||r instanceof c||r instanceof u||r instanceof P||r instanceof f||r instanceof d?r:r instanceof Error&&(r.name==="AbortError"||r.name==="TimeoutError")?new m("Request timeout"):new m(r instanceof Error?r.message:"Network request failed")}}async handleErrorResponse(e){let i;try{i=await e.json();}catch{i={message:e.statusText};}let n=i.error?.message||i.message||"Unknown error";switch(e.status){case 401:throw new g(n);case 403:throw new c(n);case 404:throw new u(n);case 400:case 422:throw new P(n,i.error?.details);case 429:throw new f(n);case 500:case 502:case 503:throw new d(n,e.status);default:throw new d(n,e.status)}}};var E={pin_type:"table",summary:"Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.",required_fields:["columns"],optional_fields:["rows"],fields:[{path:"columns",type:"TableColumn[]",required:true,description:"At least one column. Each column needs id + name (type optional, e.g. text | number)."},{path:"columns[].id",type:"string",required:true,description:"Stable column key used in row.cells."},{path:"columns[].name",type:"string",required:true,description:"Column header label."},{path:"rows",type:"TableRow[]",required:false,description:"Table data. Each row: { id, cells: { [columnId]: value } }."}],example_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Item",col2:1}}]},example_update:{pin_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Updated",col2:42}}]}}},_={table:E,markdown:{pin_type:"markdown",summary:"Rich text / markdown body.",required_fields:[],optional_fields:["content","collaboration"],fields:[{path:"content",type:"string",required:false,description:"Markdown source. Server seeds Yjs when set on create."}],example_config:{content:`# Hello
2
2
 
3
3
  Body text.`},example_update:{pin_config:{content:`# Updated
4
4
 
5
- New body.`}}},"stat-cards":{pin_type:"stat-cards",summary:"KPI cards grid.",required_fields:["cards"],optional_fields:[],fields:[{path:"cards",type:"StatCardItem[]",required:true,description:"Each card: title, value; optional change, trend (up|down|neutral)."}],example_config:{cards:[{title:"Revenue",value:"1000",change:"+5%",trend:"up"}]},example_update:{pin_config:{cards:[{title:"Revenue",value:"1234",change:"+8%",trend:"up"}]}}}};function h(r){return T[r]}function I(r){let e=h(r);return e?[`Pin type: ${e.pin_type}`,e.summary,"","Required pin_config fields:",...e.required_fields.map(n=>` - ${n}`),"","Optional pin_config fields:",...e.optional_fields.length?e.optional_fields.map(n=>` - ${n}`):[" (none documented)"],"","Field reference:",...e.fields.map(n=>` ${n.path} (${n.type}${n.required?", required":""}): ${n.description}`),"","Example update payload:",JSON.stringify(e.example_update,null,2)].join(`
6
- `):[`No built-in hint for pin type "${r}".`,"Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,","or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config."].join(`
7
- `)}exports.AuthenticationError=u;exports.ForbiddenError=l;exports.NetworkError=m;exports.NotFoundError=P;exports.PIN_CONFIG_HINTS=T;exports.PindownClient=C;exports.PindownError=p;exports.RateLimitError=g;exports.ServerError=c;exports.ValidationError=f;exports.formatPinConfigHint=I;exports.getPinConfigHint=h;//# sourceMappingURL=index.cjs.map
5
+ New body.`}}},"stat-cards":{pin_type:"stat-cards",summary:"KPI cards grid.",required_fields:["cards"],optional_fields:[],fields:[{path:"cards",type:"StatCardItem[]",required:true,description:"Each card: title, value; optional change, trend (up|down|neutral)."}],example_config:{cards:[{title:"Revenue",value:"1000",change:"+5%",trend:"up"}]},example_update:{pin_config:{cards:[{title:"Revenue",value:"1234",change:"+8%",trend:"up"}]}}}};function h(t){return _[t]}function L(t){let e=h(t);return e?[`Pin type: ${e.pin_type}`,e.summary,"","Required pin_config fields:",...e.required_fields.map(n=>` - ${n}`),"","Optional pin_config fields:",...e.optional_fields.length?e.optional_fields.map(n=>` - ${n}`):[" (none documented)"],"","Field reference:",...e.fields.map(n=>` ${n.path} (${n.type}${n.required?", required":""}): ${n.description}`),"","Example update payload:",JSON.stringify(e.example_update,null,2)].join(`
6
+ `):[`No built-in hint for pin type "${t}".`,"Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,","or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config."].join(`
7
+ `)}exports.AuthenticationError=g;exports.ForbiddenError=c;exports.NetworkError=m;exports.NotFoundError=u;exports.PIN_CONFIG_HINTS=_;exports.PindownClient=w;exports.PindownError=p;exports.RateLimitError=f;exports.ServerError=d;exports.ValidationError=P;exports.formatPinConfigHint=L;exports.getPinConfigHint=h;//# sourceMappingURL=index.cjs.map
8
8
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/client/pins/index.ts","../src/errors/index.ts","../src/client/PindownClient.ts","../src/pin-config-hints.ts"],"names":["PinsMethods","client","request","pinId","options","params","query","endpoint","pinIds","pins","updates","input","content","title","tags","description","pin_layout","is_public","allow_edit","require_sign_in","allow_comments","pending_invites","cards","columns","rows","pin_config","url","type","additionalMetadata","PindownError","message","AuthenticationError","ForbiddenError","NotFoundError","resource","ValidationError","details","RateLimitError","ServerError","statusCode","NetworkError","PindownClient","config","method","data","headers","requestOptions","response","error","errorData","TABLE_HINT","PIN_CONFIG_HINTS","getPinConfigHint","pinType","formatPinConfigHint","hint","f"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Pins API Methods\n */\n\nimport type { PindownClient } from '../PindownClient'\nimport type {\n Pin,\n PinTypeId,\n CreatePinRequest,\n UpdatePinRequest,\n SharePinRequest,\n ListPinsOptions,\n CreateMarkdownPinInput,\n CreateStatCardsPinInput,\n CreateTablePinInput,\n UpdateTablePinInput,\n CreateEmbedPinInput,\n TablePinConfig,\n} from '../../types/pins'\nimport type { PaginatedResponse } from '../../types/api'\n\nexport class PinsMethods {\n constructor(private client: PindownClient) {}\n\n /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */\n async create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('POST', '/pins', request)\n }\n\n async get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('GET', `/pins/${pinId}`)\n }\n\n async list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>> {\n const params = new URLSearchParams()\n if (options?.limit) params.append('limit', options.limit.toString())\n if (options?.offset) params.append('offset', options.offset.toString())\n\n const query = params.toString()\n const endpoint = query ? `/pins?${query}` : '/pins'\n\n return this.client.request<PaginatedResponse<Pin>>('GET', endpoint)\n }\n\n async update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('PUT', `/pins/${pinId}`, request)\n }\n\n async delete(pinId: string): Promise<void> {\n return this.client.request<void>('DELETE', `/pins/${pinId}`)\n }\n\n async share(pinId: string, request: SharePinRequest): Promise<Pin> {\n return this.client.request<Pin>('POST', `/pins/${pinId}/share`, request)\n }\n\n async batchGet(pinIds: string[]): Promise<{\n found: Pin[]\n not_found: string[]\n permission_denied: string[]\n }> {\n return this.client.request('POST', '/pins/batch/get', { pin_ids: pinIds })\n }\n\n async batchCreate(pins: CreatePinRequest[]): Promise<{\n created: Array<{ id: string; index: number; created_at: number }>\n failed: Array<{ index: number; error: string }>\n }> {\n return this.client.request('POST', '/pins/batch', { pins })\n }\n\n async batchUpdate(updates: Array<{ id: string } & UpdatePinRequest>): Promise<{\n updated: string[]\n failed: Array<{ id: string; error: string }>\n updated_at: number\n }> {\n return this.client.request('PATCH', '/pins/batch', { updates })\n }\n\n async batchDelete(pinIds: string[]): Promise<{\n deleted: string[]\n failed: Array<{ id: string; error: string }>\n }> {\n return this.client.request('DELETE', '/pins/batch', { pin_ids: pinIds })\n }\n\n /** Create a markdown pin with pin_config.content (seeds Yjs on the server). */\n async createMarkdown(input: CreateMarkdownPinInput): Promise<Pin<'markdown'>> {\n const { content, title, tags, description, pin_layout, is_public, allow_edit, require_sign_in, allow_comments, pending_invites } = input\n return this.create({\n pin_type: 'markdown',\n pin_config: { content },\n pin_layout,\n is_public,\n allow_edit,\n require_sign_in,\n allow_comments,\n pending_invites,\n metadata: { title, tags, description },\n })\n }\n\n async createStatCards(input: CreateStatCardsPinInput): Promise<Pin<'stat-cards'>> {\n const { cards, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'stat-cards',\n pin_config: { cards },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n async createTable(input: CreateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'table',\n pin_config: { columns, rows },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /** Partial table pin_config update with typed columns/rows. */\n async updateTable(pinId: string, input: UpdateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description } = input\n const pin_config: Partial<TablePinConfig> = {}\n if (columns !== undefined) pin_config.columns = columns\n if (rows !== undefined) pin_config.rows = rows\n\n return this.update<'table'>(pinId, {\n pin_config: pin_config as TablePinConfig,\n ...(title !== undefined || tags !== undefined || description !== undefined\n ? { metadata: { ...(title !== undefined && { title }), ...(tags !== undefined && { tags }), ...(description !== undefined && { description }) } }\n : {}),\n })\n }\n\n async createEmbed(input: CreateEmbedPinInput): Promise<Pin<'embed'>> {\n const { url, type, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'embed',\n pin_config: { url, type },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /**\n * @deprecated Use createMarkdown({ title, content, ... }) — old signature ignored content in title\n */\n async createMarkdownLegacy(title: string, additionalMetadata?: Record<string, unknown>): Promise<Pin<'markdown'>> {\n return this.createMarkdown({\n title,\n content: '',\n ...(additionalMetadata as Partial<CreateMarkdownPinInput>),\n })\n }\n}\n","/**\n * Error classes for the v1 Pins API client\n */\n\nexport class PindownError extends Error {\n constructor(message: string) {\n super(message)\n this.name = 'PindownError'\n }\n}\n\nexport class AuthenticationError extends PindownError {\n constructor(message: string = 'Authentication failed') {\n super(message)\n this.name = 'AuthenticationError'\n }\n}\n\nexport class ForbiddenError extends PindownError {\n constructor(message: string = 'Access forbidden') {\n super(message)\n this.name = 'ForbiddenError'\n }\n}\n\nexport class NotFoundError extends PindownError {\n constructor(resource: string) {\n super(`${resource} not found`)\n this.name = 'NotFoundError'\n }\n}\n\nexport class ValidationError extends PindownError {\n public details?: unknown\n\n constructor(message: string, details?: unknown) {\n super(message)\n this.name = 'ValidationError'\n this.details = details\n }\n}\n\nexport class RateLimitError extends PindownError {\n constructor(message: string = 'Rate limit exceeded (429 RATE_LIMITED)') {\n super(message)\n this.name = 'RateLimitError'\n }\n}\n\nexport class ServerError extends PindownError {\n public statusCode: number\n\n constructor(message: string, statusCode: number = 500) {\n super(message)\n this.name = 'ServerError'\n this.statusCode = statusCode\n }\n}\n\nexport class NetworkError extends PindownError {\n constructor(message: string = 'Network request failed') {\n super(message)\n this.name = 'NetworkError'\n }\n}\n","/**\n * Pindown API Client — v1 Pins API only\n */\n\nimport { PinsMethods } from './pins'\nimport type { PindownConfig } from '../types/config'\nimport {\n AuthenticationError,\n ForbiddenError,\n NotFoundError,\n ValidationError,\n RateLimitError,\n ServerError,\n NetworkError,\n} from '../errors'\n\nexport class PindownClient {\n private config: Required<Omit<PindownConfig, 'baseURL'>> & { baseURL: string }\n\n public readonly pins: PinsMethods\n\n constructor(config: PindownConfig) {\n if (!config.apiKey) {\n throw new Error('API key is required')\n }\n\n this.config = {\n apiKey: config.apiKey,\n baseURL: config.baseURL || 'https://api.pindown.ai/v1',\n maxRetries: config.maxRetries ?? 3,\n timeout: config.timeout ?? 30000,\n }\n\n this.pins = new PinsMethods(this)\n }\n\n async request<T = unknown>(method: string, endpoint: string, data?: unknown): Promise<T> {\n const url = `${this.config.baseURL}${endpoint}`\n const headers: Record<string, string> = {\n Authorization: `Bearer ${this.config.apiKey}`,\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n headers['Content-Type'] = 'application/json'\n }\n\n const requestOptions: RequestInit = {\n method,\n headers,\n signal: AbortSignal.timeout(this.config.timeout),\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n requestOptions.body = JSON.stringify(data)\n }\n\n try {\n const response = await fetch(url, requestOptions)\n\n if (!response.ok) {\n await this.handleErrorResponse(response)\n }\n\n const result = await response.json()\n return result.data as T\n } catch (error: unknown) {\n if (\n error instanceof AuthenticationError ||\n error instanceof ForbiddenError ||\n error instanceof NotFoundError ||\n error instanceof ValidationError ||\n error instanceof RateLimitError ||\n error instanceof ServerError\n ) {\n throw error\n }\n\n if (error instanceof Error && (error.name === 'AbortError' || error.name === 'TimeoutError')) {\n throw new NetworkError('Request timeout')\n }\n\n throw new NetworkError(error instanceof Error ? error.message : 'Network request failed')\n }\n }\n\n private async handleErrorResponse(response: Response): Promise<never> {\n let errorData: { error?: { code?: string; message?: string; details?: unknown }; message?: string }\n\n try {\n errorData = await response.json()\n } catch {\n errorData = { message: response.statusText }\n }\n\n const message = errorData.error?.message || errorData.message || 'Unknown error'\n\n switch (response.status) {\n case 401:\n throw new AuthenticationError(message)\n case 403:\n throw new ForbiddenError(message)\n case 404:\n throw new NotFoundError(message)\n case 400:\n case 422:\n throw new ValidationError(message, errorData.error?.details)\n case 429:\n throw new RateLimitError(message)\n case 500:\n case 502:\n case 503:\n throw new ServerError(message, response.status)\n default:\n throw new ServerError(message, response.status)\n }\n }\n}\n","/**\n * Runtime hints + minimal examples per pin type.\n * Use when building API payloads without opening the docs every time.\n */\n\nimport type { PinConfigByType, PinTypeId, UpdatePinRequest } from './types/pins'\n\nexport interface PinConfigFieldHint {\n path: string\n type: string\n required: boolean\n description: string\n}\n\nexport interface PinConfigHint<T extends PinTypeId = PinTypeId> {\n pin_type: T\n summary: string\n required_fields: string[]\n optional_fields: string[]\n fields: PinConfigFieldHint[]\n /** Minimal valid pin_config for create/update */\n example_config: PinConfigByType[T]\n /** Typical PUT /v1/pins/:id body (root-level pin_config) */\n example_update: UpdatePinRequest<T>\n}\n\nconst TABLE_HINT: PinConfigHint<'table'> = {\n pin_type: 'table',\n summary: 'Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.',\n required_fields: ['columns'],\n optional_fields: ['rows'],\n fields: [\n {\n path: 'columns',\n type: 'TableColumn[]',\n required: true,\n description: 'At least one column. Each column needs id + name (type optional, e.g. text | number).',\n },\n {\n path: 'columns[].id',\n type: 'string',\n required: true,\n description: 'Stable column key used in row.cells.',\n },\n {\n path: 'columns[].name',\n type: 'string',\n required: true,\n description: 'Column header label.',\n },\n {\n path: 'rows',\n type: 'TableRow[]',\n required: false,\n description: 'Table data. Each row: { id, cells: { [columnId]: value } }.',\n },\n ],\n example_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Item', col2: 1 } }],\n },\n example_update: {\n pin_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Updated', col2: 42 } }],\n },\n },\n}\n\n/** Per-type hints (expand over time; table is fully documented). */\nexport const PIN_CONFIG_HINTS: Partial<Record<PinTypeId, PinConfigHint>> = {\n table: TABLE_HINT,\n markdown: {\n pin_type: 'markdown',\n summary: 'Rich text / markdown body.',\n required_fields: [],\n optional_fields: ['content', 'collaboration'],\n fields: [\n {\n path: 'content',\n type: 'string',\n required: false,\n description: 'Markdown source. Server seeds Yjs when set on create.',\n },\n ],\n example_config: { content: '# Hello\\n\\nBody text.' },\n example_update: { pin_config: { content: '# Updated\\n\\nNew body.' } },\n },\n 'stat-cards': {\n pin_type: 'stat-cards',\n summary: 'KPI cards grid.',\n required_fields: ['cards'],\n optional_fields: [],\n fields: [\n {\n path: 'cards',\n type: 'StatCardItem[]',\n required: true,\n description: 'Each card: title, value; optional change, trend (up|down|neutral).',\n },\n ],\n example_config: {\n cards: [{ title: 'Revenue', value: '1000', change: '+5%', trend: 'up' }],\n },\n example_update: {\n pin_config: {\n cards: [{ title: 'Revenue', value: '1234', change: '+8%', trend: 'up' }],\n },\n },\n },\n}\n\nexport function getPinConfigHint<T extends PinTypeId>(pinType: T): PinConfigHint<T> | undefined {\n return PIN_CONFIG_HINTS[pinType] as PinConfigHint<T> | undefined\n}\n\n/** Pretty-print field hints for CLI / logging. */\nexport function formatPinConfigHint(pinType: PinTypeId): string {\n const hint = getPinConfigHint(pinType)\n if (!hint) {\n return [\n `No built-in hint for pin type \"${pinType}\".`,\n 'Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,',\n 'or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config.',\n ].join('\\n')\n }\n\n const lines = [\n `Pin type: ${hint.pin_type}`,\n hint.summary,\n '',\n 'Required pin_config fields:',\n ...hint.required_fields.map((f) => ` - ${f}`),\n '',\n 'Optional pin_config fields:',\n ...(hint.optional_fields.length ? hint.optional_fields.map((f) => ` - ${f}`) : [' (none documented)']),\n '',\n 'Field reference:',\n ...hint.fields.map(\n (f) => ` ${f.path} (${f.type}${f.required ? ', required' : ''}): ${f.description}`,\n ),\n '',\n 'Example update payload:',\n JSON.stringify(hint.example_update, null, 2),\n ]\n return lines.join('\\n')\n}\n"]}
1
+ {"version":3,"sources":["../src/types/pins.ts","../src/client/pins/pin-helper-core.ts","../src/client/pins/index.ts","../src/errors/index.ts","../src/client/PindownClient.ts","../src/pin-config-hints.ts"],"names":["PRODUCT_PIN_TYPES","PIN_CONFIG_FIELDS","pinTypeToMethodSuffix","pinType","part","pickPinConfig","input","fields","pin_config","key","toCreatePinRequest","metadata","toUpdatePinRequest","hasPinConfig","hasMetadata","attachNamedPinHelpers","ctor","suffix","pinId","PinsMethods","client","request","options","params","query","endpoint","pinIds","pins","updates","content","title","tags","description","pin_layout","is_public","allow_edit","require_sign_in","allow_comments","pending_invites","cards","columns","rows","url","type","additionalMetadata","PindownError","message","AuthenticationError","ForbiddenError","NotFoundError","resource","ValidationError","details","RateLimitError","ServerError","statusCode","NetworkError","PindownClient","config","method","data","headers","requestOptions","response","error","errorData","TABLE_HINT","PIN_CONFIG_HINTS","getPinConfigHint","formatPinConfigHint","hint","f"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Pin types for the v1 Pins API.\n * Aligned with backend-api/src/lib/pin-types.ts + pin-config-schemas.ts.\n * Import per-type *PinConfig interfaces for typed CRUD payloads.\n */\n\nexport const PRODUCT_PIN_TYPES = [\n 'markdown',\n 'image',\n 'gallery',\n 'table',\n 'charts',\n 'mermaid',\n 'code',\n 'embed',\n 'pdf-viewer',\n 'excel-viewer',\n 'stat-cards',\n 'timeline',\n 'json-viewer',\n 'json-list',\n 'links',\n 'qr-code',\n 'social-handles',\n 'steps',\n 'trace',\n 'plan',\n 'notes',\n 'csv-viewer',\n 'user-story',\n 'chat',\n 'intro',\n 'mastra',\n 'text-media',\n 'business-card',\n 'video',\n 'audio',\n 'file-upload',\n 'kanban-board',\n 'checklist',\n 'comparison',\n 'calendar',\n 'roadmap',\n 'realtime-canvas',\n] as const\n\nexport const ALL_PIN_TYPES = [...PRODUCT_PIN_TYPES] as const\n\nexport type ProductPinTypeId = (typeof PRODUCT_PIN_TYPES)[number]\nexport type PinTypeId = (typeof ALL_PIN_TYPES)[number]\n\nexport type PinLayout = '1x1' | '1x2' | '2x1' | '2x2' | '3x1' | '3x2' | '3x3' | '4x4'\n\nexport type PinDataType = 'markdown' | 'json' | 'text' | 'pin-card'\n\n/** @deprecated Use PinTypeId */\nexport type PinCardType = PinTypeId\n\nexport interface StatCardItem {\n title: string\n value: string | number\n change?: string\n trend?: 'up' | 'down' | 'neutral' | string\n icon?: string\n [key: string]: unknown\n}\n\nexport interface TableColumn {\n id: string\n name: string\n type?: string\n [key: string]: unknown\n}\n\nexport interface TableRow {\n id: string\n cells: Record<string, unknown>\n [key: string]: unknown\n}\n\nexport interface KanbanColumn {\n id: string\n title: string\n cards?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface ChecklistItem {\n id: string\n name: string\n checked?: boolean\n [key: string]: unknown\n}\n\nexport interface GalleryImage {\n url: string\n alt?: string\n [key: string]: unknown\n}\n\nexport interface LinkItem {\n title: string\n url: string\n [key: string]: unknown\n}\n\nexport interface StepItem {\n title: string\n description?: string\n [key: string]: unknown\n}\n\nexport interface MarkdownPinConfig {\n content?: string\n collaboration?: { enabled?: boolean }\n [key: string]: unknown\n}\n\nexport interface ImagePinConfig {\n url?: string\n altText?: string\n fit?: 'cover' | 'contain' | string\n [key: string]: unknown\n}\n\nexport interface GalleryPinConfig {\n images?: GalleryImage[]\n [key: string]: unknown\n}\n\nexport interface TablePinConfig {\n columns: TableColumn[]\n rows?: TableRow[]\n [key: string]: unknown\n}\n\nexport interface ChartsPinConfig {\n chartType?: string\n data?: Array<Record<string, unknown>>\n xAxis?: string\n yAxis?: string\n [key: string]: unknown\n}\n\nexport interface MermaidPinConfig {\n diagram?: string\n code?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface CodePinConfig {\n code: string\n language?: string\n filename?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface EmbedPinConfig {\n url?: string\n type?: string\n [key: string]: unknown\n}\n\nexport interface PdfViewerPinConfig {\n pdf: { url: string; fileName?: string; title?: string; [key: string]: unknown }\n [key: string]: unknown\n}\n\nexport interface ExcelViewerPinConfig {\n excel: { url: string; fileName?: string; title?: string; [key: string]: unknown }\n [key: string]: unknown\n}\n\nexport interface StatCardsPinConfig {\n cards: StatCardItem[]\n [key: string]: unknown\n}\n\nexport interface TimelinePinConfig {\n mode?: string\n items?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface JsonViewerPinConfig {\n json?: unknown\n jsonString?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface JsonListPinConfig {\n json?: unknown[]\n jsonString?: string\n [key: string]: unknown\n}\n\nexport interface LinksPinConfig {\n links?: LinkItem[]\n [key: string]: unknown\n}\n\nexport interface QrCodePinConfig {\n url?: string\n label?: string\n [key: string]: unknown\n}\n\nexport interface SocialHandleItem {\n id?: string\n platform: string\n url: string\n label?: string\n [key: string]: unknown\n}\n\nexport interface SocialHandlesPinConfig {\n title?: string\n showLabels?: boolean\n iconSize?: number\n handles?: SocialHandleItem[]\n [key: string]: unknown\n}\n\nexport interface StepsPinConfig {\n steps: StepItem[]\n [key: string]: unknown\n}\n\nexport type TraceSpanStatus = 'completed' | 'running' | 'pending' | 'failed'\nexport type TraceSpanType = 'system' | 'agent' | 'tool'\n\nexport interface TraceSpanItem {\n id?: string\n type?: TraceSpanType\n name: string\n status: TraceSpanStatus\n timestamp?: string\n duration?: string\n details?: string\n}\n\nexport interface TracePinConfig {\n title?: string\n live?: boolean\n spans: TraceSpanItem[]\n [key: string]: unknown\n}\n\nexport type PlanContentBlock =\n | { type: 'details'; title?: string; items: string[] }\n | { type: 'command'; command: string; label?: string }\n | { type: 'code'; code: string; language?: string; filename?: string }\n | { type: 'text'; content: string }\n | { type: 'link'; url: string; label?: string }\n | { type: 'mermaid'; diagram: string; title?: string }\n | { type: 'summary'; content: string; title?: string }\n\nexport interface PlanTaskItem {\n id?: string\n number?: string\n title: string\n label?: string\n description?: string\n blocks?: PlanContentBlock[]\n [key: string]: unknown\n}\n\nexport interface PlanPhaseItem {\n id?: string\n title: string\n status?: 'pending' | 'in-progress' | 'completed'\n tasks: PlanTaskItem[]\n [key: string]: unknown\n}\n\nexport interface PlanPinConfig {\n title?: string\n status?: 'draft' | 'in-progress' | 'completed'\n breadcrumbs?: Array<{ label: string }>\n phases: PlanPhaseItem[]\n [key: string]: unknown\n}\n\nexport interface NoteItem {\n id?: string\n title: string\n content?: string\n order?: number\n createdAt?: number\n updatedAt?: number\n}\n\nexport interface NotesPinConfig {\n notes?: NoteItem[]\n [key: string]: unknown\n}\n\nexport interface CsvViewerPinConfig {\n csvText?: string\n csvData?: Array<Record<string, unknown>>\n fileName?: string\n [key: string]: unknown\n}\n\nexport interface UserStoryPinConfig {\n title?: string\n userStory: string\n acceptanceCriteria?: string\n [key: string]: unknown\n}\n\nexport interface ChatPinConfig {\n title?: string\n placeholder?: string\n /** Pin this discussion thread is about (commentary / feedback). */\n linked_pin_id?: string\n /** Cached title for display without fetching the linked pin. */\n linked_pin_title?: string\n [key: string]: unknown\n}\n\nexport interface IntroPinConfig {\n heading: string\n subheading?: string\n [key: string]: unknown\n}\n\nexport interface MastraPinConfig {\n mode?: 'workflow' | 'agent' | string\n agentId?: string\n workflowId?: string\n [key: string]: unknown\n}\n\nexport interface BusinessCardField {\n id: string\n key: string\n value: string\n}\n\nexport interface BusinessCardPinConfig {\n sectionTitle?: string\n fields?: BusinessCardField[]\n imageConfig?: { url?: string; alt?: string; fileId?: string; [key: string]: unknown }\n imagePosition?: 'left' | 'right' | string\n [key: string]: unknown\n}\n\nexport interface VideoPinConfig {\n url?: string\n fileId?: string\n fileName?: string\n mimeType?: 'video/mp4' | string\n caption?: string\n size?: number\n [key: string]: unknown\n}\n\nexport interface AudioPinTrack {\n url: string\n fileId?: string\n fileName?: string\n mimeType?: 'audio/mpeg' | 'audio/wav' | 'audio/x-wav' | string\n size?: number\n [key: string]: unknown\n}\n\nexport interface AudioPinConfig {\n url?: string\n fileId?: string\n fileName?: string\n mimeType?: 'audio/mpeg' | 'audio/wav' | 'audio/x-wav' | string\n caption?: string\n size?: number\n tracks?: AudioPinTrack[]\n [key: string]: unknown\n}\n\nexport interface TextMediaPinConfig {\n title?: string\n text?: string\n subtext?: string\n textPosition?: 'left' | 'right' | string\n mediaType?: 'embed' | 'image' | string\n embedConfig?: {\n type?: string\n url?: string\n aspectRatio?: string\n autoplay?: boolean\n [key: string]: unknown\n }\n imageConfig?: {\n url?: string\n alt?: string\n fileId?: string\n [key: string]: unknown\n }\n [key: string]: unknown\n}\n\nexport interface FileUploadPinConfig {\n files?: Array<Record<string, unknown>>\n displayMode?: string\n [key: string]: unknown\n}\n\nexport interface KanbanBoardPinConfig {\n columns: KanbanColumn[]\n [key: string]: unknown\n}\n\nexport interface ChecklistPinConfig {\n title?: string\n items: ChecklistItem[]\n [key: string]: unknown\n}\n\nexport interface ComparisonSideConfig {\n label: string\n body: string\n}\n\nexport interface ComparisonMatchPair {\n left: number\n right: number\n}\n\nexport interface ComparisonPinConfig {\n title?: string\n left: ComparisonSideConfig\n right: ComparisonSideConfig\n highlightedLines?: { left?: number[]; right?: number[] }\n matches?: ComparisonMatchPair[]\n showVsBadge?: boolean\n [key: string]: unknown\n}\n\nexport interface CalendarPinConfig {\n weekStartsOn?: number\n events?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface RoadmapPinConfig {\n title?: string\n months?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface RealtimeCanvasPinConfig {\n title?: string\n description?: string\n roomId?: string\n [key: string]: unknown\n}\n\nexport interface PinConfigByType {\n markdown: MarkdownPinConfig\n image: ImagePinConfig\n gallery: GalleryPinConfig\n table: TablePinConfig\n charts: ChartsPinConfig\n mermaid: MermaidPinConfig\n code: CodePinConfig\n embed: EmbedPinConfig\n 'pdf-viewer': PdfViewerPinConfig\n 'excel-viewer': ExcelViewerPinConfig\n 'stat-cards': StatCardsPinConfig\n timeline: TimelinePinConfig\n 'json-viewer': JsonViewerPinConfig\n 'json-list': JsonListPinConfig\n links: LinksPinConfig\n 'qr-code': QrCodePinConfig\n 'social-handles': SocialHandlesPinConfig\n steps: StepsPinConfig\n trace: TracePinConfig\n plan: PlanPinConfig\n notes: NotesPinConfig\n 'csv-viewer': CsvViewerPinConfig\n 'user-story': UserStoryPinConfig\n chat: ChatPinConfig\n intro: IntroPinConfig\n mastra: MastraPinConfig\n 'text-media': TextMediaPinConfig\n 'business-card': BusinessCardPinConfig\n video: VideoPinConfig\n audio: AudioPinConfig\n 'file-upload': FileUploadPinConfig\n 'kanban-board': KanbanBoardPinConfig\n checklist: ChecklistPinConfig\n comparison: ComparisonPinConfig\n calendar: CalendarPinConfig\n roadmap: RoadmapPinConfig\n 'realtime-canvas': RealtimeCanvasPinConfig\n}\n\nexport interface PinMetadataBase {\n title: string\n tags?: string[]\n description?: string\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n}\n\nexport type PinMetadata<T extends PinTypeId = PinTypeId> = PinMetadataBase & {\n pin_type?: T\n pin_config?: PinConfigByType[T]\n pin_layout?: PinLayout\n}\n\nexport interface CreateTypedPinRequest<T extends PinTypeId> {\n pin_type: T\n pin_config: PinConfigByType[T]\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n metadata: PinMetadataBase\n pending_invites?: Record<string, 'editor' | 'viewer'>\n /** @deprecated Inferred from pin_type */\n data_type?: PinDataType\n}\n\nexport interface CreateNestedPinRequest<T extends PinTypeId> {\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n metadata: PinMetadata<T> & PinMetadataBase\n pending_invites?: Record<string, 'editor' | 'viewer'>\n data_type?: PinDataType\n}\n\nexport type CreatePinRequest<T extends PinTypeId = PinTypeId> =\n | CreateTypedPinRequest<T>\n | CreateNestedPinRequest<T>\n\nexport interface UpdatePinRequest<T extends PinTypeId = PinTypeId> {\n pin_type?: T\n pin_config?: PinConfigByType[T]\n pin_layout?: PinLayout\n is_public?: boolean\n metadata?: Partial<PinMetadata<T>>\n}\n\nexport interface Pin<T extends PinTypeId = PinTypeId> {\n id: string\n owner_id: string\n user_id?: string\n title?: string\n description?: string\n data_type: PinDataType\n is_public: boolean\n allow_edit: boolean\n require_sign_in: boolean\n allow_comments: boolean\n metadata?: PinMetadata<T>\n created_at: string | number\n updated_at: string | number\n}\n\nexport interface SharePinRequest {\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n}\n\nexport interface ListPinsOptions {\n limit?: number\n offset?: number\n}\n\nexport interface CreatePinOptions {\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n pending_invites?: Record<string, 'editor' | 'viewer'>\n}\n\n/** Flat create input: metadata + pin_config fields (all pin types). */\nexport type CreatePinHelperInput<T extends PinTypeId> = PinMetadataBase &\n CreatePinOptions &\n PinConfigByType[T]\n\n/** Flat update input: optional metadata + partial pin_config fields. */\nexport type UpdatePinHelperInput<T extends PinTypeId> = {\n pin_layout?: PinLayout\n is_public?: boolean\n title?: string\n tags?: string[]\n description?: string\n metadata?: Partial<PinMetadataBase>\n} & Partial<PinConfigByType[T]>\n\nexport interface CreateMarkdownPinInput extends PinMetadataBase {\n content: string\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n pending_invites?: Record<string, 'editor' | 'viewer'>\n}\n\nexport interface CreateStatCardsPinInput extends PinMetadataBase {\n cards: StatCardItem[]\n pin_layout?: PinLayout\n is_public?: boolean\n}\n\nexport interface CreateTablePinInput extends PinMetadataBase {\n columns: TableColumn[]\n rows?: TableRow[]\n pin_layout?: PinLayout\n is_public?: boolean\n}\n\nexport interface UpdateTablePinInput extends UpdatePinHelperInput<'table'> {}\n\nexport interface CreateEmbedPinInput extends PinMetadataBase {\n url: string\n type?: string\n pin_layout?: PinLayout\n is_public?: boolean\n}\n","import {\n PRODUCT_PIN_TYPES,\n type CreatePinHelperInput,\n type CreateTypedPinRequest,\n type PinConfigByType,\n type PinMetadataBase,\n type PinTypeId,\n type UpdatePinHelperInput,\n type UpdatePinRequest,\n} from '../../types/pins'\n\n/** Known pin_config keys per type (top-level only). */\nexport const PIN_CONFIG_FIELDS: { readonly [K in PinTypeId]: readonly (keyof PinConfigByType[K] & string)[] } = {\n markdown: ['content', 'collaboration'],\n image: ['url', 'altText', 'fit'],\n gallery: ['images'],\n table: ['columns', 'rows'],\n charts: ['chartType', 'data', 'xAxis', 'yAxis'],\n mermaid: ['diagram', 'code', 'title'],\n code: ['code', 'language', 'filename', 'title'],\n embed: ['url', 'type'],\n 'pdf-viewer': ['pdf'],\n 'excel-viewer': ['excel'],\n 'stat-cards': ['cards'],\n timeline: ['mode', 'items'],\n 'json-viewer': ['json', 'jsonString', 'title'],\n 'json-list': ['json', 'jsonString'],\n links: ['links'],\n 'qr-code': ['url', 'label'],\n 'social-handles': ['title', 'showLabels', 'iconSize', 'handles'],\n steps: ['steps'],\n trace: ['title', 'live', 'spans'],\n plan: ['title', 'status', 'breadcrumbs', 'phases'],\n notes: ['notes'],\n 'csv-viewer': ['csvText', 'csvData', 'fileName'],\n 'user-story': ['title', 'userStory', 'acceptanceCriteria'],\n chat: ['title', 'placeholder', 'linked_pin_id', 'linked_pin_title'],\n intro: ['heading', 'subheading'],\n mastra: ['mode', 'agentId', 'workflowId'],\n 'text-media': ['title', 'text', 'subtext', 'textPosition', 'mediaType', 'embedConfig', 'imageConfig'],\n 'business-card': ['sectionTitle', 'fields', 'imageConfig', 'imagePosition'],\n video: ['url', 'fileId', 'fileName', 'mimeType', 'caption', 'size'],\n audio: ['url', 'fileId', 'fileName', 'mimeType', 'caption', 'size', 'tracks'],\n 'file-upload': ['files', 'displayMode'],\n 'kanban-board': ['columns'],\n checklist: ['title', 'items'],\n comparison: ['title', 'left', 'right', 'highlightedLines', 'matches', 'showVsBadge'],\n calendar: ['weekStartsOn', 'events'],\n roadmap: ['title', 'months'],\n 'realtime-canvas': ['title', 'description', 'roomId'],\n}\n\nexport function pinTypeToMethodSuffix(pinType: PinTypeId): string {\n return pinType\n .split('-')\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join('')\n}\n\nfunction pickPinConfig<T extends PinTypeId>(\n pinType: T,\n input: Record<string, unknown>,\n): PinConfigByType[T] {\n const fields = PIN_CONFIG_FIELDS[pinType]\n const pin_config = {} as PinConfigByType[T]\n for (const key of fields) {\n if (key in input && input[key] !== undefined) {\n ;(pin_config as Record<string, unknown>)[key] = input[key]\n }\n }\n return pin_config\n}\n\nexport function toCreatePinRequest<T extends PinTypeId>(\n pinType: T,\n input: CreatePinHelperInput<T>,\n): CreateTypedPinRequest<T> {\n const raw = input as Record<string, unknown>\n const pin_config = pickPinConfig(pinType, raw)\n\n const metadata: PinMetadataBase = {\n title: input.title,\n tags: input.tags,\n description: input.description,\n allow_edit: input.allow_edit,\n require_sign_in: input.require_sign_in,\n allow_comments: input.allow_comments,\n }\n\n return {\n pin_type: pinType,\n pin_config,\n pin_layout: input.pin_layout,\n is_public: input.is_public,\n allow_edit: input.allow_edit,\n require_sign_in: input.require_sign_in,\n allow_comments: input.allow_comments,\n pending_invites: input.pending_invites,\n metadata,\n }\n}\n\nexport function toUpdatePinRequest<T extends PinTypeId>(\n pinType: T,\n input: UpdatePinHelperInput<T>,\n): UpdatePinRequest<T> {\n const raw = input as Record<string, unknown>\n const pin_config = pickPinConfig(pinType, raw) as PinConfigByType[T]\n const hasPinConfig = Object.keys(pin_config as object).length > 0\n\n const metadata: Partial<PinMetadataBase> = {\n ...(input.metadata ?? {}),\n }\n if (input.title !== undefined) metadata.title = input.title\n if (input.tags !== undefined) metadata.tags = input.tags\n if (input.description !== undefined) metadata.description = input.description\n\n const hasMetadata = Object.keys(metadata).length > 0\n\n return {\n ...(hasPinConfig ? { pin_config } : {}),\n pin_layout: input.pin_layout,\n is_public: input.is_public,\n ...(hasMetadata ? { metadata } : {}),\n }\n}\n\nexport function attachNamedPinHelpers(ctor: { prototype: Record<string, unknown> }) {\n for (const pinType of PRODUCT_PIN_TYPES as readonly PinTypeId[]) {\n const suffix = pinTypeToMethodSuffix(pinType)\n ctor.prototype[`create${suffix}`] = function (\n this: { createPin: (t: PinTypeId, i: unknown) => unknown },\n input: unknown,\n ) {\n return this.createPin(pinType, input)\n }\n ctor.prototype[`update${suffix}`] = function (\n this: { updatePin: (id: string, t: PinTypeId, i: unknown) => unknown },\n pinId: string,\n input: unknown,\n ) {\n return this.updatePin(pinId, pinType, input)\n }\n }\n}\n","/**\n * Pins API Methods\n */\n\nimport type { PindownClient } from '../PindownClient'\nimport type {\n Pin,\n PinTypeId,\n CreatePinRequest,\n CreatePinHelperInput,\n UpdatePinRequest,\n UpdatePinHelperInput,\n SharePinRequest,\n ListPinsOptions,\n CreateMarkdownPinInput,\n CreateStatCardsPinInput,\n CreateTablePinInput,\n UpdateTablePinInput,\n CreateEmbedPinInput,\n} from '../../types/pins'\nimport type { PaginatedResponse } from '../../types/api'\nimport {\n attachNamedPinHelpers,\n toCreatePinRequest,\n toUpdatePinRequest,\n} from './pin-helper-core'\n\nexport class PinsMethods {\n constructor(private client: PindownClient) {}\n\n /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */\n async create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('POST', '/pins', request)\n }\n\n /** Create helper for any pin type via flat typed input. */\n async createPin<T extends PinTypeId>(\n pinType: T,\n input: CreatePinHelperInput<T>,\n ): Promise<Pin<T>> {\n return this.create(toCreatePinRequest(pinType, input))\n }\n\n async get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('GET', `/pins/${pinId}`)\n }\n\n async list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>> {\n const params = new URLSearchParams()\n if (options?.limit) params.append('limit', options.limit.toString())\n if (options?.offset) params.append('offset', options.offset.toString())\n\n const query = params.toString()\n const endpoint = query ? `/pins?${query}` : '/pins'\n\n return this.client.request<PaginatedResponse<Pin>>('GET', endpoint)\n }\n\n async update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('PUT', `/pins/${pinId}`, request)\n }\n\n /** Update helper for any pin type via flat typed input. */\n async updatePin<T extends PinTypeId>(\n pinId: string,\n pinType: T,\n input: UpdatePinHelperInput<T>,\n ): Promise<Pin<T>> {\n return this.update(pinId, toUpdatePinRequest(pinType, input))\n }\n\n async delete(pinId: string): Promise<void> {\n return this.client.request<void>('DELETE', `/pins/${pinId}`)\n }\n\n async share(pinId: string, request: SharePinRequest): Promise<Pin> {\n return this.client.request<Pin>('POST', `/pins/${pinId}/share`, request)\n }\n\n async batchGet(pinIds: string[]): Promise<{\n found: Pin[]\n not_found: string[]\n permission_denied: string[]\n }> {\n return this.client.request('POST', '/pins/batch/get', { pin_ids: pinIds })\n }\n\n async batchCreate(pins: CreatePinRequest[]): Promise<{\n created: Array<{ id: string; index: number; created_at: number }>\n failed: Array<{ index: number; error: string }>\n }> {\n return this.client.request('POST', '/pins/batch', { pins })\n }\n\n async batchUpdate(updates: Array<{ id: string } & UpdatePinRequest>): Promise<{\n updated: string[]\n failed: Array<{ id: string; error: string }>\n updated_at: number\n }> {\n return this.client.request('PATCH', '/pins/batch', { updates })\n }\n\n async batchDelete(pinIds: string[]): Promise<{\n deleted: string[]\n failed: Array<{ id: string; error: string }>\n }> {\n return this.client.request('DELETE', '/pins/batch', { pin_ids: pinIds })\n }\n\n /** Create a markdown pin with pin_config.content (seeds Yjs on the server). */\n async createMarkdown(input: CreateMarkdownPinInput): Promise<Pin<'markdown'>> {\n const { content, title, tags, description, pin_layout, is_public, allow_edit, require_sign_in, allow_comments, pending_invites } = input\n return this.create({\n pin_type: 'markdown',\n pin_config: { content },\n pin_layout,\n is_public,\n allow_edit,\n require_sign_in,\n allow_comments,\n pending_invites,\n metadata: { title, tags, description },\n })\n }\n\n async createStatCards(input: CreateStatCardsPinInput): Promise<Pin<'stat-cards'>> {\n const { cards, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'stat-cards',\n pin_config: { cards },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n async createTable(input: CreateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'table',\n pin_config: { columns, rows },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /** Partial table pin_config update with typed columns/rows. */\n async updateTable(pinId: string, input: UpdateTablePinInput): Promise<Pin<'table'>> {\n return this.updatePin(pinId, 'table', input)\n }\n\n async createEmbed(input: CreateEmbedPinInput): Promise<Pin<'embed'>> {\n const { url, type, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'embed',\n pin_config: { url, type },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /**\n * @deprecated Use createMarkdown({ title, content, ... }) — old signature ignored content in title\n */\n async createMarkdownLegacy(title: string, additionalMetadata?: Record<string, unknown>): Promise<Pin<'markdown'>> {\n return this.createMarkdown({\n title,\n content: '',\n ...(additionalMetadata as Partial<CreateMarkdownPinInput>),\n })\n }\n}\n\nattachNamedPinHelpers(PinsMethods as unknown as { prototype: Record<string, unknown> })\n","/**\n * Error classes for the v1 Pins API client\n */\n\nexport class PindownError extends Error {\n constructor(message: string) {\n super(message)\n this.name = 'PindownError'\n }\n}\n\nexport class AuthenticationError extends PindownError {\n constructor(message: string = 'Authentication failed') {\n super(message)\n this.name = 'AuthenticationError'\n }\n}\n\nexport class ForbiddenError extends PindownError {\n constructor(message: string = 'Access forbidden') {\n super(message)\n this.name = 'ForbiddenError'\n }\n}\n\nexport class NotFoundError extends PindownError {\n constructor(resource: string) {\n super(`${resource} not found`)\n this.name = 'NotFoundError'\n }\n}\n\nexport class ValidationError extends PindownError {\n public details?: unknown\n\n constructor(message: string, details?: unknown) {\n super(message)\n this.name = 'ValidationError'\n this.details = details\n }\n}\n\nexport class RateLimitError extends PindownError {\n constructor(message: string = 'Rate limit exceeded (429 RATE_LIMITED)') {\n super(message)\n this.name = 'RateLimitError'\n }\n}\n\nexport class ServerError extends PindownError {\n public statusCode: number\n\n constructor(message: string, statusCode: number = 500) {\n super(message)\n this.name = 'ServerError'\n this.statusCode = statusCode\n }\n}\n\nexport class NetworkError extends PindownError {\n constructor(message: string = 'Network request failed') {\n super(message)\n this.name = 'NetworkError'\n }\n}\n","/**\n * Pindown API Client — v1 Pins API only\n */\n\nimport { PinsMethods } from './pins'\nimport type { PindownConfig } from '../types/config'\nimport {\n AuthenticationError,\n ForbiddenError,\n NotFoundError,\n ValidationError,\n RateLimitError,\n ServerError,\n NetworkError,\n} from '../errors'\n\nexport class PindownClient {\n private config: Required<Omit<PindownConfig, 'baseURL'>> & { baseURL: string }\n\n public readonly pins: PinsMethods\n\n constructor(config: PindownConfig) {\n if (!config.apiKey) {\n throw new Error('API key is required')\n }\n\n this.config = {\n apiKey: config.apiKey,\n baseURL: config.baseURL || 'https://api.pindown.ai/v1',\n maxRetries: config.maxRetries ?? 3,\n timeout: config.timeout ?? 30000,\n }\n\n this.pins = new PinsMethods(this)\n }\n\n async request<T = unknown>(method: string, endpoint: string, data?: unknown): Promise<T> {\n const url = `${this.config.baseURL}${endpoint}`\n const headers: Record<string, string> = {\n Authorization: `Bearer ${this.config.apiKey}`,\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n headers['Content-Type'] = 'application/json'\n }\n\n const requestOptions: RequestInit = {\n method,\n headers,\n signal: AbortSignal.timeout(this.config.timeout),\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n requestOptions.body = JSON.stringify(data)\n }\n\n try {\n const response = await fetch(url, requestOptions)\n\n if (!response.ok) {\n await this.handleErrorResponse(response)\n }\n\n const result = await response.json()\n return result.data as T\n } catch (error: unknown) {\n if (\n error instanceof AuthenticationError ||\n error instanceof ForbiddenError ||\n error instanceof NotFoundError ||\n error instanceof ValidationError ||\n error instanceof RateLimitError ||\n error instanceof ServerError\n ) {\n throw error\n }\n\n if (error instanceof Error && (error.name === 'AbortError' || error.name === 'TimeoutError')) {\n throw new NetworkError('Request timeout')\n }\n\n throw new NetworkError(error instanceof Error ? error.message : 'Network request failed')\n }\n }\n\n private async handleErrorResponse(response: Response): Promise<never> {\n let errorData: { error?: { code?: string; message?: string; details?: unknown }; message?: string }\n\n try {\n errorData = await response.json()\n } catch {\n errorData = { message: response.statusText }\n }\n\n const message = errorData.error?.message || errorData.message || 'Unknown error'\n\n switch (response.status) {\n case 401:\n throw new AuthenticationError(message)\n case 403:\n throw new ForbiddenError(message)\n case 404:\n throw new NotFoundError(message)\n case 400:\n case 422:\n throw new ValidationError(message, errorData.error?.details)\n case 429:\n throw new RateLimitError(message)\n case 500:\n case 502:\n case 503:\n throw new ServerError(message, response.status)\n default:\n throw new ServerError(message, response.status)\n }\n }\n}\n","/**\n * Runtime hints + minimal examples per pin type.\n * Use when building API payloads without opening the docs every time.\n */\n\nimport type { PinConfigByType, PinTypeId, UpdatePinRequest } from './types/pins'\n\nexport interface PinConfigFieldHint {\n path: string\n type: string\n required: boolean\n description: string\n}\n\nexport interface PinConfigHint<T extends PinTypeId = PinTypeId> {\n pin_type: T\n summary: string\n required_fields: string[]\n optional_fields: string[]\n fields: PinConfigFieldHint[]\n /** Minimal valid pin_config for create/update */\n example_config: PinConfigByType[T]\n /** Typical PUT /v1/pins/:id body (root-level pin_config) */\n example_update: UpdatePinRequest<T>\n}\n\nconst TABLE_HINT: PinConfigHint<'table'> = {\n pin_type: 'table',\n summary: 'Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.',\n required_fields: ['columns'],\n optional_fields: ['rows'],\n fields: [\n {\n path: 'columns',\n type: 'TableColumn[]',\n required: true,\n description: 'At least one column. Each column needs id + name (type optional, e.g. text | number).',\n },\n {\n path: 'columns[].id',\n type: 'string',\n required: true,\n description: 'Stable column key used in row.cells.',\n },\n {\n path: 'columns[].name',\n type: 'string',\n required: true,\n description: 'Column header label.',\n },\n {\n path: 'rows',\n type: 'TableRow[]',\n required: false,\n description: 'Table data. Each row: { id, cells: { [columnId]: value } }.',\n },\n ],\n example_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Item', col2: 1 } }],\n },\n example_update: {\n pin_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Updated', col2: 42 } }],\n },\n },\n}\n\n/** Per-type hints (expand over time; table is fully documented). */\nexport const PIN_CONFIG_HINTS: Partial<Record<PinTypeId, PinConfigHint>> = {\n table: TABLE_HINT,\n markdown: {\n pin_type: 'markdown',\n summary: 'Rich text / markdown body.',\n required_fields: [],\n optional_fields: ['content', 'collaboration'],\n fields: [\n {\n path: 'content',\n type: 'string',\n required: false,\n description: 'Markdown source. Server seeds Yjs when set on create.',\n },\n ],\n example_config: { content: '# Hello\\n\\nBody text.' },\n example_update: { pin_config: { content: '# Updated\\n\\nNew body.' } },\n },\n 'stat-cards': {\n pin_type: 'stat-cards',\n summary: 'KPI cards grid.',\n required_fields: ['cards'],\n optional_fields: [],\n fields: [\n {\n path: 'cards',\n type: 'StatCardItem[]',\n required: true,\n description: 'Each card: title, value; optional change, trend (up|down|neutral).',\n },\n ],\n example_config: {\n cards: [{ title: 'Revenue', value: '1000', change: '+5%', trend: 'up' }],\n },\n example_update: {\n pin_config: {\n cards: [{ title: 'Revenue', value: '1234', change: '+8%', trend: 'up' }],\n },\n },\n },\n}\n\nexport function getPinConfigHint<T extends PinTypeId>(pinType: T): PinConfigHint<T> | undefined {\n return PIN_CONFIG_HINTS[pinType] as PinConfigHint<T> | undefined\n}\n\n/** Pretty-print field hints for CLI / logging. */\nexport function formatPinConfigHint(pinType: PinTypeId): string {\n const hint = getPinConfigHint(pinType)\n if (!hint) {\n return [\n `No built-in hint for pin type \"${pinType}\".`,\n 'Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,',\n 'or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config.',\n ].join('\\n')\n }\n\n const lines = [\n `Pin type: ${hint.pin_type}`,\n hint.summary,\n '',\n 'Required pin_config fields:',\n ...hint.required_fields.map((f) => ` - ${f}`),\n '',\n 'Optional pin_config fields:',\n ...(hint.optional_fields.length ? hint.optional_fields.map((f) => ` - ${f}`) : [' (none documented)']),\n '',\n 'Field reference:',\n ...hint.fields.map(\n (f) => ` ${f.path} (${f.type}${f.required ? ', required' : ''}): ${f.description}`,\n ),\n '',\n 'Example update payload:',\n JSON.stringify(hint.example_update, null, 2),\n ]\n return lines.join('\\n')\n}\n"]}
package/dist/index.d.cts CHANGED
@@ -507,6 +507,25 @@ interface ListPinsOptions {
507
507
  limit?: number;
508
508
  offset?: number;
509
509
  }
510
+ interface CreatePinOptions {
511
+ pin_layout?: PinLayout;
512
+ is_public?: boolean;
513
+ allow_edit?: boolean;
514
+ require_sign_in?: boolean;
515
+ allow_comments?: boolean;
516
+ pending_invites?: Record<string, 'editor' | 'viewer'>;
517
+ }
518
+ /** Flat create input: metadata + pin_config fields (all pin types). */
519
+ type CreatePinHelperInput<T extends PinTypeId> = PinMetadataBase & CreatePinOptions & PinConfigByType[T];
520
+ /** Flat update input: optional metadata + partial pin_config fields. */
521
+ type UpdatePinHelperInput<T extends PinTypeId> = {
522
+ pin_layout?: PinLayout;
523
+ is_public?: boolean;
524
+ title?: string;
525
+ tags?: string[];
526
+ description?: string;
527
+ metadata?: Partial<PinMetadataBase>;
528
+ } & Partial<PinConfigByType[T]>;
510
529
  interface CreateMarkdownPinInput extends PinMetadataBase {
511
530
  content: string;
512
531
  pin_layout?: PinLayout;
@@ -527,12 +546,7 @@ interface CreateTablePinInput extends PinMetadataBase {
527
546
  pin_layout?: PinLayout;
528
547
  is_public?: boolean;
529
548
  }
530
- interface UpdateTablePinInput {
531
- columns?: TableColumn[];
532
- rows?: TableRow[];
533
- title?: string;
534
- tags?: string[];
535
- description?: string;
549
+ interface UpdateTablePinInput extends UpdatePinHelperInput<'table'> {
536
550
  }
537
551
  interface CreateEmbedPinInput extends PinMetadataBase {
538
552
  url: string;
@@ -569,9 +583,13 @@ declare class PinsMethods {
569
583
  constructor(client: PindownClient);
570
584
  /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */
571
585
  create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>>;
586
+ /** Create helper for any pin type via flat typed input. */
587
+ createPin<T extends PinTypeId>(pinType: T, input: CreatePinHelperInput<T>): Promise<Pin<T>>;
572
588
  get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>>;
573
589
  list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>>;
574
590
  update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>>;
591
+ /** Update helper for any pin type via flat typed input. */
592
+ updatePin<T extends PinTypeId>(pinId: string, pinType: T, input: UpdatePinHelperInput<T>): Promise<Pin<T>>;
575
593
  delete(pinId: string): Promise<void>;
576
594
  share(pinId: string, request: SharePinRequest): Promise<Pin>;
577
595
  batchGet(pinIds: string[]): Promise<{
@@ -646,6 +664,18 @@ declare class PindownClient {
646
664
  private handleErrorResponse;
647
665
  }
648
666
 
667
+ type CapitalizeWord<S extends string> = S extends `${infer C}${infer R}` ? `${Uppercase<C>}${R}` : S;
668
+ type PascalFromKebab<S extends string> = S extends `${infer Head}-${infer Tail}` ? `${CapitalizeWord<Head>}${PascalFromKebab<Tail>}` : CapitalizeWord<S>;
669
+ /** `createMarkdown`, `createTable`, … — one per {@link PinTypeId}. */
670
+ type PinCreateMethods = {
671
+ [T in PinTypeId as `create${PascalFromKebab<T>}`]: (input: CreatePinHelperInput<T>) => Promise<Pin<T>>;
672
+ };
673
+ /** `updateMarkdown`, `updateTable`, … — one per {@link PinTypeId}. */
674
+ type PinUpdateMethods = {
675
+ [T in PinTypeId as `update${PascalFromKebab<T>}`]: (pinId: string, input: UpdatePinHelperInput<T>) => Promise<Pin<T>>;
676
+ };
677
+ type PinTypedHelperMethods = PinCreateMethods & PinUpdateMethods;
678
+
649
679
  /**
650
680
  * Runtime hints + minimal examples per pin type.
651
681
  * Use when building API payloads without opening the docs every time.
@@ -704,4 +734,4 @@ declare class NetworkError extends PindownError {
704
734
  constructor(message?: string);
705
735
  }
706
736
 
707
- export { ALL_PIN_TYPES, type ApiResponse, type AudioPinConfig, type AudioPinTrack, AuthenticationError, type BusinessCardField, type BusinessCardPinConfig, type CalendarPinConfig, type ChartsPinConfig, type ChatPinConfig, type ChecklistItem, type ChecklistPinConfig, type CreateEmbedPinInput, type CreateMarkdownPinInput, type CreateNestedPinRequest, type CreatePinRequest, type CreateStatCardsPinInput, type CreateTablePinInput, type CreateTypedPinRequest, type CsvViewerPinConfig, type EmbedPinConfig, type ExcelViewerPinConfig, type FileUploadPinConfig, ForbiddenError, type GalleryImage, type GalleryPinConfig, type ImagePinConfig, type IntroPinConfig, type JsonListPinConfig, type JsonViewerPinConfig, type KanbanBoardPinConfig, type KanbanColumn, type LinkItem, type LinksPinConfig, type ListPinsOptions, type MarkdownPinConfig, type MastraPinConfig, type MermaidPinConfig, NetworkError, NotFoundError, PIN_CONFIG_HINTS, PRODUCT_PIN_TYPES, type PaginatedResponse, type PdfViewerPinConfig, type Pin, type PinCardType, type PinConfigByType, type PinConfigFieldHint, type PinConfigHint, type PinDataType, type PinLayout, type PinMetadata, type PinMetadataBase, type PinTypeId, PindownClient, type PindownConfig, PindownError, type ProductPinTypeId, type QrCodePinConfig, RateLimitError, type RealtimeCanvasPinConfig, type RoadmapPinConfig, ServerError, type SharePinRequest, type StatCardItem, type StatCardsPinConfig, type StepItem, type StepsPinConfig, type TableColumn, type TablePinConfig, type TableRow, type TextMediaPinConfig, type TimelinePinConfig, type UpdatePinRequest, type UpdateTablePinInput, type UserStoryPinConfig, ValidationError, type VideoPinConfig, formatPinConfigHint, getPinConfigHint };
737
+ export { ALL_PIN_TYPES, type ApiResponse, type AudioPinConfig, type AudioPinTrack, AuthenticationError, type BusinessCardField, type BusinessCardPinConfig, type CalendarPinConfig, type ChartsPinConfig, type ChatPinConfig, type ChecklistItem, type ChecklistPinConfig, type CreateEmbedPinInput, type CreateMarkdownPinInput, type CreateNestedPinRequest, type CreatePinHelperInput, type CreatePinOptions, type CreatePinRequest, type CreateStatCardsPinInput, type CreateTablePinInput, type CreateTypedPinRequest, type CsvViewerPinConfig, type EmbedPinConfig, type ExcelViewerPinConfig, type FileUploadPinConfig, ForbiddenError, type GalleryImage, type GalleryPinConfig, type ImagePinConfig, type IntroPinConfig, type JsonListPinConfig, type JsonViewerPinConfig, type KanbanBoardPinConfig, type KanbanColumn, type LinkItem, type LinksPinConfig, type ListPinsOptions, type MarkdownPinConfig, type MastraPinConfig, type MermaidPinConfig, NetworkError, NotFoundError, PIN_CONFIG_HINTS, PRODUCT_PIN_TYPES, type PaginatedResponse, type PdfViewerPinConfig, type Pin, type PinCardType, type PinConfigByType, type PinConfigFieldHint, type PinConfigHint, type PinCreateMethods, type PinDataType, type PinLayout, type PinMetadata, type PinMetadataBase, type PinTypeId, type PinTypedHelperMethods, type PinUpdateMethods, PindownClient, type PindownConfig, PindownError, type ProductPinTypeId, type QrCodePinConfig, RateLimitError, type RealtimeCanvasPinConfig, type RoadmapPinConfig, ServerError, type SharePinRequest, type StatCardItem, type StatCardsPinConfig, type StepItem, type StepsPinConfig, type TableColumn, type TablePinConfig, type TableRow, type TextMediaPinConfig, type TimelinePinConfig, type UpdatePinHelperInput, type UpdatePinRequest, type UpdateTablePinInput, type UserStoryPinConfig, ValidationError, type VideoPinConfig, formatPinConfigHint, getPinConfigHint };
package/dist/index.d.ts CHANGED
@@ -507,6 +507,25 @@ interface ListPinsOptions {
507
507
  limit?: number;
508
508
  offset?: number;
509
509
  }
510
+ interface CreatePinOptions {
511
+ pin_layout?: PinLayout;
512
+ is_public?: boolean;
513
+ allow_edit?: boolean;
514
+ require_sign_in?: boolean;
515
+ allow_comments?: boolean;
516
+ pending_invites?: Record<string, 'editor' | 'viewer'>;
517
+ }
518
+ /** Flat create input: metadata + pin_config fields (all pin types). */
519
+ type CreatePinHelperInput<T extends PinTypeId> = PinMetadataBase & CreatePinOptions & PinConfigByType[T];
520
+ /** Flat update input: optional metadata + partial pin_config fields. */
521
+ type UpdatePinHelperInput<T extends PinTypeId> = {
522
+ pin_layout?: PinLayout;
523
+ is_public?: boolean;
524
+ title?: string;
525
+ tags?: string[];
526
+ description?: string;
527
+ metadata?: Partial<PinMetadataBase>;
528
+ } & Partial<PinConfigByType[T]>;
510
529
  interface CreateMarkdownPinInput extends PinMetadataBase {
511
530
  content: string;
512
531
  pin_layout?: PinLayout;
@@ -527,12 +546,7 @@ interface CreateTablePinInput extends PinMetadataBase {
527
546
  pin_layout?: PinLayout;
528
547
  is_public?: boolean;
529
548
  }
530
- interface UpdateTablePinInput {
531
- columns?: TableColumn[];
532
- rows?: TableRow[];
533
- title?: string;
534
- tags?: string[];
535
- description?: string;
549
+ interface UpdateTablePinInput extends UpdatePinHelperInput<'table'> {
536
550
  }
537
551
  interface CreateEmbedPinInput extends PinMetadataBase {
538
552
  url: string;
@@ -569,9 +583,13 @@ declare class PinsMethods {
569
583
  constructor(client: PindownClient);
570
584
  /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */
571
585
  create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>>;
586
+ /** Create helper for any pin type via flat typed input. */
587
+ createPin<T extends PinTypeId>(pinType: T, input: CreatePinHelperInput<T>): Promise<Pin<T>>;
572
588
  get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>>;
573
589
  list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>>;
574
590
  update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>>;
591
+ /** Update helper for any pin type via flat typed input. */
592
+ updatePin<T extends PinTypeId>(pinId: string, pinType: T, input: UpdatePinHelperInput<T>): Promise<Pin<T>>;
575
593
  delete(pinId: string): Promise<void>;
576
594
  share(pinId: string, request: SharePinRequest): Promise<Pin>;
577
595
  batchGet(pinIds: string[]): Promise<{
@@ -646,6 +664,18 @@ declare class PindownClient {
646
664
  private handleErrorResponse;
647
665
  }
648
666
 
667
+ type CapitalizeWord<S extends string> = S extends `${infer C}${infer R}` ? `${Uppercase<C>}${R}` : S;
668
+ type PascalFromKebab<S extends string> = S extends `${infer Head}-${infer Tail}` ? `${CapitalizeWord<Head>}${PascalFromKebab<Tail>}` : CapitalizeWord<S>;
669
+ /** `createMarkdown`, `createTable`, … — one per {@link PinTypeId}. */
670
+ type PinCreateMethods = {
671
+ [T in PinTypeId as `create${PascalFromKebab<T>}`]: (input: CreatePinHelperInput<T>) => Promise<Pin<T>>;
672
+ };
673
+ /** `updateMarkdown`, `updateTable`, … — one per {@link PinTypeId}. */
674
+ type PinUpdateMethods = {
675
+ [T in PinTypeId as `update${PascalFromKebab<T>}`]: (pinId: string, input: UpdatePinHelperInput<T>) => Promise<Pin<T>>;
676
+ };
677
+ type PinTypedHelperMethods = PinCreateMethods & PinUpdateMethods;
678
+
649
679
  /**
650
680
  * Runtime hints + minimal examples per pin type.
651
681
  * Use when building API payloads without opening the docs every time.
@@ -704,4 +734,4 @@ declare class NetworkError extends PindownError {
704
734
  constructor(message?: string);
705
735
  }
706
736
 
707
- export { ALL_PIN_TYPES, type ApiResponse, type AudioPinConfig, type AudioPinTrack, AuthenticationError, type BusinessCardField, type BusinessCardPinConfig, type CalendarPinConfig, type ChartsPinConfig, type ChatPinConfig, type ChecklistItem, type ChecklistPinConfig, type CreateEmbedPinInput, type CreateMarkdownPinInput, type CreateNestedPinRequest, type CreatePinRequest, type CreateStatCardsPinInput, type CreateTablePinInput, type CreateTypedPinRequest, type CsvViewerPinConfig, type EmbedPinConfig, type ExcelViewerPinConfig, type FileUploadPinConfig, ForbiddenError, type GalleryImage, type GalleryPinConfig, type ImagePinConfig, type IntroPinConfig, type JsonListPinConfig, type JsonViewerPinConfig, type KanbanBoardPinConfig, type KanbanColumn, type LinkItem, type LinksPinConfig, type ListPinsOptions, type MarkdownPinConfig, type MastraPinConfig, type MermaidPinConfig, NetworkError, NotFoundError, PIN_CONFIG_HINTS, PRODUCT_PIN_TYPES, type PaginatedResponse, type PdfViewerPinConfig, type Pin, type PinCardType, type PinConfigByType, type PinConfigFieldHint, type PinConfigHint, type PinDataType, type PinLayout, type PinMetadata, type PinMetadataBase, type PinTypeId, PindownClient, type PindownConfig, PindownError, type ProductPinTypeId, type QrCodePinConfig, RateLimitError, type RealtimeCanvasPinConfig, type RoadmapPinConfig, ServerError, type SharePinRequest, type StatCardItem, type StatCardsPinConfig, type StepItem, type StepsPinConfig, type TableColumn, type TablePinConfig, type TableRow, type TextMediaPinConfig, type TimelinePinConfig, type UpdatePinRequest, type UpdateTablePinInput, type UserStoryPinConfig, ValidationError, type VideoPinConfig, formatPinConfigHint, getPinConfigHint };
737
+ export { ALL_PIN_TYPES, type ApiResponse, type AudioPinConfig, type AudioPinTrack, AuthenticationError, type BusinessCardField, type BusinessCardPinConfig, type CalendarPinConfig, type ChartsPinConfig, type ChatPinConfig, type ChecklistItem, type ChecklistPinConfig, type CreateEmbedPinInput, type CreateMarkdownPinInput, type CreateNestedPinRequest, type CreatePinHelperInput, type CreatePinOptions, type CreatePinRequest, type CreateStatCardsPinInput, type CreateTablePinInput, type CreateTypedPinRequest, type CsvViewerPinConfig, type EmbedPinConfig, type ExcelViewerPinConfig, type FileUploadPinConfig, ForbiddenError, type GalleryImage, type GalleryPinConfig, type ImagePinConfig, type IntroPinConfig, type JsonListPinConfig, type JsonViewerPinConfig, type KanbanBoardPinConfig, type KanbanColumn, type LinkItem, type LinksPinConfig, type ListPinsOptions, type MarkdownPinConfig, type MastraPinConfig, type MermaidPinConfig, NetworkError, NotFoundError, PIN_CONFIG_HINTS, PRODUCT_PIN_TYPES, type PaginatedResponse, type PdfViewerPinConfig, type Pin, type PinCardType, type PinConfigByType, type PinConfigFieldHint, type PinConfigHint, type PinCreateMethods, type PinDataType, type PinLayout, type PinMetadata, type PinMetadataBase, type PinTypeId, type PinTypedHelperMethods, type PinUpdateMethods, PindownClient, type PindownConfig, PindownError, type ProductPinTypeId, type QrCodePinConfig, RateLimitError, type RealtimeCanvasPinConfig, type RoadmapPinConfig, ServerError, type SharePinRequest, type StatCardItem, type StatCardsPinConfig, type StepItem, type StepsPinConfig, type TableColumn, type TablePinConfig, type TableRow, type TextMediaPinConfig, type TimelinePinConfig, type UpdatePinHelperInput, type UpdatePinRequest, type UpdateTablePinInput, type UserStoryPinConfig, ValidationError, type VideoPinConfig, formatPinConfigHint, getPinConfigHint };
package/dist/index.js CHANGED
@@ -1,8 +1,8 @@
1
- var y=class{constructor(e){this.client=e;}async create(e){return this.client.request("POST","/pins",e)}async get(e){return this.client.request("GET",`/pins/${e}`)}async list(e){let i=new URLSearchParams;e?.limit&&i.append("limit",e.limit.toString()),e?.offset&&i.append("offset",e.offset.toString());let n=i.toString(),s=n?`/pins?${n}`:"/pins";return this.client.request("GET",s)}async update(e,i){return this.client.request("PUT",`/pins/${e}`,i)}async delete(e){return this.client.request("DELETE",`/pins/${e}`)}async share(e,i){return this.client.request("POST",`/pins/${e}/share`,i)}async batchGet(e){return this.client.request("POST","/pins/batch/get",{pin_ids:e})}async batchCreate(e){return this.client.request("POST","/pins/batch",{pins:e})}async batchUpdate(e){return this.client.request("PATCH","/pins/batch",{updates:e})}async batchDelete(e){return this.client.request("DELETE","/pins/batch",{pin_ids:e})}async createMarkdown(e){let{content:i,title:n,tags:s,description:a,pin_layout:o,is_public:t,allow_edit:d,require_sign_in:w,allow_comments:b,pending_invites:_}=e;return this.create({pin_type:"markdown",pin_config:{content:i},pin_layout:o,is_public:t,allow_edit:d,require_sign_in:w,allow_comments:b,pending_invites:_,metadata:{title:n,tags:s,description:a}})}async createStatCards(e){let{cards:i,title:n,tags:s,description:a,pin_layout:o,is_public:t}=e;return this.create({pin_type:"stat-cards",pin_config:{cards:i},pin_layout:o,is_public:t,metadata:{title:n,tags:s,description:a}})}async createTable(e){let{columns:i,rows:n,title:s,tags:a,description:o,pin_layout:t,is_public:d}=e;return this.create({pin_type:"table",pin_config:{columns:i,rows:n},pin_layout:t,is_public:d,metadata:{title:s,tags:a,description:o}})}async updateTable(e,i){let{columns:n,rows:s,title:a,tags:o,description:t}=i,d={};return n!==void 0&&(d.columns=n),s!==void 0&&(d.rows=s),this.update(e,{pin_config:d,...a!==void 0||o!==void 0||t!==void 0?{metadata:{...a!==void 0&&{title:a},...o!==void 0&&{tags:o},...t!==void 0&&{description:t}}}:{}})}async createEmbed(e){let{url:i,type:n,title:s,tags:a,description:o,pin_layout:t,is_public:d}=e;return this.create({pin_type:"embed",pin_config:{url:i,type:n},pin_layout:t,is_public:d,metadata:{title:s,tags:a,description:o}})}async createMarkdownLegacy(e,i){return this.createMarkdown({title:e,content:"",...i})}};var p=class extends Error{constructor(e){super(e),this.name="PindownError";}},u=class extends p{constructor(e="Authentication failed"){super(e),this.name="AuthenticationError";}},l=class extends p{constructor(e="Access forbidden"){super(e),this.name="ForbiddenError";}},P=class extends p{constructor(e){super(`${e} not found`),this.name="NotFoundError";}},f=class extends p{constructor(e,i){super(e),this.name="ValidationError",this.details=i;}},g=class extends p{constructor(e="Rate limit exceeded (429 RATE_LIMITED)"){super(e),this.name="RateLimitError";}},c=class extends p{constructor(e,i=500){super(e),this.name="ServerError",this.statusCode=i;}},m=class extends p{constructor(e="Network request failed"){super(e),this.name="NetworkError";}};var C=class{constructor(e){if(!e.apiKey)throw new Error("API key is required");this.config={apiKey:e.apiKey,baseURL:e.baseURL||"https://api.pindown.ai/v1",maxRetries:e.maxRetries??3,timeout:e.timeout??3e4},this.pins=new y(this);}async request(e,i,n){let s=`${this.config.baseURL}${i}`,a={Authorization:`Bearer ${this.config.apiKey}`};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(a["Content-Type"]="application/json");let o={method:e,headers:a,signal:AbortSignal.timeout(this.config.timeout)};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(o.body=JSON.stringify(n));try{let t=await fetch(s,o);return t.ok||await this.handleErrorResponse(t),(await t.json()).data}catch(t){throw t instanceof u||t instanceof l||t instanceof P||t instanceof f||t instanceof g||t instanceof c?t:t instanceof Error&&(t.name==="AbortError"||t.name==="TimeoutError")?new m("Request timeout"):new m(t instanceof Error?t.message:"Network request failed")}}async handleErrorResponse(e){let i;try{i=await e.json();}catch{i={message:e.statusText};}let n=i.error?.message||i.message||"Unknown error";switch(e.status){case 401:throw new u(n);case 403:throw new l(n);case 404:throw new P(n);case 400:case 422:throw new f(n,i.error?.details);case 429:throw new g(n);case 500:case 502:case 503:throw new c(n,e.status);default:throw new c(n,e.status)}}};var x={pin_type:"table",summary:"Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.",required_fields:["columns"],optional_fields:["rows"],fields:[{path:"columns",type:"TableColumn[]",required:true,description:"At least one column. Each column needs id + name (type optional, e.g. text | number)."},{path:"columns[].id",type:"string",required:true,description:"Stable column key used in row.cells."},{path:"columns[].name",type:"string",required:true,description:"Column header label."},{path:"rows",type:"TableRow[]",required:false,description:"Table data. Each row: { id, cells: { [columnId]: value } }."}],example_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Item",col2:1}}]},example_update:{pin_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Updated",col2:42}}]}}},T={table:x,markdown:{pin_type:"markdown",summary:"Rich text / markdown body.",required_fields:[],optional_fields:["content","collaboration"],fields:[{path:"content",type:"string",required:false,description:"Markdown source. Server seeds Yjs when set on create."}],example_config:{content:`# Hello
1
+ var C=["markdown","image","gallery","table","charts","mermaid","code","embed","pdf-viewer","excel-viewer","stat-cards","timeline","json-viewer","json-list","links","qr-code","social-handles","steps","trace","plan","notes","csv-viewer","user-story","chat","intro","mastra","text-media","business-card","video","audio","file-upload","kanban-board","checklist","comparison","calendar","roadmap","realtime-canvas"];[...C];var S={markdown:["content","collaboration"],image:["url","altText","fit"],gallery:["images"],table:["columns","rows"],charts:["chartType","data","xAxis","yAxis"],mermaid:["diagram","code","title"],code:["code","language","filename","title"],embed:["url","type"],"pdf-viewer":["pdf"],"excel-viewer":["excel"],"stat-cards":["cards"],timeline:["mode","items"],"json-viewer":["json","jsonString","title"],"json-list":["json","jsonString"],links:["links"],"qr-code":["url","label"],"social-handles":["title","showLabels","iconSize","handles"],steps:["steps"],trace:["title","live","spans"],plan:["title","status","breadcrumbs","phases"],notes:["notes"],"csv-viewer":["csvText","csvData","fileName"],"user-story":["title","userStory","acceptanceCriteria"],chat:["title","placeholder","linked_pin_id","linked_pin_title"],intro:["heading","subheading"],mastra:["mode","agentId","workflowId"],"text-media":["title","text","subtext","textPosition","mediaType","embedConfig","imageConfig"],"business-card":["sectionTitle","fields","imageConfig","imagePosition"],video:["url","fileId","fileName","mimeType","caption","size"],audio:["url","fileId","fileName","mimeType","caption","size","tracks"],"file-upload":["files","displayMode"],"kanban-board":["columns"],checklist:["title","items"],comparison:["title","left","right","highlightedLines","matches","showVsBadge"],calendar:["weekStartsOn","events"],roadmap:["title","months"],"realtime-canvas":["title","description","roomId"]};function v(t){return t.split("-").map(e=>e.charAt(0).toUpperCase()+e.slice(1)).join("")}function T(t,e){let i=S[t],n={};for(let a of i)a in e&&e[a]!==void 0&&(n[a]=e[a]);return n}function k(t,e){let n=T(t,e),a={title:e.title,tags:e.tags,description:e.description,allow_edit:e.allow_edit,require_sign_in:e.require_sign_in,allow_comments:e.allow_comments};return {pin_type:t,pin_config:n,pin_layout:e.pin_layout,is_public:e.is_public,allow_edit:e.allow_edit,require_sign_in:e.require_sign_in,allow_comments:e.allow_comments,pending_invites:e.pending_invites,metadata:a}}function b(t,e){let n=T(t,e),a=Object.keys(n).length>0,o={...e.metadata??{}};e.title!==void 0&&(o.title=e.title),e.tags!==void 0&&(o.tags=e.tags),e.description!==void 0&&(o.description=e.description);let s=Object.keys(o).length>0;return {...a?{pin_config:n}:{},pin_layout:e.pin_layout,is_public:e.is_public,...s?{metadata:o}:{}}}function x(t){for(let e of C){let i=v(e);t.prototype[`create${i}`]=function(n){return this.createPin(e,n)},t.prototype[`update${i}`]=function(n,a){return this.updatePin(n,e,a)};}}var y=class{constructor(e){this.client=e;}async create(e){return this.client.request("POST","/pins",e)}async createPin(e,i){return this.create(k(e,i))}async get(e){return this.client.request("GET",`/pins/${e}`)}async list(e){let i=new URLSearchParams;e?.limit&&i.append("limit",e.limit.toString()),e?.offset&&i.append("offset",e.offset.toString());let n=i.toString(),a=n?`/pins?${n}`:"/pins";return this.client.request("GET",a)}async update(e,i){return this.client.request("PUT",`/pins/${e}`,i)}async updatePin(e,i,n){return this.update(e,b(i,n))}async delete(e){return this.client.request("DELETE",`/pins/${e}`)}async share(e,i){return this.client.request("POST",`/pins/${e}/share`,i)}async batchGet(e){return this.client.request("POST","/pins/batch/get",{pin_ids:e})}async batchCreate(e){return this.client.request("POST","/pins/batch",{pins:e})}async batchUpdate(e){return this.client.request("PATCH","/pins/batch",{updates:e})}async batchDelete(e){return this.client.request("DELETE","/pins/batch",{pin_ids:e})}async createMarkdown(e){let{content:i,title:n,tags:a,description:o,pin_layout:s,is_public:r,allow_edit:l,require_sign_in:I,allow_comments:R,pending_invites:q}=e;return this.create({pin_type:"markdown",pin_config:{content:i},pin_layout:s,is_public:r,allow_edit:l,require_sign_in:I,allow_comments:R,pending_invites:q,metadata:{title:n,tags:a,description:o}})}async createStatCards(e){let{cards:i,title:n,tags:a,description:o,pin_layout:s,is_public:r}=e;return this.create({pin_type:"stat-cards",pin_config:{cards:i},pin_layout:s,is_public:r,metadata:{title:n,tags:a,description:o}})}async createTable(e){let{columns:i,rows:n,title:a,tags:o,description:s,pin_layout:r,is_public:l}=e;return this.create({pin_type:"table",pin_config:{columns:i,rows:n},pin_layout:r,is_public:l,metadata:{title:a,tags:o,description:s}})}async updateTable(e,i){return this.updatePin(e,"table",i)}async createEmbed(e){let{url:i,type:n,title:a,tags:o,description:s,pin_layout:r,is_public:l}=e;return this.create({pin_type:"embed",pin_config:{url:i,type:n},pin_layout:r,is_public:l,metadata:{title:a,tags:o,description:s}})}async createMarkdownLegacy(e,i){return this.createMarkdown({title:e,content:"",...i})}};x(y);var p=class extends Error{constructor(e){super(e),this.name="PindownError";}},g=class extends p{constructor(e="Authentication failed"){super(e),this.name="AuthenticationError";}},c=class extends p{constructor(e="Access forbidden"){super(e),this.name="ForbiddenError";}},u=class extends p{constructor(e){super(`${e} not found`),this.name="NotFoundError";}},P=class extends p{constructor(e,i){super(e),this.name="ValidationError",this.details=i;}},f=class extends p{constructor(e="Rate limit exceeded (429 RATE_LIMITED)"){super(e),this.name="RateLimitError";}},d=class extends p{constructor(e,i=500){super(e),this.name="ServerError",this.statusCode=i;}},m=class extends p{constructor(e="Network request failed"){super(e),this.name="NetworkError";}};var w=class{constructor(e){if(!e.apiKey)throw new Error("API key is required");this.config={apiKey:e.apiKey,baseURL:e.baseURL||"https://api.pindown.ai/v1",maxRetries:e.maxRetries??3,timeout:e.timeout??3e4},this.pins=new y(this);}async request(e,i,n){let a=`${this.config.baseURL}${i}`,o={Authorization:`Bearer ${this.config.apiKey}`};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(o["Content-Type"]="application/json");let s={method:e,headers:o,signal:AbortSignal.timeout(this.config.timeout)};n&&(e==="POST"||e==="PUT"||e==="PATCH"||e==="DELETE")&&(s.body=JSON.stringify(n));try{let r=await fetch(a,s);return r.ok||await this.handleErrorResponse(r),(await r.json()).data}catch(r){throw r instanceof g||r instanceof c||r instanceof u||r instanceof P||r instanceof f||r instanceof d?r:r instanceof Error&&(r.name==="AbortError"||r.name==="TimeoutError")?new m("Request timeout"):new m(r instanceof Error?r.message:"Network request failed")}}async handleErrorResponse(e){let i;try{i=await e.json();}catch{i={message:e.statusText};}let n=i.error?.message||i.message||"Unknown error";switch(e.status){case 401:throw new g(n);case 403:throw new c(n);case 404:throw new u(n);case 400:case 422:throw new P(n,i.error?.details);case 429:throw new f(n);case 500:case 502:case 503:throw new d(n,e.status);default:throw new d(n,e.status)}}};var E={pin_type:"table",summary:"Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.",required_fields:["columns"],optional_fields:["rows"],fields:[{path:"columns",type:"TableColumn[]",required:true,description:"At least one column. Each column needs id + name (type optional, e.g. text | number)."},{path:"columns[].id",type:"string",required:true,description:"Stable column key used in row.cells."},{path:"columns[].name",type:"string",required:true,description:"Column header label."},{path:"rows",type:"TableRow[]",required:false,description:"Table data. Each row: { id, cells: { [columnId]: value } }."}],example_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Item",col2:1}}]},example_update:{pin_config:{columns:[{id:"col1",name:"Name",type:"text"},{id:"col2",name:"Value",type:"number"}],rows:[{id:"row1",cells:{col1:"Updated",col2:42}}]}}},_={table:E,markdown:{pin_type:"markdown",summary:"Rich text / markdown body.",required_fields:[],optional_fields:["content","collaboration"],fields:[{path:"content",type:"string",required:false,description:"Markdown source. Server seeds Yjs when set on create."}],example_config:{content:`# Hello
2
2
 
3
3
  Body text.`},example_update:{pin_config:{content:`# Updated
4
4
 
5
- New body.`}}},"stat-cards":{pin_type:"stat-cards",summary:"KPI cards grid.",required_fields:["cards"],optional_fields:[],fields:[{path:"cards",type:"StatCardItem[]",required:true,description:"Each card: title, value; optional change, trend (up|down|neutral)."}],example_config:{cards:[{title:"Revenue",value:"1000",change:"+5%",trend:"up"}]},example_update:{pin_config:{cards:[{title:"Revenue",value:"1234",change:"+8%",trend:"up"}]}}}};function h(r){return T[r]}function I(r){let e=h(r);return e?[`Pin type: ${e.pin_type}`,e.summary,"","Required pin_config fields:",...e.required_fields.map(n=>` - ${n}`),"","Optional pin_config fields:",...e.optional_fields.length?e.optional_fields.map(n=>` - ${n}`):[" (none documented)"],"","Field reference:",...e.fields.map(n=>` ${n.path} (${n.type}${n.required?", required":""}): ${n.description}`),"","Example update payload:",JSON.stringify(e.example_update,null,2)].join(`
6
- `):[`No built-in hint for pin type "${r}".`,"Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,","or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config."].join(`
7
- `)}export{u as AuthenticationError,l as ForbiddenError,m as NetworkError,P as NotFoundError,T as PIN_CONFIG_HINTS,C as PindownClient,p as PindownError,g as RateLimitError,c as ServerError,f as ValidationError,I as formatPinConfigHint,h as getPinConfigHint};//# sourceMappingURL=index.js.map
5
+ New body.`}}},"stat-cards":{pin_type:"stat-cards",summary:"KPI cards grid.",required_fields:["cards"],optional_fields:[],fields:[{path:"cards",type:"StatCardItem[]",required:true,description:"Each card: title, value; optional change, trend (up|down|neutral)."}],example_config:{cards:[{title:"Revenue",value:"1000",change:"+5%",trend:"up"}]},example_update:{pin_config:{cards:[{title:"Revenue",value:"1234",change:"+8%",trend:"up"}]}}}};function h(t){return _[t]}function L(t){let e=h(t);return e?[`Pin type: ${e.pin_type}`,e.summary,"","Required pin_config fields:",...e.required_fields.map(n=>` - ${n}`),"","Optional pin_config fields:",...e.optional_fields.length?e.optional_fields.map(n=>` - ${n}`):[" (none documented)"],"","Field reference:",...e.fields.map(n=>` ${n.path} (${n.type}${n.required?", required":""}): ${n.description}`),"","Example update payload:",JSON.stringify(e.example_update,null,2)].join(`
6
+ `):[`No built-in hint for pin type "${t}".`,"Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,","or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config."].join(`
7
+ `)}export{g as AuthenticationError,c as ForbiddenError,m as NetworkError,u as NotFoundError,_ as PIN_CONFIG_HINTS,w as PindownClient,p as PindownError,f as RateLimitError,d as ServerError,P as ValidationError,L as formatPinConfigHint,h as getPinConfigHint};//# sourceMappingURL=index.js.map
8
8
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/client/pins/index.ts","../src/errors/index.ts","../src/client/PindownClient.ts","../src/pin-config-hints.ts"],"names":["PinsMethods","client","request","pinId","options","params","query","endpoint","pinIds","pins","updates","input","content","title","tags","description","pin_layout","is_public","allow_edit","require_sign_in","allow_comments","pending_invites","cards","columns","rows","pin_config","url","type","additionalMetadata","PindownError","message","AuthenticationError","ForbiddenError","NotFoundError","resource","ValidationError","details","RateLimitError","ServerError","statusCode","NetworkError","PindownClient","config","method","data","headers","requestOptions","response","error","errorData","TABLE_HINT","PIN_CONFIG_HINTS","getPinConfigHint","pinType","formatPinConfigHint","hint","f"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Pins API Methods\n */\n\nimport type { PindownClient } from '../PindownClient'\nimport type {\n Pin,\n PinTypeId,\n CreatePinRequest,\n UpdatePinRequest,\n SharePinRequest,\n ListPinsOptions,\n CreateMarkdownPinInput,\n CreateStatCardsPinInput,\n CreateTablePinInput,\n UpdateTablePinInput,\n CreateEmbedPinInput,\n TablePinConfig,\n} from '../../types/pins'\nimport type { PaginatedResponse } from '../../types/api'\n\nexport class PinsMethods {\n constructor(private client: PindownClient) {}\n\n /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */\n async create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('POST', '/pins', request)\n }\n\n async get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('GET', `/pins/${pinId}`)\n }\n\n async list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>> {\n const params = new URLSearchParams()\n if (options?.limit) params.append('limit', options.limit.toString())\n if (options?.offset) params.append('offset', options.offset.toString())\n\n const query = params.toString()\n const endpoint = query ? `/pins?${query}` : '/pins'\n\n return this.client.request<PaginatedResponse<Pin>>('GET', endpoint)\n }\n\n async update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('PUT', `/pins/${pinId}`, request)\n }\n\n async delete(pinId: string): Promise<void> {\n return this.client.request<void>('DELETE', `/pins/${pinId}`)\n }\n\n async share(pinId: string, request: SharePinRequest): Promise<Pin> {\n return this.client.request<Pin>('POST', `/pins/${pinId}/share`, request)\n }\n\n async batchGet(pinIds: string[]): Promise<{\n found: Pin[]\n not_found: string[]\n permission_denied: string[]\n }> {\n return this.client.request('POST', '/pins/batch/get', { pin_ids: pinIds })\n }\n\n async batchCreate(pins: CreatePinRequest[]): Promise<{\n created: Array<{ id: string; index: number; created_at: number }>\n failed: Array<{ index: number; error: string }>\n }> {\n return this.client.request('POST', '/pins/batch', { pins })\n }\n\n async batchUpdate(updates: Array<{ id: string } & UpdatePinRequest>): Promise<{\n updated: string[]\n failed: Array<{ id: string; error: string }>\n updated_at: number\n }> {\n return this.client.request('PATCH', '/pins/batch', { updates })\n }\n\n async batchDelete(pinIds: string[]): Promise<{\n deleted: string[]\n failed: Array<{ id: string; error: string }>\n }> {\n return this.client.request('DELETE', '/pins/batch', { pin_ids: pinIds })\n }\n\n /** Create a markdown pin with pin_config.content (seeds Yjs on the server). */\n async createMarkdown(input: CreateMarkdownPinInput): Promise<Pin<'markdown'>> {\n const { content, title, tags, description, pin_layout, is_public, allow_edit, require_sign_in, allow_comments, pending_invites } = input\n return this.create({\n pin_type: 'markdown',\n pin_config: { content },\n pin_layout,\n is_public,\n allow_edit,\n require_sign_in,\n allow_comments,\n pending_invites,\n metadata: { title, tags, description },\n })\n }\n\n async createStatCards(input: CreateStatCardsPinInput): Promise<Pin<'stat-cards'>> {\n const { cards, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'stat-cards',\n pin_config: { cards },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n async createTable(input: CreateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'table',\n pin_config: { columns, rows },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /** Partial table pin_config update with typed columns/rows. */\n async updateTable(pinId: string, input: UpdateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description } = input\n const pin_config: Partial<TablePinConfig> = {}\n if (columns !== undefined) pin_config.columns = columns\n if (rows !== undefined) pin_config.rows = rows\n\n return this.update<'table'>(pinId, {\n pin_config: pin_config as TablePinConfig,\n ...(title !== undefined || tags !== undefined || description !== undefined\n ? { metadata: { ...(title !== undefined && { title }), ...(tags !== undefined && { tags }), ...(description !== undefined && { description }) } }\n : {}),\n })\n }\n\n async createEmbed(input: CreateEmbedPinInput): Promise<Pin<'embed'>> {\n const { url, type, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'embed',\n pin_config: { url, type },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /**\n * @deprecated Use createMarkdown({ title, content, ... }) — old signature ignored content in title\n */\n async createMarkdownLegacy(title: string, additionalMetadata?: Record<string, unknown>): Promise<Pin<'markdown'>> {\n return this.createMarkdown({\n title,\n content: '',\n ...(additionalMetadata as Partial<CreateMarkdownPinInput>),\n })\n }\n}\n","/**\n * Error classes for the v1 Pins API client\n */\n\nexport class PindownError extends Error {\n constructor(message: string) {\n super(message)\n this.name = 'PindownError'\n }\n}\n\nexport class AuthenticationError extends PindownError {\n constructor(message: string = 'Authentication failed') {\n super(message)\n this.name = 'AuthenticationError'\n }\n}\n\nexport class ForbiddenError extends PindownError {\n constructor(message: string = 'Access forbidden') {\n super(message)\n this.name = 'ForbiddenError'\n }\n}\n\nexport class NotFoundError extends PindownError {\n constructor(resource: string) {\n super(`${resource} not found`)\n this.name = 'NotFoundError'\n }\n}\n\nexport class ValidationError extends PindownError {\n public details?: unknown\n\n constructor(message: string, details?: unknown) {\n super(message)\n this.name = 'ValidationError'\n this.details = details\n }\n}\n\nexport class RateLimitError extends PindownError {\n constructor(message: string = 'Rate limit exceeded (429 RATE_LIMITED)') {\n super(message)\n this.name = 'RateLimitError'\n }\n}\n\nexport class ServerError extends PindownError {\n public statusCode: number\n\n constructor(message: string, statusCode: number = 500) {\n super(message)\n this.name = 'ServerError'\n this.statusCode = statusCode\n }\n}\n\nexport class NetworkError extends PindownError {\n constructor(message: string = 'Network request failed') {\n super(message)\n this.name = 'NetworkError'\n }\n}\n","/**\n * Pindown API Client — v1 Pins API only\n */\n\nimport { PinsMethods } from './pins'\nimport type { PindownConfig } from '../types/config'\nimport {\n AuthenticationError,\n ForbiddenError,\n NotFoundError,\n ValidationError,\n RateLimitError,\n ServerError,\n NetworkError,\n} from '../errors'\n\nexport class PindownClient {\n private config: Required<Omit<PindownConfig, 'baseURL'>> & { baseURL: string }\n\n public readonly pins: PinsMethods\n\n constructor(config: PindownConfig) {\n if (!config.apiKey) {\n throw new Error('API key is required')\n }\n\n this.config = {\n apiKey: config.apiKey,\n baseURL: config.baseURL || 'https://api.pindown.ai/v1',\n maxRetries: config.maxRetries ?? 3,\n timeout: config.timeout ?? 30000,\n }\n\n this.pins = new PinsMethods(this)\n }\n\n async request<T = unknown>(method: string, endpoint: string, data?: unknown): Promise<T> {\n const url = `${this.config.baseURL}${endpoint}`\n const headers: Record<string, string> = {\n Authorization: `Bearer ${this.config.apiKey}`,\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n headers['Content-Type'] = 'application/json'\n }\n\n const requestOptions: RequestInit = {\n method,\n headers,\n signal: AbortSignal.timeout(this.config.timeout),\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n requestOptions.body = JSON.stringify(data)\n }\n\n try {\n const response = await fetch(url, requestOptions)\n\n if (!response.ok) {\n await this.handleErrorResponse(response)\n }\n\n const result = await response.json()\n return result.data as T\n } catch (error: unknown) {\n if (\n error instanceof AuthenticationError ||\n error instanceof ForbiddenError ||\n error instanceof NotFoundError ||\n error instanceof ValidationError ||\n error instanceof RateLimitError ||\n error instanceof ServerError\n ) {\n throw error\n }\n\n if (error instanceof Error && (error.name === 'AbortError' || error.name === 'TimeoutError')) {\n throw new NetworkError('Request timeout')\n }\n\n throw new NetworkError(error instanceof Error ? error.message : 'Network request failed')\n }\n }\n\n private async handleErrorResponse(response: Response): Promise<never> {\n let errorData: { error?: { code?: string; message?: string; details?: unknown }; message?: string }\n\n try {\n errorData = await response.json()\n } catch {\n errorData = { message: response.statusText }\n }\n\n const message = errorData.error?.message || errorData.message || 'Unknown error'\n\n switch (response.status) {\n case 401:\n throw new AuthenticationError(message)\n case 403:\n throw new ForbiddenError(message)\n case 404:\n throw new NotFoundError(message)\n case 400:\n case 422:\n throw new ValidationError(message, errorData.error?.details)\n case 429:\n throw new RateLimitError(message)\n case 500:\n case 502:\n case 503:\n throw new ServerError(message, response.status)\n default:\n throw new ServerError(message, response.status)\n }\n }\n}\n","/**\n * Runtime hints + minimal examples per pin type.\n * Use when building API payloads without opening the docs every time.\n */\n\nimport type { PinConfigByType, PinTypeId, UpdatePinRequest } from './types/pins'\n\nexport interface PinConfigFieldHint {\n path: string\n type: string\n required: boolean\n description: string\n}\n\nexport interface PinConfigHint<T extends PinTypeId = PinTypeId> {\n pin_type: T\n summary: string\n required_fields: string[]\n optional_fields: string[]\n fields: PinConfigFieldHint[]\n /** Minimal valid pin_config for create/update */\n example_config: PinConfigByType[T]\n /** Typical PUT /v1/pins/:id body (root-level pin_config) */\n example_update: UpdatePinRequest<T>\n}\n\nconst TABLE_HINT: PinConfigHint<'table'> = {\n pin_type: 'table',\n summary: 'Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.',\n required_fields: ['columns'],\n optional_fields: ['rows'],\n fields: [\n {\n path: 'columns',\n type: 'TableColumn[]',\n required: true,\n description: 'At least one column. Each column needs id + name (type optional, e.g. text | number).',\n },\n {\n path: 'columns[].id',\n type: 'string',\n required: true,\n description: 'Stable column key used in row.cells.',\n },\n {\n path: 'columns[].name',\n type: 'string',\n required: true,\n description: 'Column header label.',\n },\n {\n path: 'rows',\n type: 'TableRow[]',\n required: false,\n description: 'Table data. Each row: { id, cells: { [columnId]: value } }.',\n },\n ],\n example_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Item', col2: 1 } }],\n },\n example_update: {\n pin_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Updated', col2: 42 } }],\n },\n },\n}\n\n/** Per-type hints (expand over time; table is fully documented). */\nexport const PIN_CONFIG_HINTS: Partial<Record<PinTypeId, PinConfigHint>> = {\n table: TABLE_HINT,\n markdown: {\n pin_type: 'markdown',\n summary: 'Rich text / markdown body.',\n required_fields: [],\n optional_fields: ['content', 'collaboration'],\n fields: [\n {\n path: 'content',\n type: 'string',\n required: false,\n description: 'Markdown source. Server seeds Yjs when set on create.',\n },\n ],\n example_config: { content: '# Hello\\n\\nBody text.' },\n example_update: { pin_config: { content: '# Updated\\n\\nNew body.' } },\n },\n 'stat-cards': {\n pin_type: 'stat-cards',\n summary: 'KPI cards grid.',\n required_fields: ['cards'],\n optional_fields: [],\n fields: [\n {\n path: 'cards',\n type: 'StatCardItem[]',\n required: true,\n description: 'Each card: title, value; optional change, trend (up|down|neutral).',\n },\n ],\n example_config: {\n cards: [{ title: 'Revenue', value: '1000', change: '+5%', trend: 'up' }],\n },\n example_update: {\n pin_config: {\n cards: [{ title: 'Revenue', value: '1234', change: '+8%', trend: 'up' }],\n },\n },\n },\n}\n\nexport function getPinConfigHint<T extends PinTypeId>(pinType: T): PinConfigHint<T> | undefined {\n return PIN_CONFIG_HINTS[pinType] as PinConfigHint<T> | undefined\n}\n\n/** Pretty-print field hints for CLI / logging. */\nexport function formatPinConfigHint(pinType: PinTypeId): string {\n const hint = getPinConfigHint(pinType)\n if (!hint) {\n return [\n `No built-in hint for pin type \"${pinType}\".`,\n 'Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,',\n 'or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config.',\n ].join('\\n')\n }\n\n const lines = [\n `Pin type: ${hint.pin_type}`,\n hint.summary,\n '',\n 'Required pin_config fields:',\n ...hint.required_fields.map((f) => ` - ${f}`),\n '',\n 'Optional pin_config fields:',\n ...(hint.optional_fields.length ? hint.optional_fields.map((f) => ` - ${f}`) : [' (none documented)']),\n '',\n 'Field reference:',\n ...hint.fields.map(\n (f) => ` ${f.path} (${f.type}${f.required ? ', required' : ''}): ${f.description}`,\n ),\n '',\n 'Example update payload:',\n JSON.stringify(hint.example_update, null, 2),\n ]\n return lines.join('\\n')\n}\n"]}
1
+ {"version":3,"sources":["../src/types/pins.ts","../src/client/pins/pin-helper-core.ts","../src/client/pins/index.ts","../src/errors/index.ts","../src/client/PindownClient.ts","../src/pin-config-hints.ts"],"names":["PRODUCT_PIN_TYPES","PIN_CONFIG_FIELDS","pinTypeToMethodSuffix","pinType","part","pickPinConfig","input","fields","pin_config","key","toCreatePinRequest","metadata","toUpdatePinRequest","hasPinConfig","hasMetadata","attachNamedPinHelpers","ctor","suffix","pinId","PinsMethods","client","request","options","params","query","endpoint","pinIds","pins","updates","content","title","tags","description","pin_layout","is_public","allow_edit","require_sign_in","allow_comments","pending_invites","cards","columns","rows","url","type","additionalMetadata","PindownError","message","AuthenticationError","ForbiddenError","NotFoundError","resource","ValidationError","details","RateLimitError","ServerError","statusCode","NetworkError","PindownClient","config","method","data","headers","requestOptions","response","error","errorData","TABLE_HINT","PIN_CONFIG_HINTS","getPinConfigHint","formatPinConfigHint","hint","f"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Pin types for the v1 Pins API.\n * Aligned with backend-api/src/lib/pin-types.ts + pin-config-schemas.ts.\n * Import per-type *PinConfig interfaces for typed CRUD payloads.\n */\n\nexport const PRODUCT_PIN_TYPES = [\n 'markdown',\n 'image',\n 'gallery',\n 'table',\n 'charts',\n 'mermaid',\n 'code',\n 'embed',\n 'pdf-viewer',\n 'excel-viewer',\n 'stat-cards',\n 'timeline',\n 'json-viewer',\n 'json-list',\n 'links',\n 'qr-code',\n 'social-handles',\n 'steps',\n 'trace',\n 'plan',\n 'notes',\n 'csv-viewer',\n 'user-story',\n 'chat',\n 'intro',\n 'mastra',\n 'text-media',\n 'business-card',\n 'video',\n 'audio',\n 'file-upload',\n 'kanban-board',\n 'checklist',\n 'comparison',\n 'calendar',\n 'roadmap',\n 'realtime-canvas',\n] as const\n\nexport const ALL_PIN_TYPES = [...PRODUCT_PIN_TYPES] as const\n\nexport type ProductPinTypeId = (typeof PRODUCT_PIN_TYPES)[number]\nexport type PinTypeId = (typeof ALL_PIN_TYPES)[number]\n\nexport type PinLayout = '1x1' | '1x2' | '2x1' | '2x2' | '3x1' | '3x2' | '3x3' | '4x4'\n\nexport type PinDataType = 'markdown' | 'json' | 'text' | 'pin-card'\n\n/** @deprecated Use PinTypeId */\nexport type PinCardType = PinTypeId\n\nexport interface StatCardItem {\n title: string\n value: string | number\n change?: string\n trend?: 'up' | 'down' | 'neutral' | string\n icon?: string\n [key: string]: unknown\n}\n\nexport interface TableColumn {\n id: string\n name: string\n type?: string\n [key: string]: unknown\n}\n\nexport interface TableRow {\n id: string\n cells: Record<string, unknown>\n [key: string]: unknown\n}\n\nexport interface KanbanColumn {\n id: string\n title: string\n cards?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface ChecklistItem {\n id: string\n name: string\n checked?: boolean\n [key: string]: unknown\n}\n\nexport interface GalleryImage {\n url: string\n alt?: string\n [key: string]: unknown\n}\n\nexport interface LinkItem {\n title: string\n url: string\n [key: string]: unknown\n}\n\nexport interface StepItem {\n title: string\n description?: string\n [key: string]: unknown\n}\n\nexport interface MarkdownPinConfig {\n content?: string\n collaboration?: { enabled?: boolean }\n [key: string]: unknown\n}\n\nexport interface ImagePinConfig {\n url?: string\n altText?: string\n fit?: 'cover' | 'contain' | string\n [key: string]: unknown\n}\n\nexport interface GalleryPinConfig {\n images?: GalleryImage[]\n [key: string]: unknown\n}\n\nexport interface TablePinConfig {\n columns: TableColumn[]\n rows?: TableRow[]\n [key: string]: unknown\n}\n\nexport interface ChartsPinConfig {\n chartType?: string\n data?: Array<Record<string, unknown>>\n xAxis?: string\n yAxis?: string\n [key: string]: unknown\n}\n\nexport interface MermaidPinConfig {\n diagram?: string\n code?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface CodePinConfig {\n code: string\n language?: string\n filename?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface EmbedPinConfig {\n url?: string\n type?: string\n [key: string]: unknown\n}\n\nexport interface PdfViewerPinConfig {\n pdf: { url: string; fileName?: string; title?: string; [key: string]: unknown }\n [key: string]: unknown\n}\n\nexport interface ExcelViewerPinConfig {\n excel: { url: string; fileName?: string; title?: string; [key: string]: unknown }\n [key: string]: unknown\n}\n\nexport interface StatCardsPinConfig {\n cards: StatCardItem[]\n [key: string]: unknown\n}\n\nexport interface TimelinePinConfig {\n mode?: string\n items?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface JsonViewerPinConfig {\n json?: unknown\n jsonString?: string\n title?: string\n [key: string]: unknown\n}\n\nexport interface JsonListPinConfig {\n json?: unknown[]\n jsonString?: string\n [key: string]: unknown\n}\n\nexport interface LinksPinConfig {\n links?: LinkItem[]\n [key: string]: unknown\n}\n\nexport interface QrCodePinConfig {\n url?: string\n label?: string\n [key: string]: unknown\n}\n\nexport interface SocialHandleItem {\n id?: string\n platform: string\n url: string\n label?: string\n [key: string]: unknown\n}\n\nexport interface SocialHandlesPinConfig {\n title?: string\n showLabels?: boolean\n iconSize?: number\n handles?: SocialHandleItem[]\n [key: string]: unknown\n}\n\nexport interface StepsPinConfig {\n steps: StepItem[]\n [key: string]: unknown\n}\n\nexport type TraceSpanStatus = 'completed' | 'running' | 'pending' | 'failed'\nexport type TraceSpanType = 'system' | 'agent' | 'tool'\n\nexport interface TraceSpanItem {\n id?: string\n type?: TraceSpanType\n name: string\n status: TraceSpanStatus\n timestamp?: string\n duration?: string\n details?: string\n}\n\nexport interface TracePinConfig {\n title?: string\n live?: boolean\n spans: TraceSpanItem[]\n [key: string]: unknown\n}\n\nexport type PlanContentBlock =\n | { type: 'details'; title?: string; items: string[] }\n | { type: 'command'; command: string; label?: string }\n | { type: 'code'; code: string; language?: string; filename?: string }\n | { type: 'text'; content: string }\n | { type: 'link'; url: string; label?: string }\n | { type: 'mermaid'; diagram: string; title?: string }\n | { type: 'summary'; content: string; title?: string }\n\nexport interface PlanTaskItem {\n id?: string\n number?: string\n title: string\n label?: string\n description?: string\n blocks?: PlanContentBlock[]\n [key: string]: unknown\n}\n\nexport interface PlanPhaseItem {\n id?: string\n title: string\n status?: 'pending' | 'in-progress' | 'completed'\n tasks: PlanTaskItem[]\n [key: string]: unknown\n}\n\nexport interface PlanPinConfig {\n title?: string\n status?: 'draft' | 'in-progress' | 'completed'\n breadcrumbs?: Array<{ label: string }>\n phases: PlanPhaseItem[]\n [key: string]: unknown\n}\n\nexport interface NoteItem {\n id?: string\n title: string\n content?: string\n order?: number\n createdAt?: number\n updatedAt?: number\n}\n\nexport interface NotesPinConfig {\n notes?: NoteItem[]\n [key: string]: unknown\n}\n\nexport interface CsvViewerPinConfig {\n csvText?: string\n csvData?: Array<Record<string, unknown>>\n fileName?: string\n [key: string]: unknown\n}\n\nexport interface UserStoryPinConfig {\n title?: string\n userStory: string\n acceptanceCriteria?: string\n [key: string]: unknown\n}\n\nexport interface ChatPinConfig {\n title?: string\n placeholder?: string\n /** Pin this discussion thread is about (commentary / feedback). */\n linked_pin_id?: string\n /** Cached title for display without fetching the linked pin. */\n linked_pin_title?: string\n [key: string]: unknown\n}\n\nexport interface IntroPinConfig {\n heading: string\n subheading?: string\n [key: string]: unknown\n}\n\nexport interface MastraPinConfig {\n mode?: 'workflow' | 'agent' | string\n agentId?: string\n workflowId?: string\n [key: string]: unknown\n}\n\nexport interface BusinessCardField {\n id: string\n key: string\n value: string\n}\n\nexport interface BusinessCardPinConfig {\n sectionTitle?: string\n fields?: BusinessCardField[]\n imageConfig?: { url?: string; alt?: string; fileId?: string; [key: string]: unknown }\n imagePosition?: 'left' | 'right' | string\n [key: string]: unknown\n}\n\nexport interface VideoPinConfig {\n url?: string\n fileId?: string\n fileName?: string\n mimeType?: 'video/mp4' | string\n caption?: string\n size?: number\n [key: string]: unknown\n}\n\nexport interface AudioPinTrack {\n url: string\n fileId?: string\n fileName?: string\n mimeType?: 'audio/mpeg' | 'audio/wav' | 'audio/x-wav' | string\n size?: number\n [key: string]: unknown\n}\n\nexport interface AudioPinConfig {\n url?: string\n fileId?: string\n fileName?: string\n mimeType?: 'audio/mpeg' | 'audio/wav' | 'audio/x-wav' | string\n caption?: string\n size?: number\n tracks?: AudioPinTrack[]\n [key: string]: unknown\n}\n\nexport interface TextMediaPinConfig {\n title?: string\n text?: string\n subtext?: string\n textPosition?: 'left' | 'right' | string\n mediaType?: 'embed' | 'image' | string\n embedConfig?: {\n type?: string\n url?: string\n aspectRatio?: string\n autoplay?: boolean\n [key: string]: unknown\n }\n imageConfig?: {\n url?: string\n alt?: string\n fileId?: string\n [key: string]: unknown\n }\n [key: string]: unknown\n}\n\nexport interface FileUploadPinConfig {\n files?: Array<Record<string, unknown>>\n displayMode?: string\n [key: string]: unknown\n}\n\nexport interface KanbanBoardPinConfig {\n columns: KanbanColumn[]\n [key: string]: unknown\n}\n\nexport interface ChecklistPinConfig {\n title?: string\n items: ChecklistItem[]\n [key: string]: unknown\n}\n\nexport interface ComparisonSideConfig {\n label: string\n body: string\n}\n\nexport interface ComparisonMatchPair {\n left: number\n right: number\n}\n\nexport interface ComparisonPinConfig {\n title?: string\n left: ComparisonSideConfig\n right: ComparisonSideConfig\n highlightedLines?: { left?: number[]; right?: number[] }\n matches?: ComparisonMatchPair[]\n showVsBadge?: boolean\n [key: string]: unknown\n}\n\nexport interface CalendarPinConfig {\n weekStartsOn?: number\n events?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface RoadmapPinConfig {\n title?: string\n months?: Array<Record<string, unknown>>\n [key: string]: unknown\n}\n\nexport interface RealtimeCanvasPinConfig {\n title?: string\n description?: string\n roomId?: string\n [key: string]: unknown\n}\n\nexport interface PinConfigByType {\n markdown: MarkdownPinConfig\n image: ImagePinConfig\n gallery: GalleryPinConfig\n table: TablePinConfig\n charts: ChartsPinConfig\n mermaid: MermaidPinConfig\n code: CodePinConfig\n embed: EmbedPinConfig\n 'pdf-viewer': PdfViewerPinConfig\n 'excel-viewer': ExcelViewerPinConfig\n 'stat-cards': StatCardsPinConfig\n timeline: TimelinePinConfig\n 'json-viewer': JsonViewerPinConfig\n 'json-list': JsonListPinConfig\n links: LinksPinConfig\n 'qr-code': QrCodePinConfig\n 'social-handles': SocialHandlesPinConfig\n steps: StepsPinConfig\n trace: TracePinConfig\n plan: PlanPinConfig\n notes: NotesPinConfig\n 'csv-viewer': CsvViewerPinConfig\n 'user-story': UserStoryPinConfig\n chat: ChatPinConfig\n intro: IntroPinConfig\n mastra: MastraPinConfig\n 'text-media': TextMediaPinConfig\n 'business-card': BusinessCardPinConfig\n video: VideoPinConfig\n audio: AudioPinConfig\n 'file-upload': FileUploadPinConfig\n 'kanban-board': KanbanBoardPinConfig\n checklist: ChecklistPinConfig\n comparison: ComparisonPinConfig\n calendar: CalendarPinConfig\n roadmap: RoadmapPinConfig\n 'realtime-canvas': RealtimeCanvasPinConfig\n}\n\nexport interface PinMetadataBase {\n title: string\n tags?: string[]\n description?: string\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n}\n\nexport type PinMetadata<T extends PinTypeId = PinTypeId> = PinMetadataBase & {\n pin_type?: T\n pin_config?: PinConfigByType[T]\n pin_layout?: PinLayout\n}\n\nexport interface CreateTypedPinRequest<T extends PinTypeId> {\n pin_type: T\n pin_config: PinConfigByType[T]\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n metadata: PinMetadataBase\n pending_invites?: Record<string, 'editor' | 'viewer'>\n /** @deprecated Inferred from pin_type */\n data_type?: PinDataType\n}\n\nexport interface CreateNestedPinRequest<T extends PinTypeId> {\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n metadata: PinMetadata<T> & PinMetadataBase\n pending_invites?: Record<string, 'editor' | 'viewer'>\n data_type?: PinDataType\n}\n\nexport type CreatePinRequest<T extends PinTypeId = PinTypeId> =\n | CreateTypedPinRequest<T>\n | CreateNestedPinRequest<T>\n\nexport interface UpdatePinRequest<T extends PinTypeId = PinTypeId> {\n pin_type?: T\n pin_config?: PinConfigByType[T]\n pin_layout?: PinLayout\n is_public?: boolean\n metadata?: Partial<PinMetadata<T>>\n}\n\nexport interface Pin<T extends PinTypeId = PinTypeId> {\n id: string\n owner_id: string\n user_id?: string\n title?: string\n description?: string\n data_type: PinDataType\n is_public: boolean\n allow_edit: boolean\n require_sign_in: boolean\n allow_comments: boolean\n metadata?: PinMetadata<T>\n created_at: string | number\n updated_at: string | number\n}\n\nexport interface SharePinRequest {\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n}\n\nexport interface ListPinsOptions {\n limit?: number\n offset?: number\n}\n\nexport interface CreatePinOptions {\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n pending_invites?: Record<string, 'editor' | 'viewer'>\n}\n\n/** Flat create input: metadata + pin_config fields (all pin types). */\nexport type CreatePinHelperInput<T extends PinTypeId> = PinMetadataBase &\n CreatePinOptions &\n PinConfigByType[T]\n\n/** Flat update input: optional metadata + partial pin_config fields. */\nexport type UpdatePinHelperInput<T extends PinTypeId> = {\n pin_layout?: PinLayout\n is_public?: boolean\n title?: string\n tags?: string[]\n description?: string\n metadata?: Partial<PinMetadataBase>\n} & Partial<PinConfigByType[T]>\n\nexport interface CreateMarkdownPinInput extends PinMetadataBase {\n content: string\n pin_layout?: PinLayout\n is_public?: boolean\n allow_edit?: boolean\n require_sign_in?: boolean\n allow_comments?: boolean\n pending_invites?: Record<string, 'editor' | 'viewer'>\n}\n\nexport interface CreateStatCardsPinInput extends PinMetadataBase {\n cards: StatCardItem[]\n pin_layout?: PinLayout\n is_public?: boolean\n}\n\nexport interface CreateTablePinInput extends PinMetadataBase {\n columns: TableColumn[]\n rows?: TableRow[]\n pin_layout?: PinLayout\n is_public?: boolean\n}\n\nexport interface UpdateTablePinInput extends UpdatePinHelperInput<'table'> {}\n\nexport interface CreateEmbedPinInput extends PinMetadataBase {\n url: string\n type?: string\n pin_layout?: PinLayout\n is_public?: boolean\n}\n","import {\n PRODUCT_PIN_TYPES,\n type CreatePinHelperInput,\n type CreateTypedPinRequest,\n type PinConfigByType,\n type PinMetadataBase,\n type PinTypeId,\n type UpdatePinHelperInput,\n type UpdatePinRequest,\n} from '../../types/pins'\n\n/** Known pin_config keys per type (top-level only). */\nexport const PIN_CONFIG_FIELDS: { readonly [K in PinTypeId]: readonly (keyof PinConfigByType[K] & string)[] } = {\n markdown: ['content', 'collaboration'],\n image: ['url', 'altText', 'fit'],\n gallery: ['images'],\n table: ['columns', 'rows'],\n charts: ['chartType', 'data', 'xAxis', 'yAxis'],\n mermaid: ['diagram', 'code', 'title'],\n code: ['code', 'language', 'filename', 'title'],\n embed: ['url', 'type'],\n 'pdf-viewer': ['pdf'],\n 'excel-viewer': ['excel'],\n 'stat-cards': ['cards'],\n timeline: ['mode', 'items'],\n 'json-viewer': ['json', 'jsonString', 'title'],\n 'json-list': ['json', 'jsonString'],\n links: ['links'],\n 'qr-code': ['url', 'label'],\n 'social-handles': ['title', 'showLabels', 'iconSize', 'handles'],\n steps: ['steps'],\n trace: ['title', 'live', 'spans'],\n plan: ['title', 'status', 'breadcrumbs', 'phases'],\n notes: ['notes'],\n 'csv-viewer': ['csvText', 'csvData', 'fileName'],\n 'user-story': ['title', 'userStory', 'acceptanceCriteria'],\n chat: ['title', 'placeholder', 'linked_pin_id', 'linked_pin_title'],\n intro: ['heading', 'subheading'],\n mastra: ['mode', 'agentId', 'workflowId'],\n 'text-media': ['title', 'text', 'subtext', 'textPosition', 'mediaType', 'embedConfig', 'imageConfig'],\n 'business-card': ['sectionTitle', 'fields', 'imageConfig', 'imagePosition'],\n video: ['url', 'fileId', 'fileName', 'mimeType', 'caption', 'size'],\n audio: ['url', 'fileId', 'fileName', 'mimeType', 'caption', 'size', 'tracks'],\n 'file-upload': ['files', 'displayMode'],\n 'kanban-board': ['columns'],\n checklist: ['title', 'items'],\n comparison: ['title', 'left', 'right', 'highlightedLines', 'matches', 'showVsBadge'],\n calendar: ['weekStartsOn', 'events'],\n roadmap: ['title', 'months'],\n 'realtime-canvas': ['title', 'description', 'roomId'],\n}\n\nexport function pinTypeToMethodSuffix(pinType: PinTypeId): string {\n return pinType\n .split('-')\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join('')\n}\n\nfunction pickPinConfig<T extends PinTypeId>(\n pinType: T,\n input: Record<string, unknown>,\n): PinConfigByType[T] {\n const fields = PIN_CONFIG_FIELDS[pinType]\n const pin_config = {} as PinConfigByType[T]\n for (const key of fields) {\n if (key in input && input[key] !== undefined) {\n ;(pin_config as Record<string, unknown>)[key] = input[key]\n }\n }\n return pin_config\n}\n\nexport function toCreatePinRequest<T extends PinTypeId>(\n pinType: T,\n input: CreatePinHelperInput<T>,\n): CreateTypedPinRequest<T> {\n const raw = input as Record<string, unknown>\n const pin_config = pickPinConfig(pinType, raw)\n\n const metadata: PinMetadataBase = {\n title: input.title,\n tags: input.tags,\n description: input.description,\n allow_edit: input.allow_edit,\n require_sign_in: input.require_sign_in,\n allow_comments: input.allow_comments,\n }\n\n return {\n pin_type: pinType,\n pin_config,\n pin_layout: input.pin_layout,\n is_public: input.is_public,\n allow_edit: input.allow_edit,\n require_sign_in: input.require_sign_in,\n allow_comments: input.allow_comments,\n pending_invites: input.pending_invites,\n metadata,\n }\n}\n\nexport function toUpdatePinRequest<T extends PinTypeId>(\n pinType: T,\n input: UpdatePinHelperInput<T>,\n): UpdatePinRequest<T> {\n const raw = input as Record<string, unknown>\n const pin_config = pickPinConfig(pinType, raw) as PinConfigByType[T]\n const hasPinConfig = Object.keys(pin_config as object).length > 0\n\n const metadata: Partial<PinMetadataBase> = {\n ...(input.metadata ?? {}),\n }\n if (input.title !== undefined) metadata.title = input.title\n if (input.tags !== undefined) metadata.tags = input.tags\n if (input.description !== undefined) metadata.description = input.description\n\n const hasMetadata = Object.keys(metadata).length > 0\n\n return {\n ...(hasPinConfig ? { pin_config } : {}),\n pin_layout: input.pin_layout,\n is_public: input.is_public,\n ...(hasMetadata ? { metadata } : {}),\n }\n}\n\nexport function attachNamedPinHelpers(ctor: { prototype: Record<string, unknown> }) {\n for (const pinType of PRODUCT_PIN_TYPES as readonly PinTypeId[]) {\n const suffix = pinTypeToMethodSuffix(pinType)\n ctor.prototype[`create${suffix}`] = function (\n this: { createPin: (t: PinTypeId, i: unknown) => unknown },\n input: unknown,\n ) {\n return this.createPin(pinType, input)\n }\n ctor.prototype[`update${suffix}`] = function (\n this: { updatePin: (id: string, t: PinTypeId, i: unknown) => unknown },\n pinId: string,\n input: unknown,\n ) {\n return this.updatePin(pinId, pinType, input)\n }\n }\n}\n","/**\n * Pins API Methods\n */\n\nimport type { PindownClient } from '../PindownClient'\nimport type {\n Pin,\n PinTypeId,\n CreatePinRequest,\n CreatePinHelperInput,\n UpdatePinRequest,\n UpdatePinHelperInput,\n SharePinRequest,\n ListPinsOptions,\n CreateMarkdownPinInput,\n CreateStatCardsPinInput,\n CreateTablePinInput,\n UpdateTablePinInput,\n CreateEmbedPinInput,\n} from '../../types/pins'\nimport type { PaginatedResponse } from '../../types/api'\nimport {\n attachNamedPinHelpers,\n toCreatePinRequest,\n toUpdatePinRequest,\n} from './pin-helper-core'\n\nexport class PinsMethods {\n constructor(private client: PindownClient) {}\n\n /** Create a pin (typed via CreatePinRequest&lt;T&gt;) */\n async create<T extends PinTypeId>(request: CreatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('POST', '/pins', request)\n }\n\n /** Create helper for any pin type via flat typed input. */\n async createPin<T extends PinTypeId>(\n pinType: T,\n input: CreatePinHelperInput<T>,\n ): Promise<Pin<T>> {\n return this.create(toCreatePinRequest(pinType, input))\n }\n\n async get<T extends PinTypeId = PinTypeId>(pinId: string): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('GET', `/pins/${pinId}`)\n }\n\n async list(options?: ListPinsOptions): Promise<PaginatedResponse<Pin>> {\n const params = new URLSearchParams()\n if (options?.limit) params.append('limit', options.limit.toString())\n if (options?.offset) params.append('offset', options.offset.toString())\n\n const query = params.toString()\n const endpoint = query ? `/pins?${query}` : '/pins'\n\n return this.client.request<PaginatedResponse<Pin>>('GET', endpoint)\n }\n\n async update<T extends PinTypeId = PinTypeId>(pinId: string, request: UpdatePinRequest<T>): Promise<Pin<T>> {\n return this.client.request<Pin<T>>('PUT', `/pins/${pinId}`, request)\n }\n\n /** Update helper for any pin type via flat typed input. */\n async updatePin<T extends PinTypeId>(\n pinId: string,\n pinType: T,\n input: UpdatePinHelperInput<T>,\n ): Promise<Pin<T>> {\n return this.update(pinId, toUpdatePinRequest(pinType, input))\n }\n\n async delete(pinId: string): Promise<void> {\n return this.client.request<void>('DELETE', `/pins/${pinId}`)\n }\n\n async share(pinId: string, request: SharePinRequest): Promise<Pin> {\n return this.client.request<Pin>('POST', `/pins/${pinId}/share`, request)\n }\n\n async batchGet(pinIds: string[]): Promise<{\n found: Pin[]\n not_found: string[]\n permission_denied: string[]\n }> {\n return this.client.request('POST', '/pins/batch/get', { pin_ids: pinIds })\n }\n\n async batchCreate(pins: CreatePinRequest[]): Promise<{\n created: Array<{ id: string; index: number; created_at: number }>\n failed: Array<{ index: number; error: string }>\n }> {\n return this.client.request('POST', '/pins/batch', { pins })\n }\n\n async batchUpdate(updates: Array<{ id: string } & UpdatePinRequest>): Promise<{\n updated: string[]\n failed: Array<{ id: string; error: string }>\n updated_at: number\n }> {\n return this.client.request('PATCH', '/pins/batch', { updates })\n }\n\n async batchDelete(pinIds: string[]): Promise<{\n deleted: string[]\n failed: Array<{ id: string; error: string }>\n }> {\n return this.client.request('DELETE', '/pins/batch', { pin_ids: pinIds })\n }\n\n /** Create a markdown pin with pin_config.content (seeds Yjs on the server). */\n async createMarkdown(input: CreateMarkdownPinInput): Promise<Pin<'markdown'>> {\n const { content, title, tags, description, pin_layout, is_public, allow_edit, require_sign_in, allow_comments, pending_invites } = input\n return this.create({\n pin_type: 'markdown',\n pin_config: { content },\n pin_layout,\n is_public,\n allow_edit,\n require_sign_in,\n allow_comments,\n pending_invites,\n metadata: { title, tags, description },\n })\n }\n\n async createStatCards(input: CreateStatCardsPinInput): Promise<Pin<'stat-cards'>> {\n const { cards, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'stat-cards',\n pin_config: { cards },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n async createTable(input: CreateTablePinInput): Promise<Pin<'table'>> {\n const { columns, rows, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'table',\n pin_config: { columns, rows },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /** Partial table pin_config update with typed columns/rows. */\n async updateTable(pinId: string, input: UpdateTablePinInput): Promise<Pin<'table'>> {\n return this.updatePin(pinId, 'table', input)\n }\n\n async createEmbed(input: CreateEmbedPinInput): Promise<Pin<'embed'>> {\n const { url, type, title, tags, description, pin_layout, is_public } = input\n return this.create({\n pin_type: 'embed',\n pin_config: { url, type },\n pin_layout,\n is_public,\n metadata: { title, tags, description },\n })\n }\n\n /**\n * @deprecated Use createMarkdown({ title, content, ... }) — old signature ignored content in title\n */\n async createMarkdownLegacy(title: string, additionalMetadata?: Record<string, unknown>): Promise<Pin<'markdown'>> {\n return this.createMarkdown({\n title,\n content: '',\n ...(additionalMetadata as Partial<CreateMarkdownPinInput>),\n })\n }\n}\n\nattachNamedPinHelpers(PinsMethods as unknown as { prototype: Record<string, unknown> })\n","/**\n * Error classes for the v1 Pins API client\n */\n\nexport class PindownError extends Error {\n constructor(message: string) {\n super(message)\n this.name = 'PindownError'\n }\n}\n\nexport class AuthenticationError extends PindownError {\n constructor(message: string = 'Authentication failed') {\n super(message)\n this.name = 'AuthenticationError'\n }\n}\n\nexport class ForbiddenError extends PindownError {\n constructor(message: string = 'Access forbidden') {\n super(message)\n this.name = 'ForbiddenError'\n }\n}\n\nexport class NotFoundError extends PindownError {\n constructor(resource: string) {\n super(`${resource} not found`)\n this.name = 'NotFoundError'\n }\n}\n\nexport class ValidationError extends PindownError {\n public details?: unknown\n\n constructor(message: string, details?: unknown) {\n super(message)\n this.name = 'ValidationError'\n this.details = details\n }\n}\n\nexport class RateLimitError extends PindownError {\n constructor(message: string = 'Rate limit exceeded (429 RATE_LIMITED)') {\n super(message)\n this.name = 'RateLimitError'\n }\n}\n\nexport class ServerError extends PindownError {\n public statusCode: number\n\n constructor(message: string, statusCode: number = 500) {\n super(message)\n this.name = 'ServerError'\n this.statusCode = statusCode\n }\n}\n\nexport class NetworkError extends PindownError {\n constructor(message: string = 'Network request failed') {\n super(message)\n this.name = 'NetworkError'\n }\n}\n","/**\n * Pindown API Client — v1 Pins API only\n */\n\nimport { PinsMethods } from './pins'\nimport type { PindownConfig } from '../types/config'\nimport {\n AuthenticationError,\n ForbiddenError,\n NotFoundError,\n ValidationError,\n RateLimitError,\n ServerError,\n NetworkError,\n} from '../errors'\n\nexport class PindownClient {\n private config: Required<Omit<PindownConfig, 'baseURL'>> & { baseURL: string }\n\n public readonly pins: PinsMethods\n\n constructor(config: PindownConfig) {\n if (!config.apiKey) {\n throw new Error('API key is required')\n }\n\n this.config = {\n apiKey: config.apiKey,\n baseURL: config.baseURL || 'https://api.pindown.ai/v1',\n maxRetries: config.maxRetries ?? 3,\n timeout: config.timeout ?? 30000,\n }\n\n this.pins = new PinsMethods(this)\n }\n\n async request<T = unknown>(method: string, endpoint: string, data?: unknown): Promise<T> {\n const url = `${this.config.baseURL}${endpoint}`\n const headers: Record<string, string> = {\n Authorization: `Bearer ${this.config.apiKey}`,\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n headers['Content-Type'] = 'application/json'\n }\n\n const requestOptions: RequestInit = {\n method,\n headers,\n signal: AbortSignal.timeout(this.config.timeout),\n }\n\n if (data && (method === 'POST' || method === 'PUT' || method === 'PATCH' || method === 'DELETE')) {\n requestOptions.body = JSON.stringify(data)\n }\n\n try {\n const response = await fetch(url, requestOptions)\n\n if (!response.ok) {\n await this.handleErrorResponse(response)\n }\n\n const result = await response.json()\n return result.data as T\n } catch (error: unknown) {\n if (\n error instanceof AuthenticationError ||\n error instanceof ForbiddenError ||\n error instanceof NotFoundError ||\n error instanceof ValidationError ||\n error instanceof RateLimitError ||\n error instanceof ServerError\n ) {\n throw error\n }\n\n if (error instanceof Error && (error.name === 'AbortError' || error.name === 'TimeoutError')) {\n throw new NetworkError('Request timeout')\n }\n\n throw new NetworkError(error instanceof Error ? error.message : 'Network request failed')\n }\n }\n\n private async handleErrorResponse(response: Response): Promise<never> {\n let errorData: { error?: { code?: string; message?: string; details?: unknown }; message?: string }\n\n try {\n errorData = await response.json()\n } catch {\n errorData = { message: response.statusText }\n }\n\n const message = errorData.error?.message || errorData.message || 'Unknown error'\n\n switch (response.status) {\n case 401:\n throw new AuthenticationError(message)\n case 403:\n throw new ForbiddenError(message)\n case 404:\n throw new NotFoundError(message)\n case 400:\n case 422:\n throw new ValidationError(message, errorData.error?.details)\n case 429:\n throw new RateLimitError(message)\n case 500:\n case 502:\n case 503:\n throw new ServerError(message, response.status)\n default:\n throw new ServerError(message, response.status)\n }\n }\n}\n","/**\n * Runtime hints + minimal examples per pin type.\n * Use when building API payloads without opening the docs every time.\n */\n\nimport type { PinConfigByType, PinTypeId, UpdatePinRequest } from './types/pins'\n\nexport interface PinConfigFieldHint {\n path: string\n type: string\n required: boolean\n description: string\n}\n\nexport interface PinConfigHint<T extends PinTypeId = PinTypeId> {\n pin_type: T\n summary: string\n required_fields: string[]\n optional_fields: string[]\n fields: PinConfigFieldHint[]\n /** Minimal valid pin_config for create/update */\n example_config: PinConfigByType[T]\n /** Typical PUT /v1/pins/:id body (root-level pin_config) */\n example_update: UpdatePinRequest<T>\n}\n\nconst TABLE_HINT: PinConfigHint<'table'> = {\n pin_type: 'table',\n summary: 'Spreadsheet-style pin. columns is required; rows are optional but needed for visible data.',\n required_fields: ['columns'],\n optional_fields: ['rows'],\n fields: [\n {\n path: 'columns',\n type: 'TableColumn[]',\n required: true,\n description: 'At least one column. Each column needs id + name (type optional, e.g. text | number).',\n },\n {\n path: 'columns[].id',\n type: 'string',\n required: true,\n description: 'Stable column key used in row.cells.',\n },\n {\n path: 'columns[].name',\n type: 'string',\n required: true,\n description: 'Column header label.',\n },\n {\n path: 'rows',\n type: 'TableRow[]',\n required: false,\n description: 'Table data. Each row: { id, cells: { [columnId]: value } }.',\n },\n ],\n example_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Item', col2: 1 } }],\n },\n example_update: {\n pin_config: {\n columns: [\n { id: 'col1', name: 'Name', type: 'text' },\n { id: 'col2', name: 'Value', type: 'number' },\n ],\n rows: [{ id: 'row1', cells: { col1: 'Updated', col2: 42 } }],\n },\n },\n}\n\n/** Per-type hints (expand over time; table is fully documented). */\nexport const PIN_CONFIG_HINTS: Partial<Record<PinTypeId, PinConfigHint>> = {\n table: TABLE_HINT,\n markdown: {\n pin_type: 'markdown',\n summary: 'Rich text / markdown body.',\n required_fields: [],\n optional_fields: ['content', 'collaboration'],\n fields: [\n {\n path: 'content',\n type: 'string',\n required: false,\n description: 'Markdown source. Server seeds Yjs when set on create.',\n },\n ],\n example_config: { content: '# Hello\\n\\nBody text.' },\n example_update: { pin_config: { content: '# Updated\\n\\nNew body.' } },\n },\n 'stat-cards': {\n pin_type: 'stat-cards',\n summary: 'KPI cards grid.',\n required_fields: ['cards'],\n optional_fields: [],\n fields: [\n {\n path: 'cards',\n type: 'StatCardItem[]',\n required: true,\n description: 'Each card: title, value; optional change, trend (up|down|neutral).',\n },\n ],\n example_config: {\n cards: [{ title: 'Revenue', value: '1000', change: '+5%', trend: 'up' }],\n },\n example_update: {\n pin_config: {\n cards: [{ title: 'Revenue', value: '1234', change: '+8%', trend: 'up' }],\n },\n },\n },\n}\n\nexport function getPinConfigHint<T extends PinTypeId>(pinType: T): PinConfigHint<T> | undefined {\n return PIN_CONFIG_HINTS[pinType] as PinConfigHint<T> | undefined\n}\n\n/** Pretty-print field hints for CLI / logging. */\nexport function formatPinConfigHint(pinType: PinTypeId): string {\n const hint = getPinConfigHint(pinType)\n if (!hint) {\n return [\n `No built-in hint for pin type \"${pinType}\".`,\n 'Use CreatePinRequest<typeof pinType> / PinConfigByType[typeof pinType] in TypeScript,',\n 'or client.pins.create({ pin_type, pin_config, metadata }) with typed pin_config.',\n ].join('\\n')\n }\n\n const lines = [\n `Pin type: ${hint.pin_type}`,\n hint.summary,\n '',\n 'Required pin_config fields:',\n ...hint.required_fields.map((f) => ` - ${f}`),\n '',\n 'Optional pin_config fields:',\n ...(hint.optional_fields.length ? hint.optional_fields.map((f) => ` - ${f}`) : [' (none documented)']),\n '',\n 'Field reference:',\n ...hint.fields.map(\n (f) => ` ${f.path} (${f.type}${f.required ? ', required' : ''}): ${f.description}`,\n ),\n '',\n 'Example update payload:',\n JSON.stringify(hint.example_update, null, 2),\n ]\n return lines.join('\\n')\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pindownai/client-js",
3
- "version": "1.3.2",
3
+ "version": "1.3.3",
4
4
  "description": "Official TypeScript/JavaScript client for the Pindown v1 Pins API",
5
5
  "main": "./dist/index.cjs",
6
6
  "module": "./dist/index.js",