From dc29e21b141574247b5f9f859c019b4ad4be9742 Mon Sep 17 00:00:00 2001 From: Pawel Kozlowski Date: Tue, 23 Aug 2022 14:21:59 +0200 Subject: [PATCH] fix(common): consider density descriptors with multiple digits as valid (#47230) Valid density descriptors used in the NgOptimizedImage can contain multiple digits (ex. 1.25x, 25x). This change fixes the issue where density descriptors with multiple digits (ex. 25x) where considered invalid. Please note that a valid density descriptor might still be rejected by the directive's validation logic if the supplied value is too big. PR Close #47230 --- .../ng_optimized_image/ng_optimized_image.ts | 6 ++-- .../directives/ng_optimized_image_spec.ts | 31 ++++++++++++++++++- 2 files changed, 33 insertions(+), 4 deletions(-) diff --git a/packages/common/src/directives/ng_optimized_image/ng_optimized_image.ts b/packages/common/src/directives/ng_optimized_image/ng_optimized_image.ts index e9bca7074ede4..3795ce379829d 100644 --- a/packages/common/src/directives/ng_optimized_image/ng_optimized_image.ts +++ b/packages/common/src/directives/ng_optimized_image/ng_optimized_image.ts @@ -32,9 +32,9 @@ const VALID_WIDTH_DESCRIPTOR_SRCSET = /^((\s*\d+w\s*(,|$)){1,})$/; /** * RegExpr to determine whether a src in a srcset is using density descriptors. - * Should match something like: "1x, 2x". Also supports decimals like "1.5x". + * Should match something like: "1x, 2x, 50x". Also supports decimals like "1.5x, 1.50x". */ -const VALID_DENSITY_DESCRIPTOR_SRCSET = /^((\s*\d(\.\d+)?x\s*(,|$)){1,})$/; +const VALID_DENSITY_DESCRIPTOR_SRCSET = /^((\s*\d+(\.\d+)?x\s*(,|$)){1,})$/; /** * Srcset values with a density descriptor higher than this value will actively @@ -506,7 +506,7 @@ function assertUnderDensityCap(dir: NgOptimizedImage, value: string) { `${RECOMMENDED_SRCSET_DENSITY_CAP}x but supports image densities up to ` + `${ABSOLUTE_SRCSET_DENSITY_CAP}x. The human eye cannot distinguish between image densities ` + `greater than ${RECOMMENDED_SRCSET_DENSITY_CAP}x - which makes them unnecessary for ` + - `most use cases. Images that will be pinch-zoomed are typically the primary use case for` + + `most use cases. Images that will be pinch-zoomed are typically the primary use case for ` + `${ABSOLUTE_SRCSET_DENSITY_CAP}x images. Please remove the high density descriptor and try again.`); } } diff --git a/packages/common/test/directives/ng_optimized_image_spec.ts b/packages/common/test/directives/ng_optimized_image_spec.ts index 429aae3b5a620..d5bb1a44fb2de 100644 --- a/packages/common/test/directives/ng_optimized_image_spec.ts +++ b/packages/common/test/directives/ng_optimized_image_spec.ts @@ -367,7 +367,36 @@ describe('Image directive', () => { `${ABSOLUTE_SRCSET_DENSITY_CAP}x. The human eye cannot distinguish between image densities ` + `greater than ${ RECOMMENDED_SRCSET_DENSITY_CAP}x - which makes them unnecessary for ` + - `most use cases. Images that will be pinch-zoomed are typically the primary use case for` + + `most use cases. Images that will be pinch-zoomed are typically the primary use case for ` + + `${ABSOLUTE_SRCSET_DENSITY_CAP}x images. Please remove the high density descriptor and try again.`); + }); + + + it('should throw if rawSrcset exceeds the density cap with multiple digits', () => { + const imageLoader = (config: ImageLoaderConfig) => { + const width = config.width ? `-${config.width}` : ``; + return window.location.origin + `/path/${config.src}${width}.png`; + }; + setupTestingModule({imageLoader}); + + const template = ` + + `; + expect(() => { + const fixture = createTestComponent(template); + fixture.detectChanges(); + }) + .toThrowError( + `NG0${ + RuntimeErrorCode + .INVALID_INPUT}: The NgOptimizedImage directive (activated on an element with the \`rawSrc="img"\`) ` + + `has detected that the \`rawSrcset\` contains an unsupported image density:` + + `\`1x, 200x\`. NgOptimizedImage generally recommends a max image density of ` + + `${RECOMMENDED_SRCSET_DENSITY_CAP}x but supports image densities up to ` + + `${ABSOLUTE_SRCSET_DENSITY_CAP}x. The human eye cannot distinguish between image densities ` + + `greater than ${ + RECOMMENDED_SRCSET_DENSITY_CAP}x - which makes them unnecessary for ` + + `most use cases. Images that will be pinch-zoomed are typically the primary use case for ` + `${ABSOLUTE_SRCSET_DENSITY_CAP}x images. Please remove the high density descriptor and try again.`); });