Skip to content

Commit b2fa49c

Browse files
committed
fix(backend-native): Pass req.securityContext to Python config
This is necessary for `extend_context`. By the time `extendContext` is called, `req` in JS-land is already extended with `securityContext` after `checkAuth`, and JS config receives it with extensions.
1 parent 1cf867a commit b2fa49c

File tree

3 files changed

+44
-0
lines changed

3 files changed

+44
-0
lines changed

packages/cubejs-backend-native/js/index.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -352,6 +352,7 @@ export interface PyConfiguration {
352352
repositoryFactory?: (ctx: unknown) => Promise<unknown>,
353353
logger?: (msg: string, params: Record<string, any>) => void,
354354
checkAuth?: (req: unknown, authorization: string) => Promise<{ 'security_context'?: unknown }>
355+
extendContext?: (req: unknown) => Promise<unknown>
355356
queryRewrite?: (query: unknown, ctx: unknown) => Promise<unknown>
356357
contextToApiScopes?: () => Promise<string[]>
357358
contextToRoles?: (ctx: unknown) => Promise<string[]>
@@ -365,6 +366,11 @@ function simplifyExpressRequest(req: ExpressRequest) {
365366
method: req.method,
366367
headers: req.headers,
367368
ip: req.ip,
369+
370+
// req.securityContext is an extension of request done by api-gateway
371+
// But its typings currently live in api-gateway package, which has native-backend (this package) as it's dependency
372+
// TODO extract typings to separate package and drop as any
373+
...(Object.hasOwn(req, 'securityContext') ? { securityContext: (req as any).securityContext } : {}),
368374
};
369375
}
370376

packages/cubejs-backend-native/test/config.py

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,21 @@ async def check_auth(req, authorization):
2020
}
2121

2222

23+
@config('extend_context')
24+
def extend_context(req):
25+
print("[python] extend_context req=", req)
26+
if "securityContext" not in req:
27+
return {
28+
"security_context": "missing",
29+
}
30+
31+
req["securityContext"]["extended_by_config"] = True
32+
33+
return {
34+
"security_context": req["securityContext"],
35+
}
36+
37+
2338
@config
2439
async def repository_factory(ctx):
2540
print("[python] repository_factory ctx=", ctx)

packages/cubejs-backend-native/test/python.test.ts

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,29 @@ suite('Python Config', () => {
8383
expect(await config.contextToApiScopes()).toEqual(['meta', 'data', 'jobs']);
8484
});
8585

86+
test('extend_context', async () => {
87+
if (!config.extendContext) {
88+
throw new Error('extendContext was not defined in config.py');
89+
}
90+
91+
// Without security context
92+
expect(await config.extendContext({})).toEqual({
93+
security_context: 'missing',
94+
});
95+
96+
// With security context
97+
expect(await config.extendContext({
98+
securityContext: { sub: '1234567890', iat: 1516239022, user_id: 42 }
99+
})).toEqual({
100+
security_context: {
101+
extended_by_config: true,
102+
sub: '1234567890',
103+
iat: 1516239022,
104+
user_id: 42
105+
},
106+
});
107+
});
108+
86109
test('repository factory', async () => {
87110
if (!config.repositoryFactory) {
88111
throw new Error('repositoryFactory was not defined in config.py');

0 commit comments

Comments
 (0)