├── .eslintrc ├── .github └── workflows │ └── push.yml ├── .gitignore ├── CHANGELOG.md ├── LICENSE ├── README.md ├── bin └── octokit.js ├── example.gif ├── package.json ├── renovate.json ├── src ├── formatters │ ├── emojis │ │ └── get.ts │ └── index.ts └── index.ts ├── test └── blah.test.ts ├── tsconfig.json ├── typings └── extra.d.ts └── yarn.lock /.eslintrc: -------------------------------------------------------------------------------- 1 | { 2 | "extends": [ 3 | "airbnb-base", 4 | "xo", 5 | "prettier", 6 | "plugin:@typescript-eslint/recommended", 7 | "prettier/@typescript-eslint" 8 | ], 9 | "plugins": ["prettier", "eslint-plugin-jsdoc", "@typescript-eslint"], 10 | "parser": "@typescript-eslint/parser", 11 | "parserOptions": { 12 | "project": "./tsconfig.json", 13 | "sourceType": "module" 14 | }, 15 | "settings": { 16 | "import/resolver": { 17 | "node": { 18 | "extensions": [".js", ".jsx", ".ts", ".tsx"] 19 | } 20 | } 21 | }, 22 | "rules": { 23 | "@typescript-eslint/explicit-function-return-type": 0, 24 | "@typescript-eslint/camelcase": 0, 25 | "@typescript-eslint/no-explicit-any": 0, 26 | "@typescript-eslint/ban-ts-ignore": 1, 27 | 28 | "valid-jsdoc": 0, 29 | "jsdoc/check-alignment": 1, 30 | "jsdoc/check-param-names": 1, 31 | "jsdoc/check-tag-names": 1, 32 | "jsdoc/implements-on-classes": 1, 33 | "jsdoc/newline-after-description": 1, 34 | "jsdoc/no-types": 1, 35 | "jsdoc/require-param-description": 1, 36 | "jsdoc/require-returns-check": 1, 37 | "jsdoc/require-returns-description": 1, 38 | "jsdoc/require-hyphen-before-param-description": [1, "always"], 39 | "jsdoc/require-jsdoc": [ 40 | 1, 41 | { 42 | "require": { 43 | "ArrowFunctionExpression": true, 44 | "FunctionDeclaration": true, 45 | "ClassDeclaration": true 46 | } 47 | } 48 | ] 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /.github/workflows/push.yml: -------------------------------------------------------------------------------- 1 | name: Node CI 2 | 3 | on: [push] 4 | 5 | jobs: 6 | build: 7 | runs-on: ubuntu-latest 8 | 9 | strategy: 10 | matrix: 11 | node-version: [8.x, 10.x, 12.x] 12 | 13 | steps: 14 | - uses: actions/checkout@v1 15 | - name: Use Node.js ${{ matrix.node-version }} 16 | uses: actions/setup-node@v1 17 | with: 18 | node-version: ${{ matrix.node-version }} 19 | - name: npm install, build, and lint 20 | run: | 21 | yarn 22 | yarn build 23 | yarn lint 24 | release: 25 | runs-on: ubuntu-latest 26 | 27 | steps: 28 | - uses: actions/checkout@v1 29 | - name: Skip CI 30 | uses: veggiemonk/skip-commit@master 31 | env: 32 | COMMIT_FILTER: skip ci 33 | - name: Prepare repository 34 | env: 35 | GH_TOKEN: ${{ secrets.GH_TOKEN }} 36 | run: | 37 | git checkout "${GITHUB_REF:11}" -- 38 | git remote rm origin 39 | git remote add origin "https://$GH_TOKEN@github.com/hipstersmoothie/octokit-cli.git" 40 | git fetch origin 41 | git branch --set-upstream-to origin/master 42 | - name: Use Node.js 12.x 43 | uses: actions/setup-node@v1 44 | with: 45 | node-version: 12.x 46 | - name: Create Release 47 | env: 48 | GH_TOKEN: ${{ secrets.GH_TOKEN }} 49 | NPM_TOKEN: ${{ secrets.NPM_TOKEN }} 50 | run: | 51 | git remote -v 52 | yarn 53 | yarn build 54 | yarn release 55 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | *.log 2 | .DS_Store 3 | node_modules 4 | .rts2_cache_cjs 5 | .rts2_cache_esm 6 | .rts2_cache_umd 7 | dist 8 | .env 9 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # v0.2.0 (Mon Sep 30 2019) 2 | 3 | #### 🚀 Enhancement 4 | 5 | - Update deps and fix build [#20](https://github.com/hipstersmoothie/octokit-cli/pull/20) ([@renovate-bot](https://github.com/renovate-bot) [@hipstersmoothie](https://github.com/hipstersmoothie)) 6 | 7 | #### 🏠 Internal 8 | 9 | - Use shared configs [#4](https://github.com/hipstersmoothie/octokit-cli/pull/4) ([@hipstersmoothie](https://github.com/hipstersmoothie)) 10 | 11 | #### 🔩 Dependency Updates 12 | 13 | - Update dependency auto to v7.6.2 [#19](https://github.com/hipstersmoothie/octokit-cli/pull/19) ([@renovate-bot](https://github.com/renovate-bot)) 14 | - Update dependency tsdx to v0.9.3 [#18](https://github.com/hipstersmoothie/octokit-cli/pull/18) ([@renovate-bot](https://github.com/renovate-bot)) 15 | - Update dependency husky to v3.0.7 [#17](https://github.com/hipstersmoothie/octokit-cli/pull/17) ([@renovate-bot](https://github.com/renovate-bot)) 16 | - Update dependency eslint-plugin-jsdoc to v15.9.5 [#13](https://github.com/hipstersmoothie/octokit-cli/pull/13) ([@renovate-bot](https://github.com/renovate-bot)) 17 | - Update dependency auto to v7.6.0 [#11](https://github.com/hipstersmoothie/octokit-cli/pull/11) ([@renovate-bot](https://github.com/renovate-bot)) 18 | - Update dependency typescript to v3.6.3 [#10](https://github.com/hipstersmoothie/octokit-cli/pull/10) ([@renovate-bot](https://github.com/renovate-bot)) 19 | - Update dependency auto to v7.4.5 [#9](https://github.com/hipstersmoothie/octokit-cli/pull/9) ([@renovate-bot](https://github.com/renovate-bot)) 20 | - Update dependency tsdx to v0.9.2 [#7](https://github.com/hipstersmoothie/octokit-cli/pull/7) ([@renovate-bot](https://github.com/renovate-bot)) 21 | - Update dependency auto to v7.4.4 [#6](https://github.com/hipstersmoothie/octokit-cli/pull/6) ([@renovate-bot](https://github.com/renovate-bot)) 22 | - Update dependency tsdx to v0.9.1 [#5](https://github.com/hipstersmoothie/octokit-cli/pull/5) ([@renovate-bot](https://github.com/renovate-bot)) 23 | - Pin dependencies [#3](https://github.com/hipstersmoothie/octokit-cli/pull/3) ([@renovate-bot](https://github.com/renovate-bot)) 24 | 25 | #### Authors: 2 26 | 27 | - Renovate Bot ([@renovate-bot](https://github.com/renovate-bot)) 28 | - Andrew Lisowski ([@hipstersmoothie](https://github.com/hipstersmoothie)) 29 | 30 | --- 31 | 32 | # v0.1.5 (Tue Sep 03 2019) 33 | 34 | #### 🐛 Bug Fix 35 | 36 | - Configure Renovate [#2](https://github.com/hipstersmoothie/octokit-cli/pull/2) ([@renovate-bot](https://github.com/renovate-bot)) 37 | 38 | #### 📝 Documentation 39 | 40 | - add example GIF [#1](https://github.com/hipstersmoothie/octokit-cli/pull/1) ([@hipstersmoothie](https://github.com/hipstersmoothie)) 41 | 42 | #### Authors: 2 43 | 44 | - Renovate Bot ([@renovate-bot](https://github.com/renovate-bot)) 45 | - Andrew Lisowski ([@hipstersmoothie](https://github.com/hipstersmoothie)) 46 | 47 | --- 48 | 49 | # v0.1.4 (Mon Sep 02 2019) 50 | 51 | #### ⚠️ Pushed to master 52 | 53 | - tslib is a runtime dep ([@hipstersmoothie](https://github.com/hipstersmoothie)) 54 | 55 | #### Authors: 1 56 | 57 | - Andrew Lisowski ([@hipstersmoothie](https://github.com/hipstersmoothie)) 58 | 59 | --- 60 | 61 | # v0.1.3 (Mon Sep 02 2019) 62 | 63 | #### ⚠️ Pushed to master 64 | 65 | - must publish "bin" folder ([@hipstersmoothie](https://github.com/hipstersmoothie)) 66 | 67 | #### Authors: 1 68 | 69 | - Andrew Lisowski ([@hipstersmoothie](https://github.com/hipstersmoothie)) 70 | 71 | --- 72 | 73 | # v0.1.2 (Mon Sep 02 2019) 74 | 75 | 76 | 77 | --- 78 | 79 | # v0.1.1 (Mon Sep 02 2019) 80 | 81 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2019 Andrew Lisowski 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is 8 | furnished to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in all 11 | copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 14 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 15 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 16 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 17 | DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 18 | OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE 19 | OR OTHER DEALINGS IN THE SOFTWARE. 20 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # `octokit-cli` 2 | 3 | A cli for [@octokit/rest](https://octokit.github.io/rest.js/). 4 | 5 | > NOTE: This a WIP side-project. If you want to see this project do something it doesn't feel free to contribute! Currently the descriptions could use some work. 6 | 7 | Features: 8 | 9 | :rocket: Run any octokit endpoint from the CLI 10 | 11 | :rocket: Automatically detect certain args in CI (owner, repo, issue_number) 12 | 13 | ![Example showing fuzzy searching for an emoji](./example.gif) 14 | 15 | ## Installation 16 | 17 | You can either install `octokit-cli` to your project: 18 | 19 | ```sh 20 | npm i --save-dev octokit-cli 21 | # or 22 | yarn add -D octokit-cli 23 | ``` 24 | 25 | Or globally on your computer: 26 | 27 | ```sh 28 | npm i -g octokit-cli 29 | ``` 30 | 31 | ## Usage 32 | 33 | Most commands require authentication to work. To authenticate create a [personal-access-token](https://github.com/settings/tokens) then set `GH_TOKEN` to the token. 34 | 35 | Locally you can add your `GH_TOKEN` to a file at the root of your project named `.env`. 36 | 37 | ```sh 38 | GH_TOKEN=YOUR_PERSONAL_ACCESS_TOKEN 39 | ``` 40 | 41 | Now when you run `octokit-cli` you do not have to include your `GH_TOKEN`. 42 | 43 | ### Commands 44 | 45 | `octokit-cli` is a thin wrapper around [@octokit/rest](https://octokit.github.io/rest.js/) so it has a very similar API. 46 | 47 | To get help for every command just add the `--help` flag. 48 | 49 | ### Examples 50 | 51 | _Create a status on a PR_: 52 | 53 | ```sh 54 | octokit repos create-status --owner hipstersmoothie --repo octokit-cli --state error --sha b3859f9e787145c904aee28668e20960b8407e2 --context "My Status" 55 | ``` 56 | 57 | _Create a comment on a PR_: 58 | 59 | ```sh 60 | octokit issues create-comment --body "My Comment" --owner hipstersmoothie --repo octokit-cli --issue_number 26 61 | ``` 62 | 63 | _Fuzzy find an emoji_: 64 | 65 | Using [fzf](https://github.com/junegunn/fzf) 66 | 67 | ```sh 68 | octokit emojis get | fzf 69 | ``` 70 | 71 | ### Commands in CI 72 | 73 | When run from a continuos integration (CI) environment, `octokit-cli` will detect the `owner`, `repo`, and `issue_number` and set these as defaults when running a command. 74 | 75 | For example, if you ran the following command from a PR in your CI it would automatically include `owner`, `repo`, and `issue_number`. If ran locally these arguments would be required. 76 | 77 | ```sh 78 | octokit issues create-comment --body "My Comment" 79 | ``` 80 | 81 | ## Contributing 82 | 83 | If you want a feature or can fix a bug, submit a PR! 84 | 85 | If you think a particular endpoint can be formatted better for the CLI, add a formatter in `src/formatters`. 86 | 87 | ### Developing 88 | 89 | First install the dependencies: 90 | 91 | ```sh 92 | yarn 93 | ``` 94 | 95 | #### Scripts 96 | 97 | - `yarn start` - Build the CLI and watch for changes 98 | - `yarn build` - Create a build of the CLI 99 | -------------------------------------------------------------------------------- /bin/octokit.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | require('../dist').default(); 4 | -------------------------------------------------------------------------------- /example.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hipstersmoothie/octokit-cli/256932ecc8edc56e46737a10d95ddd1badcc2941/example.gif -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "octokit-cli", 3 | "version": "0.2.0", 4 | "main": "dist/index.js", 5 | "module": "dist/octokit-cli.esm.js", 6 | "typings": "dist/index.d.ts", 7 | "license": "MIT", 8 | "repository": "hipstersmoothie/octokit-cli", 9 | "author": "Andrew Lisowski ", 10 | "files": [ 11 | "dist", 12 | "bin" 13 | ], 14 | "bin": { 15 | "octokit": "./bin/octokit.js" 16 | }, 17 | "scripts": { 18 | "start": "tsdx watch", 19 | "build": "tsdx build", 20 | "test": "tsdx test", 21 | "lint": "eslint src --ext .ts,.js", 22 | "release": "auto shipit" 23 | }, 24 | "devDependencies": { 25 | "@types/dotenv": "6.1.1", 26 | "@types/env-ci": "3.1.0", 27 | "@types/got": "9.6.7", 28 | "@types/jest": "24.0.18", 29 | "@typescript-eslint/eslint-plugin": "2.3.2", 30 | "@typescript-eslint/parser": "2.3.2", 31 | "auto": "7.6.2", 32 | "auto-config-hipstersmoothie": "1.0.4", 33 | "babel-eslint": "10.0.3", 34 | "eslint": "6.5.0", 35 | "eslint-config-airbnb-base": "14.0.0", 36 | "eslint-config-prettier": "6.3.0", 37 | "eslint-config-xo": "0.27.1", 38 | "eslint-plugin-import": "2.18.2", 39 | "eslint-plugin-jsdoc": "15.9.5", 40 | "eslint-plugin-jsx-a11y": "6.2.3", 41 | "eslint-plugin-prettier": "3.1.1", 42 | "husky": "3.0.7", 43 | "prettier": "1.18.2", 44 | "pretty-quick": "1.11.1", 45 | "tsdx": "0.9.3", 46 | "typescript": "3.6.3" 47 | }, 48 | "dependencies": { 49 | "@octokit/rest": "^16.28.7", 50 | "@octokit/routes": "^25.0.0", 51 | "change-case": "^3.1.0", 52 | "command-line-application": "^0.8.0", 53 | "dotenv": "^8.1.0", 54 | "env-ci": "^4.1.1", 55 | "terminal-link": "^2.0.0", 56 | "tslib": "^1.10.0" 57 | }, 58 | "husky": { 59 | "hooks": { 60 | "pre-commit": "pretty-quick --staged" 61 | } 62 | }, 63 | "prettier": { 64 | "printWidth": 80, 65 | "semi": true, 66 | "singleQuote": true, 67 | "trailingComma": "es5" 68 | }, 69 | "auto": { 70 | "extends": "hipstersmoothie" 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /renovate.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": ["config:base"], 3 | "labels": ["dependencies"] 4 | } 5 | -------------------------------------------------------------------------------- /src/formatters/emojis/get.ts: -------------------------------------------------------------------------------- 1 | import Octokit from '@octokit/rest'; 2 | import terminalLink from 'terminal-link'; 3 | 4 | /** Format the emoji results into a terse list */ 5 | export default ({ data }: Octokit.Response) => { 6 | const lines = Object.entries(data).map(([emoji, link]) => { 7 | const copyable = `:${emoji}:`; 8 | 9 | return terminalLink.isSupported 10 | ? terminalLink(copyable, link as string) 11 | : copyable; 12 | }); 13 | 14 | return lines.join('\n'); 15 | }; 16 | -------------------------------------------------------------------------------- /src/formatters/index.ts: -------------------------------------------------------------------------------- 1 | import emojisGet from './emojis/get'; 2 | 3 | export default { 4 | emojis: { 5 | get: emojisGet, 6 | }, 7 | }; 8 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | import Octokit from '@octokit/rest'; 2 | import GitHubApi from '@octokit/routes/api.github.com.json'; 3 | import changeCase from 'change-case'; 4 | import { app, Command, Option, MultiCommand } from 'command-line-application'; 5 | import dotenv from 'dotenv'; 6 | import envCi from 'env-ci'; 7 | 8 | import formatters from './formatters'; 9 | 10 | interface Param { 11 | name: string; 12 | type: string; 13 | description: string; 14 | required?: boolean; 15 | } 16 | 17 | interface Api { 18 | paths: Record< 19 | string, 20 | Record< 21 | string, 22 | { 23 | operationId: string; 24 | description: string; 25 | parameters: Param[]; 26 | requestBody?: { 27 | content: { 28 | 'application/json': { 29 | schema: { properties: Param[]; required: string[] }; 30 | }; 31 | }; 32 | }; 33 | } 34 | > 35 | >; 36 | } 37 | 38 | const routes = Object.values((GitHubApi as Api).paths).reduce( 39 | (acc, path) => { 40 | Object.values(path).forEach(route => { 41 | const [apiName, method] = route.operationId.split('/'); 42 | const methodDef = { 43 | ...route, 44 | idName: method, 45 | parameters: [...route.parameters].filter(p => p.name !== 'accept'), 46 | }; 47 | 48 | if ( 49 | route.requestBody && 50 | route.requestBody.content['application/json'].schema.properties 51 | ) { 52 | const required = 53 | route.requestBody.content['application/json'].schema.required || []; 54 | 55 | methodDef.parameters = [ 56 | ...methodDef.parameters, 57 | ...Object.entries( 58 | route.requestBody.content['application/json'].schema.properties 59 | ).map(([name, def]) => ({ 60 | name, 61 | ...def, 62 | required: required.includes(name), 63 | })), 64 | ]; 65 | } 66 | 67 | if (acc[apiName]) { 68 | acc[apiName].push(methodDef); 69 | } else { 70 | acc[apiName] = [methodDef]; 71 | } 72 | }); 73 | 74 | return acc; 75 | }, 76 | {} as Record 77 | ); 78 | 79 | const { isCi, ...env } = envCi(); 80 | const slug = 'slug' in env ? env.slug : ''; 81 | const prNumber = 'pr' in env ? env.pr : ''; 82 | const [owner, repo] = slug.split('/'); 83 | 84 | type ApiName = keyof typeof routes; 85 | 86 | interface Param { 87 | name: string; 88 | type: string; 89 | description: string; 90 | required?: boolean; 91 | } 92 | 93 | interface Method { 94 | idName: string; 95 | description: string; 96 | parameters: Param[]; 97 | } 98 | 99 | /** Convert the string based type to a javascript Type */ 100 | function createType(type: string) { 101 | if (type === 'string') { 102 | return String; 103 | } 104 | 105 | if (type === 'boolean') { 106 | return Boolean; 107 | } 108 | 109 | if (type === 'integer') { 110 | return Number; 111 | } 112 | 113 | return undefined; 114 | } 115 | 116 | const optionParamsInCI = ['owner', 'repo', 'issue_number']; 117 | 118 | /** Create a command-line-application Option from the param */ 119 | function createOption(param: Param): Option { 120 | return { 121 | name: param.name, 122 | type: createType(param.type), 123 | description: optionParamsInCI.includes(param.name) 124 | ? `${param.description}Not required in CI` 125 | : param.description, 126 | }; 127 | } 128 | 129 | /** Create a command-line-application Command from the method */ 130 | function createCommand(method: Method, truncateDescriptions: boolean): Command { 131 | const requiredParams = method.parameters 132 | .filter(({ name, required }) => 133 | isCi && optionParamsInCI.includes(name) ? false : required 134 | ) 135 | .map(({ name }) => name); 136 | 137 | return { 138 | name: method.idName, 139 | options: method.parameters.map(createOption), 140 | require: requiredParams, 141 | description: truncateDescriptions 142 | ? method.description.slice(0, method.description.indexOf('.')) 143 | : method.description, 144 | }; 145 | } 146 | 147 | /** Create a command-line-application MultiCommand from the API */ 148 | function createMultiCommand( 149 | name: string, 150 | methods: Method[], 151 | truncateDescriptions: boolean 152 | ): MultiCommand { 153 | return { 154 | name, 155 | description: `The GitHub API for ${name}`, 156 | commands: methods.map(route => createCommand(route, truncateDescriptions)), 157 | }; 158 | } 159 | 160 | /** Return the identity of the value */ 161 | const Identity = (i: T) => i; 162 | 163 | /** Call the formatter for method if it exists */ 164 | async function formatResponse(api: ApiName, method: string, response: any) { 165 | type FormatterName = keyof typeof formatters; 166 | 167 | const formatterGroup = 168 | api in formatters ? formatters[api as FormatterName] : {}; 169 | 170 | const formatter = 171 | method in formatterGroup 172 | ? formatterGroup[method as keyof typeof formatterGroup] 173 | : Identity; 174 | 175 | const formatted = await formatter(response); 176 | 177 | return formatted; 178 | } 179 | 180 | /** Create the CLi definition for the routes found in @octokit/routes */ 181 | function createCli(): MultiCommand { 182 | const commandIndex = process.argv.findIndex(arg => 183 | Object.keys(routes).includes(arg) 184 | ); 185 | const truncateDescriptions = 186 | process.argv[commandIndex + 1] === '--help' || 187 | process.argv[commandIndex + 1] === '-h' || 188 | process.argv[commandIndex + 1] === undefined; 189 | 190 | const commands = Object.entries(routes).map(([route, methods]) => 191 | createMultiCommand(route, methods, truncateDescriptions) 192 | ); 193 | 194 | return { 195 | name: 'octokit', 196 | description: 'A CLI for interacting with GitHub via octokit', 197 | commands, 198 | }; 199 | } 200 | 201 | /** Create the CLI and run the users input through @octokit/rest */ 202 | export default async () => { 203 | dotenv.config(); 204 | 205 | const cli = createCli(); 206 | const args = app(cli, { camelCase: false }); 207 | 208 | if (!args) { 209 | return; 210 | } 211 | 212 | // eslint-disable-next-line @typescript-eslint/no-explicit-any, no-underscore-dangle 213 | const [api, method] = args._command as [ApiName, any]; 214 | const octokit = new Octokit({ 215 | auth: process.env.GH_TOKEN, 216 | }); 217 | 218 | try { 219 | // @ts-ignore 220 | const response = await octokit[api][changeCase.camelCase(method)]({ 221 | owner, 222 | repo, 223 | issue_number: prNumber, 224 | ...args, 225 | }); 226 | 227 | // eslint-disable-next-line no-console 228 | console.log(await formatResponse(api, method, response)); 229 | } catch (error) { 230 | console.log(error); 231 | } 232 | }; 233 | -------------------------------------------------------------------------------- /test/blah.test.ts: -------------------------------------------------------------------------------- 1 | import { sum } from '../src'; 2 | 3 | describe('blah', () => { 4 | it('works', () => { 5 | expect(sum(1, 1)).toEqual(2); 6 | }); 7 | }); 8 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "include": ["src", "typings"], 3 | "compilerOptions": { 4 | "target": "es5", 5 | "module": "esnext", 6 | "lib": ["dom", "esnext"], 7 | "importHelpers": true, 8 | "declaration": true, 9 | "sourceMap": true, 10 | "rootDir": "./", 11 | "strict": true, 12 | "noImplicitAny": true, 13 | "strictNullChecks": true, 14 | "strictFunctionTypes": true, 15 | "strictPropertyInitialization": true, 16 | "noImplicitThis": true, 17 | "alwaysStrict": true, 18 | "noImplicitReturns": true, 19 | "noFallthroughCasesInSwitch": true, 20 | "resolveJsonModule": true, 21 | "moduleResolution": "node", 22 | "baseUrl": "./", 23 | "paths": { 24 | "*": ["src/*", "node_modules/*"] 25 | }, 26 | "jsx": "react", 27 | "esModuleInterop": true 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /typings/extra.d.ts: -------------------------------------------------------------------------------- 1 | declare module '@octokit/routes/api.github.com.json'; 2 | --------------------------------------------------------------------------------