GoogleChrome / GoogleChrome/workbox
workbox-precaching: TypeScript type checking fails with exactOptionalPropertyTypes: true
- Dominant language
- JavaScript
- Stars
- 13k
- Forks
- 880
- Avg merge
- 2h 44m
- Merged PRs (30d)
- 8
Description
With TypeScript 5.9.3, type checking fails in projects that use workbox-precaching when `exactOptionalPropertyTypes` is enabled:
```txt
./node_modules/workbox-precaching/PrecacheFallbackPlugin.d.ts:18:15 - error TS2420: Class 'PrecacheFallbackPlugin' incorrectly implements interface 'WorkboxPlugin'.
Types of property 'handlerDidError' are incompatible.
Type 'HandlerDidErrorCallback | undefined' is not assignable to type 'HandlerDidErrorCallback'.
Type 'undefined' is not assignable to type 'HandlerDidErrorCallback'.
```
The problem is in `workbox-precaching/PrecacheFallbackPlugin.d.ts`:
```typescript
declare class PrecacheFallbackPlugin implements WorkboxPlugin {
// ...
handlerDidError: WorkboxPlugin['handlerDidError'];
}
```
In `workbox-core/types.d.ts`, `handlerDidError` is optional:
```typescript
export declare interface WorkboxPlugin {
// ...
handlerDidError?: HandlerDidErrorCallback;
// ...
}
```
Because `handlerDidError` is optional, `WorkboxPlugin['handlerDidError']` resolves to `HandlerDidErrorCallback | undefined`.
With `exactOptionalPropertyTypes` enabled, TypeScript distinguishes between the case where a property is not present and the case where it is present and explicitly set to `undefined` (JavaScript also has subtly different behaviour in these two cases, so this TypeScript setting sometimes catches actual bugs).
The interface declaration of `WorkboxPlugin` specifies that `handlerDidError` is optional, but that if it is present then it must have the type `HandlerDidErrorCallback`.
`HandlerDidErrorCallback | undefined` is not assignable to `HandlerDidErrorCallback`, therefore `PrecacheFallbackPlugin` does not implement the `WorkboxPlugin` interface correctly.
`PrecacheFallbackPlugin` should instead be declared like:
```typescript
declare class PrecacheFallbackPlugin implements WorkboxPlugin {
// ...
handlerDidError: HandlerDidErrorCallback;
}
```
or possibly
```typescript
declare class PrecacheFallbackPlugin implements WorkboxPlugin {
// ...
handlerDidError?: HandlerDidErrorCallback;
}
```
Or, alternatively, if workbox allows explicitly setting optional properties to `undefined`, then `undefined` should be added to the types of optional properties, for example:
```typescript
export declare interface WorkboxPlugin {
// ...
handlerDidError?: HandlerDidErrorCallback | undefined;
// ...
}
```
Contributor guide
Assessment
This issue has not been assessed yet.