{"id":21800307,"url":"https://github.com/justlep/github-email-authentication","last_synced_at":"2025-04-13T17:42:00.557Z","repository":{"id":55050273,"uuid":"154860508","full_name":"justlep/github-email-authentication","owner":"justlep","description":"User authentication based on verified, primary Github account email addresses using Github OAuth","archived":false,"fork":false,"pushed_at":"2024-10-24T06:57:28.000Z","size":153,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2024-10-25T02:18:24.017Z","etag":null,"topics":["authentication","email","github","oauth"],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/justlep.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2018-10-26T16:05:00.000Z","updated_at":"2024-10-24T06:57:25.000Z","dependencies_parsed_at":"2024-06-20T03:55:29.241Z","dependency_job_id":"fd103547-5d3b-4b6d-a92c-4a5375dd9dc2","html_url":"https://github.com/justlep/github-email-authentication","commit_stats":{"total_commits":17,"total_committers":3,"mean_commits":5.666666666666667,"dds":"0.23529411764705888","last_synced_commit":"3d9e429a3759aa45ab59f313cc3e7177b985b786"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/justlep%2Fgithub-email-authentication","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/justlep%2Fgithub-email-authentication/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/justlep%2Fgithub-email-authentication/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/justlep%2Fgithub-email-authentication/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/justlep","download_url":"https://codeload.github.com/justlep/github-email-authentication/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248755680,"owners_count":21156632,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["authentication","email","github","oauth"],"created_at":"2024-11-27T10:45:47.092Z","updated_at":"2025-04-13T17:42:00.551Z","avatar_url":"https://github.com/justlep.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# github-email-authentication [![NPM Version][npm-image]][npm-url] [![Node.js Version][node-version-image]][node-version-url]\n\nUser authentication based on a Github account's verified, primary email address using Github OAuth.\n\nEach authentication process can be started for either a _known_ email address or _any_ Github account's email address (as long as it's the primary, verified email address).\nUpon successful authentication, the Github account's primary, verified email address and, \noptionally, the access token are passed to a given success handler. \nWhen authentication is started for a _known_ email address, that address is expected to be the logged-in \nGithub account's _primary, verified_ email address, otherwise authentication fails.\n  \n### Requirements\n* Node 16+\n* Express (or similar, it's up to you)\n* Your Github OAuth app providing Client ID and Client secret.  \n  See: https://github.com/settings/developers\n\n### Security\n* Using signed values for the `state` parameter (HMAC-SHA256), unique for each started\n  login process and verified before accepting any authorization code. \n  Also, `state` expires after max. 2 minutes by using [rotating secrets](https://github.com/justlep/keygrip-autorotate) \n  for signing.\n* Login processes started for a *known* email address will succeed only if\n  that email address is really the Github account's primary, verified email.\n* Github accounts with no verified, primary email addresses are rejected in all cases.  \n\n\n## Usage\n\n```javascript\nimport {GithubEmailAuthentication} from 'github-email-authentication';\nimport express from 'express';\n\nimport {CLIENT_ID, CLIENT_SECRET, PORT} from './app-config.js'; \n\nconst app = express();\n\nconst githubAuth = new GithubEmailAuthentication({\n        appOrRouter: app,\n        routableCallbackUri: '/loginCallback',\n        absoluteCallbackUrl: `https://my-domain.tld:${PORT}/loginCallback`,\n        githubClientId: CLIENT_ID,\n        githubClientSecret: CLIENT_SECRET,\n        exposeAccessToken: false,\n        maxLoginProcessDuration: 2 * 60 * 1000,\n        onSuccess: (validatedPrimaryEmail, accessToken, req, res, next) =\u003e {\n            // (1) `validatedPrimaryEmail` is never empty here\n            // (2) `accessToken` is null here due to `exposeAccessToken: false`\n            \n            // TODO check who logged in \u0026 put customer into session or so\n            \n            res.redirect(302, '/account');\n        },\n        onError: (message, res, next) =\u003e {\n            console.warn('Login failed, reason: %s', message);\n            res.status(403).send('Login failed. Reason: ' + message);\n        }\n    });\n\napp.post('/loginNewCustomer', (req, res) =\u003e {\n    console.log('Initiating github login for any account');\n    githubAuth.startLoginForUnknown(res);\n});\n\napp.post('loginExistingCustomer', (req, res) =\u003e {\n    let {email} = req.query;\n    console.log('Initiating github login for email %s', email);\n    githubAuth.startLoginForEmail(email, res);\n});\n\n```\n\n## Options\n\nProperties of the `opts` object for `new GithubEmailAuthentication(opts)`:\n\n\n| Param | Type |  Description |\n| --- | --- | --- |\n| appOrRouter | \u003ccode\u003eExpress\u003c/code\u003e \\| \u003ccode\u003eRouter\u003c/code\u003e | some Express app or router |\n| routableCallbackUri | \u003ccode\u003estring\u003c/code\u003e | e.g. '/githubCallback', this route will be added to the given `appOrRouter` to receive authorization codes |\n| absoluteCallbackUrl | \u003ccode\u003estring\u003c/code\u003e | the absolute URL for the redirect from Github OAuth login, so basically the absolute URL for the `routableCallbackUri`. (!)  Must equal the \"Authorization callback URL\" defined in your OAuth App's settings on Github, see https://github.com/settings/developers.\n| githubClientId | \u003ccode\u003estring\u003c/code\u003e |  |\n| githubClientSecret | \u003ccode\u003estring\u003c/code\u003e |  |\n| [scopes] | \u003ccode\u003estring[]\u003c/code\u003e | scopes for the access token (default: `['user:email']`); If given, the scopes must allow read-access to the user's Github email addresses ('user:email'), otherwise authentication will fail. |\n| [exposeAccessToken] | \u003ccode\u003eboolean\u003c/code\u003e | if true, the access token will be passed to the `onSuccess` callback,  otherwise `null` is passed as token (default: false) |\n| [maxLoginProcessDuration] | \u003ccode\u003enumber\u003c/code\u003e | the max. time in millis from initiating a login and the time an authorization token is passed to the `routableCallbackUri` callback.  Essentially the time users have to enter their Github credentials and authorize the app to access their email addresses. Technically, the time after which a `state` can no longer be verified since the secret used for signing it got rotated out. (default: 2\\*60\\*1000, i.e. 2 minutes) |\n| onSuccess | function | see [\u003ccode\u003eGithubEmailAuthentication\\_SuccessHandler\u003c/code\u003e](#GithubEmailAuthentication_SuccessHandler) |\n| onError | function | see [\u003ccode\u003eGithubEmailAuthentication\\_ErrorHandler\u003c/code\u003e](#GithubEmailAuthentication_ErrorHandler) |\n| [logEnabled] | \u003ccode\u003eboolean\u003c/code\u003e | if true, errors/warning will be logged to the console (default: false).                                      (!) Logged messages may contain sensitive data like email addresses. |\n\n### Notes\n\n#### `exposeAccessToken` (default=false)\nSet this `true` if you need the access token for anything beyond the authentication process.\n\n#### `scopes` (default=`['user:email']`)\nThe default scope only allows read-access to Github accounts' email addresses.\nAdd any scopes you want to use the access token for beyond authentication (requires `exposeAccessToken` set true).\nWith custom scopes, make sure read-access to account email addresses remains possible, otherwise authentication will fail.\n\n\u003ca name=\"GithubEmailAuthentication_ErrorHandler\"\u003e\u003c/a\u003e\n\n### GithubEmailAuthentication\\_ErrorHandler : \u003ccode\u003efunction\u003c/code\u003e\n\n| Param | Type |\n| --- | --- |\n| errorMessage | \u003ccode\u003estring\u003c/code\u003e | \n| response | \u003ccode\u003eResponse\u003c/code\u003e | \n| [next] | \u003ccode\u003efunction\u003c/code\u003e | \n\n\u003ca name=\"GithubEmailAuthentication_SuccessHandler\"\u003e\u003c/a\u003e\n\n### GithubEmailAuthentication\\_SuccessHandler : \u003ccode\u003efunction\u003c/code\u003e\n\n| Param | Type |\n| --- | --- |\n| validatedPrimaryEmail | \u003ccode\u003estring\u003c/code\u003e | \n| accessToken | \u003ccode\u003e?string\u003c/code\u003e | \n| request | \u003ccode\u003eRequest\u003c/code\u003e | \n| response | \u003ccode\u003eResponse\u003c/code\u003e | \n| [next] | \u003ccode\u003efunction\u003c/code\u003e | \n\n\n\n\n\n## Credits\n\n* [github-oauth](https://github.com/maxogden/github-oauth) for the inspiration \n\n## License \n[MIT](./LICENSE)\n\n\n\n[npm-image]: https://img.shields.io/npm/v/github-email-authentication.svg\n[npm-url]: https://npmjs.org/package/github-email-authentication\n[node-version-image]: https://img.shields.io/node/v/github-email-authentication.svg\n[node-version-url]: https://nodejs.org/en/download/\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjustlep%2Fgithub-email-authentication","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjustlep%2Fgithub-email-authentication","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjustlep%2Fgithub-email-authentication/lists"}