@@ -407,6 +407,7 @@ export interface StaticHandler {
407
407
opts ?: {
408
408
loadRouteIds ?: string [ ] ;
409
409
requestContext ?: unknown ;
410
+ skipLoaders ?: boolean ;
410
411
skipLoaderErrorBubbling ?: boolean ;
411
412
}
412
413
) : Promise < StaticHandlerContext | Response > ;
@@ -2988,25 +2989,29 @@ export function createStaticHandler(
2988
2989
* propagate that out and return the raw Response so the HTTP server can
2989
2990
* return it directly.
2990
2991
*
2991
- * - `opts.loadRouteIds` is an optional array of routeIds if you wish to only
2992
- * run a subset of route loaders on a GET request
2992
+ * - `opts.loadRouteIds` is an optional array of routeIds to run only a subset of
2993
+ * loaders during a query() call
2993
2994
* - `opts.requestContext` is an optional server context that will be passed
2994
2995
* to actions/loaders in the `context` parameter
2995
2996
* - `opts.skipLoaderErrorBubbling` is an optional parameter that will prevent
2996
- * the bubbling of loader errors which allows single-fetch-type implementations
2997
+ * the bubbling of errors which allows single-fetch-type implementations
2997
2998
* where the client will handle the bubbling and we may need to return data
2998
2999
* for the handling route
3000
+ * - `opts.skipLoaders` is an optional parameter that will prevent loaders
3001
+ * from running after an action
2999
3002
*/
3000
3003
async function query (
3001
3004
request : Request ,
3002
3005
{
3003
3006
loadRouteIds,
3004
3007
requestContext,
3005
3008
skipLoaderErrorBubbling,
3009
+ skipLoaders,
3006
3010
} : {
3007
3011
loadRouteIds ?: string [ ] ;
3008
3012
requestContext ?: unknown ;
3009
3013
skipLoaderErrorBubbling ?: boolean ;
3014
+ skipLoaders ?: boolean ;
3010
3015
} = { }
3011
3016
) : Promise < StaticHandlerContext | Response > {
3012
3017
let url = new URL ( request . url ) ;
@@ -3060,6 +3065,7 @@ export function createStaticHandler(
3060
3065
requestContext ,
3061
3066
loadRouteIds || null ,
3062
3067
skipLoaderErrorBubbling === true ,
3068
+ skipLoaders === true ,
3063
3069
null
3064
3070
) ;
3065
3071
if ( isResponse ( result ) ) {
@@ -3138,6 +3144,7 @@ export function createStaticHandler(
3138
3144
requestContext ,
3139
3145
null ,
3140
3146
false ,
3147
+ false ,
3141
3148
match
3142
3149
) ;
3143
3150
if ( isResponse ( result ) ) {
@@ -3176,6 +3183,7 @@ export function createStaticHandler(
3176
3183
requestContext : unknown ,
3177
3184
loadRouteIds : string [ ] | null ,
3178
3185
skipLoaderErrorBubbling : boolean ,
3186
+ skipLoaders : boolean ,
3179
3187
routeMatch : AgnosticDataRouteMatch | null
3180
3188
) : Promise < Omit < StaticHandlerContext , "location" | "basename" > | Response > {
3181
3189
invariant (
@@ -3192,6 +3200,7 @@ export function createStaticHandler(
3192
3200
requestContext ,
3193
3201
loadRouteIds ,
3194
3202
skipLoaderErrorBubbling ,
3203
+ skipLoaders ,
3195
3204
routeMatch != null
3196
3205
) ;
3197
3206
return result ;
@@ -3238,6 +3247,7 @@ export function createStaticHandler(
3238
3247
requestContext : unknown ,
3239
3248
loadRouteIds : string [ ] | null ,
3240
3249
skipLoaderErrorBubbling : boolean ,
3250
+ skipLoaders : boolean ,
3241
3251
isRouteRequest : boolean
3242
3252
) : Promise < Omit < StaticHandlerContext , "location" | "basename" > | Response > {
3243
3253
let result : DataResult ;
@@ -3326,7 +3336,33 @@ export function createStaticHandler(
3326
3336
if ( isErrorResult ( result ) ) {
3327
3337
// Store off the pending error - we use it to determine which loaders
3328
3338
// to call and will commit it when we complete the navigation
3329
- let boundaryMatch = findNearestBoundary ( matches , actionMatch . route . id ) ;
3339
+ let boundaryMatch = skipLoaderErrorBubbling
3340
+ ? actionMatch
3341
+ : findNearestBoundary ( matches , actionMatch . route . id ) ;
3342
+ let statusCode = isRouteErrorResponse ( result . error )
3343
+ ? result . error . status
3344
+ : result . statusCode != null
3345
+ ? result . statusCode
3346
+ : 500 ;
3347
+ let actionHeaders = {
3348
+ ...( result . headers ? { [ actionMatch . route . id ] : result . headers } : { } ) ,
3349
+ } ;
3350
+
3351
+ if ( skipLoaders ) {
3352
+ return {
3353
+ matches,
3354
+ loaderData : { } ,
3355
+ actionData : { } ,
3356
+ errors : {
3357
+ [ boundaryMatch . route . id ] : result . error ,
3358
+ } ,
3359
+ statusCode,
3360
+ loaderHeaders : { } ,
3361
+ actionHeaders,
3362
+ activeDeferreds : null ,
3363
+ } ;
3364
+ }
3365
+
3330
3366
let context = await loadRouteData (
3331
3367
loaderRequest ,
3332
3368
matches ,
@@ -3340,13 +3376,28 @@ export function createStaticHandler(
3340
3376
// action status codes take precedence over loader status codes
3341
3377
return {
3342
3378
...context ,
3343
- statusCode : isRouteErrorResponse ( result . error )
3344
- ? result . error . status
3345
- : 500 ,
3379
+ statusCode,
3346
3380
actionData : null ,
3347
- actionHeaders : {
3348
- ...( result . headers ? { [ actionMatch . route . id ] : result . headers } : { } ) ,
3381
+ actionHeaders,
3382
+ } ;
3383
+ }
3384
+
3385
+ let actionHeaders = result . headers
3386
+ ? { [ actionMatch . route . id ] : result . headers }
3387
+ : { } ;
3388
+
3389
+ if ( skipLoaders ) {
3390
+ return {
3391
+ matches,
3392
+ loaderData : { } ,
3393
+ actionData : {
3394
+ [ actionMatch . route . id ] : result . data ,
3349
3395
} ,
3396
+ errors : null ,
3397
+ statusCode : result . statusCode || 200 ,
3398
+ loaderHeaders : { } ,
3399
+ actionHeaders,
3400
+ activeDeferreds : null ,
3350
3401
} ;
3351
3402
}
3352
3403
@@ -4188,6 +4239,7 @@ async function callDataStrategyImpl(
4188
4239
} ) ,
4189
4240
request,
4190
4241
params : matches [ 0 ] . params ,
4242
+ context : requestContext ,
4191
4243
} ) ;
4192
4244
4193
4245
// Throw if any loadRoute implementations not called since they are what
0 commit comments