Skip to content

Commit ed14e05

Browse files
feat: add support for context.params in edge functions (#5964)
Co-authored-by: Simon Knott <info@simonknott.de>
1 parent 42478fd commit ed14e05

File tree

4 files changed

+58
-17
lines changed

4 files changed

+58
-17
lines changed

src/lib/edge-functions/bootstrap.mjs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { env } from 'process'
22

3-
const latestBootstrapURL = 'https://64c264287e9cbb0008621df3--edge.netlify.com/bootstrap/index-combined.ts'
3+
const latestBootstrapURL = 'https://64e7783fce8cfe0008496c72--edge.netlify.com/bootstrap/index-combined.ts'
44

55
export const getBootstrapURL = () => env.NETLIFY_EDGE_BOOTSTRAP || latestBootstrapURL

src/lib/edge-functions/registry.mjs

Lines changed: 28 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -318,23 +318,38 @@ export class EdgeFunctionsRegistry {
318318
functions: this.#functions,
319319
featureFlags,
320320
})
321-
const invocationMetadata = {
322-
function_config: manifest.function_config,
323-
routes: manifest.routes.map((route) => ({ function: route.function, pattern: route.pattern })),
324-
}
325321
const routes = [...manifest.routes, ...manifest.post_cache_routes].map((route) => ({
326322
...route,
327323
pattern: new RegExp(route.pattern),
328324
}))
329-
const functionNames = routes
330-
.filter(({ pattern }) => pattern.test(urlPath))
331-
.filter(({ function: name }) => {
332-
const isExcluded = manifest.function_config[name]?.excluded_patterns?.some((pattern) =>
333-
new RegExp(pattern).test(urlPath),
334-
)
335-
return !isExcluded
336-
})
337-
.map((route) => route.function)
325+
326+
/** @type string[] */
327+
const functionNames = []
328+
329+
/** @type number[] */
330+
const routeIndexes = []
331+
332+
routes.forEach((route, index) => {
333+
if (!route.pattern.test(urlPath)) {
334+
return
335+
}
336+
337+
const isExcluded = manifest.function_config[route.function]?.excluded_patterns?.some((pattern) =>
338+
new RegExp(pattern).test(urlPath),
339+
)
340+
341+
if (isExcluded) {
342+
return
343+
}
344+
345+
functionNames.push(route.function)
346+
routeIndexes.push(index)
347+
})
348+
const invocationMetadata = {
349+
function_config: manifest.function_config,
350+
req_routes: routeIndexes,
351+
routes: manifest.routes.map((route) => ({ function: route.function, path: route.path, pattern: route.pattern })),
352+
}
338353
const orphanedDeclarations = this.#matchURLPathAgainstOrphanedDeclarations(urlPath)
339354

340355
return { functionNames, invocationMetadata, orphanedDeclarations }
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
import { Config, Context } from 'https://edge.netlify.com'
2+
3+
export default (_, context: Context) => Response.json(context)
4+
5+
export const config: Config = {
6+
path: '/categories/:category/products/:product',
7+
}

tests/integration/commands/dev/edge-functions.test.ts

Lines changed: 22 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { describe, expect, test } from 'vitest'
1+
import { describe, expect, expectTypeOf, test } from 'vitest'
22

33
import { FixtureTestContext, setupFixtureTests } from '../../utils/fixture.js'
44
import got from '../../utils/got.cjs'
@@ -16,15 +16,34 @@ describe('edge functions', () => {
1616
expect(response.body).toMatchSnapshot()
1717
})
1818

19-
test<FixtureTestContext>('should provide geo location', async ({ devServer }) => {
19+
test<FixtureTestContext>('should provide context properties', async ({ devServer }) => {
2020
const response = await got(`http://localhost:${devServer.port}/context`, {
2121
throwHttpErrors: false,
2222
retry: { limit: 0 },
2323
})
2424

25-
const { geo } = JSON.parse(response.body)
25+
const { deploy, geo, ip, params, requestId, server, site } = JSON.parse(response.body)
2626
expect(geo.city).toEqual('Mock City')
2727
expect(geo.country.code).toEqual('DE')
28+
expect(deploy).toEqual({ id: '0' })
29+
expectTypeOf(ip).toBeString()
30+
expect(params).toEqual({})
31+
expectTypeOf(requestId).toBeString()
32+
expect(server).toEqual({ region: 'local' })
33+
expect(site).toEqual({ id: 'foo' })
34+
})
35+
36+
test<FixtureTestContext>('should expose URL parameters', async ({ devServer }) => {
37+
const response = await got(`http://localhost:${devServer.port}/categories/foo/products/bar`, {
38+
throwHttpErrors: false,
39+
retry: { limit: 0 },
40+
})
41+
42+
const { params } = JSON.parse(response.body)
43+
expect(params).toEqual({
44+
category: 'foo',
45+
product: 'bar',
46+
})
2847
})
2948
})
3049

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy