Lack of images property in response from Kinesis Video Streams / GetImages retrieved by aws-sdk-js-v3

324 Views Asked by At

Body of the handler:

const one: ValidatedEventAPIGatewayProxyEvent<typeof schema> = async (event) => {
  const input = {
    "EndTimestamp": new Date(1653843539000),
    "Format": "JPEG",
    "ImageSelectorType": "PRODUCER_TIMESTAMP",   
    "MaxResults": 10,
    "SamplingInterval": 3000,
    "StartTimestamp": new Date(1653843480000),
    "StreamName": "ExampleStream"
  }

  console.log('input', JSON.stringify(input, null,2))
  const client = new KinesisVideoArchivedMediaClient({ region: "eu-central-1" });
  const command = new GetImagesCommand(input);
  const res = await client.send(command);

  console.log('res', JSON.stringify(res, null,2))

  return formatJSONResponse({
    message: 'success',
    event,
  });
}

Current result - log from the code:

2022-05-29T17:43:31.063Z    2d#################535  INFO    res {
    "$metadata": {
        "httpStatusCode": 200,
        "requestId": "38##################0e",
        "attempts": 1,
        "totalRetryDelay": 0
    }
}

Expected: response including Images, NextToken properties

Other details:

Request with the same input executed from Postman gives a correct response:

{
    "Images": [
        {
            "Error": "NO_MEDIA",
            "ImageContent": null,
            "TimeStamp": 1.65384348E9
        },
        {
            "Error": null,
            "ImageContent": "/9j/4AAQSkZJRgABAgAAAQABAAD//gARTGF2YzU4LjEzNC4xMDAA/...",
            "TimeStamp": 1.653843486E9
        }
    ],
    "NextToken": "eyJleHB...n0ifQ=="
}

What I'm doing wrong? Thanks in advance

2

There are 2 best solutions below

0
jagonzalr On

I had the same issue using the v3 SDK so I tried using v2 with no luck and data was returning anything.

But I manage to make it work with v2 by getting first the data endpoint before calling getImages.

Like this:

import { KinesisVideo, KinesisVideoArchivedMedia } from 'aws-sdk'

const kinesisVideoClient = new KinesisVideo({
  apiVersion: '2017-09-30'
  region: process.env.AWS_REGION
})

const { DataEndpoint } = await kinesisVideoClient.getDataEndpoint({ APIName: 'GET_IMAGES', StreamName: 'my-stream' }).promise()

const params = {
  StreamName: 'my-stream',
  ImageSelectorType: 'PRODUCER_TIMESTAMP',
  StartTimestamp: new Date(),
  EndTimestamp: new Date(),
  SamplingInterval: 3000,
  Format: 'JPEG'
}

const options = {
  endpoint: DataEndpoint,
  apiVersion: '2017-09-30',
  region: process.env.AWS_REGION
}

const kinesisVideoArchiveMediaClient = new KinesisVideoArchivedMedia(options)

const { Images } = await kinesisVideoArchiveMediaClient.getImages(params).promise()

console.log(Images)

Hope this helps :)

PS. I used the latest AWS SDK v2 with a Lambda layer, the version provided by default on Lambda doesn't have the getImages function.

0
SquareNerd On

In case anyone else struggles with this, here is working V3 code. The bug is not in the code, it is in the documentation (according to AWS folks)

import { KinesisVideo } from '@aws-sdk/client-kinesis-video';
import {
    GetImagesCommandInput,
    GetImagesCommandOutput,
    KinesisVideoArchivedMedia,
} from '@aws-sdk/client-kinesis-video-archived-media';

const kinesisVideoClient = new KinesisVideo({
    region: 'us-east-1',
});
const response = await kinesisVideoClient.getDataEndpoint({
    APIName: 'GET_IMAGES',
    StreamName: streamName,
});
const kvArchiveMediaClient = new KinesisVideoArchivedMedia({
    endpoint: response.DataEndpoint!,
    region: 'us-east-1',
});

const params: GetImagesCommandInput = {
    StreamName: streamName,
    ImageSelectorType: 'PRODUCER_TIMESTAMP',
    StartTimestamp: new Date(startSecond * 1000),
    EndTimestamp: new Date(endSecond * 1000),
    SamplingInterval: 500, // in milliseconds
    Format: 'JPEG',
};

const images : Promise<GetImagesCommandOutput> = kvArchiveMediaClient.getImages(params);