@@ -42,7 +42,7 @@ export default {
4242 if ( url . pathname === '/health' ) {
4343 return new Response ( JSON . stringify ( { status : 'ok' } ) , {
4444 headers : {
45- 'Content-Type' : 'application/json' ,
45+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
4646 ...getCorsHeaders ( request ) ,
4747 } ,
4848 } ) ;
@@ -53,7 +53,7 @@ export default {
5353 return new Response ( JSON . stringify ( festivalsData ) , {
5454 status : 200 ,
5555 headers : {
56- 'Content-Type' : 'application/json' ,
56+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
5757 'Cache-Control' : FESTIVALS_CACHE_CONTROL ,
5858 ...getCorsHeaders ( request ) ,
5959 } ,
@@ -81,6 +81,13 @@ export default {
8181 // Clone the response and add CORS headers
8282 const newHeaders = new Headers ( response . headers ) ;
8383 setCorsHeaders ( newHeaders , request ) ;
84+
85+ // Ensure JSON responses explicitly declare UTF-8 encoding
86+ // This prevents mojibake when non-ASCII characters (é, ö, ä, ñ) are present
87+ const contentType = newHeaders . get ( 'Content-Type' ) ;
88+ if ( contentType && contentType . includes ( 'application/json' ) && ! contentType . includes ( 'charset' ) ) {
89+ newHeaders . set ( 'Content-Type' , 'application/json; charset=utf-8' ) ;
90+ }
8491
8592 return new Response ( response . body , {
8693 status : response . status ,
@@ -91,7 +98,7 @@ export default {
9198 return new Response ( JSON . stringify ( { error : 'Proxy error' , message : error . message } ) , {
9299 status : 502 ,
93100 headers : {
94- 'Content-Type' : 'application/json' ,
101+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
95102 ...getCorsHeaders ( request ) ,
96103 } ,
97104 } ) ;
@@ -124,7 +131,7 @@ async function handleAvailableBeverageTypes(festivalId, request) {
124131 } ) , {
125132 status : 404 ,
126133 headers : {
127- 'Content-Type' : 'application/json' ,
134+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
128135 ...getCorsHeaders ( request ) ,
129136 } ,
130137 } ) ;
@@ -142,7 +149,7 @@ async function handleAvailableBeverageTypes(festivalId, request) {
142149 } ) , {
143150 status : 200 ,
144151 headers : {
145- 'Content-Type' : 'application/json' ,
152+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
146153 'Cache-Control' : 'public, max-age=3600' , // Cache for 1 hour
147154 ...getCorsHeaders ( request ) ,
148155 } ,
@@ -154,7 +161,7 @@ async function handleAvailableBeverageTypes(festivalId, request) {
154161 } ) , {
155162 status : 500 ,
156163 headers : {
157- 'Content-Type' : 'application/json' ,
164+ 'Content-Type' : 'application/json; charset=utf-8 ' ,
158165 ...getCorsHeaders ( request ) ,
159166 } ,
160167 } ) ;
0 commit comments