diff --git a/apps/dev/.env.local.example b/apps/dev/.env.local.example index 109d5a59cb..9f8819002f 100644 --- a/apps/dev/.env.local.example +++ b/apps/dev/.env.local.example @@ -50,3 +50,6 @@ DATABASE_URL= BOXYHQSAML_ISSUER="https://jackson-demo.boxyhq.com" BOXYHQSAML_ID="tenant=boxyhq.com&product=saml-demo.boxyhq.com" BOXYHQSAML_SECRET="dummy" + +WIKIMEDIA_ID= +WIKIMEDIA_SECRET= \ No newline at end of file diff --git a/apps/dev/pages/api/auth/[...nextauth].ts b/apps/dev/pages/api/auth/[...nextauth].ts index 1f6fbba7b7..8c03a779f4 100644 --- a/apps/dev/pages/api/auth/[...nextauth].ts +++ b/apps/dev/pages/api/auth/[...nextauth].ts @@ -32,6 +32,7 @@ import PatreonProvider from "next-auth/providers/patreon" import TraktProvider from "next-auth/providers/trakt" import WorkOSProvider from "next-auth/providers/workos" import BoxyHQSAMLProvider from "next-auth/providers/boxyhq-saml" +import WikimediaProvider from "next-auth/providers/wikimedia" // TypeORM import { TypeORMLegacyAdapter } from "@next-auth/typeorm-legacy-adapter" @@ -229,6 +230,10 @@ export const authOptions: NextAuthOptions = { clientId: process.env.BOXYHQSAML_ID, clientSecret: process.env.BOXYHQSAML_SECRET, }), + WikimediaProvider({ + clientId: process.env.WIKIMEDIA_ID, + clientSecret: process.env.WIKIMEDIA_SECRET, + }), ], debug: true, theme: { diff --git a/docs/docs/providers/wikimedia.md b/docs/docs/providers/wikimedia.md new file mode 100644 index 0000000000..47d3f2533e --- /dev/null +++ b/docs/docs/providers/wikimedia.md @@ -0,0 +1,50 @@ +--- +id: wikimedia +title: Wikimedia +--- + +## Documentation + +https://www.mediawiki.org/wiki/Extension:OAuth + +This provider also supports all Wikimedia projects: + +- Wikipedia +- Wikidata +- Wikibooks +- Wiktionary +- etc.. + +Please be aware that Wikimedia accounts do not have to have an associated email address. So you may want to add check if the user has an email address before allowing them to login. + +## Configuration + +1. Go to and accept the Consumer Registration doc: https://meta.wikimedia.org/wiki/Special:OAuthConsumerRegistration +2. Request a new OAuth 2.0 consumer to get the `clientId` and `clientSecret`: https://meta.wikimedia.org/wiki/Special:OAuthConsumerRegistration/propose/oauth2 + 2a. Add the following redirect URL into the console `http:///api/auth/callback/wikimedia` + 2b. Do not check the box next to `This consumer is only for [your username]` + 2c. Unless you explicitly need a larger scope, feel free to select the radio button labelled `User identity verification only - no ability to read pages or act on the users behalf.` + +After registration, you can initally test your application only with your own Wikimedia account. You may have to wait several days for the application to be approved for it to be used by everyone. + +## Options + +The **Wikimedia Provider** comes with a set of default options: + +- [Wikimedia Provider options](https://github.com/nextauthjs/next-auth/blob/main/packages/next-auth/src/providers/wikimedia.ts) + +You can override any of the options to suit your own use case. + +## Example + +```js +import WikimediaProvider from "next-auth/providers/wikimedia"; +... +providers: [ + WikimediaProvider({ + clientId: process.env.WIKIMEDIA_CLIENT_ID, + clientSecret: process.env.WIKIMEDIA_CLIENT_SECRET + }) +] +... +``` diff --git a/packages/next-auth/src/providers/wikimedia.ts b/packages/next-auth/src/providers/wikimedia.ts new file mode 100644 index 0000000000..4e017c0c44 --- /dev/null +++ b/packages/next-auth/src/providers/wikimedia.ts @@ -0,0 +1,185 @@ +import type { OAuthConfig, OAuthUserConfig } from "." + +export type WikimediaGroup = + | "*" + | "user" + | "autoconfirmed" + | "extendedconfirmed" + | "bot" + | "sysop" + | "bureaucrat" + | "steward" + | "accountcreator" + | "import" + | "transwiki" + | "ipblock-exempt" + | "oversight" + | "rollbacker" + | "propertycreator" + | "wikidata-staff" + | "flood" + | "translationadmin" + | "confirmed" + | "flow-bot" + | "checkuser" + +export type WikimediaGrant = + | "basic" + | "blockusers" + | "checkuser" + | "createaccount" + | "delete" + | "editinterface" + | "editmycssjs" + | "editmyoptions" + | "editmywatchlist" + | "editpage" + | "editprotected" + | "editsiteconfig" + | "globalblock" + | "highvolume" + | "import" + | "mergehistory" + | "oath" + | "oversight" + | "patrol" + | "privateinfo" + | "protect" + | "rollback" + | "sendemail" + | "shortenurls" + | "uploadfile" + | "viewdeleted" + | "viewmywatchlist" + +export type WikimediaRight = + | "abusefilter-log" + | "apihighlimits" + | "applychangetags" + | "autoconfirmed" + | "autopatrol" + | "autoreview" + | "bigdelete" + | "block" + | "blockemail" + | "bot" + | "browsearchive" + | "changetags" + | "checkuser" + | "checkuser-log" + | "createaccount" + | "createpage" + | "createpagemainns" + | "createtalk" + | "delete" + | "delete-redirect" + | "deletedhistory" + | "deletedtext" + | "deletelogentry" + | "deleterevision" + | "edit" + | "edit-legal" + | "editinterface" + | "editmyoptions" + | "editmyusercss" + | "editmyuserjs" + | "editmyuserjson" + | "editmywatchlist" + | "editprotected" + | "editsemiprotected" + | "editsitecss" + | "editsitejs" + | "editsitejson" + | "editusercss" + | "edituserjs" + | "edituserjson" + | "globalblock" + | "import" + | "importupload" + | "ipblock-exempt" + | "item-merge" + | "item-redirect" + | "item-term" + | "markbotedits" + | "massmessage" + | "mergehistory" + | "minoredit" + | "move" + | "move-subpages" + | "movefile" + | "movestable" + | "mwoauth-authonlyprivate" + | "nominornewtalk" + | "noratelimit" + | "nuke" + | "patrol" + | "patrolmarks" + | "property-create" + | "property-term" + | "protect" + | "purge" + | "read" + | "reupload" + | "reupload-own" + | "reupload-shared" + | "rollback" + | "sendemail" + | "skipcaptcha" + | "suppressionlog" + | "tboverride" + | "templateeditor" + | "torunblocked" + | "transcode-reset" + | "translate" + | "undelete" + | "unwatchedpages" + | "upload" + | "upload_by_url" + | "viewmywatchlist" + | "viewsuppressed" + | "writeapi" + +export interface WikimediaProfile extends Record { + sub: string + username: string + editcount: number + confirmed_email: boolean + blocked: boolean + registered: string + groups: WikimediaGroup[] + rights: WikimediaRight[] + grants: WikimediaGrant[] + realname: string + email: string +} + +/** + * Wikimedia OAuth2 provider. + * All Wikimedia wikis are supported. Wikipedia, Wikidata, etc... + * + * (Register)[https://meta.wikimedia.org/wiki/Special:OAuthConsumerRegistration] + * (Documentation)[https://www.mediawiki.org/wiki/Extension:OAuth] + */ +export default function Wikimedia

( + options: OAuthUserConfig

+): OAuthConfig

{ + return { + id: "wikimedia", + name: "Wikimedia", + type: "oauth", + token: "https://meta.wikimedia.org/w/rest.php/oauth2/access_token", + userinfo: "https://meta.wikimedia.org/w/rest.php/oauth2/resource/profile", + authorization: { + url: "https://meta.wikimedia.org/w/rest.php/oauth2/authorize", + params: { scope: "" }, + }, + profile(profile) { + return { + id: profile.sub, + name: profile.username, + email: profile.email, + } + }, + options, + } +}