Skip to content

Instantly share code, notes, and snippets.

@panva
Last active October 20, 2024 09:23
Show Gist options
  • Save panva/ebaacfe433a8677bdbf458f6e1132045 to your computer and use it in GitHub Desktop.
Save panva/ebaacfe433a8677bdbf458f6e1132045 to your computer and use it in GitHub Desktop.
Simple Device Flow Login CLI implementation

Simple Device Flow Login CLI implementation

run

npx https://gist.github.com/panva/ebaacfe433a8677bdbf458f6e1132045
const r = await fetch("https://op.panva.cz/reg", {
method: "POST",
headers: {
"content-type": "application/json",
},
body: JSON.stringify({
grant_types: ["urn:ietf:params:oauth:grant-type:device_code"],
response_types: [],
redirect_uris: [],
token_endpoint_auth_method: "none",
application_type: "native",
}),
});
const { client_id } = await r.json();
export { client_id };
#!/usr/bin/env node
import * as client from "openid-client";
import open from "open";
import { client_id } from "./dcr.mjs";
const config = await client.discovery(
new URL("https://op.panva.cz"),
client_id,
);
const deviceAuthorizationResponse = await client.initiateDeviceAuthorization(
config,
{ scope: "openid email" },
);
console.log("user code:", deviceAuthorizationResponse.user_code);
await open(deviceAuthorizationResponse.verification_uri_complete, {
wait: false,
});
const tokens = await client.pollDeviceAuthorizationGrant(
config,
deviceAuthorizationResponse,
);
console.log("got", tokens);
const idTokenClaims = tokens.claims();
if (idTokenClaims) {
console.log("id token claims", idTokenClaims);
const userinfo = await client.fetchUserInfo(
config,
tokens.access_token,
idTokenClaims.sub,
);
console.log("userinfo", userinfo);
}
{
"name": "pg",
"version": "1.0.0",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "pg",
"version": "1.0.0",
"license": "ISC",
"dependencies": {
"open": "^10.1.0",
"openid-client": "^6.1.1"
},
"bin": {
"pg": "index.js"
},
"devDependencies": {
"@types/node": "^22.7.7"
}
},
"node_modules/@types/node": {
"version": "22.7.7",
"resolved": "https://registry.npmjs.org/@types/node/-/node-22.7.7.tgz",
"integrity": "sha512-SRxCrrg9CL/y54aiMCG3edPKdprgMVGDXjA3gB8UmmBW5TcXzRUYAh8EWzTnSJFAd1rgImPELza+A3bJ+qxz8Q==",
"dev": true,
"license": "MIT",
"dependencies": {
"undici-types": "~6.19.2"
}
},
"node_modules/bundle-name": {
"version": "4.1.0",
"resolved": "https://registry.npmjs.org/bundle-name/-/bundle-name-4.1.0.tgz",
"integrity": "sha512-tjwM5exMg6BGRI+kNmTntNsvdZS1X8BFYS6tnJ2hdH0kVxM6/eVZ2xy+FqStSWvYmtfFMDLIxurorHwDKfDz5Q==",
"license": "MIT",
"dependencies": {
"run-applescript": "^7.0.0"
},
"engines": {
"node": ">=18"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/default-browser": {
"version": "5.2.1",
"resolved": "https://registry.npmjs.org/default-browser/-/default-browser-5.2.1.tgz",
"integrity": "sha512-WY/3TUME0x3KPYdRRxEJJvXRHV4PyPoUsxtZa78lwItwRQRHhd2U9xOscaT/YTf8uCXIAjeJOFBVEh/7FtD8Xg==",
"license": "MIT",
"dependencies": {
"bundle-name": "^4.1.0",
"default-browser-id": "^5.0.0"
},
"engines": {
"node": ">=18"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/default-browser-id": {
"version": "5.0.0",
"resolved": "https://registry.npmjs.org/default-browser-id/-/default-browser-id-5.0.0.tgz",
"integrity": "sha512-A6p/pu/6fyBcA1TRz/GqWYPViplrftcW2gZC9q79ngNCKAeR/X3gcEdXQHl4KNXV+3wgIJ1CPkJQ3IHM6lcsyA==",
"license": "MIT",
"engines": {
"node": ">=18"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/define-lazy-prop": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-3.0.0.tgz",
"integrity": "sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg==",
"license": "MIT",
"engines": {
"node": ">=12"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/is-docker": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/is-docker/-/is-docker-3.0.0.tgz",
"integrity": "sha512-eljcgEDlEns/7AXFosB5K/2nCM4P7FQPkGc/DWLy5rmFEWvZayGrik1d9/QIY5nJ4f9YsVvBkA6kJpHn9rISdQ==",
"license": "MIT",
"bin": {
"is-docker": "cli.js"
},
"engines": {
"node": "^12.20.0 || ^14.13.1 || >=16.0.0"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/is-inside-container": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/is-inside-container/-/is-inside-container-1.0.0.tgz",
"integrity": "sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA==",
"license": "MIT",
"dependencies": {
"is-docker": "^3.0.0"
},
"bin": {
"is-inside-container": "cli.js"
},
"engines": {
"node": ">=14.16"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/is-wsl": {
"version": "3.1.0",
"resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-3.1.0.tgz",
"integrity": "sha512-UcVfVfaK4Sc4m7X3dUSoHoozQGBEFeDC+zVo06t98xe8CzHSZZBekNXH+tu0NalHolcJ/QAGqS46Hef7QXBIMw==",
"license": "MIT",
"dependencies": {
"is-inside-container": "^1.0.0"
},
"engines": {
"node": ">=16"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/jose": {
"version": "5.9.4",
"resolved": "https://registry.npmjs.org/jose/-/jose-5.9.4.tgz",
"integrity": "sha512-WBBl6au1qg6OHj67yCffCgFR3BADJBXN8MdRvCgJDuMv3driV2nHr7jdGvaKX9IolosAsn+M0XRArqLXUhyJHQ==",
"license": "MIT",
"funding": {
"url": "https://github.com/sponsors/panva"
}
},
"node_modules/oauth4webapi": {
"version": "3.1.1",
"resolved": "https://registry.npmjs.org/oauth4webapi/-/oauth4webapi-3.1.1.tgz",
"integrity": "sha512-0h4FZjsntbKQ5IHGM9mFT7uOwQCRdcTG7YhC0xXlWIcCch24wUa6Vggaipa3Sw6Ab7nEnmO4rctROmyuHBfP7Q==",
"license": "MIT",
"funding": {
"url": "https://github.com/sponsors/panva"
}
},
"node_modules/open": {
"version": "10.1.0",
"resolved": "https://registry.npmjs.org/open/-/open-10.1.0.tgz",
"integrity": "sha512-mnkeQ1qP5Ue2wd+aivTD3NHd/lZ96Lu0jgf0pwktLPtx6cTZiH7tyeGRRHs0zX0rbrahXPnXlUnbeXyaBBuIaw==",
"license": "MIT",
"dependencies": {
"default-browser": "^5.2.1",
"define-lazy-prop": "^3.0.0",
"is-inside-container": "^1.0.0",
"is-wsl": "^3.1.0"
},
"engines": {
"node": ">=18"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/openid-client": {
"version": "6.1.1",
"resolved": "https://registry.npmjs.org/openid-client/-/openid-client-6.1.1.tgz",
"integrity": "sha512-JVN2ao1ErxHdWTme+xAQrLsQV2rV4RlhdiR8ZfaN0ktMhE8lEapU+VH7XuHSxTPHaAK7Rz7AqIB98ea+cHaCUg==",
"license": "MIT",
"dependencies": {
"jose": "^5.9.4",
"oauth4webapi": "^3.1.1"
},
"funding": {
"url": "https://github.com/sponsors/panva"
}
},
"node_modules/run-applescript": {
"version": "7.0.0",
"resolved": "https://registry.npmjs.org/run-applescript/-/run-applescript-7.0.0.tgz",
"integrity": "sha512-9by4Ij99JUr/MCFBUkDKLWK3G9HVXmabKz9U5MlIAIuvuzkiOicRYs8XJLxX+xahD+mLiiCYDqF9dKAgtzKP1A==",
"license": "MIT",
"engines": {
"node": ">=18"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/undici-types": {
"version": "6.19.8",
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.19.8.tgz",
"integrity": "sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==",
"dev": true,
"license": "MIT"
}
}
}
{
"name": "pg",
"version": "1.0.0",
"description": "",
"main": "index.mjs",
"bin": "./index.mjs",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"dependencies": {
"open": "^10.1.0",
"openid-client": "^6.1.1"
},
"devDependencies": {
"@types/node": "^22.7.7"
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment