@notionhq/notion-mcp-server 1.6.0 → 1.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -10
- package/bin/cli.mjs +1 -1
- package/package.json +1 -1
- package/scripts/notion-openapi.json +182 -53
package/README.md
CHANGED
|
@@ -19,7 +19,14 @@ For example, you can create a read-only integration token by giving only "Read c
|
|
|
19
19
|
|
|
20
20
|

|
|
21
21
|
|
|
22
|
-
#### 2.
|
|
22
|
+
#### 2. Connecting content to integration:
|
|
23
|
+
Ensure relevant pages and databases are connected to your integration.
|
|
24
|
+
|
|
25
|
+
To do this, you'll need to visit that page, and click on the 3 dots, and select "Connect to integration".
|
|
26
|
+
|
|
27
|
+

|
|
28
|
+
|
|
29
|
+
#### 3. Adding MCP config to your client:
|
|
23
30
|
|
|
24
31
|
##### Using npm:
|
|
25
32
|
Add the following to your `.cursor/mcp.json` or `claude_desktop_config.json` (MacOS: `~/Library/Application\ Support/Claude/claude_desktop_config.json`)
|
|
@@ -39,7 +46,41 @@ Add the following to your `.cursor/mcp.json` or `claude_desktop_config.json` (Ma
|
|
|
39
46
|
```
|
|
40
47
|
|
|
41
48
|
##### Using Docker:
|
|
42
|
-
|
|
49
|
+
|
|
50
|
+
There are two options for running the MCP server with Docker:
|
|
51
|
+
|
|
52
|
+
###### Option 1: Using the official Docker Hub image:
|
|
53
|
+
|
|
54
|
+
Add the following to your `.cursor/mcp.json` or `claude_desktop_config.json`:
|
|
55
|
+
|
|
56
|
+
```javascript
|
|
57
|
+
{
|
|
58
|
+
"mcpServers": {
|
|
59
|
+
"notionApi": {
|
|
60
|
+
"command": "docker",
|
|
61
|
+
"args": [
|
|
62
|
+
"run",
|
|
63
|
+
"--rm",
|
|
64
|
+
"-i",
|
|
65
|
+
"-e", "OPENAPI_MCP_HEADERS",
|
|
66
|
+
"mcp/notion"
|
|
67
|
+
],
|
|
68
|
+
"env": {
|
|
69
|
+
"OPENAPI_MCP_HEADERS": "{\"Authorization\":\"Bearer ntn_****\",\"Notion-Version\":\"2022-06-28\"}"
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
This approach:
|
|
77
|
+
- Uses the official Docker Hub image
|
|
78
|
+
- Properly handles JSON escaping via environment variables
|
|
79
|
+
- Provides a more reliable configuration method
|
|
80
|
+
|
|
81
|
+
###### Option 2: Building the Docker image locally:
|
|
82
|
+
|
|
83
|
+
You can also build and run the Docker image locally. First, build the Docker image:
|
|
43
84
|
|
|
44
85
|
```bash
|
|
45
86
|
docker-compose build
|
|
@@ -58,7 +99,7 @@ Then, add the following to your `.cursor/mcp.json` or `claude_desktop_config.jso
|
|
|
58
99
|
"-i",
|
|
59
100
|
"-e",
|
|
60
101
|
"OPENAPI_MCP_HEADERS={\"Authorization\": \"Bearer ntn_****\", \"Notion-Version\": \"2022-06-28\"}",
|
|
61
|
-
"notion-mcp-server
|
|
102
|
+
"notion-mcp-server"
|
|
62
103
|
]
|
|
63
104
|
}
|
|
64
105
|
}
|
|
@@ -69,13 +110,6 @@ Don't forget to replace `ntn_****` with your integration secret. Find it from yo
|
|
|
69
110
|
|
|
70
111
|

|
|
71
112
|
|
|
72
|
-
#### 3. Connecting content to integration:
|
|
73
|
-
Ensure relevant pages and databases are connected to your integration.
|
|
74
|
-
|
|
75
|
-
To do this, you'll need to visit that page, and click on the 3 dots, and select "Connect to integration".
|
|
76
|
-
|
|
77
|
-

|
|
78
|
-
|
|
79
113
|
### Examples
|
|
80
114
|
|
|
81
115
|
1. Using the following instruction
|
package/bin/cli.mjs
CHANGED
|
@@ -47,7 +47,7 @@ var Xu=Object.create;var So=Object.defineProperty;var Qu=Object.getOwnPropertyDe
|
|
|
47
47
|
`}var hi=class{constructor(t=Yo.stdin,n=Yo.stdout){this._stdin=t,this._stdout=n,this._readBuffer=new fi,this._started=!1,this._ondata=i=>{this._readBuffer.append(i),this.processReadBuffer()},this._onerror=i=>{var a;(a=this.onerror)===null||a===void 0||a.call(this,i)}}async start(){if(this._started)throw new Error("StdioServerTransport already started! If using Server class, note that connect() calls start() automatically.");this._started=!0,this._stdin.on("data",this._ondata),this._stdin.on("error",this._onerror)}processReadBuffer(){for(var t,n;;)try{let i=this._readBuffer.readMessage();if(i===null)break;(t=this.onmessage)===null||t===void 0||t.call(this,i)}catch(i){(n=this.onerror)===null||n===void 0||n.call(this,i)}}async close(){var t;this._stdin.off("data",this._ondata),this._stdin.off("error",this._onerror),this._stdin.listenerCount("data")===0&&this._stdin.pause(),this._readBuffer.clear(),(t=this.onclose)===null||t===void 0||t.call(this)}send(t){return new Promise(n=>{let i=Wo(t);this._stdout.write(i)?n():this._stdout.once("drain",n)})}};import S_ from"node:fs";import k_ from"node:path";var af=6e4,xi=class{constructor(t){this._options=t,this._requestMessageId=0,this._requestHandlers=new Map,this._requestHandlerAbortControllers=new Map,this._notificationHandlers=new Map,this._responseHandlers=new Map,this._progressHandlers=new Map,this._timeoutInfo=new Map,this.setNotificationHandler(si,n=>{let i=this._requestHandlerAbortControllers.get(n.params.requestId);i?.abort(n.params.reason)}),this.setNotificationHandler(pi,n=>{this._onprogress(n)}),this.setRequestHandler(ci,n=>({}))}_setupTimeout(t,n,i,a){this._timeoutInfo.set(t,{timeoutId:setTimeout(a,n),startTime:Date.now(),timeout:n,maxTotalTimeout:i,onTimeout:a})}_resetTimeout(t){let n=this._timeoutInfo.get(t);if(!n)return!1;let i=Date.now()-n.startTime;if(n.maxTotalTimeout&&i>=n.maxTotalTimeout)throw this._timeoutInfo.delete(t),new Et(Qe.RequestTimeout,"Maximum total timeout exceeded",{maxTotalTimeout:n.maxTotalTimeout,totalElapsed:i});return clearTimeout(n.timeoutId),n.timeoutId=setTimeout(n.onTimeout,n.timeout),!0}_cleanupTimeout(t){let n=this._timeoutInfo.get(t);n&&(clearTimeout(n.timeoutId),this._timeoutInfo.delete(t))}async connect(t){this._transport=t,this._transport.onclose=()=>{this._onclose()},this._transport.onerror=n=>{this._onerror(n)},this._transport.onmessage=n=>{"method"in n?"id"in n?this._onrequest(n):this._onnotification(n):this._onresponse(n)},await this._transport.start()}_onclose(){var t;let n=this._responseHandlers;this._responseHandlers=new Map,this._progressHandlers.clear(),this._transport=void 0,(t=this.onclose)===null||t===void 0||t.call(this);let i=new Et(Qe.ConnectionClosed,"Connection closed");for(let a of n.values())a(i)}_onerror(t){var n;(n=this.onerror)===null||n===void 0||n.call(this,t)}_onnotification(t){var n;let i=(n=this._notificationHandlers.get(t.method))!==null&&n!==void 0?n:this.fallbackNotificationHandler;i!==void 0&&Promise.resolve().then(()=>i(t)).catch(a=>this._onerror(new Error(`Uncaught error in notification handler: ${a}`)))}_onrequest(t){var n,i,a;let r=(n=this._requestHandlers.get(t.method))!==null&&n!==void 0?n:this.fallbackRequestHandler;if(r===void 0){(i=this._transport)===null||i===void 0||i.send({jsonrpc:"2.0",id:t.id,error:{code:Qe.MethodNotFound,message:"Method not found"}}).catch(p=>this._onerror(new Error(`Failed to send an error response: ${p}`)));return}let o=new AbortController;this._requestHandlerAbortControllers.set(t.id,o);let s={signal:o.signal,sessionId:(a=this._transport)===null||a===void 0?void 0:a.sessionId};Promise.resolve().then(()=>r(t,s)).then(p=>{var c;if(!o.signal.aborted)return(c=this._transport)===null||c===void 0?void 0:c.send({result:p,jsonrpc:"2.0",id:t.id})},p=>{var c,l;if(!o.signal.aborted)return(c=this._transport)===null||c===void 0?void 0:c.send({jsonrpc:"2.0",id:t.id,error:{code:Number.isSafeInteger(p.code)?p.code:Qe.InternalError,message:(l=p.message)!==null&&l!==void 0?l:"Internal error"}})}).catch(p=>this._onerror(new Error(`Failed to send response: ${p}`))).finally(()=>{this._requestHandlerAbortControllers.delete(t.id)})}_onprogress(t){let{progressToken:n,...i}=t.params,a=Number(n),r=this._progressHandlers.get(a);if(!r){this._onerror(new Error(`Received a progress notification for an unknown token: ${JSON.stringify(t)}`));return}let o=this._responseHandlers.get(a);if(this._timeoutInfo.has(a)&&o)try{this._resetTimeout(a)}catch(s){o(s);return}r(i)}_onresponse(t){let n=Number(t.id),i=this._responseHandlers.get(n);if(i===void 0){this._onerror(new Error(`Received a response for an unknown message ID: ${JSON.stringify(t)}`));return}if(this._responseHandlers.delete(n),this._progressHandlers.delete(n),this._cleanupTimeout(n),"result"in t)i(t);else{let a=new Et(t.error.code,t.error.message,t.error.data);i(a)}}get transport(){return this._transport}async close(){var t;await((t=this._transport)===null||t===void 0?void 0:t.close())}request(t,n,i){return new Promise((a,r)=>{var o,s,p,c;if(!this._transport){r(new Error("Not connected"));return}((o=this._options)===null||o===void 0?void 0:o.enforceStrictCapabilities)===!0&&this.assertCapabilityForMethod(t.method),(s=i?.signal)===null||s===void 0||s.throwIfAborted();let l=this._requestMessageId++,d={...t,jsonrpc:"2.0",id:l};i?.onprogress&&(this._progressHandlers.set(l,i.onprogress),d.params={...t.params,_meta:{progressToken:l}});let f=x=>{var g;this._responseHandlers.delete(l),this._progressHandlers.delete(l),this._cleanupTimeout(l),(g=this._transport)===null||g===void 0||g.send({jsonrpc:"2.0",method:"notifications/cancelled",params:{requestId:l,reason:String(x)}}).catch(S=>this._onerror(new Error(`Failed to send cancellation: ${S}`))),r(x)};this._responseHandlers.set(l,x=>{var g;if(!(!((g=i?.signal)===null||g===void 0)&&g.aborted)){if(x instanceof Error)return r(x);try{let S=n.parse(x.result);a(S)}catch(S){r(S)}}}),(p=i?.signal)===null||p===void 0||p.addEventListener("abort",()=>{var x;f((x=i?.signal)===null||x===void 0?void 0:x.reason)});let v=(c=i?.timeout)!==null&&c!==void 0?c:af,h=()=>f(new Et(Qe.RequestTimeout,"Request timed out",{timeout:v}));this._setupTimeout(l,v,i?.maxTotalTimeout,h),this._transport.send(d).catch(x=>{this._cleanupTimeout(l),r(x)})})}async notification(t){if(!this._transport)throw new Error("Not connected");this.assertNotificationCapability(t.method);let n={...t,jsonrpc:"2.0"};await this._transport.send(n)}setRequestHandler(t,n){let i=t.shape.method.value;this.assertRequestHandlerCapability(i),this._requestHandlers.set(i,(a,r)=>Promise.resolve(n(t.parse(a),r)))}removeRequestHandler(t){this._requestHandlers.delete(t)}assertCanSetRequestHandler(t){if(this._requestHandlers.has(t))throw new Error(`A request handler for ${t} already exists, which would be overridden`)}setNotificationHandler(t,n){this._notificationHandlers.set(t.shape.method.value,i=>Promise.resolve(n(t.parse(i))))}removeNotificationHandler(t){this._notificationHandlers.delete(t)}};function Go(e,t){return Object.entries(t).reduce((n,[i,a])=>(a&&typeof a=="object"?n[i]=n[i]?{...n[i],...a}:a:n[i]=a,n),{...e})}var vi=class extends xi{constructor(t,n){var i;super(n),this._serverInfo=t,this._capabilities=(i=n?.capabilities)!==null&&i!==void 0?i:{},this._instructions=n?.instructions,this.setRequestHandler(va,a=>this._oninitialize(a)),this.setNotificationHandler(ga,()=>{var a;return(a=this.oninitialized)===null||a===void 0?void 0:a.call(this)})}registerCapabilities(t){if(this.transport)throw new Error("Cannot register capabilities after connecting to transport");this._capabilities=Go(this._capabilities,t)}assertCapabilityForMethod(t){var n,i;switch(t){case"sampling/createMessage":if(!(!((n=this._clientCapabilities)===null||n===void 0)&&n.sampling))throw new Error(`Client does not support sampling (required for ${t})`);break;case"roots/list":if(!(!((i=this._clientCapabilities)===null||i===void 0)&&i.roots))throw new Error(`Client does not support listing roots (required for ${t})`);break;case"ping":break}}assertNotificationCapability(t){switch(t){case"notifications/message":if(!this._capabilities.logging)throw new Error(`Server does not support logging (required for ${t})`);break;case"notifications/resources/updated":case"notifications/resources/list_changed":if(!this._capabilities.resources)throw new Error(`Server does not support notifying about resources (required for ${t})`);break;case"notifications/tools/list_changed":if(!this._capabilities.tools)throw new Error(`Server does not support notifying of tool list changes (required for ${t})`);break;case"notifications/prompts/list_changed":if(!this._capabilities.prompts)throw new Error(`Server does not support notifying of prompt list changes (required for ${t})`);break;case"notifications/cancelled":break;case"notifications/progress":break}}assertRequestHandlerCapability(t){switch(t){case"sampling/createMessage":if(!this._capabilities.sampling)throw new Error(`Server does not support sampling (required for ${t})`);break;case"logging/setLevel":if(!this._capabilities.logging)throw new Error(`Server does not support logging (required for ${t})`);break;case"prompts/get":case"prompts/list":if(!this._capabilities.prompts)throw new Error(`Server does not support prompts (required for ${t})`);break;case"resources/list":case"resources/templates/list":case"resources/read":if(!this._capabilities.resources)throw new Error(`Server does not support resources (required for ${t})`);break;case"tools/call":case"tools/list":if(!this._capabilities.tools)throw new Error(`Server does not support tools (required for ${t})`);break;case"ping":case"initialize":break}}async _oninitialize(t){let n=t.params.protocolVersion;return this._clientCapabilities=t.params.capabilities,this._clientVersion=t.params.clientInfo,{protocolVersion:Fo.includes(n)?n:xa,capabilities:this.getCapabilities(),serverInfo:this._serverInfo,...this._instructions&&{instructions:this._instructions}}}getClientCapabilities(){return this._clientCapabilities}getClientVersion(){return this._clientVersion}getCapabilities(){return this._capabilities}async ping(){return this.request({method:"ping"},oi)}async createMessage(t,n){return this.request({method:"sampling/createMessage",params:t},_a,n)}async listRoots(t,n){return this.request({method:"roots/list",params:t},wa,n)}async sendLoggingMessage(t){return this.notification({method:"notifications/message",params:t})}async sendResourceUpdated(t){return this.notification({method:"notifications/resources/updated",params:t})}async sendResourceListChanged(){return this.notification({method:"notifications/resources/list_changed"})}async sendToolListChanged(){return this.notification({method:"notifications/tools/list_changed"})}async sendPromptListChanged(){return this.notification({method:"notifications/prompts/list_changed"})}};var gi=class{constructor(t){this.openApiSpec=t;this.schemaCache={};this.nameCounter=0}internalResolveRef(t,n){if(!t.startsWith("#/")||n.has(t))return null;let i=t.replace(/^#\//,"").split("/"),a=this.openApiSpec;for(let r of i)if(a=a[r],!a)return null;return n.add(t),a}convertOpenApiSchemaToJsonSchema(t,n,i=!1){if("$ref"in t){let r=t.$ref;if(!i){if(r.startsWith("#/components/schemas/"))return{$ref:r.replace(/^#\/components\/schemas\//,"#/$defs/"),..."description"in t?{description:t.description}:{}};console.error(`Attempting to resolve ref ${r} not found in components collection.`)}let o={$ref:r};if("description"in t&&t.description&&(o.description=t.description),this.schemaCache[r])return this.schemaCache[r];let s=this.internalResolveRef(r,n);if(s){let p=this.convertOpenApiSchemaToJsonSchema(s,n,i);return this.schemaCache[r]=p,p}else return console.error(`Failed to resolve ref ${r}`),{$ref:r.replace(/^#\/components\/schemas\//,"#/$defs/"),description:"description"in t?t.description??"":""}}let a={};if(t.type&&(a.type=t.type),t.format==="binary"){a.format="uri-reference";let r="absolute paths to local files";a.description=t.description?`${t.description} (${r})`:r}else t.format&&(a.format=t.format),t.description&&(a.description=t.description);if(t.enum&&(a.enum=t.enum),t.default!==void 0&&(a.default=t.default),t.type==="object"){if(a.type="object",t.properties){a.properties={};for(let[r,o]of Object.entries(t.properties))a.properties[r]=this.convertOpenApiSchemaToJsonSchema(o,n,i)}t.required&&(a.required=t.required),t.additionalProperties===!0||t.additionalProperties===void 0?a.additionalProperties=!0:t.additionalProperties&&typeof t.additionalProperties=="object"?a.additionalProperties=this.convertOpenApiSchemaToJsonSchema(t.additionalProperties,n,i):a.additionalProperties=!1}return t.type==="array"&&t.items&&(a.type="array",a.items=this.convertOpenApiSchemaToJsonSchema(t.items,n,i)),t.oneOf&&(a.oneOf=t.oneOf.map(r=>this.convertOpenApiSchemaToJsonSchema(r,n,i))),t.anyOf&&(a.anyOf=t.anyOf.map(r=>this.convertOpenApiSchemaToJsonSchema(r,n,i))),t.allOf&&(a.allOf=t.allOf.map(r=>this.convertOpenApiSchemaToJsonSchema(r,n,i))),a}convertToMCPTools(){let t="API",n={},i={[t]:{methods:[]}},a={};for(let[r,o]of Object.entries(this.openApiSpec.paths||{}))if(o)for(let[s,p]of Object.entries(o)){if(!this.isOperation(s,p))continue;let c=this.convertOperationToMCPMethod(p,s,r);if(c){let l=this.ensureUniqueName(c.name);c.name=l,i[t].methods.push(c),n[t+"-"+l]={...p,method:s,path:r},a[t+"-"+l]={openApi:{...p,method:s,path:r},mcp:c}}}return{tools:i,openApiLookup:n,zip:a}}convertToOpenAITools(){let t=[];for(let[n,i]of Object.entries(this.openApiSpec.paths||{}))if(i)for(let[a,r]of Object.entries(i)){if(!this.isOperation(a,r))continue;let o=this.convertOperationToJsonSchema(r,a,n),s={type:"function",function:{name:r.operationId,description:r.summary||r.description||"",parameters:o}};t.push(s)}return t}convertToAnthropicTools(){let t=[];for(let[n,i]of Object.entries(this.openApiSpec.paths||{}))if(i)for(let[a,r]of Object.entries(i)){if(!this.isOperation(a,r))continue;let o=this.convertOperationToJsonSchema(r,a,n),s={name:r.operationId,description:r.summary||r.description||"",input_schema:o};t.push(s)}return t}convertComponentsToJsonSchema(){let t=this.openApiSpec.components||{},n={};for(let[i,a]of Object.entries(t.schemas||{}))n[i]=this.convertOpenApiSchemaToJsonSchema(a,new Set);return n}convertOperationToJsonSchema(t,n,i){let a={type:"object",properties:{},required:[],$defs:this.convertComponentsToJsonSchema()};if(t.parameters)for(let r of t.parameters){let o=this.resolveParameter(r);if(o&&o.schema){let s=this.convertOpenApiSchemaToJsonSchema(o.schema,new Set);o.description&&(s.description=o.description),a.properties[o.name]=s,o.required&&a.required.push(o.name)}}if(t.requestBody){let r=this.resolveRequestBody(t.requestBody);if(r?.content&&r.content["application/json"]?.schema){let o=this.convertOpenApiSchemaToJsonSchema(r.content["application/json"].schema,new Set);if(o.type==="object"&&o.properties){for(let[s,p]of Object.entries(o.properties))a.properties[s]=p;o.required&&a.required.push(...o.required)}}}return a}isOperation(t,n){return["get","post","put","delete","patch"].includes(t.toLowerCase())}isParameterObject(t){return!("$ref"in t)}isRequestBodyObject(t){return!("$ref"in t)}resolveParameter(t){if(this.isParameterObject(t))return t;{let n=this.internalResolveRef(t.$ref,new Set);if(n&&n.name)return n}return null}resolveRequestBody(t){if(this.isRequestBodyObject(t))return t;{let n=this.internalResolveRef(t.$ref,new Set);if(n)return n}return null}resolveResponse(t){if("$ref"in t){let n=this.internalResolveRef(t.$ref,new Set);return n||null}return t}convertOperationToMCPMethod(t,n,i){if(!t.operationId)return console.warn(`Operation without operationId at ${n} ${i}`),null;let a=t.operationId,r={$defs:this.convertComponentsToJsonSchema(),type:"object",properties:{},required:[]};if(t.parameters)for(let p of t.parameters){let c=this.resolveParameter(p);if(c&&c.schema){let l=this.convertOpenApiSchemaToJsonSchema(c.schema,new Set,!1);c.description&&(l.description=c.description),r.properties[c.name]=l,c.required&&r.required.push(c.name)}}if(t.requestBody){let p=this.resolveRequestBody(t.requestBody);if(p?.content){if(p.content["multipart/form-data"]?.schema){let c=this.convertOpenApiSchemaToJsonSchema(p.content["multipart/form-data"].schema,new Set,!1);if(c.type==="object"&&c.properties){for(let[l,d]of Object.entries(c.properties))r.properties[l]=d;c.required&&r.required.push(...c.required)}}else if(p.content["application/json"]?.schema){let c=this.convertOpenApiSchemaToJsonSchema(p.content["application/json"].schema,new Set,!1);if(c.type==="object"&&c.properties){for(let[l,d]of Object.entries(c.properties))r.properties[l]=d;c.required&&r.required.push(...c.required)}else r.properties.body=c,r.required.push("body")}}}let o=t.summary||t.description||"";if(t.responses){let p=Object.entries(t.responses).filter(([c])=>c.startsWith("4")||c.startsWith("5")).map(([c,l])=>{let f=this.resolveResponse(l)?.description||"";return`${c}: ${f}`});p.length>0&&(o+=`
|
|
48
48
|
Error Responses:
|
|
49
49
|
`+p.join(`
|
|
50
|
-
`))}let s=this.extractResponseType(t.responses);try{return{name:a,description:o,inputSchema:r,...s?{returnSchema:s}:{}}}catch(p){return console.warn(`Failed to generate Zod schema for ${a}:`,p),{name:a,description:o,inputSchema:r,...s?{returnSchema:s}:{}}}}extractResponseType(t){let n=t?.["200"]||t?.["201"]||t?.["202"]||t?.["204"];if(!n)return null;let i=this.resolveResponse(n);if(!i||!i.content)return null;if(i.content["application/json"]?.schema){let a=this.convertOpenApiSchemaToJsonSchema(i.content["application/json"].schema,new Set,!1);return a.$defs=this.convertComponentsToJsonSchema(),i.description&&!a.description&&(a.description=i.description),a}return i.content["image/png"]||i.content["image/jpeg"]?{type:"string",format:"binary",description:i.description||""}:{type:"string",description:i.description||""}}ensureUniqueName(t){if(t.length<=64)return t;let n=t.slice(0,59),i=this.generateUniqueSuffix();return`${n}-${i}`}generateUniqueSuffix(){return this.nameCounter+=1,this.nameCounter.toString().padStart(4,"0")}};var bo=ko($u(),1),Vu=ko($a(),1);import w_ from"fs";function Hu(e){let t=[];if(!e.requestBody)return t;let a=(e.requestBody.content||{})["multipart/form-data"];if(!a?.schema)return t;let r=a.schema;return r.type!=="object"||!r.properties||Object.entries(r.properties).forEach(([o,s])=>{let p=s;if(p.type==="string"&&p.format==="binary"&&t.push(o),p.type==="array"&&p.items){let c=p.items;c.type==="string"&&c.format==="binary"&&t.push(o)}}),t}var Wn=class extends Error{constructor(n,i,a,r){super(`${i} ${n}`);this.status=i;this.data=a;this.headers=r;this.name="HttpClientError"}},sa=class{constructor(t,n){this.client=new(bo.default.default??bo.default)({definition:n,axiosConfigDefaults:{baseURL:t.baseUrl,headers:{"Content-Type":"application/json","User-Agent":"notion-mcp-server",...t.headers}}}),this.api=this.client.init()}async prepareFileUpload(t,n){
|
|
50
|
+
`))}let s=this.extractResponseType(t.responses);try{return{name:a,description:o,inputSchema:r,...s?{returnSchema:s}:{}}}catch(p){return console.warn(`Failed to generate Zod schema for ${a}:`,p),{name:a,description:o,inputSchema:r,...s?{returnSchema:s}:{}}}}extractResponseType(t){let n=t?.["200"]||t?.["201"]||t?.["202"]||t?.["204"];if(!n)return null;let i=this.resolveResponse(n);if(!i||!i.content)return null;if(i.content["application/json"]?.schema){let a=this.convertOpenApiSchemaToJsonSchema(i.content["application/json"].schema,new Set,!1);return a.$defs=this.convertComponentsToJsonSchema(),i.description&&!a.description&&(a.description=i.description),a}return i.content["image/png"]||i.content["image/jpeg"]?{type:"string",format:"binary",description:i.description||""}:{type:"string",description:i.description||""}}ensureUniqueName(t){if(t.length<=64)return t;let n=t.slice(0,59),i=this.generateUniqueSuffix();return`${n}-${i}`}generateUniqueSuffix(){return this.nameCounter+=1,this.nameCounter.toString().padStart(4,"0")}};var bo=ko($u(),1),Vu=ko($a(),1);import w_ from"fs";function Hu(e){let t=[];if(!e.requestBody)return t;let a=(e.requestBody.content||{})["multipart/form-data"];if(!a?.schema)return t;let r=a.schema;return r.type!=="object"||!r.properties||Object.entries(r.properties).forEach(([o,s])=>{let p=s;if(p.type==="string"&&p.format==="binary"&&t.push(o),p.type==="array"&&p.items){let c=p.items;c.type==="string"&&c.format==="binary"&&t.push(o)}}),t}var Wn=class extends Error{constructor(n,i,a,r){super(`${i} ${n}`);this.status=i;this.data=a;this.headers=r;this.name="HttpClientError"}},sa=class{constructor(t,n){this.client=new(bo.default.default??bo.default)({definition:n,axiosConfigDefaults:{baseURL:t.baseUrl,headers:{"Content-Type":"application/json","User-Agent":"notion-mcp-server",...t.headers}}}),this.api=this.client.init()}async prepareFileUpload(t,n){let i=Hu(t);if(i.length===0)return null;let a=new Vu.default;for(let o of i){let p=function(c,l){try{let d=w_.createReadStream(l);a.append(c,d)}catch(d){throw new Error(`Failed to read file at ${l}: ${d}`)}};var r=p;let s=n[o];if(!s)throw new Error(`File path must be provided for parameter: ${o}`);switch(typeof s){case"string":p(o,s);break;case"object":if(Array.isArray(s)){let c=0;for(let l of s)p(o,l),c++;break}default:throw new Error(`Unsupported file type: ${typeof s}`)}}for(let[o,s]of Object.entries(n))i.includes(o)||a.append(o,s);return a}async executeOperation(t,n={}){let i=await this.api,a=t.operationId;if(!a)throw new Error("Operation ID is required");let r=await this.prepareFileUpload(t,n),o={},s=r||{...n};if(t.parameters)for(let c of t.parameters)"name"in c&&c.name&&c.in&&(c.in==="path"||c.in==="query")&&n[c.name]!==void 0&&(o[c.name]=n[c.name],r||delete s[c.name]);if(!t.requestBody&&!r)for(let c in s)s[c]!==void 0&&(o[c]=s[c],delete s[c]);let p=i[a];if(!p)throw new Error(`Operation ${a} not found`);try{let c=Object.keys(s).length>0,d={headers:{...r?r.getHeaders():{...c?{"Content-Type":"application/json"}:{"Content-Type":null}}}},f=await p(o,c?s:void 0,d),v=new Headers;return Object.entries(f.headers).forEach(([h,x])=>{x&&v.append(h,x.toString())}),{data:f.data,status:f.status,headers:v}}catch(c){if(c.response){console.error("Error in http client",c);let l=new Headers;throw Object.entries(c.response.headers).forEach(([d,f])=>{f&&l.append(d,f.toString())}),new Wn(c.response.statusText||"Request failed",c.response.status,c.response.data,l)}throw c}}};var ca=class{constructor(t,n){this.server=new vi({name:t,version:"1.0.0"},{capabilities:{tools:{}}});let i=n.servers?.[0].url;if(!i)throw new Error("No base URL found in OpenAPI spec");this.httpClient=new sa({baseUrl:i,headers:this.parseHeadersFromEnv()},n);let a=new gi(n),{tools:r,openApiLookup:o}=a.convertToMCPTools();this.tools=r,this.openApiLookup=o,this.setupHandlers()}setupHandlers(){this.server.setRequestHandler(ba,async()=>{let t=[];return Object.entries(this.tools).forEach(([n,i])=>{i.methods.forEach(a=>{let r=`${n}-${a.name}`,o=this.truncateToolName(r);t.push({name:o,description:a.description,inputSchema:a.inputSchema})})}),{tools:t}}),this.server.setRequestHandler(ya,async t=>{let{name:n,arguments:i}=t.params,a=this.findOperation(n);if(!a)throw new Error(`Method ${n} not found`);try{let r=await this.httpClient.executeOperation(a,i);return{content:[{type:"text",text:JSON.stringify(r.data)}]}}catch(r){if(console.error("Error in tool call",r),r instanceof Wn){console.error("HttpClientError encountered, returning structured error",r);let o=r.data?.response?.data??r.data??{};return{content:[{type:"text",text:JSON.stringify({status:"error",...typeof o=="object"?o:{data:o}})}]}}throw r}})}findOperation(t){return this.openApiLookup[t]??null}parseHeadersFromEnv(){let t=process.env.OPENAPI_MCP_HEADERS;if(!t)return{};try{let n=JSON.parse(t);return typeof n!="object"||n===null?(console.warn("OPENAPI_MCP_HEADERS environment variable must be a JSON object, got:",typeof n),{}):n}catch(n){return console.warn("Failed to parse OPENAPI_MCP_HEADERS environment variable:",n),{}}}getContentType(t){let n=t.get("content-type");return n?n.includes("text")||n.includes("json")?"text":n.includes("image")?"image":"binary":"binary"}truncateToolName(t){return t.length<=64?t:t.slice(0,64)}async connect(t){await this.server.connect(t)}getServer(){return this.server}};var Yn=class extends Error{constructor(n){super("OpenAPI validation failed");this.errors=n;this.name="ValidationError"}};async function O_(e,t){let n;try{n=S_.readFileSync(k_.resolve(process.cwd(),e),"utf-8")}catch(i){console.error("Failed to read OpenAPI specification file:",i.message),process.exit(1)}try{let i=JSON.parse(n);return t&&(i.servers[0].url=t),i}catch(i){if(i instanceof Yn)throw i;console.error("Failed to parse OpenAPI spec:",i.message),process.exit(1)}}async function Zu(e,t){let n=await O_(e,t);return new ca("Notion API",n)}async function T_(e=process.argv.slice(2)){let t=A_(import.meta.url),n=Ju.dirname(t),i=Ju.resolve(n,"../scripts/notion-openapi.json"),a=process.env.BASE_URL??void 0,r=await Zu(i,a);return await r.connect(new hi),r.getServer()}T_().catch(e=>{e instanceof Yn?(console.error("Invalid OpenAPI 3.1 specification:"),e.errors.forEach(t=>console.error(t))):console.error("Error:",e),process.exit(1)});export{T_ as startServer};
|
|
51
51
|
/*! Bundled license information:
|
|
52
52
|
|
|
53
53
|
mime-db/index.js:
|
package/package.json
CHANGED
|
@@ -800,13 +800,20 @@
|
|
|
800
800
|
"description": "When supplied, orders the results based on the provided [sort criteria](ref:post-database-query-sort).",
|
|
801
801
|
"items": {
|
|
802
802
|
"type": "object",
|
|
803
|
-
"required": [
|
|
803
|
+
"required": [
|
|
804
|
+
"property",
|
|
805
|
+
"direction"
|
|
806
|
+
],
|
|
804
807
|
"properties": {
|
|
805
808
|
"property": {
|
|
806
809
|
"type": "string"
|
|
807
810
|
},
|
|
808
811
|
"direction": {
|
|
809
|
-
"enum": [
|
|
812
|
+
"enum": [
|
|
813
|
+
"ascending",
|
|
814
|
+
"descending"
|
|
815
|
+
],
|
|
816
|
+
"type": "string"
|
|
810
817
|
}
|
|
811
818
|
}
|
|
812
819
|
}
|
|
@@ -983,30 +990,44 @@
|
|
|
983
990
|
"maxLength": 2000
|
|
984
991
|
},
|
|
985
992
|
"link": {
|
|
986
|
-
"type": [
|
|
993
|
+
"type": [
|
|
994
|
+
"object",
|
|
995
|
+
"null"
|
|
996
|
+
],
|
|
987
997
|
"properties": {
|
|
988
998
|
"url": {
|
|
989
999
|
"type": "string"
|
|
990
1000
|
}
|
|
991
1001
|
},
|
|
992
|
-
"required": [
|
|
1002
|
+
"required": [
|
|
1003
|
+
"url"
|
|
1004
|
+
]
|
|
993
1005
|
}
|
|
994
1006
|
},
|
|
995
1007
|
"additionalProperties": false,
|
|
996
|
-
"required": [
|
|
1008
|
+
"required": [
|
|
1009
|
+
"content"
|
|
1010
|
+
]
|
|
997
1011
|
},
|
|
998
1012
|
"type": {
|
|
999
|
-
"enum": [
|
|
1013
|
+
"enum": [
|
|
1014
|
+
"text"
|
|
1015
|
+
],
|
|
1016
|
+
"type": "string"
|
|
1000
1017
|
}
|
|
1001
1018
|
},
|
|
1002
1019
|
"additionalProperties": false,
|
|
1003
|
-
"required": [
|
|
1020
|
+
"required": [
|
|
1021
|
+
"text"
|
|
1022
|
+
]
|
|
1004
1023
|
},
|
|
1005
1024
|
"maxItems": 100
|
|
1006
1025
|
}
|
|
1007
1026
|
},
|
|
1008
1027
|
"additionalProperties": false,
|
|
1009
|
-
"required": [
|
|
1028
|
+
"required": [
|
|
1029
|
+
"rich_text"
|
|
1030
|
+
]
|
|
1010
1031
|
},
|
|
1011
1032
|
"bulleted_list_item": {
|
|
1012
1033
|
"type": "object",
|
|
@@ -1024,33 +1045,51 @@
|
|
|
1024
1045
|
"maxLength": 2000
|
|
1025
1046
|
},
|
|
1026
1047
|
"link": {
|
|
1027
|
-
"type": [
|
|
1048
|
+
"type": [
|
|
1049
|
+
"object",
|
|
1050
|
+
"null"
|
|
1051
|
+
],
|
|
1028
1052
|
"properties": {
|
|
1029
1053
|
"url": {
|
|
1030
1054
|
"type": "string"
|
|
1031
1055
|
}
|
|
1032
1056
|
},
|
|
1033
|
-
"required": [
|
|
1057
|
+
"required": [
|
|
1058
|
+
"url"
|
|
1059
|
+
]
|
|
1034
1060
|
}
|
|
1035
1061
|
},
|
|
1036
1062
|
"additionalProperties": false,
|
|
1037
|
-
"required": [
|
|
1063
|
+
"required": [
|
|
1064
|
+
"content"
|
|
1065
|
+
]
|
|
1038
1066
|
},
|
|
1039
1067
|
"type": {
|
|
1040
|
-
"enum": [
|
|
1068
|
+
"enum": [
|
|
1069
|
+
"text"
|
|
1070
|
+
],
|
|
1071
|
+
"type": "string"
|
|
1041
1072
|
}
|
|
1042
1073
|
},
|
|
1043
1074
|
"additionalProperties": false,
|
|
1044
|
-
"required": [
|
|
1075
|
+
"required": [
|
|
1076
|
+
"text"
|
|
1077
|
+
]
|
|
1045
1078
|
},
|
|
1046
1079
|
"maxItems": 100
|
|
1047
1080
|
}
|
|
1048
1081
|
},
|
|
1049
1082
|
"additionalProperties": false,
|
|
1050
|
-
"required": [
|
|
1083
|
+
"required": [
|
|
1084
|
+
"rich_text"
|
|
1085
|
+
]
|
|
1051
1086
|
},
|
|
1052
1087
|
"type": {
|
|
1053
|
-
"enum": [
|
|
1088
|
+
"enum": [
|
|
1089
|
+
"paragraph",
|
|
1090
|
+
"bulleted_list_item"
|
|
1091
|
+
],
|
|
1092
|
+
"type": "string"
|
|
1054
1093
|
}
|
|
1055
1094
|
},
|
|
1056
1095
|
"additionalProperties": false
|
|
@@ -1217,33 +1256,50 @@
|
|
|
1217
1256
|
"maxLength": 2000
|
|
1218
1257
|
},
|
|
1219
1258
|
"link": {
|
|
1220
|
-
"type": [
|
|
1259
|
+
"type": [
|
|
1260
|
+
"object",
|
|
1261
|
+
"null"
|
|
1262
|
+
],
|
|
1221
1263
|
"properties": {
|
|
1222
1264
|
"url": {
|
|
1223
1265
|
"type": "string"
|
|
1224
1266
|
}
|
|
1225
1267
|
},
|
|
1226
|
-
"required": [
|
|
1268
|
+
"required": [
|
|
1269
|
+
"url"
|
|
1270
|
+
]
|
|
1227
1271
|
}
|
|
1228
1272
|
},
|
|
1229
1273
|
"additionalProperties": false,
|
|
1230
|
-
"required": [
|
|
1274
|
+
"required": [
|
|
1275
|
+
"content"
|
|
1276
|
+
]
|
|
1231
1277
|
},
|
|
1232
1278
|
"type": {
|
|
1233
|
-
"enum": [
|
|
1279
|
+
"enum": [
|
|
1280
|
+
"text"
|
|
1281
|
+
],
|
|
1282
|
+
"type": "string"
|
|
1234
1283
|
}
|
|
1235
1284
|
},
|
|
1236
1285
|
"additionalProperties": false,
|
|
1237
|
-
"required": [
|
|
1286
|
+
"required": [
|
|
1287
|
+
"text"
|
|
1288
|
+
]
|
|
1238
1289
|
},
|
|
1239
1290
|
"maxItems": 100
|
|
1240
1291
|
},
|
|
1241
1292
|
"type": {
|
|
1242
|
-
"enum": [
|
|
1293
|
+
"enum": [
|
|
1294
|
+
"title"
|
|
1295
|
+
],
|
|
1296
|
+
"type": "string"
|
|
1243
1297
|
}
|
|
1244
1298
|
},
|
|
1245
1299
|
"additionalProperties": false,
|
|
1246
|
-
"required": [
|
|
1300
|
+
"required": [
|
|
1301
|
+
"title"
|
|
1302
|
+
]
|
|
1247
1303
|
},
|
|
1248
1304
|
"in_trash": {
|
|
1249
1305
|
"type": "boolean",
|
|
@@ -1262,7 +1318,9 @@
|
|
|
1262
1318
|
}
|
|
1263
1319
|
},
|
|
1264
1320
|
"additionalProperties": false,
|
|
1265
|
-
"required": [
|
|
1321
|
+
"required": [
|
|
1322
|
+
"emoji"
|
|
1323
|
+
]
|
|
1266
1324
|
},
|
|
1267
1325
|
"cover": {
|
|
1268
1326
|
"type": "object",
|
|
@@ -1276,13 +1334,20 @@
|
|
|
1276
1334
|
}
|
|
1277
1335
|
},
|
|
1278
1336
|
"additionalProperties": false,
|
|
1279
|
-
"required": [
|
|
1337
|
+
"required": [
|
|
1338
|
+
"url"
|
|
1339
|
+
]
|
|
1280
1340
|
},
|
|
1281
1341
|
"type": {
|
|
1282
|
-
"enum": [
|
|
1342
|
+
"enum": [
|
|
1343
|
+
"external"
|
|
1344
|
+
],
|
|
1345
|
+
"type": "string"
|
|
1283
1346
|
}
|
|
1284
1347
|
},
|
|
1285
|
-
"required": [
|
|
1348
|
+
"required": [
|
|
1349
|
+
"external"
|
|
1350
|
+
],
|
|
1286
1351
|
"additionalProperties": false
|
|
1287
1352
|
}
|
|
1288
1353
|
}
|
|
@@ -1319,7 +1384,9 @@
|
|
|
1319
1384
|
"format": "uuid"
|
|
1320
1385
|
}
|
|
1321
1386
|
},
|
|
1322
|
-
"required": [
|
|
1387
|
+
"required": [
|
|
1388
|
+
"page_id"
|
|
1389
|
+
]
|
|
1323
1390
|
},
|
|
1324
1391
|
"properties": {
|
|
1325
1392
|
"type": "object",
|
|
@@ -1328,11 +1395,15 @@
|
|
|
1328
1395
|
"type": "array",
|
|
1329
1396
|
"items": {
|
|
1330
1397
|
"type": "object",
|
|
1331
|
-
"required": [
|
|
1398
|
+
"required": [
|
|
1399
|
+
"text"
|
|
1400
|
+
],
|
|
1332
1401
|
"properties": {
|
|
1333
1402
|
"text": {
|
|
1334
1403
|
"type": "object",
|
|
1335
|
-
"required": [
|
|
1404
|
+
"required": [
|
|
1405
|
+
"content"
|
|
1406
|
+
],
|
|
1336
1407
|
"properties": {
|
|
1337
1408
|
"content": {
|
|
1338
1409
|
"type": "string",
|
|
@@ -1345,11 +1416,16 @@
|
|
|
1345
1416
|
"maxItems": 100
|
|
1346
1417
|
},
|
|
1347
1418
|
"type": {
|
|
1348
|
-
"enum": [
|
|
1419
|
+
"enum": [
|
|
1420
|
+
"title"
|
|
1421
|
+
],
|
|
1422
|
+
"type": "string"
|
|
1349
1423
|
}
|
|
1350
1424
|
},
|
|
1351
1425
|
"additionalProperties": false,
|
|
1352
|
-
"required": [
|
|
1426
|
+
"required": [
|
|
1427
|
+
"title"
|
|
1428
|
+
]
|
|
1353
1429
|
},
|
|
1354
1430
|
"children": {
|
|
1355
1431
|
"type": "array",
|
|
@@ -1389,20 +1465,29 @@
|
|
|
1389
1465
|
"application/json": {
|
|
1390
1466
|
"schema": {
|
|
1391
1467
|
"type": "object",
|
|
1392
|
-
"required": [
|
|
1468
|
+
"required": [
|
|
1469
|
+
"parent",
|
|
1470
|
+
"properties"
|
|
1471
|
+
],
|
|
1393
1472
|
"properties": {
|
|
1394
1473
|
"parent": {
|
|
1395
1474
|
"type": "object",
|
|
1396
1475
|
"properties": {
|
|
1397
1476
|
"type": {
|
|
1398
|
-
"enum": [
|
|
1477
|
+
"enum": [
|
|
1478
|
+
"page_id"
|
|
1479
|
+
],
|
|
1480
|
+
"type": "string"
|
|
1399
1481
|
},
|
|
1400
1482
|
"page_id": {
|
|
1401
1483
|
"type": "string",
|
|
1402
1484
|
"format": "uuid"
|
|
1403
1485
|
}
|
|
1404
1486
|
},
|
|
1405
|
-
"required": [
|
|
1487
|
+
"required": [
|
|
1488
|
+
"type",
|
|
1489
|
+
"page_id"
|
|
1490
|
+
]
|
|
1406
1491
|
},
|
|
1407
1492
|
"properties": {
|
|
1408
1493
|
"type": "object",
|
|
@@ -1424,7 +1509,9 @@
|
|
|
1424
1509
|
}
|
|
1425
1510
|
},
|
|
1426
1511
|
"additionalProperties": false,
|
|
1427
|
-
"required": [
|
|
1512
|
+
"required": [
|
|
1513
|
+
"title"
|
|
1514
|
+
]
|
|
1428
1515
|
}
|
|
1429
1516
|
]
|
|
1430
1517
|
}
|
|
@@ -1433,7 +1520,9 @@
|
|
|
1433
1520
|
"type": "array",
|
|
1434
1521
|
"items": {
|
|
1435
1522
|
"type": "object",
|
|
1436
|
-
"required": [
|
|
1523
|
+
"required": [
|
|
1524
|
+
"text"
|
|
1525
|
+
],
|
|
1437
1526
|
"properties": {
|
|
1438
1527
|
"text": {
|
|
1439
1528
|
"type": "object",
|
|
@@ -1443,20 +1532,30 @@
|
|
|
1443
1532
|
"maxLength": 2000
|
|
1444
1533
|
},
|
|
1445
1534
|
"link": {
|
|
1446
|
-
"type": [
|
|
1535
|
+
"type": [
|
|
1536
|
+
"object",
|
|
1537
|
+
"null"
|
|
1538
|
+
],
|
|
1447
1539
|
"properties": {
|
|
1448
1540
|
"url": {
|
|
1449
1541
|
"type": "string"
|
|
1450
1542
|
}
|
|
1451
1543
|
},
|
|
1452
|
-
"required": [
|
|
1544
|
+
"required": [
|
|
1545
|
+
"url"
|
|
1546
|
+
]
|
|
1453
1547
|
}
|
|
1454
1548
|
},
|
|
1455
1549
|
"additionalProperties": false,
|
|
1456
|
-
"required": [
|
|
1550
|
+
"required": [
|
|
1551
|
+
"content"
|
|
1552
|
+
]
|
|
1457
1553
|
},
|
|
1458
1554
|
"type": {
|
|
1459
|
-
"enum": [
|
|
1555
|
+
"enum": [
|
|
1556
|
+
"text"
|
|
1557
|
+
],
|
|
1558
|
+
"type": "string"
|
|
1460
1559
|
}
|
|
1461
1560
|
},
|
|
1462
1561
|
"additionalProperties": false
|
|
@@ -1513,7 +1612,9 @@
|
|
|
1513
1612
|
"type": "array",
|
|
1514
1613
|
"items": {
|
|
1515
1614
|
"type": "object",
|
|
1516
|
-
"required": [
|
|
1615
|
+
"required": [
|
|
1616
|
+
"text"
|
|
1617
|
+
],
|
|
1517
1618
|
"properties": {
|
|
1518
1619
|
"text": {
|
|
1519
1620
|
"type": "object",
|
|
@@ -1523,20 +1624,30 @@
|
|
|
1523
1624
|
"maxLength": 2000
|
|
1524
1625
|
},
|
|
1525
1626
|
"link": {
|
|
1526
|
-
"type": [
|
|
1627
|
+
"type": [
|
|
1628
|
+
"object",
|
|
1629
|
+
"null"
|
|
1630
|
+
],
|
|
1527
1631
|
"properties": {
|
|
1528
1632
|
"url": {
|
|
1529
1633
|
"type": "string"
|
|
1530
1634
|
}
|
|
1531
1635
|
},
|
|
1532
|
-
"required": [
|
|
1636
|
+
"required": [
|
|
1637
|
+
"url"
|
|
1638
|
+
]
|
|
1533
1639
|
}
|
|
1534
1640
|
},
|
|
1535
1641
|
"additionalProperties": false,
|
|
1536
|
-
"required": [
|
|
1642
|
+
"required": [
|
|
1643
|
+
"content"
|
|
1644
|
+
]
|
|
1537
1645
|
},
|
|
1538
1646
|
"type": {
|
|
1539
|
-
"enum": [
|
|
1647
|
+
"enum": [
|
|
1648
|
+
"text"
|
|
1649
|
+
],
|
|
1650
|
+
"type": "string"
|
|
1540
1651
|
}
|
|
1541
1652
|
},
|
|
1542
1653
|
"additionalProperties": false
|
|
@@ -1546,7 +1657,9 @@
|
|
|
1546
1657
|
"type": "array",
|
|
1547
1658
|
"items": {
|
|
1548
1659
|
"type": "object",
|
|
1549
|
-
"required": [
|
|
1660
|
+
"required": [
|
|
1661
|
+
"text"
|
|
1662
|
+
],
|
|
1550
1663
|
"properties": {
|
|
1551
1664
|
"text": {
|
|
1552
1665
|
"type": "object",
|
|
@@ -1556,20 +1669,30 @@
|
|
|
1556
1669
|
"maxLength": 2000
|
|
1557
1670
|
},
|
|
1558
1671
|
"link": {
|
|
1559
|
-
"type": [
|
|
1672
|
+
"type": [
|
|
1673
|
+
"object",
|
|
1674
|
+
"null"
|
|
1675
|
+
],
|
|
1560
1676
|
"properties": {
|
|
1561
1677
|
"url": {
|
|
1562
1678
|
"type": "string"
|
|
1563
1679
|
}
|
|
1564
1680
|
},
|
|
1565
|
-
"required": [
|
|
1681
|
+
"required": [
|
|
1682
|
+
"url"
|
|
1683
|
+
]
|
|
1566
1684
|
}
|
|
1567
1685
|
},
|
|
1568
1686
|
"additionalProperties": false,
|
|
1569
|
-
"required": [
|
|
1687
|
+
"required": [
|
|
1688
|
+
"content"
|
|
1689
|
+
]
|
|
1570
1690
|
},
|
|
1571
1691
|
"type": {
|
|
1572
|
-
"enum": [
|
|
1692
|
+
"enum": [
|
|
1693
|
+
"text"
|
|
1694
|
+
],
|
|
1695
|
+
"type": "string"
|
|
1573
1696
|
}
|
|
1574
1697
|
},
|
|
1575
1698
|
"additionalProperties": false
|
|
@@ -1762,7 +1885,9 @@
|
|
|
1762
1885
|
"parent": {
|
|
1763
1886
|
"type": "object",
|
|
1764
1887
|
"description": "The page that contains the comment",
|
|
1765
|
-
"required": [
|
|
1888
|
+
"required": [
|
|
1889
|
+
"page_id"
|
|
1890
|
+
],
|
|
1766
1891
|
"properties": {
|
|
1767
1892
|
"page_id": {
|
|
1768
1893
|
"type": "string",
|
|
@@ -1774,11 +1899,15 @@
|
|
|
1774
1899
|
"type": "array",
|
|
1775
1900
|
"items": {
|
|
1776
1901
|
"type": "object",
|
|
1777
|
-
"required": [
|
|
1902
|
+
"required": [
|
|
1903
|
+
"text"
|
|
1904
|
+
],
|
|
1778
1905
|
"properties": {
|
|
1779
1906
|
"text": {
|
|
1780
1907
|
"type": "object",
|
|
1781
|
-
"required": [
|
|
1908
|
+
"required": [
|
|
1909
|
+
"content"
|
|
1910
|
+
],
|
|
1782
1911
|
"properties": {
|
|
1783
1912
|
"content": {
|
|
1784
1913
|
"type": "string",
|