Skip to content

Commit

Permalink
Update dependencies and refactor code for Auth0 management models
Browse files Browse the repository at this point in the history
Updated the dependencies for more accurate types and better performance. Refactored the code in the management modules and providers to accommodate the changes in the updated dependencies. The management client now has more precise typing for options.
  • Loading branch information
taylor009 committed May 10, 2024
1 parent 5dc4aa6 commit 1008d9e
Show file tree
Hide file tree
Showing 12 changed files with 2,983 additions and 2,207 deletions.
4,959 changes: 2,893 additions & 2,066 deletions package-lock.json

Large diffs are not rendered by default.

22 changes: 11 additions & 11 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -42,22 +42,22 @@
},
"homepage": "https://github.com/Twirelab/nestjs-auth0#readme",
"dependencies": {
"auth0": "^2.40.0",
"reflect-metadata": "^0.1.13",
"auth0": "^4.4.0",
"reflect-metadata": "^0.2.2",
"rxjs": "^7.5.5"
},
"devDependencies": {
"@nestjs/common": "^8.4.4",
"@nestjs/core": "^8.4.4",
"@nestjs/testing": "^8.4.4",
"@types/auth0": "^2.34.19",
"@types/jest": "^27.5.0",
"jest": "^28.1.0",
"ts-jest": "^28.0.2",
"typescript": "^4.6.4"
"@nestjs/common": "^10.3.8",
"@nestjs/core": "^10.3.8",
"@nestjs/testing": "^10.3.8",
"@types/auth0": "^3.3.10",
"@types/jest": "^29.5.12",
"jest": "^29.7.0",
"ts-jest": "^29.1.2",
"typescript": "^5.4.5"
},
"peerDependencies": {
"@nestjs/common": "^8.0.0",
"@nestjs/core": "^8.0.0"
}
}
}
5 changes: 3 additions & 2 deletions src/clients/management.client.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { ManagementClient, ManagementClientOptions } from "auth0";
import { ManagementClient, ManagementClientOptionsWithClientCredentials } from "auth0";
// import type { ManagementClientBase } from "auth0";

/**
* Get Auth0 Authentication client.
Expand All @@ -7,6 +8,6 @@ import { ManagementClient, ManagementClientOptions } from "auth0";
*
* @return {mana}
*/
export function getManagementClient(options: ManagementClientOptions): ManagementClient {
export function getManagementClient(options: ManagementClientOptionsWithClientCredentials): ManagementClient {
return new ManagementClient(options);
}
80 changes: 25 additions & 55 deletions src/modules/authentication-core.module.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Global, Module, DynamicModule, Provider, ClassProvider } from "@nestjs/common";
import { Global, Module, DynamicModule, Provider } from "@nestjs/common";
import { AuthenticationClientOptions } from "auth0";
import { getAuthenticationClient } from "../clients/authentication.client";
import { AUTH_CLIENT, AUTH_MODULE } from "../constants";
Expand All @@ -8,91 +8,61 @@ import { createAuthenticationProvider } from "../providers/authentication.provid
@Global()
@Module({})
export class AuthenticationCoreModule {
/**
* For root.
*
* @param {AuthenticationClientOptions} options
*
* @return {DynamicModule}
*/
public static forRoot(options: AuthenticationClientOptions): DynamicModule {
const provider = createAuthenticationProvider(options);

return {
exports: [provider],
module: AuthenticationCoreModule,
providers: [provider],
}
};
}

/**
* For root async.
*
* @param {AuthenticationAsyncOptions} options
*
* @return {DynamicModule}
*/
static forRootAsync(options: AuthenticationAsyncOptions): DynamicModule {
const provider: Provider<any> = {
const provider: Provider = {
inject: [AUTH_MODULE],
provide: AUTH_CLIENT,
useFactory: (authOptions: AuthenticationClientOptions) => getAuthenticationClient(authOptions),
}
};

return {
exports: [provider],
imports: options.imports,
module: AuthenticationCoreModule,
providers: [...this.createAsyncProviders(options), provider],
}
};
}

/**
* Create async options provider.
*
* @param {AuthenticationAsyncOptions} options
*
* @return {Provider}
*/
private static createAsyncOptionsProvider(options: AuthenticationAsyncOptions): Provider {
if (options.useFactory) {
return {
inject: options.inject ?? [],
provide: AUTH_MODULE,
useFactory: options.useFactory,
};
}

return {
inject: options.useExisting
? [options.useExisting]
: options.useClass
? [options.useClass]
: [],
provide: AUTH_MODULE,
useFactory: (optionsFactory: AuthenticationOptionsFactory) => optionsFactory.createAuth0Options(),
} else if (options.useExisting || options.useClass) {
const injectToken = options.useExisting ?? options.useClass;
if (!injectToken) {
throw new Error('A valid injection token is required for useExisting or useClass');
}
return {
inject: [injectToken],
provide: AUTH_MODULE,
useFactory: (optionsFactory: AuthenticationOptionsFactory) => optionsFactory.createAuth0Options(),
};
} else {
throw new Error('Invalid configuration for the authentication module');
}
}

/**
* Create async provider.
*
* @param {AuthenticationAsyncOptions} options
*
* @return {Provider[]}
*/
private static createAsyncProviders(options: AuthenticationAsyncOptions): Provider[] {
if (options.useExisting || options.useFactory) {
return [this.createAsyncOptionsProvider(options)];
}

return [
this.createAsyncOptionsProvider(options),
{
const providers: Provider[] = [this.createAsyncOptionsProvider(options)];
if (options.useClass) {
providers.push({
provide: options.useClass,
useClass: options.useClass,
inject: [options.inject ?? []],
} as ClassProvider,
];
useClass: options.useClass
});
}
return providers;
}
}
}
74 changes: 22 additions & 52 deletions src/modules/management-core.module.ts
Original file line number Diff line number Diff line change
@@ -1,59 +1,39 @@
import { Global, Module, DynamicModule, Provider, ClassProvider } from "@nestjs/common";
import { ManagementClientOptions } from "auth0";
import { ManagementClientOptions } from "auth0/dist/cjs/management/management-client-options";
import { getManagementClient } from "../clients/management.client";
import { ManagementAsyncOptions, ManagementOptionsFactory } from "../auth0.options";
import { createManagementProvider } from "../providers/management.provider";
import { MANG_CLIENT, MANG_MODULE } from "../constants";
import { ManagementClientOptionsWithClientCredentials } from "auth0";

@Global()
@Module({})
export class ManagementCoreModule {
/**
* For root.
*
* @param {ManagementClientOptions} options
*
* @return {DynamicModule}
*/
public static forRoot(options: ManagementClientOptions): DynamicModule {
public static forRoot(options: ManagementClientOptions & { clientId: string; clientAssertionSigningKey: string; }): DynamicModule {
const provider = createManagementProvider(options);

return {
exports: [provider],
module: ManagementCoreModule,
providers: [provider],
}
};
}

/**
* For root async.
*
* @param {ManagementAsyncOptions} options
*
* @return {DynamicModule}
*/
static forRootAsync(options: ManagementAsyncOptions): DynamicModule {
const provider: Provider<any> = {
const provider: Provider = {
inject: [MANG_MODULE],
provide: MANG_CLIENT,
useFactory: (authOptions: ManagementClientOptions) => getManagementClient(authOptions),
}
useFactory: (authOptions: ManagementClientOptionsWithClientCredentials) => getManagementClient(authOptions),
};

return {
exports: [provider],
imports: options.imports,
module: ManagementCoreModule,
providers: [...this.createAsyncProviders(options), provider],
}
};
}

/**
* Create async options provider.
*
* @param {ManagementAsyncOptions} options
*
* @return {Provider}
*/
private static createAsyncOptionsProvider(options: ManagementAsyncOptions): Provider {
if (options.useFactory) {
return {
Expand All @@ -63,36 +43,26 @@ export class ManagementCoreModule {
};
}

const inject = options.useExisting ? [options.useExisting] : (options.useClass ? [options.useClass] : []);
if (inject.length === 0) {
throw new Error('Invalid configuration for the management module: A valid injection token is required');
}
return {
inject: options.useExisting
? [options.useExisting]
: options.useClass
? [options.useClass]
: [],
inject,
provide: MANG_MODULE,
useFactory: (optionsFactory: ManagementOptionsFactory) => optionsFactory.createAuth0Options(),
}
};
}

/**
* Create async provider.
*
* @param {ManagementAsyncOptions} options
*
* @return {Provider[]}
*/
private static createAsyncProviders(options: ManagementAsyncOptions): Provider[] {
if (options.useExisting || options.useFactory) {
return [this.createAsyncOptionsProvider(options)];
}

return [
this.createAsyncOptionsProvider(options),
{
const providers: Provider[] = [this.createAsyncOptionsProvider(options)];
if (options.useClass) {
providers.push({
provide: options.useClass,
useClass: options.useClass,
inject: [options.inject ?? []],
} as ClassProvider,
];
...(options.inject ? { inject: options.inject } : {}),
} as ClassProvider);
}
return providers;
}
}
}
4 changes: 2 additions & 2 deletions src/modules/management.module.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { DynamicModule, Global, Module } from "@nestjs/common";
import { ManagementClientOptions } from "auth0";
import { ManagementAsyncOptions } from "../auth0.options";
import { ManagementCoreModule } from "./management-core.module";
import {ManagementClientOptions} from "auth0";

@Global()
@Module({})
Expand All @@ -13,7 +13,7 @@ export class ManagementModule {
*
* @return {DynamicModule}
*/
public static forRoot(options: ManagementClientOptions): DynamicModule {
public static forRoot(options: ManagementClientOptions & { clientId: string; clientAssertionSigningKey: string; }): DynamicModule {
return {
module: ManagementModule,
imports: [ManagementCoreModule.forRoot(options)],
Expand Down
11 changes: 6 additions & 5 deletions src/providers/management.provider.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
import { Provider } from "@nestjs/common";
import { ManagementClient, ManagementClientOptions } from "auth0";
import { ManagementClientOptions } from "auth0";
import { ManagementClientBase as ManagementClient } from "auth0/dist/cjs/management/__generated/index";
import { getManagementClient } from "../clients/management.client";
import { MANG_CLIENT } from "../constants";

/**
* Create Auth0 Management provider.
*
* @param {ManagementClientOptions} options
*
*
* @param {ManagementClientOptions & { clientId: string, clientAssertionSigningKey: string }} options
*
* @return
*/
export function createManagementProvider(options: ManagementClientOptions): Provider<ManagementClient> {
export function createManagementProvider(options: ManagementClientOptions & { clientId: string, clientAssertionSigningKey: string }): Provider<ManagementClient> {
return {
provide: MANG_CLIENT,
useValue: getManagementClient(options),
Expand Down
3 changes: 2 additions & 1 deletion test/clients/authentication.client.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,9 @@ import { ManagementClient } from "auth0";
describe("Get ManagementClient Client", () => {
it("Returns managementClient client", () => {
const client = getManagementClient({
token: "test",
domain: "test.com",
clientId: "yourClientId",
clientAssertionSigningKey: "yourClientAssertionSigningKey"
});

expect(client).toBeInstanceOf(ManagementClient);
Expand Down
6 changes: 3 additions & 3 deletions test/inject/authentication.inject.test.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import { Injectable } from "@nestjs/common";
import { Test, TestingModule } from "@nestjs/testing";
import { AuthenticationClient } from "auth0";
import { InjectAuthentication } from "../../src/inject/authentication.inject"
import { AuthenticationModule } from "../../src/modules/authentication.module";
import { InjectAuthentication } from "../../src"
import { AuthenticationModule } from "../../src";

describe("Inject Authentication", () => {
let module: TestingModule;
Expand All @@ -14,7 +14,7 @@ describe("Inject Authentication", () => {

beforeEach(async () => {
module = await Test.createTestingModule({
imports: [AuthenticationModule.forRoot({ domain: "test.com" })],
imports: [AuthenticationModule.forRoot({ domain: "test.com", clientId: "yourClientId" })],
providers: [TestService],
}).compile();
});
Expand Down
11 changes: 8 additions & 3 deletions test/inject/management.inject.test.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import { Injectable } from "@nestjs/common";
import { Test, TestingModule } from "@nestjs/testing";
import { ManagementClient } from "auth0";
import { InjectManagement } from "../../src/inject/management.inject"
import { ManagementModule } from "../../src/modules/management.module";
import { InjectManagement } from "../../src"
import { ManagementModule } from "../../src";

describe("Inject Management", () => {
let module: TestingModule;
Expand All @@ -14,7 +14,12 @@ describe("Inject Management", () => {

beforeEach(async () => {
module = await Test.createTestingModule({
imports: [ManagementModule.forRoot({ domain: "test.com", clientId: "testId", clientSecret: "testSecret" })],
imports: [ManagementModule.forRoot({
domain: 'test.com',
audience: 'test',
clientId: 'yourClientId',
clientAssertionSigningKey: 'yourClientAssertionSigningKey'
})],
providers: [TestService],
}).compile();
});
Expand Down
Loading

0 comments on commit 1008d9e

Please sign in to comment.