https://github.com/deek87/lamba-thumbnailer
AWS S3 Video Thumbnailer with Lambda
https://github.com/deek87/lamba-thumbnailer
aws aws-lambda aws-s3 image lambda lambda-function lambda-functions s3 serverless serverless-functions thumbnail thumbnail-generator thumbnail-images thumbnailer thumbnails typescript video video-thumbnail video-thumbnail-generator webp
Last synced: 4 months ago
JSON representation
AWS S3 Video Thumbnailer with Lambda
- Host: GitHub
- URL: https://github.com/deek87/lamba-thumbnailer
- Owner: deek87
- License: mit
- Created: 2018-08-29T10:47:03.000Z (over 7 years ago)
- Default Branch: master
- Last Pushed: 2023-01-07T23:58:32.000Z (about 3 years ago)
- Last Synced: 2025-09-13T19:10:59.371Z (5 months ago)
- Topics: aws, aws-lambda, aws-s3, image, lambda, lambda-function, lambda-functions, s3, serverless, serverless-functions, thumbnail, thumbnail-generator, thumbnail-images, thumbnailer, thumbnails, typescript, video, video-thumbnail, video-thumbnail-generator, webp
- Language: TypeScript
- Size: 16 MB
- Stars: 25
- Watchers: 1
- Forks: 5
- Open Issues: 2
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README

# IMPORTANT
This branch is currently under development and is provided as is
# Roadmap for TypeScript
- [x] Convert All Code to TypeScript (done)
- [x] Use FFmpeg Layers for Lambda instead (done)
- [ ] Make the thumbnailer more moduler (in-progress)
- [ ] Implement Tests (to be done)
# Table Of Contents
- [Introduction](#Introduction)
- [Getting Started](#Getting-Started)
- [Using in your own function](#Using-in-your-own-function)
- [Thumbnail Configuration](#Thumbnail-Configuration)
- [Size](#Size)
- [Type](#Type)
- [Quality](#Quality)
- [Output Location](#Output-Location)
- [Original Tutorial](#Original-Tutorial)
- [License](#License)
## Introduction
This package was created to automatically generate thumbnails from s3 video uploads.
## Getting Started
Install this package using the following the command then require the package in your code.
```sh
npm install lambda-video-thumbnailer
```
### Using in your own function
You can use [the provided s3example.js](examples/s3.js) to get you started.
Or you can use the following code snippet for a lambda function.
```js
// Require the library
const lvt = require("lambda-video-thumbnailer");
exports.handler = function (event, context) {
// Returns a S3Thumbnailer Class
const t = new lvt.S3(event.Records[0].s3);
// Create a thumbnail will return promise
return t.createThumbnail({
width: 100,
height: 100,
time: "00:00:05",
type: "webp",
});
};
```
## Thumbnail Configuration
`createThumbnail()` takes a `thumbnailConfig` object with that has the following default options
```json
{
"prefix": "thumbnails/",
"width": 180,
"height": 180,
"time": "00:00:05",
"type": "jpg",
"quality": 2,
"thumbnailOption": "default"
}
```
### Size
To configure the output size of thumbnails simply supply a width/height number. If you want to automatically calculate width or height based on the aspect ratio of the input, just use -1. For example:
```json
{
"width": 700,
"height": -1
}
```
This will produce a 700x300 image when the input aspect ratio is 21:9
If your output needs to be a multiple of n then supply -n and it will output an output that is scaled by the ratio and a multiple of -n. For example
```json
{
"width": -3,
"height": 250
}
```
This will produce a 441x250 image when the aspect raito is 21:9
### Type
To configure the output type of thumbnails just set the type to `"jpg"`, `"png"` or `"webp"`
```json
{
"type": "webp"
}
```
NOTE: ffmpeg with png tends to output very large filesizes even with -pred mixed
### Quality
The output quality of the thumbnail is controlled by the `quality` property. It is controlled on a scale of 1-10 with 1 being the best quality and 10 being the worst quality.
```json
{
"quality": 1
}
```
### Thumbnail Option
This option determines which filter to use for capturing thumbnails via ffmpeg. The options currently are `default`,`none`. The `default` option will set the filter to `thumbnail` this will look for the best frame within the select timeslot, this can be use quite a bit of memory on large files but will generally give the best screenshots. `none` will not use any filter and pick the first frame at the given timeslot.
```json
{
"thumbnailOption": "none"
}
```
### Output Location
The output bucket is defined by the `outputBucket` thumbnail config option, by default this will output the files to the source bucket if left blank.
```json
{
"outputBucket": "mybucket"
}
```
By default the output file name will use the source file with the new type suffix. For example `movie_trailer.mp4` becomes `move_trailer.jpg` when used with the jpg type output.
However you can customize it with the `outputKey` option in your thumbnail config. It will still attach the type or replace it `my_new_filename.hello` becomes `my_new_filename.jpg`
```json
{
"outputKey": "my_new_filename"
}
```
## Setup the Lambda Function
This package requires a ffmpeg layer to function. You can use the following arns:
- [Asia](#Asia)
- [Europe](#Europe)
- [Canada](#Canada)
- [United States](#United-States)
- [South America](#South-America)
Or alternatively use the serverlesspub build (only available in ap-us-east-1)
arn:aws:lambda:us-east-1:145266761615:layer:ffmpeg:4 or build your own from their github repo [serverlesspub/ffmpeg-aws-lambda-layer](https://github.com/serverlesspub/ffmpeg-aws-lambda-layer)
Then just go onto AWS Lambda create a new function and give it a trigger of put objects with a suffix filter of _.avi, _.mov etc..
Although you don't need to do this it just reduces the number of invocations. Apply a policy of LambdaExecute to the IAM role (this gives read and write access to s3) then set the memory limit to the maximum\* and set timeout for 30seconds (again it normally takes around 6 seconds but its good to be safe).
\*NOTE: I have never reached the maximum with this function, its normally around 700mb even for 4gb mov files
## Lambda Layers
### Asia
- `arn:aws:lambda:ap-east-1:260572601982:layer:ffmpeg:1` - Hong Kong (AP East 1)
- `arn:aws:lambda:ap-south-1:260572601982:layer:ffmpeg:1` - Mumbai (AP South 1)
- `arn:aws:lambda:ap-northeast-2:260572601982:layer:ffmpeg:1` - Seoul (AP Northeast 2)
- `arn:aws:lambda:ap-southeast-1:260572601982:layer:ffmpeg:1` - Singapore (AP Southeast 1)
- `arn:aws:lambda:ap-southeast-2:260572601982:layer:ffmpeg:1` - Sydney (AP Southeast 2)
- `arn:aws:lambda:ap-northeast-1:260572601982:layer:ffmpeg:1` - Tokyo (AP Northeast 1)
### Europe
- `arn:aws:lambda:eu-central-1:260572601982:layer:ffmpeg:1` - Frankfurt (EU Central 1)
- `arn:aws:lambda:eu-west-1:260572601982:layer:ffmpeg:1` - Ireland (EU West 1)
- `arn:aws:lambda:eu-west-2:260572601982:layer:ffmpeg:1` - London (EU West 2)
- `arn:aws:lambda:eu-west-3:260572601982:layer:ffmpeg:1` - Paris (EU West 3)
- `arn:aws:lambda:eu-north-1:260572601982:layer:ffmpeg:1` - Stockholm (EU North 1)
### Canada
- `arn:aws:lambda:ca-central-1:260572601982:layer:ffmpeg:1` - Central (CA Central 1)
### South America
- `arn:aws:lambda:sa-east-1:260572601982:layer:ffmpeg:1` - São Paulo (SA East 1)
### United States
- `arn:aws:lambda:us-east-1:260572601982:layer:ffmpeg:1` - North Viginia (US East 1)
- `arn:aws:lambda:us-east-2:260572601982:layer:ffmpeg:1` - Ohio (US East 2)
- `arn:aws:lambda:us-west-1:260572601982:layer:ffmpeg:1` - N. California (US West 1)
- `arn:aws:lambda:us-west-2:260572601982:layer:ffmpeg:1` - Oregon (US West 2)
## Original Tutorial
Originally this was a tutorial I wrote back in July 2017, I updated it a bit since then. The original also contained mediainfo. [Available Here](https://concrete5.co.jp/blog/creating-video-thumbnails-aws-lambda-your-s3-bucket)
## License
[MIT](LICENSE)