-
Notifications
You must be signed in to change notification settings - Fork 117
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Typing of the result of getAuthenticateOptions is misleading/incorrect #947
Comments
This issue is related to #946. |
I guess that @eesdil's point is very important, because... The method So, currently...
export interface IAuthModuleOptions<T = any> {
defaultStrategy?: string | string[];
session?: boolean;
property?: string;
[key: string]: any;
}
export type IAuthGuard = CanActivate & {
// ...
getAuthenticateOptions(context: ExecutionContext): IAuthModuleOptions | undefined;
// ...
};
class MixinAuthGuard<TUser = any> implements CanActivate {
@Optional()
@Inject(AuthModuleOptions)
protected options: AuthModuleOptions = {};
constructor(@Optional() options?: AuthModuleOptions) {
this.options = options ?? this.options;
// ...
}
async canActivate(context: ExecutionContext): Promise<boolean> {
const options = { // <-- MERGED OPTIONS
...defaultOptions,
...this.options,
...(await this.getAuthenticateOptions(context))
};
const [request, response] = [
this.getRequest(context),
this.getResponse(context)
];
const passportFn = createPassportContext(request, response);
const user = await passportFn(
type || this.options.defaultStrategy,
options, // <-- PASS OPTIONS TO passport.authenticate
(err, user, info, status) =>
this.handleRequest(err, user, info, context, status)
);
request[options.property || defaultOptions.property] = user;
return true;
}
// ...
}
const createPassportContext =
(request, response) => (type, options, callback: Function) =>
new Promise<void>((resolve, reject) =>
passport.authenticate(type, options, (err, user, info, status) => { // <-- passport.authenticate CALL
try {
request.authInfo = info;
return resolve(callback(err, user, info, status));
} catch (err) {
reject(err);
}
})(request, response, (err) => (err ? reject(err) : resolve()))
);
I noticed this when inspecting the authorization URL generated by the client_id: my-app
scope: openid profile
response_type: code
redirect_uri: http://localhost:3000/auth/oidc/callback
state: 4nCwYO3jS8tKHzbM1FN_lv5yyAOHVMlITMUW8dND494
session: true # <-- EXPOSED OPTION
property: user # <-- EXPOSED OPTION
defaultStrategy: oidc # <-- EXPOSED OPTION
code_challenge: TYrhDeMoO9j9_CXuHSLXdCGdIXukT4orrYtZ8X3783g
code_challenge_method: S256 I think As proposed, the approach should be changed to: export interface IAuthModuleOptions<T = any> {
defaultStrategy?: string | string[];
session?: boolean;
property?: string;
authenticateOptions?: AuthenticateOptions; // <-- NEW PROPERTY
[key: string]: any;
}
export type IAuthGuard = CanActivate & {
// ...
// CHANGED RETURN TYPE
getAuthenticateOptions(context: ExecutionContext): Promise<AuthenticateOptions> | AuthenticateOptions | undefined;
// ...
};
class MixinAuthGuard<TUser = any> implements CanActivate {
@Optional()
@Inject(AuthModuleOptions)
protected options: AuthModuleOptions = {};
constructor(@Optional() options?: AuthModuleOptions) {
this.options = options ?? this.options;
// ...
}
async canActivate(context: ExecutionContext): Promise<boolean> {
const options = this.options; // <-- MODULE OPTIONS
const authenticateOptions = { // <-- AUTHENTICATE OPTIONS
...defaultOptions.authenticateOptions,
...options.authenticateOptions,
...(await this.getAuthenticateOptions(context))
};
const [request, response] = [
this.getRequest(context),
this.getResponse(context)
];
const passportFn = createPassportContext(request, response);
const user = await passportFn(
type || this.options.defaultStrategy,
authenticateOptions, // <-- PASS OPTIONS TO passport.authenticate
(err, user, info, status) =>
this.handleRequest(err, user, info, context, status)
);
request[options.property || defaultOptions.property] = user;
return true;
}
// ...
} PR #1610 |
Is there an existing issue for this?
Current behavior
Current typing is:
It is allowing/suggesting that the defaultStrategy can be passed, which in fact is ignored.
Also it is not showing that a promise can be used.
Minimum reproduction code
https://github.com/nestjs/passport/blob/master/lib/auth.guard.ts
Steps to reproduce
No response
Expected behavior
Disable adding the defaultStrategy with using different signature, something like: Omit<IAuthModuleOptions, 'defaultStrategy'>
Plus having the Promise<Omit<IAuthModuleOptions, 'defaultStrategy'>> also.
Package version
8.2.2
Passport version
No response
NestJS version
No response
Node.js version
No response
In which operating systems have you tested?
Other
No response
The text was updated successfully, but these errors were encountered: