0

Scenario:

My project is using the latest version of @okta/okta-angular. It exports the class 'OktaAuthService'. I would like to use module augmentation to add a method to it

What I've tried


import { OktaAuthService } from '@okta/okta-angular';

declare module '@okta/okta-angular' {
  interface OktaAuthService {
    getUserRole(): Promise<RoleEnum>;
  } 
}

OktaAuthService.prototype.getUserRole = function (): Promise<Role> {
  return OktaAuthService.prototype.getUser().then(userClaims => {
   //pseudo code
   if user has claim 
     return Role;
   //
  });
}

According to https://www.typescriptlang.org/docs/handbook/declaration-merging.html#module-augmentation this should work, however

  • the interface appears to be ghosting the import (TS2693 'OktaAuthService' only refers to a type, but is being used as a value here (where I set the getUserRole function)

  • If I remove the new function, but leave the module, compilation fails everywhere I import from "@okta/okta-angular"

What am I misunderstanding here?

2 Answers2

0

I recommend to use interface inheritance, example:

import { OktaAuthService } from '@okta/okta-angular';


interface OktaAuthServiceCustom extends OktaAuthService {
    getUserRole(): Promise<RoleEnum>;
} 


OktaAuthService.prototype.getUserRole = function (): Promise<Role> {
  return (OktaAuthService as OktaAuthServiceCustom).prototype.getUser().then(userClaims => {
   //pseudo code
   if user has claim 
     return Role;
   //
  });
}
anlijudavid
  • 509
  • 6
  • 12
  • Taking the example as a working example I have some challenges (this is the first time I've tried this sort of thing) This gives me compile time warnings about - getUserRole does not exist on type OktaAuthService - OktaAuthService and OktaAuthServiceCustom don't overlap enough for the cast - getUserRole isn't a member of OktaAuthService.prototype Sorry, can you expand a little more? – kjwhal-ai Jan 15 '21 at 20:36
  • So, try: interface OktaAuthServiceCustom extends OktaAuthService { prototype: { getUserRole(): Promise; } } – anlijudavid Jan 15 '21 at 20:38
0

The answer ended up being as follows

import { OktaAuthService } from '@okta/okta-angular';
import { RoleEnum } from '../model/Enums';


declare module '@okta/okta-angular/src/okta/services/okta.service' {
  interface OktaAuthService {
    getUserRole(): Promise<RoleEnum>;
  } 
}

OktaAuthService.prototype.getUserRole = function (): Promise<RoleEnum> {
  return this.getUser().then(userClaims => {
});
}