# Copyright 2019 Google LLC # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # https://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. name: storage-resize-images version: 0.3.2 specVersion: v1beta displayName: Resize Images description: Resizes images uploaded to Cloud Storage to a specified size, and optionally keeps or deletes the original image. license: Apache-2.0 sourceUrl: https://github.com/firebase/extensions/tree/master/storage-resize-images releaseNotesUrl: https://github.com/firebase/extensions/blob/master/storage-resize-images/CHANGELOG.md author: authorName: Firebase url: https://firebase.google.com contributors: - authorName: Tina Liang url: https://github.com/tinaliang - authorName: Chris Bianca email: chris@csfrequency.com url: https://github.com/chrisbianca - authorName: Invertase email: oss@invertase.io url: https://github.com/invertase billingRequired: true apis: - apiName: storage-component.googleapis.com reason: Needed to use Cloud Storage roles: - role: storage.admin reason: Allows the extension to store resized images in Cloud Storage - role: aiplatform.user reason: Allows use of Gemini models for AI content filtering, if enabled. resources: - name: generateResizedImage type: firebaseextensions.v1beta.function description: >- Listens for new images uploaded to your specified Cloud Storage bucket, resizes the images, then stores the resized images in the same bucket. Optionally keeps or deletes the original images. properties: runtime: nodejs22 availableMemoryMb: ${param:FUNCTION_MEMORY} eventTrigger: eventType: google.storage.object.finalize resource: projects/_/buckets/${param:IMG_BUCKET} # Backfill feature disabled - commented out to preserve code # - name: backfillResizedImages # type: firebaseextensions.v1beta.function # description: >- # Handles tasks from startBackfill to resize existing images. # properties: # runtime: nodejs20 # availableMemoryMb: ${param:FUNCTION_MEMORY} # taskQueueTrigger: {} params: - param: IMG_BUCKET label: Cloud Storage bucket for images description: > To which Cloud Storage bucket will you upload images that you want to resize? Resized images will be stored in this bucket. Depending on your extension configuration, original images are either kept or deleted. It is recommended to create a separate bucket for this extension. For more information, refer to the [pre-installation guide](https://firebase.google.com/products/extensions/storage-resize-images). type: selectResource resourceType: storage.googleapis.com/Bucket example: my-project-12345.appspot.com validationRegex: ^([0-9a-z_.-]*)$ validationErrorMessage: Invalid storage bucket default: ${STORAGE_BUCKET} required: true - param: IMG_SIZES label: Sizes of resized images description: > What sizes of images would you like (in pixels)? Enter the sizes as a comma-separated list of WIDTHxHEIGHT values. Learn more about [how this parameter works](https://firebase.google.com/products/extensions/storage-resize-images). type: string example: "200x200" validationRegex: ^\d+x(\d+,\d+x)*\d+$ validationErrorMessage: Invalid sizes, must be a comma-separated list of WIDTHxHEIGHT values. default: "200x200" required: true - param: DELETE_ORIGINAL_FILE label: Deletion of original file description: >- Do you want to automatically delete the original file from the Cloud Storage bucket? Warning: these deletions cannot be undone. type: select options: - label: Don't delete value: false - label: Delete on any resize attempt value: true - label: Delete only on successful resize attempts value: on_success default: false required: true - param: MAKE_PUBLIC label: Make resized images public description: >- Do you want to make the resized images public automatically? So you can access them by URL. For example: https://storage.googleapis.com/{bucket}/{path} type: select options: - label: Yes value: true - label: No value: false default: false - param: RESIZED_IMAGES_PATH label: Cloud Storage path for resized images description: > A relative path in which to store resized images. For example, if you specify a path here of `thumbs` and you upload an image to `/images/original.jpg`, then the resized image is stored at `/images/thumbs/original_200x200.jpg`. If you prefer to store resized images at the root of your bucket, leave this field empty. example: thumbnails required: false - param: INCLUDE_PATH_LIST label: Paths that contain images you want to resize description: > Restrict storage-resize-images to only resize images in specific locations in your Storage bucket by supplying a comma-separated list of absolute paths. For example, specifying the paths `/users/pictures,/restaurants/menuItems` will resize any images found in any subdirectories of `/users/pictures` and `/restaurants/menuItems`. You may also use wildcard notation for directories in the path. For example, `/users/*/pictures` would include any images in any subdirectories of `/users/foo/pictures` as well as any images in subdirectories of `/users/bar/pictures`, but also any images in subdirectories of `/users/any/level/of/subdirectories/pictures`. If you prefer not to explicitly restrict to certain directories of your Storage bucket, leave this field empty. type: string example: "/users/avatars,/design/pictures" validationRegex: ^(\/[^\s\/\,]+)+(\,(\/[^\s\/\,]+)+)*$ validationErrorMessage: Invalid paths, must be a comma-separated list of absolute path values. required: false - param: EXCLUDE_PATH_LIST label: List of absolute paths not included for resized images description: > Ensure storage-resize-images does *not* resize images in _specific locations_ in your Storage bucket by supplying a comma-separated list of absolute paths. For example, to *exclude* the images stored in the `/foo/alpha` and its subdirectories and `/bar/beta` and its subdirectories, specify the paths `/foo/alpha,/bar/beta`. You may also use wildcard notation for directories in the path. For example, `/users/*/pictures` would exclude any images in any subdirectories of `/users/foo/pictures` as well as any images in subdirectories of `/users/bar/pictures`, but also any images in subdirectories of `/users/any/level/of/subdirectories/pictures`. If you prefer to resize every image uploaded to your Storage bucket, leave this field empty. type: string example: "/users/avatars/thumbs,/design/pictures/thumbs" validationRegex: ^(\/[^\s\/\,]+)+(\,(\/[^\s\/\,]+)+)*$ validationErrorMessage: Invalid paths, must be a comma-separated list of absolute path values. required: false - param: FAILED_IMAGES_PATH label: Cloud Storage path for failed images description: > A relative path in which to store failed images. For example, if you specify a path here of `failed` and you upload an image to `/images/original.jpg`, then resizing failed, the image will be stored at `/images/failed/original.jpg`. Leave this field empty if you do not want to store failed images in a separate directory. example: failed validationRegex: ^([^\/.]*|)$ validationErrorMessage: Values cannot include "/", ".". required: false - param: CACHE_CONTROL_HEADER label: Cache-Control header for resized images description: > This extension automatically copies any `Cache-Control` metadata from the original image to the resized images. For the resized images, do you want to overwrite this copied `Cache-Control` metadata or add `Cache-Control` metadata? Learn more about [`Cache-Control` headers](https://developer.mozilla.org/docs/Web/HTTP/Headers/Cache-Control). If you prefer not to overwrite or add `Cache-Control` metadata, leave this field empty. example: max-age=86400 required: false - param: IMAGE_TYPE label: Convert image to preferred types description: > The image types you'd like your source image to convert to. The default for this option will be to keep the original file type as the destination file type. type: multiSelect options: - label: jpeg value: jpeg - label: webp value: webp - label: png value: png - label: tiff value: tiff - label: gif value: gif - label: avif value: avif - label: original value: false default: false required: true - param: OUTPUT_OPTIONS label: Output options for selected formats description: > Provide an optional output option as a stringified object containing Sharp Output Options for selected image types conversion. eg. `{"jpeg": { "quality": 5, "chromaSubsampling": "4:4:4" }, "png": { "palette": true }}` and `{"png":{"compressionLevel":9}}`. The `"compressionLevel": 9` specifies the level of compression for PNG images. Higher numbers here indicate greater compression, leading to smaller file sizes at the cost of potentially increased processing time and possible loss of image quality. type: string validationRegex: ^({(.*?)})$ validationErrorMessage: Please provide a valid JSON object. required: false - param: SHARP_OPTIONS label: Sharp constructor options for resizing images description: > Provide an optional stringified Sharp ResizeOptions object to customize resizing behavior, eg. `{ "fastShrinkOnLoad": false, "position": “centre”, "fit": "inside" }` The `"fit": "inside"` option ensures the image fits within given dimensions, maintaining aspect ratio, scaling down as needed without cropping or distortion. Learn more about [`Sharp constructor options`](https://sharp.pixelplumbing.com/api-resize#resize). type: string validationRegex: ^({(.*?)})$ validationErrorMessage: Please provide a valid JSON object. required: false - param: IS_ANIMATED label: GIF and WEBP animated option description: > Keep animation of GIF and WEBP formats. type: select options: - label: Yes value: true - label: No (1st frame only) value: false default: true required: false - param: FUNCTION_MEMORY label: Cloud Function memory description: >- Memory of the function responsible of resizing images. Choose how much memory to give to the function that resize images. (For animated GIF => GIF we recommend using a minimum of 2GB). type: select options: - label: 512 MB value: 512 - label: 1 GB value: 1024 - label: 2 GB value: 2048 - label: 4 GB value: 4096 - label: 8 GB value: 8192 default: 1024 required: true immutable: false # Backfill parameters disabled - commented out to preserve code # - param: DO_BACKFILL # label: Backfill existing images # description: > # Should existing, unresized images in the Storage bucket be resized as # well? # type: select # required: true # options: # - label: Yes # value: true # - label: No # value: false # - param: BACKFILL_BATCH_SIZE # label: Backfill batch size # description: > # The maximum number of images to resize in a single batch. By default, the # function is configured to resize 3 images at a time. This is a # conservative default to work with smallest memory option (512 MB). # # WARNING: Ensure your function has enough memory to handle the batch size. # type: string # default: 3 # validationRegex: ^[1-9][0-9]*$ # validationErrorMessage: Please provide a valid number. # required: false - param: REGENERATE_TOKEN label: Assign new access token description: > Should resized images have a new access token assigned to them, different from the original image? type: select required: false default: true options: - label: Yes value: true - label: No value: false - param: CONTENT_FILTER_LEVEL label: Content filter level description: > Set the level of content filtering to apply to uploaded images. Choose 'OFF' to disable content filtering entirely, 'BLOCK_ONLY_HIGH' to block only high-severity inappropriate content, 'BLOCK_MEDIUM_AND_ABOVE' for medium and high severity content, or 'BLOCK_LOW_AND_ABOVE' for the strictest filtering (blocks low, medium, and high severity content). type: select options: - label: Off (No filtering) value: OFF - label: Low strictness (Block only high severity content) value: BLOCK_ONLY_HIGH - label: Medium strictness (Block medium and high severity content) value: BLOCK_MEDIUM_AND_ABOVE - label: High strictness (Block low, medium, and high severity content) value: BLOCK_LOW_AND_ABOVE default: OFF required: true - param: CUSTOM_FILTER_PROMPT label: Custom content filter prompt description: > Optionally, provide a custom prompt for content filtering. This allows you to define specific criteria for filtering beyond the standard categories. Note that this prompt should be a yes/no question. For example, "Does this image contain a cat?" will filter out images that Gemini thinks contain a cat. This is additional filtering on top of whichever content filtering level you choose. Leave empty to use just your selected built-in content filtering configuration. type: string example: "Does this image contain violent or threatening content?" required: false - param: PLACEHOLDER_IMAGE_PATH label: Path to placeholder image description: > Optionally, specify a path to a placeholder image to use when an uploaded image is blocked by content filtering. This should be a relative path within your storage bucket. If not provided, a default placeholder image is used. type: string example: "placeholders/blocked-content.jpg" validationRegex: ^([a-zA-Z0-9_\-\./]+)\.(png|jpg|jpeg|gif|webp)$ validationErrorMessage: Please provide a valid image path within your bucket. required: false events: - type: firebase.extensions.storage-resize-images.v1.onStart description: Occurs when a trigger has been called within the Extension, and will include data such as the context of the trigger request. - type: firebase.extensions.storage-resize-images.v1.onSuccess description: Occurs when image resizing completes successfully. The event will contain further details about specific formats and sizes. - type: firebase.extensions.storage-resize-images.v1.onError description: Occurs when an issue has been experienced in the Extension. This will include any error data that has been included within the Error Exception. - type: firebase.extensions.storage-resize-images.v1.onCompletion description: Occurs when the function is settled. Provides no customized data other than the context. - type: firebase.extensions.storage-resize-images.v1.onStartResize description: Occurs when an image resize operation completes successfully. This event is only triggered when shouldResize returns true and the resize operation succeeds. # Lifecycle events disabled - backfill feature commented out # lifecycleEvents: # onInstall: # function: backfillResizedImages # processingMessage: Resizing existing images in ${param:IMG_BUCKET} # onUpdate: # function: backfillResizedImages # processingMessage: Resizing existing images in ${param:IMG_BUCKET} # onConfigure: # function: backfillResizedImages # processingMessage: Resizing existing images in ${param:IMG_BUCKET}