diff --git a/docs/src/content/docs/changelog/v0.35.0.md b/docs/src/content/docs/changelog/v0.35.0.md index 28cbc2ce..be1ae2c2 100644 --- a/docs/src/content/docs/changelog/v0.35.0.md +++ b/docs/src/content/docs/changelog/v0.35.0.md @@ -16,6 +16,8 @@ slug: changelog/v0.35.0 * Breaking: Remove deprecated properties from `sharpen` operation. +* Breaking: Rename `format.jp2k` as `format.jp2` for API consistency. + * Upgrade to libvips v8.18.0 for upstream bug fixes. * Deprecate Windows 32-bit (win32-ia32) prebuilt binaries. @@ -29,4 +31,7 @@ slug: changelog/v0.35.0 * Add `toUint8Array` for output image as a `TypedArray` backed by a transferable `ArrayBuffer`. [#4355](https://github.com/lovell/sharp/issues/4355) +* TypeScript: Ensure `FormatEnum` keys match reality. + [#4475](https://github.com/lovell/sharp/issues/4475) + * Add WebP `exact` option for control over transparent pixel colour values. diff --git a/lib/index.d.ts b/lib/index.d.ts index 9f35cc40..b3c2f818 100644 --- a/lib/index.d.ts +++ b/lib/index.d.ts @@ -840,7 +840,7 @@ declare namespace sharp { * @returns A sharp instance that can be used to chain operations */ toFormat( - format: keyof FormatEnum | AvailableFormatInfo, + format: keyof FormatEnum | AvailableFormatInfo | "avif", options?: | OutputOptions | JpegOptions @@ -1911,16 +1911,13 @@ declare namespace sharp { } interface FormatEnum { - avif: AvailableFormatInfo; dcraw: AvailableFormatInfo; dz: AvailableFormatInfo; exr: AvailableFormatInfo; fits: AvailableFormatInfo; gif: AvailableFormatInfo; heif: AvailableFormatInfo; - input: AvailableFormatInfo; jpeg: AvailableFormatInfo; - jpg: AvailableFormatInfo; jp2: AvailableFormatInfo; jxl: AvailableFormatInfo; magick: AvailableFormatInfo; @@ -1932,8 +1929,7 @@ declare namespace sharp { raw: AvailableFormatInfo; svg: AvailableFormatInfo; tiff: AvailableFormatInfo; - tif: AvailableFormatInfo; - v: AvailableFormatInfo; + vips: AvailableFormatInfo; webp: AvailableFormatInfo; } diff --git a/lib/output.js b/lib/output.js index 9c26b471..7de53ed1 100644 --- a/lib/output.js +++ b/lib/output.js @@ -76,7 +76,7 @@ function toFile (fileOut, callback) { err = new Error('Missing output file path'); } else if (is.string(this.options.input.file) && path.resolve(this.options.input.file) === path.resolve(fileOut)) { err = new Error('Cannot use same file for input and output'); - } else if (jp2Regex.test(path.extname(fileOut)) && !this.constructor.format.jp2k.output.file) { + } else if (jp2Regex.test(path.extname(fileOut)) && !this.constructor.format.jp2.output.file) { err = errJp2Save(); } if (err) { @@ -950,7 +950,7 @@ function gif (options) { */ function jp2 (options) { /* node:coverage ignore next 41 */ - if (!this.constructor.format.jp2k.output.buffer) { + if (!this.constructor.format.jp2.output.buffer) { throw errJp2Save(); } if (is.object(options)) { diff --git a/lib/utility.js b/lib/utility.js index c0ad39f8..4e597e1d 100644 --- a/lib/utility.js +++ b/lib/utility.js @@ -24,7 +24,7 @@ const format = sharp.format(); format.heif.output.alias = ['avif', 'heic']; format.jpeg.output.alias = ['jpe', 'jpg']; format.tiff.output.alias = ['tif']; -format.jp2k.output.alias = ['j2c', 'j2k', 'jp2', 'jpx']; +format.jp2.output.alias = ['j2c', 'j2k', 'jp2', 'jpx']; /** * An Object containing the available interpolators and their proper values diff --git a/src/utilities.cc b/src/utilities.cc index 4154c08a..03164b5c 100644 --- a/src/utilities.cc +++ b/src/utilities.cc @@ -123,6 +123,7 @@ Napi::Value format(const Napi::CallbackInfo& info) { "jpeg", "png", "webp", "tiff", "magick", "openslide", "dz", "ppm", "fits", "gif", "svg", "heif", "pdf", "vips", "jp2k", "jxl", "rad", "dcraw" }) { + std::string id = f == "jp2k" ? "jp2" : f; // Input const VipsObjectClass *oc = vips_class_find("VipsOperation", (f + "load").c_str()); Napi::Boolean hasInputFile = Napi::Boolean::New(env, oc); @@ -154,11 +155,11 @@ Napi::Value format(const Napi::CallbackInfo& info) { output.Set("stream", hasOutputBuffer); // Other attributes Napi::Object container = Napi::Object::New(env); - container.Set("id", f); + container.Set("id", id); container.Set("input", input); container.Set("output", output); // Add to set of formats - format.Set(f, container); + format.Set(id, container); } // Raw, uncompressed data diff --git a/test/types/sharp.test-d.ts b/test/types/sharp.test-d.ts index ba831b6c..fdf76af1 100644 --- a/test/types/sharp.test-d.ts +++ b/test/types/sharp.test-d.ts @@ -234,7 +234,7 @@ sharp(input) sharp(input) .resize(100, 100) - .toFormat('jpg') + .toFormat('avif') .toBuffer({ resolveWithObject: false }) .then((outputBuffer: Buffer) => { // Resolves with a Buffer object when resolveWithObject is false @@ -267,9 +267,7 @@ sharp(input) // Output to tif sharp(input) .resize(100, 100) - .toFormat('tif') .toFormat('tiff') - .toFormat(sharp.format.tif) .toFormat(sharp.format.tiff) .toBuffer(); @@ -774,3 +772,35 @@ sharp().erode(); sharp().erode(1); sharp().dilate(); sharp().dilate(1); + +sharp.format.dcraw; +sharp.format.dz; +sharp.format.fits; +sharp.format.gif; +sharp.format.heif; +sharp.format.jp2; +sharp.format.jpeg; +sharp.format.jxl; +sharp.format.magick; +sharp.format.openslide; +sharp.format.pdf; +sharp.format.png; +sharp.format.ppm; +sharp.format.rad; +sharp.format.raw; +sharp.format.svg; +sharp.format.tiff; +sharp.format.vips; +sharp.format.webp; +// @ts-expect-error +sharp.format.avif; +// @ts-expect-error +sharp.format.input; +// @ts-expect-error +sharp.format.jp2k; +// @ts-expect-error +sharp.format.jpg; +// @ts-expect-error +sharp.format.tif; +// @ts-expect-error +sharp.format.v; diff --git a/test/unit/jp2.js b/test/unit/jp2.js index 536e0a04..dc5ddb6e 100644 --- a/test/unit/jp2.js +++ b/test/unit/jp2.js @@ -11,7 +11,7 @@ const sharp = require('../../'); const fixtures = require('../fixtures'); describe('JP2 output', () => { - if (!sharp.format.jp2k.input.buffer) { + if (!sharp.format.jp2.input.buffer) { it('JP2 output should fail due to missing OpenJPEG', () => assert.rejects(async () => sharp(fixtures.inputJpg)