2021-02-05 08:22:22 +08:00
|
|
|
import { Context, Middleware } from '@nuxt/types';
|
|
|
|
import { PermissionCheck } from 'hangar-api';
|
|
|
|
import { NamedPermission, PermissionType } from '~/types/enums';
|
|
|
|
import { AuthState } from '~/store/auth';
|
|
|
|
|
2021-03-13 18:10:56 +08:00
|
|
|
const loggedInMiddleware = (code: number, msg?: string): Middleware => ({ store, error }: Context) => {
|
2021-02-05 08:22:22 +08:00
|
|
|
if (!store.state.auth.authenticated) {
|
|
|
|
error({
|
2021-03-13 18:10:56 +08:00
|
|
|
message: msg,
|
|
|
|
statusCode: code,
|
2021-02-05 08:22:22 +08:00
|
|
|
});
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2021-04-04 14:20:20 +08:00
|
|
|
export function NotLoggedIn(constructor: Function) {
|
|
|
|
addMiddleware(constructor, ({ store, redirect }) => {
|
|
|
|
if (store.state.auth.authenticated) {
|
|
|
|
redirect('/');
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2021-02-05 08:22:22 +08:00
|
|
|
export function LoggedIn(constructor: Function) {
|
2021-03-13 18:10:56 +08:00
|
|
|
addMiddleware(constructor, loggedInMiddleware(401, 'You must be logged in to perform this action'));
|
2021-02-05 08:22:22 +08:00
|
|
|
}
|
|
|
|
|
2021-04-06 16:41:02 +08:00
|
|
|
export function CurrentUser(constructor: Function) {
|
|
|
|
addMiddleware(constructor, loggedInMiddleware(403), ({ params, store, $perms, error }) => {
|
|
|
|
if (!$perms.canEditAllUserSettings) {
|
|
|
|
if (!params.user) {
|
|
|
|
throw new TypeError("Must have 'user' as a route param to use CurrentUser");
|
|
|
|
}
|
|
|
|
if (params.user !== (store.state.auth as AuthState).user!.name) {
|
|
|
|
error({
|
|
|
|
statusCode: 403,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2021-02-05 08:22:22 +08:00
|
|
|
// TODO this maybe should use the global permissions store in the JWT to reduce db lookups?
|
|
|
|
export function GlobalPermission(...permissions: NamedPermission[]) {
|
2021-04-03 14:56:55 +08:00
|
|
|
const middleware: Middleware = ({ error, $api, $util }: Context) => {
|
2021-02-05 08:22:22 +08:00
|
|
|
return $api
|
|
|
|
.request<PermissionCheck>('permissions/hasAll', true, 'get', {
|
|
|
|
permissions,
|
|
|
|
})
|
|
|
|
.then((check) => {
|
|
|
|
if (check.type !== PermissionType.GLOBAL || !check.result) {
|
|
|
|
error({
|
|
|
|
message: 'Not Found',
|
|
|
|
statusCode: 404,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
})
|
2021-04-03 14:56:55 +08:00
|
|
|
.catch($util.handlePageRequestError);
|
2021-02-05 08:22:22 +08:00
|
|
|
};
|
|
|
|
|
|
|
|
return function (constructor: Function) {
|
2021-03-13 18:10:56 +08:00
|
|
|
addMiddleware(constructor, loggedInMiddleware(404), middleware);
|
2021-02-05 08:22:22 +08:00
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
export function ProjectPermission(...permissions: NamedPermission[]) {
|
|
|
|
const middleware: Middleware = ({ store, route, $util, error }: Context) => {
|
|
|
|
if (!route.params.author || !route.params.slug) {
|
|
|
|
throw new Error("Can't use this decorator on a route without `author` and `slug` path params");
|
|
|
|
}
|
|
|
|
if (!(store.state.auth as AuthState).routePermissions) {
|
|
|
|
error({
|
|
|
|
statusCode: 404,
|
|
|
|
});
|
2021-02-07 13:44:53 +08:00
|
|
|
return;
|
2021-02-05 08:22:22 +08:00
|
|
|
}
|
2021-02-07 11:22:37 +08:00
|
|
|
if (!$util.hasPerms(...permissions)) {
|
2021-02-05 08:22:22 +08:00
|
|
|
error({
|
|
|
|
statusCode: 404,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
return function (constructor: Function) {
|
2021-03-13 18:10:56 +08:00
|
|
|
addMiddleware(constructor, loggedInMiddleware(404), middleware);
|
2021-02-05 08:22:22 +08:00
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
function addMiddleware(constructor: Function, ...middleware: Middleware[]): void {
|
|
|
|
if (!constructor.prototype.middleware) {
|
|
|
|
constructor.prototype.middleware = [...middleware];
|
|
|
|
} else if (typeof constructor.prototype.middleware === 'string') {
|
|
|
|
constructor.prototype.middleware = [constructor.prototype.middleware, ...middleware];
|
|
|
|
} else if (Array.isArray(constructor.prototype.middleware)) {
|
|
|
|
constructor.prototype.middleware = [...constructor.prototype.middleware, ...middleware];
|
|
|
|
} else {
|
|
|
|
throw new TypeError('Unable to add permissions middleware');
|
|
|
|
}
|
|
|
|
}
|