@eduzz/miau-client 1.2.0 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build$colon$types.log +1 -1
- package/dist/MiauClient.d.ts +3 -1
- package/dist/index.js +42 -22
- package/dist/index.js.map +2 -2
- package/package.json +1 -1
- package/src/MiauClient.ts +15 -1
- package/src/middleware.ts +37 -28
package/dist/MiauClient.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { type RequestHandler } from 'express';
|
|
2
|
-
import { type SecretEnv, type Permission, type Resource } from '@eduzz/miau-types';
|
|
2
|
+
import { type SecretEnv, type Permission, type Resource, type MiauClientToken } from '@eduzz/miau-types';
|
|
3
3
|
import { type RequestAugmentation } from './middleware';
|
|
4
4
|
type MiauClientConfig = {
|
|
5
5
|
apiUrl: string;
|
|
@@ -14,12 +14,14 @@ export declare class MiauClient {
|
|
|
14
14
|
getEnvironment(): SecretEnv;
|
|
15
15
|
getPublicKey(kid: string): Promise<string>;
|
|
16
16
|
getToken(): Promise<string | undefined>;
|
|
17
|
+
getTokenData: () => Promise<MiauClientToken>;
|
|
17
18
|
middleware<T = Record<string, string>>(config?: {
|
|
18
19
|
requestAugmentation?: RequestAugmentation<T>;
|
|
19
20
|
fallbackMiddleware?: RequestHandler;
|
|
20
21
|
}): RequestHandler;
|
|
21
22
|
getResources(): Promise<Resource[]>;
|
|
22
23
|
getPermissions(targetAppId: string): Promise<Permission>;
|
|
24
|
+
verify(token: string, publicKey: string): Promise<MiauClientToken>;
|
|
23
25
|
private getApiJwtUrl;
|
|
24
26
|
private getPermissionsUrl;
|
|
25
27
|
private getResourcesUrl;
|
package/dist/index.js
CHANGED
|
@@ -11909,8 +11909,8 @@ var isResourceAllowed = (resource, resources, permittedResources) => {
|
|
|
11909
11909
|
|
|
11910
11910
|
// src/middleware.ts
|
|
11911
11911
|
var HttpError = class _HttpError extends Error {
|
|
11912
|
-
constructor(status, name, message) {
|
|
11913
|
-
super(message);
|
|
11912
|
+
constructor(status, name, message, code) {
|
|
11913
|
+
super(`${message} (${code})`);
|
|
11914
11914
|
this.name = name;
|
|
11915
11915
|
this.status = status;
|
|
11916
11916
|
Object.setPrototypeOf(this, _HttpError.prototype);
|
|
@@ -11921,49 +11921,59 @@ var miauMiddleware = (miauClient, requestAugmentation, fallbackMiddleware) => {
|
|
|
11921
11921
|
try {
|
|
11922
11922
|
const token = req.headers.authorization?.split(" ").pop();
|
|
11923
11923
|
if (!token) {
|
|
11924
|
-
throw new HttpError(400, "Invalid Token", "Token not provided");
|
|
11924
|
+
throw new HttpError(400, "Invalid Token", "Token not provided", "MIAU_TKN_A");
|
|
11925
11925
|
}
|
|
11926
11926
|
const decodedToken = import_jsonwebtoken.default.decode(token, { complete: true });
|
|
11927
11927
|
if (!decodedToken) {
|
|
11928
|
-
throw new HttpError(400, "Invalid Token", "Token could not be decoded");
|
|
11928
|
+
throw new HttpError(400, "Invalid Token", "Token could not be decoded", "MIAU_TKN_B");
|
|
11929
11929
|
}
|
|
11930
11930
|
if (!decodedToken.header?.kid) {
|
|
11931
|
-
throw new HttpError(400, "Invalid Token", "Missing kid in token header");
|
|
11931
|
+
throw new HttpError(400, "Invalid Token", "Missing kid in token header", "MIAU_TKN_C");
|
|
11932
11932
|
}
|
|
11933
11933
|
if (decodedToken.payload.iss !== issuers["production"]) {
|
|
11934
|
-
throw new HttpError(400, "Invalid Token", "Token issuer is invalid");
|
|
11934
|
+
throw new HttpError(400, "Invalid Token", "Token issuer is invalid", "MIAU_TKN_D");
|
|
11935
11935
|
}
|
|
11936
11936
|
const publicKey = await miauClient.getPublicKey(decodedToken.header.kid);
|
|
11937
|
-
const
|
|
11938
|
-
|
|
11939
|
-
|
|
11940
|
-
|
|
11941
|
-
|
|
11942
|
-
|
|
11937
|
+
const clientTokenData = await miauClient.verify(token, publicKey);
|
|
11938
|
+
const serverTokenData = await miauClient.getTokenData();
|
|
11939
|
+
if (!clientTokenData || !clientTokenData.application || !clientTokenData.secret || !clientTokenData.application.id || !clientTokenData.secret.id || !clientTokenData.secret.environment) {
|
|
11940
|
+
throw new HttpError(401, "Invalid Token", "Token invalid or expired", "MIAU_TKN_E");
|
|
11941
|
+
}
|
|
11942
|
+
const { application: clientApplication, secret: clientSecret } = clientTokenData;
|
|
11943
|
+
const { application: serverApplication, secret: serverSecret } = serverTokenData;
|
|
11944
|
+
if (clientSecret.environment != serverSecret.environment) {
|
|
11943
11945
|
throw new HttpError(
|
|
11944
|
-
|
|
11946
|
+
401,
|
|
11945
11947
|
"Invalid Environment",
|
|
11946
|
-
`Secret environment ${
|
|
11948
|
+
`Secret environment ${clientSecret.environment} does not match Server environment ${serverSecret.environment}`,
|
|
11949
|
+
"MIAU_ENV_A"
|
|
11947
11950
|
);
|
|
11948
11951
|
}
|
|
11949
11952
|
const resources = await miauClient.getResources();
|
|
11950
11953
|
if (!resources) {
|
|
11951
|
-
throw new HttpError(401, "Unauthorized",
|
|
11954
|
+
throw new HttpError(401, "Unauthorized", `No resources configured in ${serverApplication.name}`, "MIAU_RES_A");
|
|
11952
11955
|
}
|
|
11953
|
-
const permission = await miauClient.getPermissions(
|
|
11956
|
+
const permission = await miauClient.getPermissions(clientApplication.id);
|
|
11954
11957
|
if (!permission) {
|
|
11955
|
-
throw new HttpError(
|
|
11958
|
+
throw new HttpError(
|
|
11959
|
+
401,
|
|
11960
|
+
"Unauthorized",
|
|
11961
|
+
`No permissions found for ${clientApplication.name} in ${serverApplication.name}`,
|
|
11962
|
+
"MIAU_PERM_A"
|
|
11963
|
+
);
|
|
11956
11964
|
}
|
|
11957
11965
|
const permittedResources = permission?.resources || [];
|
|
11958
|
-
if (!permittedResources.length) {
|
|
11959
|
-
throw new HttpError(403, "Forbidden", "No resources are permitted for this application");
|
|
11960
|
-
}
|
|
11961
11966
|
const resource = { protocol: "http", method: req.method, path: req.path };
|
|
11962
11967
|
const isAllowed = isResourceAllowed(resource, resources, permittedResources);
|
|
11963
11968
|
if (!isAllowed) {
|
|
11964
|
-
throw new HttpError(
|
|
11969
|
+
throw new HttpError(
|
|
11970
|
+
403,
|
|
11971
|
+
"Forbidden",
|
|
11972
|
+
`${clientApplication.name} does not have permission to ${req.method} ${req.path} on ${serverApplication.name}`,
|
|
11973
|
+
"MIAU_PERM_B"
|
|
11974
|
+
);
|
|
11965
11975
|
}
|
|
11966
|
-
req.miauApplication = { id:
|
|
11976
|
+
req.miauApplication = { id: clientApplication.id, name: clientApplication.name };
|
|
11967
11977
|
const environment = miauClient.getEnvironment();
|
|
11968
11978
|
req.miauMetadata = permission?.metadata?.[environment] || {};
|
|
11969
11979
|
if (requestAugmentation) {
|
|
@@ -12022,6 +12032,13 @@ var expiresHeaderToUnixtime = (expires) => {
|
|
|
12022
12032
|
};
|
|
12023
12033
|
var MiauClient = class {
|
|
12024
12034
|
constructor(config) {
|
|
12035
|
+
this.getTokenData = async () => {
|
|
12036
|
+
const token = await this.getToken();
|
|
12037
|
+
if (!token) {
|
|
12038
|
+
throw new Error("Token is undefined");
|
|
12039
|
+
}
|
|
12040
|
+
return import_jsonwebtoken2.default.decode(token);
|
|
12041
|
+
};
|
|
12025
12042
|
this.getApiJwtUrl = () => {
|
|
12026
12043
|
return `${this.config.apiUrl}/v1/jwt`;
|
|
12027
12044
|
};
|
|
@@ -12091,6 +12108,9 @@ var MiauClient = class {
|
|
|
12091
12108
|
headers: { Authorization: `Basic ${this.basicAuthToken}` }
|
|
12092
12109
|
});
|
|
12093
12110
|
}
|
|
12111
|
+
async verify(token, publicKey) {
|
|
12112
|
+
return import_jsonwebtoken2.default.verify(token, publicKey, { algorithms: ["RS256"] });
|
|
12113
|
+
}
|
|
12094
12114
|
};
|
|
12095
12115
|
// Annotate the CommonJS export names for ESM import in node:
|
|
12096
12116
|
0 && (module.exports = {
|