Skip to content

Commit adc018b

Browse files
authored
Merge pull request #385 from 2chanhaeng/hotfix/fedify/next
2 parents 88792aa + acfbb09 commit adc018b

File tree

4 files changed

+146
-59
lines changed

4 files changed

+146
-59
lines changed

docs/manual/integration.md

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -531,16 +531,30 @@ export default fedifyWith(federation)(
531531
// More details: https://nextjs.org/docs/app/api-reference/file-conventions/middleware#config-object-optional
532532
export const config = {
533533
runtime: "nodejs",
534-
matcher: [{
535-
source: "/:path*",
536-
has: [
537-
{
538-
type: "header",
539-
key: "Accept",
540-
value: ".*application\\\\/((jrd|activity|ld)\\\\+json|xrd\\\\+xml).*",
541-
},
542-
],
543-
}],
534+
matcher: [
535+
{
536+
source: "/:path*",
537+
has: [
538+
{
539+
type: "header",
540+
key: "Accept",
541+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
542+
},
543+
],
544+
},
545+
{
546+
source: "/:path*",
547+
has: [
548+
{
549+
type: "header",
550+
key: "content-type",
551+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
552+
},
553+
],
554+
},
555+
{ source: "/.well-known/nodeinfo" },
556+
{ source: "/.well-known/x-nodeinfo2" },
557+
],
544558
};
545559
~~~~
546560

packages/cli/src/init.ts

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -486,16 +486,30 @@ export default fedifyWith(federation)(
486486
// More details: https://nextjs.org/docs/app/api-reference/file-conventions/middleware#config-object-optional
487487
export const config = {
488488
runtime: "nodejs",
489-
matcher: [{
490-
source: "/:path*",
491-
has: [
492-
{
493-
type: "header",
494-
key: "Accept",
495-
value: ".*application\\\\/((jrd|activity|ld)\\\\+json|xrd\\\\+xml).*",
496-
},
497-
],
498-
}],
489+
matcher: [
490+
{
491+
source: "/:path*",
492+
has: [
493+
{
494+
type: "header",
495+
key: "Accept",
496+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
497+
},
498+
],
499+
},
500+
{
501+
source: "/:path*",
502+
has: [
503+
{
504+
type: "header",
505+
key: "content-type",
506+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
507+
},
508+
],
509+
},
510+
{ source: "/.well-known/nodeinfo" },
511+
{ source: "/.well-known/x-nodeinfo2" },
512+
],
499513
};
500514
`,
501515
},

packages/next/README.md

Lines changed: 48 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -37,16 +37,30 @@ export default fedifyWith(federation)();
3737
// This config must be defined on `middleware.ts`.
3838
export const config = {
3939
runtime: "nodejs",
40-
matcher: [{
41-
source: "/:path*",
42-
has: [
43-
{
44-
type: "header",
45-
key: "Accept",
46-
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
47-
},
48-
],
49-
}],
40+
matcher: [
41+
{
42+
source: "/:path*",
43+
has: [
44+
{
45+
type: "header",
46+
key: "Accept",
47+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
48+
},
49+
],
50+
},
51+
{
52+
source: "/:path*",
53+
has: [
54+
{
55+
type: "header",
56+
key: "content-type",
57+
value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
58+
},
59+
],
60+
},
61+
{ source: "/.well-known/nodeinfo" },
62+
{ source: "/.well-known/x-nodeinfo2" },
63+
],
5064
};
5165
~~~~
5266

@@ -108,16 +122,30 @@ type ErrorHandlers = Omit<FederationFetchOptions<unknown>, "contextData">;
108122
* // More details: https://nextjs.org/docs/app/api-reference/file-conventions/middleware#config-object-optional.
109123
* export const config = {
110124
* runtime: "nodejs",
111-
* matcher: [{
112-
* source: "/:path*",
113-
* has: [
114-
* {
115-
* type: "header",
116-
* key: "Accept",
117-
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
118-
* },
119-
* ],
120-
* }],
125+
* matcher: [
126+
* {
127+
* source: "/:path*",
128+
* has: [
129+
* {
130+
* type: "header",
131+
* key: "Accept",
132+
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
133+
* },
134+
* ],
135+
* },
136+
* {
137+
* source: "/:path*",
138+
* has: [
139+
* {
140+
* type: "header",
141+
* key: "content-type",
142+
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
143+
* },
144+
* ],
145+
* },
146+
* { source: "/.well-known/nodeinfo" },
147+
* { source: "/.well-known/x-nodeinfo2" },
148+
* ],
121149
* };
122150
* ```
123151
*/

packages/next/src/index.ts

Lines changed: 50 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -51,16 +51,30 @@ type ErrorHandlers = Omit<FederationFetchOptions<unknown>, "contextData">;
5151
* // More details: https://nextjs.org/docs/app/api-reference/file-conventions/middleware#config-object-optional.
5252
* export const config = {
5353
* runtime: "nodejs",
54-
* matcher: [{
55-
* source: "/:path*",
56-
* has: [
57-
* {
58-
* type: "header",
59-
* key: "Accept",
60-
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
61-
* },
62-
* ],
63-
* }],
54+
* matcher: [
55+
* {
56+
* source: "/:path*",
57+
* has: [
58+
* {
59+
* type: "header",
60+
* key: "Accept",
61+
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
62+
* },
63+
* ],
64+
* },
65+
* {
66+
* source: "/:path*",
67+
* has: [
68+
* {
69+
* type: "header",
70+
* key: "content-type",
71+
* value: ".*application\\/((jrd|activity|ld)\\+json|xrd\\+xml).*",
72+
* },
73+
* ],
74+
* },
75+
* { source: "/.well-known/nodeinfo" },
76+
* { source: "/.well-known/x-nodeinfo2" },
77+
* ],
6478
* };
6579
* ```
6680
*/
@@ -74,7 +88,7 @@ export const fedifyWith = <TContextData>(
7488
((_: Request) => NextResponse.next()),
7589
): (request: Request) => unknown =>
7690
async (request: Request) => {
77-
if (hasFederationAcceptHeader(request)) {
91+
if (isFederationRequest(request)) {
7892
return await integrateFederation(
7993
federation,
8094
contextDataFactory,
@@ -84,20 +98,37 @@ async (request: Request) => {
8498
return await middleware(request);
8599
};
86100

101+
export const isFederationRequest = (request: Request): boolean =>
102+
[
103+
hasFederationHeader("accept"),
104+
hasFederationHeader("content-type"),
105+
isNodeInfoRequest,
106+
].some((f) => f(request));
107+
87108
/**
88-
* Check if the request has the "Accept" header matching the federation
109+
* Check if the request has the header matching the federation
89110
* accept regex.
90-
*
111+
* @param key The header key to check.
91112
* @param request The request to check.
92-
* @returns `true` if the request has the "Accept" header matching
113+
* @returns `true` if the request has the header matching
93114
* the federation accept regex, `false` otherwise.
94115
*/
95-
export const hasFederationAcceptHeader = (request: Request): boolean => {
96-
const acceptHeader = request.headers.get("Accept");
97-
// Check if the Accept header matches the federation accept regex.
98-
// If the header is not present, return false.
99-
return acceptHeader ? FEDERATION_ACCEPT_REGEX.test(acceptHeader) : false;
116+
export const hasFederationHeader =
117+
(key: string) => (request: Request): boolean => {
118+
const value = request.headers.get(key);
119+
return value ? FEDERATION_ACCEPT_REGEX.test(value) : false;
120+
};
121+
122+
export const isNodeInfoRequest = (request: Request): boolean => {
123+
const url = new URL(request.url);
124+
return NODEINFO_PATHS.some((path) => url.pathname.startsWith(path));
100125
};
126+
127+
const NODEINFO_PATHS = [
128+
"/.well-known/nodeinfo",
129+
"/.well-known/x-nodeinfo2",
130+
];
131+
101132
const FEDERATION_ACCEPT_REGEX =
102133
/.*application\/((jrd|activity|ld)\+json|xrd\+xml).*/;
103134

0 commit comments

Comments
 (0)