# Discord

Discord login can be initialized like any other OAuth provider by adding the app id and secret to config/default.json:

{
  "authentication": {
    "oauth": {
      "discord": {
        "key": "<App ID>",
        "secret": "<App Secret>",
        "scopes": ["identify email"]
      }
    }
  }
}

Protip: A list of all available Discord scopes can be found here

# Application client and secret

The client id (App ID) and secret can be found here: Discord App

Now add this to your src/authentication.ts:

import {OAuthProfile, OAuthStrategy} from "@feathersjs/authentication-oauth";
import {AuthenticationRequest} from "@feathersjs/authentication";
import axios, {AxiosRequestConfig} from 'axios'
import {ServiceAddons} from '@feathersjs/feathers';
import {AuthenticationService, JWTStrategy} from '@feathersjs/authentication';
import {LocalStrategy} from '@feathersjs/authentication-local';
import {expressOauth} from '@feathersjs/authentication-oauth';
import {Application} from './declarations';


export default function (app: Application) {
  const authentication = new AuthenticationService(app);

  authentication.register('jwt', new JWTStrategy());
  authentication.register('local', new LocalStrategy());
  authentication.register('discord', new DiscordStrategy());

  app.use('/authentication', authentication);
  app.configure(expressOauth());
}

export default class DiscordStrategy extends OAuthStrategy {
  async getProfile(authResult: AuthenticationRequest) {
    // This is the OAuth access token that can be used
    // for Discord API requests as the Bearer token
    const accessToken = authResult.access_token;
    const userOptions: AxiosRequestConfig = {
      method: 'GET',
      headers: {'Authorization': `Bearer ${accessToken}`},
      url: `https://discord.com/api/users/@me`,
    };
    const {data} = await axios(userOptions);
    return data;
  }

  async getEntityData(profile: OAuthProfile) {
    // `profile` is the data returned by getProfile
    const baseData = await super.getEntityData(profile);
    
    if (profile.avatar == null) {
      profile.avatar = 'https://cdn.discordapp.com/embed/avatars/0.png'
    } else {
      const isGif = profile.avatar.startsWith('a_');
      profile.avatar = `https://cdn.discordapp.com/avatars/${profile['id']}/${profile['avatar']}.${isGif ? 'gif' : 'png'}`
    }
    
    return {
      ...baseData,
      username: profile.username,
      email: profile.email,
      avatar: profile.avatar,
    };
  }
}

If you don't need the avatar then you can simply remove the lines of code. If the user doesn't have an avatar then we will set it to Discord's default avatar.