├── .eslintignore
├── .eslintrc
├── .github
└── workflows
│ ├── gh-pages.yml
│ ├── publish.yml
│ └── tests.yml
├── .gitignore
├── .npmignore
├── .prettierignore
├── .prettierrc
├── LICENSE
├── README.md
├── examples
├── .eslintrc
├── README.md
├── getCurrentMemberInfo.ts
├── listCustomFields.ts
├── logo.png
└── uploadFileToStory.ts
├── package.json
├── schema
└── shortcut.swagger.json
├── scripts
└── add-typedoc-comments.ts
├── src
├── ShortcutClient.ts
├── __tests__
│ ├── ShortcutApi-unmock-test.ts
│ └── index-test.ts
├── generated
│ ├── Api.ts
│ ├── data-contracts.ts
│ └── http-client.ts
├── index.ts
└── types.d.ts
├── templates
└── http-client.ejs
├── tsconfig.json
├── tsup.config.ts
├── typedoc.json
└── yarn.lock
/.eslintignore:
--------------------------------------------------------------------------------
1 | /src/generated
2 | /lib
3 |
--------------------------------------------------------------------------------
/.eslintrc:
--------------------------------------------------------------------------------
1 | {
2 | "parser": "@typescript-eslint/parser",
3 | "extends": [
4 | "airbnb-base",
5 | "plugin:@typescript-eslint/recommended",
6 | "prettier",
7 | "plugin:prettier/recommended"
8 | ],
9 | "parserOptions": {
10 | "sourceType": "module"
11 | },
12 | "settings": {
13 | "import/extensions": [
14 | ".js",
15 | ".ts"
16 | ],
17 | "import/parsers": {
18 | "@typescript-eslint/parser": [
19 | ".ts"
20 | ]
21 | },
22 | "import/resolver": {
23 | "node": {
24 | "extensions": [
25 | ".js",
26 | ".ts"
27 | ]
28 | }
29 | }
30 | },
31 | "plugins": [
32 | "import",
33 | "jest",
34 | "prettier"
35 | ],
36 | "env": {
37 | "jest": true,
38 | "es6": true
39 | },
40 | "rules": {
41 | "no-undef": 0,
42 | "import/extensions": 0,
43 | "import/prefer-default-export": 0,
44 | "@typescript-eslint/camelcase": 0,
45 | "@typescript-eslint/no-explicit-any": 0,
46 | "no-restricted-exports": 0
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/.github/workflows/gh-pages.yml:
--------------------------------------------------------------------------------
1 | name: "GitHub Pages"
2 |
3 | on:
4 | push:
5 | branches:
6 | - main
7 |
8 | jobs:
9 | deploy:
10 | runs-on: ubuntu-latest
11 | permissions:
12 | contents: write # Required for deploying pages
13 | pages: write # Required for deploying pages
14 | steps:
15 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
16 |
17 | - name: Setup Node
18 | uses: actions/setup-node@cdca7365b2dadb8aad0a33bc7601856ffabcc48e # v4.3.0
19 | with:
20 | node-version: 'lts/*'
21 | cache: 'yarn'
22 |
23 | - run: yarn install
24 | - run: yarn build:client
25 | - run: yarn build:docs
26 |
27 | - name: Deploy
28 | uses: peaceiris/actions-gh-pages@4f9cc6602d3f66b9c108549d475ec49e8ef4d45e # v4.0.0
29 | with:
30 | github_token: ${{ secrets.GITHUB_TOKEN }}
31 | publish_dir: ./docs
32 |
--------------------------------------------------------------------------------
/.github/workflows/publish.yml:
--------------------------------------------------------------------------------
1 | name: Publish Package to npmjs
2 |
3 | on:
4 | release:
5 | types: [created]
6 |
7 | jobs:
8 | publish:
9 | runs-on: ubuntu-latest
10 | permissions:
11 | contents: read
12 | id-token: write
13 | steps:
14 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
15 | - uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
16 | with:
17 | node-version: '22.x'
18 | cache: 'yarn'
19 | registry-url: 'https://registry.npmjs.org'
20 | - name: Install dependencies
21 | run: yarn --frozen-lockfile
22 | - run: npm publish --provenance --access public
23 | env:
24 | NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
25 | - name: Rename package to @useshortcut/client
26 | run: |
27 | sed -i 's/"name": ".*"/"name": "@useshortcut\/client"/' package.json
28 | - name: Publish under @useshortcut scope
29 | run: npm publish --provenance --access public
30 | env:
31 | NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
32 |
--------------------------------------------------------------------------------
/.github/workflows/tests.yml:
--------------------------------------------------------------------------------
1 | name: Tests
2 |
3 | on:
4 | pull_request:
5 | push:
6 | branches:
7 | - main
8 |
9 | jobs:
10 | lint:
11 | runs-on: ubuntu-latest
12 | steps:
13 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
14 | - name: Use Node.js
15 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
16 | with:
17 | node-version: '22.x'
18 | cache: 'yarn'
19 | - name: Install dependencies
20 | run: yarn install --frozen-lockfile
21 | - name: Run linter
22 | run: yarn lint
23 |
24 | validate-schema:
25 | runs-on: ubuntu-latest
26 | steps:
27 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
28 | - name: Use Node.js
29 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
30 | with:
31 | node-version: '22.x'
32 | cache: 'yarn'
33 | - name: Install dependencies
34 | run: yarn install --frozen-lockfile
35 | - name: Validate schema
36 | run: yarn validate:schema
37 |
38 | test:
39 | runs-on: ubuntu-latest
40 | steps:
41 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
42 | - name: Use Node.js
43 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
44 | with:
45 | node-version: '22.x'
46 | cache: 'yarn'
47 | - name: Install dependencies
48 | run: yarn install --frozen-lockfile
49 | - name: Run Jest
50 | run: yarn test
51 |
52 | format-check:
53 | runs-on: ubuntu-latest
54 | steps:
55 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
56 | - name: Use Node.js
57 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
58 | with:
59 | node-version: '22.x'
60 | cache: 'yarn'
61 | - name: Install dependencies
62 | run: yarn install --frozen-lockfile
63 | - name: Check formatting
64 | run: yarn format:check
65 |
66 | validate-examples:
67 | runs-on: ubuntu-latest
68 | steps:
69 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
70 | - name: Use Node.js
71 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
72 | with:
73 | node-version: '22.x'
74 | cache: 'yarn'
75 | - name: Install dependencies
76 | run: yarn install --frozen-lockfile
77 | - name: Validate examples (run tsc)
78 | run: yarn validate:examples
79 |
80 | build:
81 | runs-on: ubuntu-latest
82 | steps:
83 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
84 | - name: Use Node.js
85 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
86 | with:
87 | node-version: '22.x'
88 | cache: 'yarn'
89 | - name: Install dependencies
90 | run: yarn install --frozen-lockfile
91 | - name: Build
92 | run: yarn build
93 |
94 | check-exports:
95 | runs-on: ubuntu-latest
96 | steps:
97 | - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
98 | - name: Use Node.js
99 | uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0
100 | with:
101 | node-version: '22.x'
102 | cache: 'yarn'
103 | - name: Install dependencies
104 | run: yarn install --frozen-lockfile
105 | - name: Check exports
106 | run: yarn check-exports
107 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .DS_Store
2 |
3 | lib/
4 | node_modules/
5 | npm-debug.log
6 | package-lock.json
7 | /docs
8 | *.log
9 |
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | *~
2 | .DS_Store
3 | /src
4 | **/__tests__/**
5 | /docs
6 | /schema
7 |
--------------------------------------------------------------------------------
/.prettierignore:
--------------------------------------------------------------------------------
1 | /src/generated
2 | /schema
3 | /lib
4 |
--------------------------------------------------------------------------------
/.prettierrc:
--------------------------------------------------------------------------------
1 | {
2 | "singleQuote": true,
3 | "semi": true,
4 | "trailingComma": "all",
5 | "arrowParens": "always",
6 | "overrides": [
7 | {
8 | "files": "*.ts",
9 | "options": {
10 | "parser": "typescript"
11 | }
12 | }
13 | ]
14 | }
15 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2025 Shortcut
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # @shortcut/client
2 |
3 |
4 |
5 | [](https://badge.fury.io/js/@shortcut%2Fclient)
6 | [](https://www.npmjs.org/package/@shortcut%2Fclient)
7 | [](https://github.com/useshortcut/shortcut-client-js/blob/main/LICENSE)
8 | []()
9 | [](https://twitter.com/intent/follow?screen_name=shortcut)
10 |
11 | A library for interacting with the Shortcut REST API.
12 |
13 |
14 |
15 | ## Getting Started
16 |
17 | ### Installation
18 |
19 | ```shell
20 | npm install @shortcut/client
21 | ```
22 |
23 | > [!IMPORTANT]
24 | > Our legacy npm organization namespace is `@useshortcut`.
25 | >
26 | > While it will still contain copies of all future released package versions, we **strongly** recommend switching to our primary `@shortcut` organization namespace.
27 |
28 | ### How to Get an API Token
29 |
30 | The Shortcut API uses token-based authentication, you will need one to use this library.
31 |
32 | To generate an API token, go to https://app.shortcut.com/settings/account/api-tokens.
33 |
34 | To make it easier to explore our API, we recommend saving this token as an environment variable in your local dev environment:
35 |
36 | ```bash
37 | export SHORTCUT_API_TOKEN="YOUR API TOKEN HERE"
38 | ```
39 |
40 | This will allow you to copy and paste many examples in the documentation to try them out.
41 |
42 | > [!NOTE]
43 | > Requests made with a missing or invalid token will get a `401 Unauthorized` response.
44 |
45 | > [!NOTE]
46 | > All requests must be made over HTTPS.
47 |
48 | > [!CAUTION]
49 | > Tokens provide complete access to your Shortcut account, **so keep them secure**.
50 | >
51 | > Don’t paste them into your source code, use an environment variable instead.
52 | >
53 | > For security reasons, we will immediately invalidate any tokens we find have been made public.
54 |
55 | ## Usage
56 |
57 | To see all available exports, take a look at the [API documentation](https://useshortcut.github.io/shortcut-client-js/) or check out the `.d.ts` files in this repository.
58 |
59 | ```javascript
60 | import { ShortcutClient } from '@shortcut/client';
61 | // const { ShortcutClient } = require('@shortcut/client');
62 |
63 | const shortcut = new ShortcutClient('YOUR_API_TOKEN'); // See https://github.com/useshortcut/shortcut-client-js#how-to-get-an-api-token
64 |
65 | shortcut.getCurrentMemberInfo().then((response) => console.log(response?.data));
66 |
67 | shortcut.listProjects().then((response) => console.log(response?.data));
68 | ```
69 |
70 | ## Play with It
71 |
72 | You can play with it in your web browser with this live playground:
73 |
74 | - [CodeSandbox](https://codesandbox.io/s/useshortcut-client-playground-48kq1)
75 |
76 | ## Documentation
77 |
78 | [Documentation for this client](https://useshortcut.github.io/shortcut-client-js/).
79 |
80 | [Documentation for the REST API](https://developer.shortcut.com/api/rest/v3).
81 |
--------------------------------------------------------------------------------
/examples/.eslintrc:
--------------------------------------------------------------------------------
1 | {
2 | "rules": {
3 | "no-console": 0,
4 | "import/no-extraneous-dependencies": 0
5 | }
6 | }
7 |
--------------------------------------------------------------------------------
/examples/README.md:
--------------------------------------------------------------------------------
1 | # Examples
2 |
3 | This folder contains ready-to-use examples.
4 |
5 | ## Usage
6 |
7 | You will need to set an environment variable with your API Token. See [How to Get an API Token](../README.md#how-to-get-an-api-token).
8 |
9 | Then, you can run the file you want with:
10 |
11 | ```bash
12 | SHORTCUT_API_TOKEN=YOUR_API_TOKEN npx ts-node FILE_EXAMPLE
13 | ```
--------------------------------------------------------------------------------
/examples/getCurrentMemberInfo.ts:
--------------------------------------------------------------------------------
1 | import { ShortcutClient } from '../src';
2 |
3 | const shortcut = new ShortcutClient(process.env.SHORTCUT_API_TOKEN); // See https://github.com/useshortcut/shortcut-client-js#how-to-get-an-api-token
4 |
5 | shortcut.getCurrentMemberInfo().then((response) => console.log(response?.data));
6 |
--------------------------------------------------------------------------------
/examples/listCustomFields.ts:
--------------------------------------------------------------------------------
1 | import { ShortcutClient } from '../src';
2 |
3 | const shortcut = new ShortcutClient(process.env.SHORTCUT_API_TOKEN); // See https://github.com/useshortcut/shortcut-client-js#how-to-get-an-api-token
4 |
5 | shortcut.listCustomFields().then((response) => console.log(response?.data));
6 |
--------------------------------------------------------------------------------
/examples/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/useshortcut/shortcut-client-js/732948ceb1c60ba15006f6621673c73e1c3bd5d4/examples/logo.png
--------------------------------------------------------------------------------
/examples/uploadFileToStory.ts:
--------------------------------------------------------------------------------
1 | import * as fs from 'fs';
2 | import * as streamToBlob from 'stream-to-blob';
3 |
4 | import { ShortcutClient } from '../src';
5 |
6 | (async () => {
7 | const shortcut = new ShortcutClient(process.env.SHORTCUT_API_TOKEN); // See https://github.com/useshortcut/shortcut-client-js#how-to-get-an-api-token
8 |
9 | const FILE_PATH = `${__dirname}/logo.png`;
10 |
11 | const { data: workflows } = await shortcut.listWorkflows();
12 |
13 | const { data: story } = await shortcut.createStory({
14 | name: 'Upload a file to a story',
15 | workflow_state_id: workflows[0].states[0].id,
16 | });
17 |
18 | console.log('Story created with ID:', story.id);
19 |
20 | // This is proper to Node, replace this based on your environment
21 | const fileStream = fs.createReadStream(FILE_PATH);
22 |
23 | const { data: file } = await shortcut.uploadFiles({
24 | story_id: story.id,
25 | file0: (await streamToBlob(fileStream)) as any, // On Web, this is expecting a File object, but on Node, it's a ReadableStream
26 | });
27 |
28 | console.log(file);
29 | })();
30 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@shortcut/client",
3 | "version": "2.0.0",
4 | "description": "A Promise based library to the Shortcut REST API",
5 | "homepage": "https://github.com/useshortcut/shortcut-client-js",
6 | "bugs": {
7 | "url": "https://github.com/useshortcut/shortcut-client-js/issues"
8 | },
9 | "repository": {
10 | "type": "git",
11 | "url": "https://github.com/useshortcut/shortcut-client-js.git"
12 | },
13 | "license": "MIT",
14 | "sideEffects": false,
15 | "type": "commonjs",
16 | "exports": {
17 | ".": {
18 | "import": {
19 | "types": "./lib/index.d.mts",
20 | "default": "./lib/index.mjs"
21 | },
22 | "require": {
23 | "types": "./lib/index.d.ts",
24 | "default": "./lib/index.js"
25 | }
26 | }
27 | },
28 | "main": "./lib/index.js",
29 | "module": "./lib/index.mjs",
30 | "types": "./lib/index.d.ts",
31 | "files": [
32 | "lib"
33 | ],
34 | "scripts": {
35 | "build": "yarn build:client && yarn build:add-typedoc-comments && tsup",
36 | "build:add-typedoc-comments": "npx jscodeshift -t scripts/add-typedoc-comments.ts --extensions=ts --parser=ts src/generated/**",
37 | "build:client": "swagger-typescript-api generate --path ./schema/shortcut.swagger.json --output ./src/generated --clean-output --axios --modular --templates ./templates",
38 | "build:docs": "typedoc ./src --exclude 'src/__tests__/**'",
39 | "check-exports": "attw --pack .",
40 | "format": "prettier --write -l *.{json,md,prettierrc} '{src,scripts}/**/*.ts'",
41 | "format:check": "prettier --check *.{json,md,prettierrc} '{src,scripts}/**/*.ts'",
42 | "lint": "eslint 'src/**/*.{js,ts}'",
43 | "prepublishOnly": "yarn build",
44 | "sync:schema": "curl --silent https://developer.shortcut.com/api/rest/v3/shortcut.swagger.json --output ./schema/shortcut.swagger.json && yarn validate:schema",
45 | "test": "jest",
46 | "validate:examples": "npx tsc examples/*.ts --noEmit",
47 | "validate:schema": "swagger-cli validate ./schema/shortcut.swagger.json"
48 | },
49 | "jest": {
50 | "preset": "ts-jest",
51 | "testEnvironment": "node",
52 | "testPathIgnorePatterns": [
53 | "/lib/",
54 | "/node_modules/"
55 | ]
56 | },
57 | "dependencies": {
58 | "axios": "^1.9.0"
59 | },
60 | "devDependencies": {
61 | "@arethetypeswrong/cli": "^0.18.1",
62 | "@total-typescript/tsconfig": "^1.0.4",
63 | "@types/glob": "^8.1.0",
64 | "@types/jest": "^29.5.14",
65 | "@types/jscodeshift": "17.3.0",
66 | "@types/node": "^22.15.30",
67 | "@typescript-eslint/eslint-plugin": "^8.33.1",
68 | "@typescript-eslint/parser": "^8.33.1",
69 | "eslint": "^8.57.1",
70 | "eslint-config-airbnb-base": "^15.0.0",
71 | "eslint-config-prettier": "^10.1.5",
72 | "eslint-plugin-import": "^2.31.0",
73 | "eslint-plugin-jest": "^28.12.0",
74 | "eslint-plugin-prettier": "^5.4.1",
75 | "glob": "^11.0.2",
76 | "jest": "^29.7.0",
77 | "jscodeshift": "^17.3.0",
78 | "prettier": "^3.5.3",
79 | "stream-to-blob": "^2.0.1",
80 | "swagger-cli": "^4.0.4",
81 | "swagger-typescript-api": "^13.2.0",
82 | "ts-jest": "^29.3.4",
83 | "tsup": "^8.5.0",
84 | "typedoc": "0.28.5",
85 | "typedoc-plugin-merge-modules": "7.0.0",
86 | "typescript": "^5.8.3"
87 | },
88 | "readme": "https://github.com/useshortcut/shortcut-client-js#readme"
89 | }
90 |
--------------------------------------------------------------------------------
/scripts/add-typedoc-comments.ts:
--------------------------------------------------------------------------------
1 | import { API, FileInfo } from 'jscodeshift';
2 |
3 | export default function transformer(file: FileInfo, api: API) {
4 | const j = api.jscodeshift;
5 | const root = j(file.source);
6 |
7 | return root
8 | .find(j.ClassDeclaration)
9 | .filter(
10 | (path) =>
11 | path.value.id?.type === 'Identifier' &&
12 | ['Api', 'HttpClient'].includes(path.value.id.name),
13 | )
14 | .forEach((path) => {
15 | const target =
16 | path.parent.value.type === 'ExportNamedDeclaration'
17 | ? path.parent
18 | : path;
19 |
20 | const desc =
21 | path.value.id?.name === 'Api'
22 | ? "\n * Please don't use this class directly, instead use the `ShortcutClient` class we provided which is extending this class to add headers for authorization."
23 | : '\n';
24 |
25 | target.insertBefore(`/** ${desc} * @internal\n * @private\n */`);
26 | })
27 | .toSource();
28 | }
29 |
--------------------------------------------------------------------------------
/src/ShortcutClient.ts:
--------------------------------------------------------------------------------
1 | import { Api } from './generated/Api';
2 | import type { ApiConfig } from './generated/http-client';
3 |
4 | export class ShortcutClient<
5 | SecurityDataType = unknown,
6 | > extends Api {
7 | constructor(apiToken: string, config: ApiConfig = {}) {
8 | if (apiToken == null || typeof apiToken !== 'string') {
9 | // eslint-disable-next-line no-console
10 | console.error('You need to supply an API Token.');
11 | }
12 |
13 | super({
14 | headers: { 'Shortcut-Token': apiToken, ...config.headers },
15 | ...config,
16 | });
17 | }
18 | }
19 |
--------------------------------------------------------------------------------
/src/__tests__/ShortcutApi-unmock-test.ts:
--------------------------------------------------------------------------------
1 | import { ShortcutClient } from '../ShortcutClient';
2 |
3 | jest.unmock('axios');
4 |
5 | describe('ShortcutClient', () => {
6 | const token = 'SOME-TOKEN';
7 |
8 | it('uses the expected baseURL', () => {
9 | const shortcut = new ShortcutClient(token);
10 |
11 | expect(shortcut.instance.defaults.baseURL).toBe(
12 | 'https://api.app.shortcut.com',
13 | );
14 | });
15 |
16 | it('adds Shortcut-Token to default headers', async () => {
17 | const shortcut = new ShortcutClient(token);
18 |
19 | expect(shortcut.instance.defaults.headers).toHaveProperty(
20 | 'Shortcut-Token',
21 | token,
22 | );
23 | });
24 | });
25 |
--------------------------------------------------------------------------------
/src/__tests__/index-test.ts:
--------------------------------------------------------------------------------
1 | import { ShortcutClient } from '../index';
2 |
3 | describe('index', () => {
4 | it('exposes ShortcutClient', () => {
5 | expect(ShortcutClient).toBeDefined();
6 | });
7 | });
8 |
--------------------------------------------------------------------------------
/src/generated/Api.ts:
--------------------------------------------------------------------------------
1 | /* eslint-disable */
2 | /* tslint:disable */
3 | // @ts-nocheck
4 | /*
5 | * ---------------------------------------------------------------
6 | * ## THIS FILE WAS GENERATED VIA SWAGGER-TYPESCRIPT-API ##
7 | * ## ##
8 | * ## AUTHOR: acacode ##
9 | * ## SOURCE: https://github.com/acacode/swagger-typescript-api ##
10 | * ---------------------------------------------------------------
11 | */
12 |
13 | import {
14 | Category,
15 | CreateCategory,
16 | CreateCommentComment,
17 | CreateEntityTemplate,
18 | CreateEpic,
19 | CreateEpicComment,
20 | CreateEpicHealth,
21 | CreateGenericIntegration,
22 | CreateGroup,
23 | CreateIteration,
24 | CreateLabelParams,
25 | CreateLinkedFile,
26 | CreateMilestone,
27 | CreateObjective,
28 | CreateOrDeleteStoryReaction,
29 | CreateProject,
30 | CreateStories,
31 | CreateStoryComment,
32 | CreateStoryFromTemplateParams,
33 | CreateStoryLink,
34 | CreateStoryParams,
35 | CreateTask,
36 | CustomField,
37 | DataConflictError,
38 | DeleteStories,
39 | EntityTemplate,
40 | Epic,
41 | EpicPaginatedResults,
42 | EpicSearchResults,
43 | EpicSlim,
44 | EpicWorkflow,
45 | Group,
46 | Health,
47 | History,
48 | Iteration,
49 | IterationSearchResults,
50 | IterationSlim,
51 | KeyResult,
52 | Label,
53 | LinkedFile,
54 | MaxSearchResultsExceededError,
55 | Member,
56 | MemberInfo,
57 | Milestone,
58 | Objective,
59 | ObjectiveSearchResults,
60 | Project,
61 | Repository,
62 | SearchResults,
63 | SearchStories,
64 | Story,
65 | StoryComment,
66 | StoryLink,
67 | StoryReaction,
68 | StorySearchResults,
69 | StorySlim,
70 | Task,
71 | ThreadedComment,
72 | UnusableEntitlementError,
73 | UpdateCategory,
74 | UpdateComment,
75 | UpdateCustomField,
76 | UpdateEntityTemplate,
77 | UpdateEpic,
78 | UpdateFile,
79 | UpdateGroup,
80 | UpdateHealth,
81 | UpdateIteration,
82 | UpdateKeyResult,
83 | UpdateLabel,
84 | UpdateLinkedFile,
85 | UpdateMilestone,
86 | UpdateObjective,
87 | UpdateProject,
88 | UpdateStories,
89 | UpdateStory,
90 | UpdateStoryComment,
91 | UpdateStoryLink,
92 | UpdateTask,
93 | UploadedFile,
94 | Workflow,
95 | } from "./data-contracts";
96 | import { ContentType, HttpClient, RequestParams } from "./http-client";
97 |
98 | /**
99 | * Please don't use this class directly, instead use the `ShortcutClient` class we provided which is extending this class to add headers for authorization. * @internal
100 | * @private
101 | */
102 |
103 | export class Api<
104 | SecurityDataType = unknown,
105 | > extends HttpClient {
106 | /**
107 | * @description List Categories returns a list of all Categories and their attributes.
108 | *
109 | * @name ListCategories
110 | * @summary List Categories
111 | * @request GET:/api/v3/categories
112 | * @secure
113 | */
114 | listCategories = (params: RequestParams = {}) =>
115 | this.request({
116 | path: `/api/v3/categories`,
117 | method: "GET",
118 | secure: true,
119 | format: "json",
120 | ...params,
121 | });
122 | /**
123 | * @description Create Category allows you to create a new Category in Shortcut.
124 | *
125 | * @name CreateCategory
126 | * @summary Create Category
127 | * @request POST:/api/v3/categories
128 | * @secure
129 | */
130 | createCategory = (
131 | CreateCategory: CreateCategory,
132 | params: RequestParams = {},
133 | ) =>
134 | this.request({
135 | path: `/api/v3/categories`,
136 | method: "POST",
137 | body: CreateCategory,
138 | secure: true,
139 | type: ContentType.Json,
140 | format: "json",
141 | ...params,
142 | });
143 | /**
144 | * @description Get Category returns information about the selected Category.
145 | *
146 | * @name GetCategory
147 | * @summary Get Category
148 | * @request GET:/api/v3/categories/{category-public-id}
149 | * @secure
150 | */
151 | getCategory = (categoryPublicId: number, params: RequestParams = {}) =>
152 | this.request({
153 | path: `/api/v3/categories/${categoryPublicId}`,
154 | method: "GET",
155 | secure: true,
156 | format: "json",
157 | ...params,
158 | });
159 | /**
160 | * @description Update Category allows you to replace a Category name with another name. If you try to name a Category something that already exists, you will receive a 422 response.
161 | *
162 | * @name UpdateCategory
163 | * @summary Update Category
164 | * @request PUT:/api/v3/categories/{category-public-id}
165 | * @secure
166 | */
167 | updateCategory = (
168 | categoryPublicId: number,
169 | UpdateCategory: UpdateCategory,
170 | params: RequestParams = {},
171 | ) =>
172 | this.request({
173 | path: `/api/v3/categories/${categoryPublicId}`,
174 | method: "PUT",
175 | body: UpdateCategory,
176 | secure: true,
177 | type: ContentType.Json,
178 | format: "json",
179 | ...params,
180 | });
181 | /**
182 | * @description Delete Category can be used to delete any Category.
183 | *
184 | * @name DeleteCategory
185 | * @summary Delete Category
186 | * @request DELETE:/api/v3/categories/{category-public-id}
187 | * @secure
188 | */
189 | deleteCategory = (categoryPublicId: number, params: RequestParams = {}) =>
190 | this.request({
191 | path: `/api/v3/categories/${categoryPublicId}`,
192 | method: "DELETE",
193 | secure: true,
194 | ...params,
195 | });
196 | /**
197 | * @description List Category Milestones returns a list of all Milestones with the Category.
198 | *
199 | * @name ListCategoryMilestones
200 | * @summary List Category Milestones
201 | * @request GET:/api/v3/categories/{category-public-id}/milestones
202 | * @secure
203 | */
204 | listCategoryMilestones = (
205 | categoryPublicId: number,
206 | params: RequestParams = {},
207 | ) =>
208 | this.request({
209 | path: `/api/v3/categories/${categoryPublicId}/milestones`,
210 | method: "GET",
211 | secure: true,
212 | format: "json",
213 | ...params,
214 | });
215 | /**
216 | * @description Returns a list of all Objectives with the Category.
217 | *
218 | * @name ListCategoryObjectives
219 | * @summary List Category Objectives
220 | * @request GET:/api/v3/categories/{category-public-id}/objectives
221 | * @secure
222 | */
223 | listCategoryObjectives = (
224 | categoryPublicId: number,
225 | params: RequestParams = {},
226 | ) =>
227 | this.request({
228 | path: `/api/v3/categories/${categoryPublicId}/objectives`,
229 | method: "GET",
230 | secure: true,
231 | format: "json",
232 | ...params,
233 | });
234 | /**
235 | * No description
236 | *
237 | * @name ListCustomFields
238 | * @summary List Custom Fields
239 | * @request GET:/api/v3/custom-fields
240 | * @secure
241 | */
242 | listCustomFields = (params: RequestParams = {}) =>
243 | this.request({
244 | path: `/api/v3/custom-fields`,
245 | method: "GET",
246 | secure: true,
247 | format: "json",
248 | ...params,
249 | });
250 | /**
251 | * No description
252 | *
253 | * @name GetCustomField
254 | * @summary Get Custom Field
255 | * @request GET:/api/v3/custom-fields/{custom-field-public-id}
256 | * @secure
257 | */
258 | getCustomField = (customFieldPublicId: string, params: RequestParams = {}) =>
259 | this.request({
260 | path: `/api/v3/custom-fields/${customFieldPublicId}`,
261 | method: "GET",
262 | secure: true,
263 | format: "json",
264 | ...params,
265 | });
266 | /**
267 | * @description Update Custom Field can be used to update the definition of a Custom Field. The order of items in the 'values' collection is interpreted to be their ascending sort order.To delete an existing enum value, simply omit it from the 'values' collection. New enum values may be created inline by including an object in the 'values' collection having a 'value' entry with no 'id' (eg. {'value': 'myNewValue', 'color_key': 'green'}).
268 | *
269 | * @name UpdateCustomField
270 | * @summary Update Custom Field
271 | * @request PUT:/api/v3/custom-fields/{custom-field-public-id}
272 | * @secure
273 | */
274 | updateCustomField = (
275 | customFieldPublicId: string,
276 | UpdateCustomField: UpdateCustomField,
277 | params: RequestParams = {},
278 | ) =>
279 | this.request({
280 | path: `/api/v3/custom-fields/${customFieldPublicId}`,
281 | method: "PUT",
282 | body: UpdateCustomField,
283 | secure: true,
284 | type: ContentType.Json,
285 | format: "json",
286 | ...params,
287 | });
288 | /**
289 | * No description
290 | *
291 | * @name DeleteCustomField
292 | * @summary Delete Custom Field
293 | * @request DELETE:/api/v3/custom-fields/{custom-field-public-id}
294 | * @secure
295 | */
296 | deleteCustomField = (
297 | customFieldPublicId: string,
298 | params: RequestParams = {},
299 | ) =>
300 | this.request({
301 | path: `/api/v3/custom-fields/${customFieldPublicId}`,
302 | method: "DELETE",
303 | secure: true,
304 | ...params,
305 | });
306 | /**
307 | * @description List all the entity templates for the Workspace.
308 | *
309 | * @name ListEntityTemplates
310 | * @summary List Entity Templates
311 | * @request GET:/api/v3/entity-templates
312 | * @secure
313 | */
314 | listEntityTemplates = (params: RequestParams = {}) =>
315 | this.request({
316 | path: `/api/v3/entity-templates`,
317 | method: "GET",
318 | secure: true,
319 | format: "json",
320 | ...params,
321 | });
322 | /**
323 | * @description Create a new entity template for the Workspace.
324 | *
325 | * @name CreateEntityTemplate
326 | * @summary Create Entity Template
327 | * @request POST:/api/v3/entity-templates
328 | * @secure
329 | */
330 | createEntityTemplate = (
331 | CreateEntityTemplate: CreateEntityTemplate,
332 | params: RequestParams = {},
333 | ) =>
334 | this.request({
335 | path: `/api/v3/entity-templates`,
336 | method: "POST",
337 | body: CreateEntityTemplate,
338 | secure: true,
339 | type: ContentType.Json,
340 | format: "json",
341 | ...params,
342 | });
343 | /**
344 | * @description Disables the Story Template feature for the Workspace.
345 | *
346 | * @name DisableStoryTemplates
347 | * @summary Disable Story Templates
348 | * @request PUT:/api/v3/entity-templates/disable
349 | * @secure
350 | */
351 | disableStoryTemplates = (params: RequestParams = {}) =>
352 | this.request({
353 | path: `/api/v3/entity-templates/disable`,
354 | method: "PUT",
355 | secure: true,
356 | ...params,
357 | });
358 | /**
359 | * @description Enables the Story Template feature for the Workspace.
360 | *
361 | * @name EnableStoryTemplates
362 | * @summary Enable Story Templates
363 | * @request PUT:/api/v3/entity-templates/enable
364 | * @secure
365 | */
366 | enableStoryTemplates = (params: RequestParams = {}) =>
367 | this.request({
368 | path: `/api/v3/entity-templates/enable`,
369 | method: "PUT",
370 | secure: true,
371 | ...params,
372 | });
373 | /**
374 | * @description Get Entity Template returns information about a given entity template.
375 | *
376 | * @name GetEntityTemplate
377 | * @summary Get Entity Template
378 | * @request GET:/api/v3/entity-templates/{entity-template-public-id}
379 | * @secure
380 | */
381 | getEntityTemplate = (
382 | entityTemplatePublicId: string,
383 | params: RequestParams = {},
384 | ) =>
385 | this.request({
386 | path: `/api/v3/entity-templates/${entityTemplatePublicId}`,
387 | method: "GET",
388 | secure: true,
389 | format: "json",
390 | ...params,
391 | });
392 | /**
393 | * @description Update an entity template's name or its contents.
394 | *
395 | * @name UpdateEntityTemplate
396 | * @summary Update Entity Template
397 | * @request PUT:/api/v3/entity-templates/{entity-template-public-id}
398 | * @secure
399 | */
400 | updateEntityTemplate = (
401 | entityTemplatePublicId: string,
402 | UpdateEntityTemplate: UpdateEntityTemplate,
403 | params: RequestParams = {},
404 | ) =>
405 | this.request({
406 | path: `/api/v3/entity-templates/${entityTemplatePublicId}`,
407 | method: "PUT",
408 | body: UpdateEntityTemplate,
409 | secure: true,
410 | type: ContentType.Json,
411 | format: "json",
412 | ...params,
413 | });
414 | /**
415 | * No description
416 | *
417 | * @name DeleteEntityTemplate
418 | * @summary Delete Entity Template
419 | * @request DELETE:/api/v3/entity-templates/{entity-template-public-id}
420 | * @secure
421 | */
422 | deleteEntityTemplate = (
423 | entityTemplatePublicId: string,
424 | params: RequestParams = {},
425 | ) =>
426 | this.request({
427 | path: `/api/v3/entity-templates/${entityTemplatePublicId}`,
428 | method: "DELETE",
429 | secure: true,
430 | ...params,
431 | });
432 | /**
433 | * @description Returns the Epic Workflow for the Workspace.
434 | *
435 | * @name GetEpicWorkflow
436 | * @summary Get Epic Workflow
437 | * @request GET:/api/v3/epic-workflow
438 | * @secure
439 | */
440 | getEpicWorkflow = (params: RequestParams = {}) =>
441 | this.request({
442 | path: `/api/v3/epic-workflow`,
443 | method: "GET",
444 | secure: true,
445 | format: "json",
446 | ...params,
447 | });
448 | /**
449 | * @description List Epics returns a list of all Epics and their attributes.
450 | *
451 | * @name ListEpics
452 | * @summary List Epics
453 | * @request GET:/api/v3/epics
454 | * @secure
455 | */
456 | listEpics = (
457 | query?: {
458 | /** A true/false boolean indicating whether to return Epics with their descriptions. */
459 | includes_description?: boolean;
460 | },
461 | params: RequestParams = {},
462 | ) =>
463 | this.request({
464 | path: `/api/v3/epics`,
465 | method: "GET",
466 | query: query,
467 | secure: true,
468 | format: "json",
469 | ...params,
470 | });
471 | /**
472 | * @description Create Epic allows you to create a new Epic in Shortcut.
473 | *
474 | * @name CreateEpic
475 | * @summary Create Epic
476 | * @request POST:/api/v3/epics
477 | * @secure
478 | */
479 | createEpic = (CreateEpic: CreateEpic, params: RequestParams = {}) =>
480 | this.request({
481 | path: `/api/v3/epics`,
482 | method: "POST",
483 | body: CreateEpic,
484 | secure: true,
485 | type: ContentType.Json,
486 | format: "json",
487 | ...params,
488 | });
489 | /**
490 | * @description List Epics with pagination returns a paginated list of Epics and their attributes.
491 | *
492 | * @name ListEpicsPaginated
493 | * @summary List Epics Paginated
494 | * @request GET:/api/v3/epics/paginated
495 | * @secure
496 | */
497 | listEpicsPaginated = (
498 | query?: {
499 | /** A true/false boolean indicating whether to return Epics with their descriptions. */
500 | includes_description?: boolean;
501 | /**
502 | * The page number to return, starting with 1. Defaults to 1.
503 | * @format int64
504 | */
505 | page?: number;
506 | /**
507 | * The number of Epics to return per page. Minimum 1, maximum 250, default 10.
508 | * @format int64
509 | */
510 | page_size?: number;
511 | },
512 | params: RequestParams = {},
513 | ) =>
514 | this.request({
515 | path: `/api/v3/epics/paginated`,
516 | method: "GET",
517 | query: query,
518 | secure: true,
519 | format: "json",
520 | ...params,
521 | });
522 | /**
523 | * @description Get Epic returns information about the selected Epic.
524 | *
525 | * @name GetEpic
526 | * @summary Get Epic
527 | * @request GET:/api/v3/epics/{epic-public-id}
528 | * @secure
529 | */
530 | getEpic = (epicPublicId: number, params: RequestParams = {}) =>
531 | this.request({
532 | path: `/api/v3/epics/${epicPublicId}`,
533 | method: "GET",
534 | secure: true,
535 | format: "json",
536 | ...params,
537 | });
538 | /**
539 | * @description Update Epic can be used to update numerous fields in the Epic. The only required parameter is Epic ID, which can be found in the Shortcut UI.
540 | *
541 | * @name UpdateEpic
542 | * @summary Update Epic
543 | * @request PUT:/api/v3/epics/{epic-public-id}
544 | * @secure
545 | */
546 | updateEpic = (
547 | epicPublicId: number,
548 | UpdateEpic: UpdateEpic,
549 | params: RequestParams = {},
550 | ) =>
551 | this.request({
552 | path: `/api/v3/epics/${epicPublicId}`,
553 | method: "PUT",
554 | body: UpdateEpic,
555 | secure: true,
556 | type: ContentType.Json,
557 | format: "json",
558 | ...params,
559 | });
560 | /**
561 | * @description Delete Epic can be used to delete the Epic. The only required parameter is Epic ID.
562 | *
563 | * @name DeleteEpic
564 | * @summary Delete Epic
565 | * @request DELETE:/api/v3/epics/{epic-public-id}
566 | * @secure
567 | */
568 | deleteEpic = (epicPublicId: number, params: RequestParams = {}) =>
569 | this.request({
570 | path: `/api/v3/epics/${epicPublicId}`,
571 | method: "DELETE",
572 | secure: true,
573 | ...params,
574 | });
575 | /**
576 | * @description Get a list of all Comments on an Epic.
577 | *
578 | * @name ListEpicComments
579 | * @summary List Epic Comments
580 | * @request GET:/api/v3/epics/{epic-public-id}/comments
581 | * @secure
582 | */
583 | listEpicComments = (epicPublicId: number, params: RequestParams = {}) =>
584 | this.request({
585 | path: `/api/v3/epics/${epicPublicId}/comments`,
586 | method: "GET",
587 | secure: true,
588 | format: "json",
589 | ...params,
590 | });
591 | /**
592 | * @description This endpoint allows you to create a threaded Comment on an Epic.
593 | *
594 | * @name CreateEpicComment
595 | * @summary Create Epic Comment
596 | * @request POST:/api/v3/epics/{epic-public-id}/comments
597 | * @secure
598 | */
599 | createEpicComment = (
600 | epicPublicId: number,
601 | CreateEpicComment: CreateEpicComment,
602 | params: RequestParams = {},
603 | ) =>
604 | this.request({
605 | path: `/api/v3/epics/${epicPublicId}/comments`,
606 | method: "POST",
607 | body: CreateEpicComment,
608 | secure: true,
609 | type: ContentType.Json,
610 | format: "json",
611 | ...params,
612 | });
613 | /**
614 | * @description This endpoint allows you to create a nested Comment reply to an existing Epic Comment.
615 | *
616 | * @name CreateEpicCommentComment
617 | * @summary Create Epic Comment Comment
618 | * @request POST:/api/v3/epics/{epic-public-id}/comments/{comment-public-id}
619 | * @secure
620 | */
621 | createEpicCommentComment = (
622 | epicPublicId: number,
623 | commentPublicId: number,
624 | CreateCommentComment: CreateCommentComment,
625 | params: RequestParams = {},
626 | ) =>
627 | this.request({
628 | path: `/api/v3/epics/${epicPublicId}/comments/${commentPublicId}`,
629 | method: "POST",
630 | body: CreateCommentComment,
631 | secure: true,
632 | type: ContentType.Json,
633 | format: "json",
634 | ...params,
635 | });
636 | /**
637 | * @description This endpoint returns information about the selected Epic Comment.
638 | *
639 | * @name GetEpicComment
640 | * @summary Get Epic Comment
641 | * @request GET:/api/v3/epics/{epic-public-id}/comments/{comment-public-id}
642 | * @secure
643 | */
644 | getEpicComment = (
645 | epicPublicId: number,
646 | commentPublicId: number,
647 | params: RequestParams = {},
648 | ) =>
649 | this.request({
650 | path: `/api/v3/epics/${epicPublicId}/comments/${commentPublicId}`,
651 | method: "GET",
652 | secure: true,
653 | format: "json",
654 | ...params,
655 | });
656 | /**
657 | * @description This endpoint allows you to update a threaded Comment on an Epic.
658 | *
659 | * @name UpdateEpicComment
660 | * @summary Update Epic Comment
661 | * @request PUT:/api/v3/epics/{epic-public-id}/comments/{comment-public-id}
662 | * @secure
663 | */
664 | updateEpicComment = (
665 | epicPublicId: number,
666 | commentPublicId: number,
667 | UpdateComment: UpdateComment,
668 | params: RequestParams = {},
669 | ) =>
670 | this.request({
671 | path: `/api/v3/epics/${epicPublicId}/comments/${commentPublicId}`,
672 | method: "PUT",
673 | body: UpdateComment,
674 | secure: true,
675 | type: ContentType.Json,
676 | format: "json",
677 | ...params,
678 | });
679 | /**
680 | * @description This endpoint allows you to delete a Comment from an Epic.
681 | *
682 | * @name DeleteEpicComment
683 | * @summary Delete Epic Comment
684 | * @request DELETE:/api/v3/epics/{epic-public-id}/comments/{comment-public-id}
685 | * @secure
686 | */
687 | deleteEpicComment = (
688 | epicPublicId: number,
689 | commentPublicId: number,
690 | params: RequestParams = {},
691 | ) =>
692 | this.request({
693 | path: `/api/v3/epics/${epicPublicId}/comments/${commentPublicId}`,
694 | method: "DELETE",
695 | secure: true,
696 | ...params,
697 | });
698 | /**
699 | * @description Get the current health for the specified Epic.
700 | *
701 | * @name GetEpicHealth
702 | * @summary Get Epic Health
703 | * @request GET:/api/v3/epics/{epic-public-id}/health
704 | * @secure
705 | */
706 | getEpicHealth = (epicPublicId: number, params: RequestParams = {}) =>
707 | this.request({
708 | path: `/api/v3/epics/${epicPublicId}/health`,
709 | method: "GET",
710 | secure: true,
711 | format: "json",
712 | ...params,
713 | });
714 | /**
715 | * @description Create a new health status for the specified Epic.
716 | *
717 | * @name CreateEpicHealth
718 | * @summary Create Epic Health
719 | * @request POST:/api/v3/epics/{epic-public-id}/health
720 | * @secure
721 | */
722 | createEpicHealth = (
723 | epicPublicId: number,
724 | CreateEpicHealth: CreateEpicHealth,
725 | params: RequestParams = {},
726 | ) =>
727 | this.request({
728 | path: `/api/v3/epics/${epicPublicId}/health`,
729 | method: "POST",
730 | body: CreateEpicHealth,
731 | secure: true,
732 | type: ContentType.Json,
733 | format: "json",
734 | ...params,
735 | });
736 | /**
737 | * @description List the history of health statuses for the specified Epic, most recent first.
738 | *
739 | * @name ListEpicHealths
740 | * @summary List Epic Healths
741 | * @request GET:/api/v3/epics/{epic-public-id}/health-history
742 | * @secure
743 | */
744 | listEpicHealths = (epicPublicId: number, params: RequestParams = {}) =>
745 | this.request({
746 | path: `/api/v3/epics/${epicPublicId}/health-history`,
747 | method: "GET",
748 | secure: true,
749 | format: "json",
750 | ...params,
751 | });
752 | /**
753 | * @description Get a list of all Stories in an Epic.
754 | *
755 | * @name ListEpicStories
756 | * @summary List Epic Stories
757 | * @request GET:/api/v3/epics/{epic-public-id}/stories
758 | * @secure
759 | */
760 | listEpicStories = (
761 | epicPublicId: number,
762 | query?: {
763 | /** A true/false boolean indicating whether to return Stories with their descriptions. */
764 | includes_description?: boolean;
765 | },
766 | params: RequestParams = {},
767 | ) =>
768 | this.request({
769 | path: `/api/v3/epics/${epicPublicId}/stories`,
770 | method: "GET",
771 | query: query,
772 | secure: true,
773 | format: "json",
774 | ...params,
775 | });
776 | /**
777 | * @description This endpoint allows you to unlink a productboard epic.
778 | *
779 | * @name UnlinkProductboardFromEpic
780 | * @summary Unlink Productboard from Epic
781 | * @request POST:/api/v3/epics/{epic-public-id}/unlink-productboard
782 | * @secure
783 | */
784 | unlinkProductboardFromEpic = (
785 | epicPublicId: number,
786 | params: RequestParams = {},
787 | ) =>
788 | this.request({
789 | path: `/api/v3/epics/${epicPublicId}/unlink-productboard`,
790 | method: "POST",
791 | secure: true,
792 | ...params,
793 | });
794 | /**
795 | * @description Get Stories which have a given External Link associated with them.
796 | *
797 | * @name GetExternalLinkStories
798 | * @summary Get External Link Stories
799 | * @request GET:/api/v3/external-link/stories
800 | * @secure
801 | */
802 | getExternalLinkStories = (
803 | query: {
804 | /**
805 | * The external link associated with one or more stories.
806 | * @maxLength 2048
807 | * @pattern ^https?://.+$
808 | */
809 | external_link: string;
810 | },
811 | params: RequestParams = {},
812 | ) =>
813 | this.request({
814 | path: `/api/v3/external-link/stories`,
815 | method: "GET",
816 | query: query,
817 | secure: true,
818 | format: "json",
819 | ...params,
820 | });
821 | /**
822 | * @description List Files returns a list of all UploadedFiles in the workspace.
823 | *
824 | * @name ListFiles
825 | * @summary List Files
826 | * @request GET:/api/v3/files
827 | * @secure
828 | */
829 | listFiles = (params: RequestParams = {}) =>
830 | this.request({
831 | path: `/api/v3/files`,
832 | method: "GET",
833 | secure: true,
834 | format: "json",
835 | ...params,
836 | });
837 | /**
838 | * @description Upload Files uploads one or many files and optionally associates them with a story. Use the multipart/form-data content-type to upload. Each `file` key should contain a separate file. Each UploadedFile's name comes from the Content-Disposition header "filename" directive for that field.
839 | *
840 | * @name UploadFiles
841 | * @summary Upload Files
842 | * @request POST:/api/v3/files
843 | * @secure
844 | */
845 | uploadFiles = (
846 | data: {
847 | /**
848 | * The story ID that these files will be associated with.
849 | * @format int64
850 | */
851 | story_id?: number;
852 | /**
853 | * A file upload. At least one is required.
854 | * @format binary
855 | */
856 | file0: File;
857 | /**
858 | * Optional additional files.
859 | * @format binary
860 | */
861 | file1?: File;
862 | /**
863 | * Optional additional files.
864 | * @format binary
865 | */
866 | file2?: File;
867 | /**
868 | * Optional additional files.
869 | * @format binary
870 | */
871 | file3?: File;
872 | },
873 | params: RequestParams = {},
874 | ) =>
875 | this.request({
876 | path: `/api/v3/files`,
877 | method: "POST",
878 | body: data,
879 | secure: true,
880 | type: ContentType.FormData,
881 | format: "json",
882 | ...params,
883 | });
884 | /**
885 | * @description Get File returns information about the selected UploadedFile.
886 | *
887 | * @name GetFile
888 | * @summary Get File
889 | * @request GET:/api/v3/files/{file-public-id}
890 | * @secure
891 | */
892 | getFile = (filePublicId: number, params: RequestParams = {}) =>
893 | this.request({
894 | path: `/api/v3/files/${filePublicId}`,
895 | method: "GET",
896 | secure: true,
897 | format: "json",
898 | ...params,
899 | });
900 | /**
901 | * @description Update File updates the properties of an UploadedFile (but not its content).
902 | *
903 | * @name UpdateFile
904 | * @summary Update File
905 | * @request PUT:/api/v3/files/{file-public-id}
906 | * @secure
907 | */
908 | updateFile = (
909 | filePublicId: number,
910 | UpdateFile: UpdateFile,
911 | params: RequestParams = {},
912 | ) =>
913 | this.request({
914 | path: `/api/v3/files/${filePublicId}`,
915 | method: "PUT",
916 | body: UpdateFile,
917 | secure: true,
918 | type: ContentType.Json,
919 | format: "json",
920 | ...params,
921 | });
922 | /**
923 | * @description Delete File deletes a previously uploaded file.
924 | *
925 | * @name DeleteFile
926 | * @summary Delete File
927 | * @request DELETE:/api/v3/files/{file-public-id}
928 | * @secure
929 | */
930 | deleteFile = (filePublicId: number, params: RequestParams = {}) =>
931 | this.request({
932 | path: `/api/v3/files/${filePublicId}`,
933 | method: "DELETE",
934 | secure: true,
935 | ...params,
936 | });
937 | /**
938 | * @description A group in our API maps to a "Team" within the Shortcut Product. A Team is a collection of Users that can be associated to Stories, Epics, and Iterations within Shortcut.
939 | *
940 | * @name ListGroups
941 | * @summary List Groups
942 | * @request GET:/api/v3/groups
943 | * @secure
944 | */
945 | listGroups = (params: RequestParams = {}) =>
946 | this.request({
947 | path: `/api/v3/groups`,
948 | method: "GET",
949 | secure: true,
950 | format: "json",
951 | ...params,
952 | });
953 | /**
954 | * No description
955 | *
956 | * @name CreateGroup
957 | * @summary Create Group
958 | * @request POST:/api/v3/groups
959 | * @secure
960 | */
961 | createGroup = (CreateGroup: CreateGroup, params: RequestParams = {}) =>
962 | this.request({
963 | path: `/api/v3/groups`,
964 | method: "POST",
965 | body: CreateGroup,
966 | secure: true,
967 | type: ContentType.Json,
968 | format: "json",
969 | ...params,
970 | });
971 | /**
972 | * No description
973 | *
974 | * @name GetGroup
975 | * @summary Get Group
976 | * @request GET:/api/v3/groups/{group-public-id}
977 | * @secure
978 | */
979 | getGroup = (groupPublicId: string, params: RequestParams = {}) =>
980 | this.request({
981 | path: `/api/v3/groups/${groupPublicId}`,
982 | method: "GET",
983 | secure: true,
984 | format: "json",
985 | ...params,
986 | });
987 | /**
988 | * No description
989 | *
990 | * @name UpdateGroup
991 | * @summary Update Group
992 | * @request PUT:/api/v3/groups/{group-public-id}
993 | * @secure
994 | */
995 | updateGroup = (
996 | groupPublicId: string,
997 | UpdateGroup: UpdateGroup,
998 | params: RequestParams = {},
999 | ) =>
1000 | this.request({
1001 | path: `/api/v3/groups/${groupPublicId}`,
1002 | method: "PUT",
1003 | body: UpdateGroup,
1004 | secure: true,
1005 | type: ContentType.Json,
1006 | format: "json",
1007 | ...params,
1008 | });
1009 | /**
1010 | * @description List the Stories assigned to the Group. (By default, limited to 1,000).
1011 | *
1012 | * @name ListGroupStories
1013 | * @summary List Group Stories
1014 | * @request GET:/api/v3/groups/{group-public-id}/stories
1015 | * @secure
1016 | */
1017 | listGroupStories = (
1018 | groupPublicId: string,
1019 | query?: {
1020 | /**
1021 | * The maximum number of results to return. (Defaults to 1000, max 1000)
1022 | * @format int64
1023 | */
1024 | limit?: number;
1025 | /**
1026 | * The offset at which to begin returning results. (Defaults to 0)
1027 | * @format int64
1028 | */
1029 | offset?: number;
1030 | },
1031 | params: RequestParams = {},
1032 | ) =>
1033 | this.request({
1034 | path: `/api/v3/groups/${groupPublicId}/stories`,
1035 | method: "GET",
1036 | query: query,
1037 | secure: true,
1038 | format: "json",
1039 | ...params,
1040 | });
1041 | /**
1042 | * @description Update an existing health status by its ID.
1043 | *
1044 | * @name UpdateHealth
1045 | * @summary Update Health
1046 | * @request PUT:/api/v3/health/{health-public-id}
1047 | * @secure
1048 | */
1049 | updateHealth = (
1050 | healthPublicId: string,
1051 | UpdateHealth: UpdateHealth,
1052 | params: RequestParams = {},
1053 | ) =>
1054 | this.request({
1055 | path: `/api/v3/health/${healthPublicId}`,
1056 | method: "PUT",
1057 | body: UpdateHealth,
1058 | secure: true,
1059 | type: ContentType.Json,
1060 | format: "json",
1061 | ...params,
1062 | });
1063 | /**
1064 | * No description
1065 | *
1066 | * @name CreateGenericIntegration
1067 | * @summary Create Generic Integration
1068 | * @request POST:/api/v3/integrations/webhook
1069 | * @secure
1070 | */
1071 | createGenericIntegration = (
1072 | CreateGenericIntegration: CreateGenericIntegration,
1073 | params: RequestParams = {},
1074 | ) =>
1075 | this.request({
1076 | path: `/api/v3/integrations/webhook`,
1077 | method: "POST",
1078 | body: CreateGenericIntegration,
1079 | secure: true,
1080 | type: ContentType.Json,
1081 | ...params,
1082 | });
1083 | /**
1084 | * No description
1085 | *
1086 | * @name GetGenericIntegration
1087 | * @summary Get Generic Integration
1088 | * @request GET:/api/v3/integrations/webhook/{integration-public-id}
1089 | * @secure
1090 | */
1091 | getGenericIntegration = (
1092 | integrationPublicId: number,
1093 | params: RequestParams = {},
1094 | ) =>
1095 | this.request({
1096 | path: `/api/v3/integrations/webhook/${integrationPublicId}`,
1097 | method: "GET",
1098 | secure: true,
1099 | ...params,
1100 | });
1101 | /**
1102 | * No description
1103 | *
1104 | * @name DeleteGenericIntegration
1105 | * @summary Delete Generic Integration
1106 | * @request DELETE:/api/v3/integrations/webhook/{integration-public-id}
1107 | * @secure
1108 | */
1109 | deleteGenericIntegration = (
1110 | integrationPublicId: number,
1111 | params: RequestParams = {},
1112 | ) =>
1113 | this.request({
1114 | path: `/api/v3/integrations/webhook/${integrationPublicId}`,
1115 | method: "DELETE",
1116 | secure: true,
1117 | ...params,
1118 | });
1119 | /**
1120 | * No description
1121 | *
1122 | * @name ListIterations
1123 | * @summary List Iterations
1124 | * @request GET:/api/v3/iterations
1125 | * @secure
1126 | */
1127 | listIterations = (params: RequestParams = {}) =>
1128 | this.request({
1129 | path: `/api/v3/iterations`,
1130 | method: "GET",
1131 | secure: true,
1132 | format: "json",
1133 | ...params,
1134 | });
1135 | /**
1136 | * No description
1137 | *
1138 | * @name CreateIteration
1139 | * @summary Create Iteration
1140 | * @request POST:/api/v3/iterations
1141 | * @secure
1142 | */
1143 | createIteration = (
1144 | CreateIteration: CreateIteration,
1145 | params: RequestParams = {},
1146 | ) =>
1147 | this.request({
1148 | path: `/api/v3/iterations`,
1149 | method: "POST",
1150 | body: CreateIteration,
1151 | secure: true,
1152 | type: ContentType.Json,
1153 | format: "json",
1154 | ...params,
1155 | });
1156 | /**
1157 | * @description Disables Iterations for the current workspace
1158 | *
1159 | * @name DisableIterations
1160 | * @summary Disable Iterations
1161 | * @request PUT:/api/v3/iterations/disable
1162 | * @secure
1163 | */
1164 | disableIterations = (params: RequestParams = {}) =>
1165 | this.request({
1166 | path: `/api/v3/iterations/disable`,
1167 | method: "PUT",
1168 | secure: true,
1169 | ...params,
1170 | });
1171 | /**
1172 | * @description Enables Iterations for the current workspace
1173 | *
1174 | * @name EnableIterations
1175 | * @summary Enable Iterations
1176 | * @request PUT:/api/v3/iterations/enable
1177 | * @secure
1178 | */
1179 | enableIterations = (params: RequestParams = {}) =>
1180 | this.request({
1181 | path: `/api/v3/iterations/enable`,
1182 | method: "PUT",
1183 | secure: true,
1184 | ...params,
1185 | });
1186 | /**
1187 | * No description
1188 | *
1189 | * @name GetIteration
1190 | * @summary Get Iteration
1191 | * @request GET:/api/v3/iterations/{iteration-public-id}
1192 | * @secure
1193 | */
1194 | getIteration = (iterationPublicId: number, params: RequestParams = {}) =>
1195 | this.request({
1196 | path: `/api/v3/iterations/${iterationPublicId}`,
1197 | method: "GET",
1198 | secure: true,
1199 | format: "json",
1200 | ...params,
1201 | });
1202 | /**
1203 | * No description
1204 | *
1205 | * @name UpdateIteration
1206 | * @summary Update Iteration
1207 | * @request PUT:/api/v3/iterations/{iteration-public-id}
1208 | * @secure
1209 | */
1210 | updateIteration = (
1211 | iterationPublicId: number,
1212 | UpdateIteration: UpdateIteration,
1213 | params: RequestParams = {},
1214 | ) =>
1215 | this.request({
1216 | path: `/api/v3/iterations/${iterationPublicId}`,
1217 | method: "PUT",
1218 | body: UpdateIteration,
1219 | secure: true,
1220 | type: ContentType.Json,
1221 | format: "json",
1222 | ...params,
1223 | });
1224 | /**
1225 | * No description
1226 | *
1227 | * @name DeleteIteration
1228 | * @summary Delete Iteration
1229 | * @request DELETE:/api/v3/iterations/{iteration-public-id}
1230 | * @secure
1231 | */
1232 | deleteIteration = (iterationPublicId: number, params: RequestParams = {}) =>
1233 | this.request({
1234 | path: `/api/v3/iterations/${iterationPublicId}`,
1235 | method: "DELETE",
1236 | secure: true,
1237 | ...params,
1238 | });
1239 | /**
1240 | * @description Get a list of all Stories in an Iteration.
1241 | *
1242 | * @name ListIterationStories
1243 | * @summary List Iteration Stories
1244 | * @request GET:/api/v3/iterations/{iteration-public-id}/stories
1245 | * @secure
1246 | */
1247 | listIterationStories = (
1248 | iterationPublicId: number,
1249 | query?: {
1250 | /** A true/false boolean indicating whether to return Stories with their descriptions. */
1251 | includes_description?: boolean;
1252 | },
1253 | params: RequestParams = {},
1254 | ) =>
1255 | this.request({
1256 | path: `/api/v3/iterations/${iterationPublicId}/stories`,
1257 | method: "GET",
1258 | query: query,
1259 | secure: true,
1260 | format: "json",
1261 | ...params,
1262 | });
1263 | /**
1264 | * @description Get Key Result returns information about a chosen Key Result.
1265 | *
1266 | * @name GetKeyResult
1267 | * @summary Get Key Result
1268 | * @request GET:/api/v3/key-results/{key-result-public-id}
1269 | * @secure
1270 | */
1271 | getKeyResult = (keyResultPublicId: string, params: RequestParams = {}) =>
1272 | this.request({
1273 | path: `/api/v3/key-results/${keyResultPublicId}`,
1274 | method: "GET",
1275 | secure: true,
1276 | format: "json",
1277 | ...params,
1278 | });
1279 | /**
1280 | * @description Update Key Result allows updating a Key Result's name or initial, observed, or target values.
1281 | *
1282 | * @name UpdateKeyResult
1283 | * @summary Update Key Result
1284 | * @request PUT:/api/v3/key-results/{key-result-public-id}
1285 | * @secure
1286 | */
1287 | updateKeyResult = (
1288 | keyResultPublicId: string,
1289 | UpdateKeyResult: UpdateKeyResult,
1290 | params: RequestParams = {},
1291 | ) =>
1292 | this.request({
1293 | path: `/api/v3/key-results/${keyResultPublicId}`,
1294 | method: "PUT",
1295 | body: UpdateKeyResult,
1296 | secure: true,
1297 | type: ContentType.Json,
1298 | format: "json",
1299 | ...params,
1300 | });
1301 | /**
1302 | * @description List Labels returns a list of all Labels and their attributes.
1303 | *
1304 | * @name ListLabels
1305 | * @summary List Labels
1306 | * @request GET:/api/v3/labels
1307 | * @secure
1308 | */
1309 | listLabels = (
1310 | query?: {
1311 | /** A true/false boolean indicating if the slim versions of the Label should be returned. */
1312 | slim?: boolean;
1313 | },
1314 | params: RequestParams = {},
1315 | ) =>
1316 | this.request