diff --git a/samples/analyze/README.md b/samples/analyze/README.md new file mode 100644 index 00000000..52fdd058 --- /dev/null +++ b/samples/analyze/README.md @@ -0,0 +1,32 @@ +# Google Cloud Video Intelligence Sample + +Demonstrates face detection, label detection, and shot change detection using +the Google Cloud API.. + +## Setup +Please follow the [Set Up Your Project](https://cloud.google.com/video-intelligence/docs/getting-started#set_up_your_project) +steps in the Quickstart doc to create a project and enable the Google Cloud +Video Intelligence API. Following those steps, make sure that you +[Set Up a Service Account](https://cloud.google.com/video-intelligence/docs/common/auth#set_up_a_service_account), +and export the following environment variable: + +``` +export GOOGLE_APPLICATION_CREDENTIALS=/path/to/your-project-credentials.json +``` + +## Run the sample + +Install [pip](https://pip.pypa.io/en/stable/installing) if not already installed. + +Install the necessary libraries using pip: + +```sh +$ pip install -r requirements.txt +``` + +Run the sample, for example: +``` +python analyze.py faces gs://demomaker/google_gmail.mp4 +python analyze.py labels gs://demomaker/cat.mp4 +python analyze.py shots gs://demomaker/gbikes_dinosaur.mp4 +``` diff --git a/samples/analyze/analyze.py b/samples/analyze/analyze.py new file mode 100644 index 00000000..06f182ed --- /dev/null +++ b/samples/analyze/analyze.py @@ -0,0 +1,138 @@ +#!/usr/bin/env python + +# Copyright 2017 Google Inc. All Rights Reserved. +# +# 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 +# +# http://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. + +"""This application demonstrates how to perform basic operations with the +Google Cloud Video Intelligence API. + +For more information, check out the documentation at +https://cloud.google.com/videointelligence/docs. +""" + +import argparse +import sys +import time + +from google.cloud.gapic.videointelligence.v1beta1 import enums +from google.cloud.gapic.videointelligence.v1beta1 import ( + video_intelligence_service_client) + + +def analyze_faces(path): + """ Detects faces given a GCS path. """ + video_client = (video_intelligence_service_client. + VideoIntelligenceServiceClient()) + features = [enums.Feature.FACE_DETECTION] + operation = video_client.annotate_video(path, features) + print('\nProcessing video for label annotations:') + + while not operation.done(): + sys.stdout.write('.') + sys.stdout.flush() + time.sleep(20) + + print('\nFinished processing.') + + # first result is retrieved because a single video was processed + face_annotations = (operation.result().annotation_results[0]. + face_annotations) + + for face_id, face in enumerate(face_annotations): + print('Thumbnail size: {}'.format(len(face.thumbnail))) + + for segment_id, segment in enumerate(face.segments): + print('Track {}: {} to {}'.format( + segment_id, + segment.start_time_offset, + segment.end_time_offset)) + + +def analyze_labels(path): + """ Detects labels given a GCS path. """ + video_client = (video_intelligence_service_client. + VideoIntelligenceServiceClient()) + features = [enums.Feature.LABEL_DETECTION] + operation = video_client.annotate_video(path, features) + print('\nProcessing video for label annotations:') + + while not operation.done(): + sys.stdout.write('.') + sys.stdout.flush() + time.sleep(20) + + print('\nFinished processing.') + + # first result is retrieved because a single video was processed + results = operation.result().annotation_results[0] + + for label in results.label_annotations: + print('Label description: {}'.format(label.description)) + print('Locations:') + + for l, location in enumerate(label.locations): + print('\t{}: {} to {}'.format( + l, + location.segment.start_time_offset, + location.segment.end_time_offset)) + + +def analyze_shots(path): + """ Detects camera shot changes. """ + video_client = (video_intelligence_service_client. + VideoIntelligenceServiceClient()) + features = [enums.Feature.SHOT_CHANGE_DETECTION] + operation = video_client.annotate_video(path, features) + print('\nProcessing video for shot change annotations:') + + while not operation.done(): + sys.stdout.write('.') + sys.stdout.flush() + time.sleep(20) + + print('\nFinished processing.') + + # first result is retrieved because a single video was processed + shots = operation.result().annotation_results[0] + + for note, shot in enumerate(shots.shot_annotations): + print('Scene {}: {} to {}'.format( + note, + shot.start_time_offset, + shot.end_time_offset)) + + +if __name__ == '__main__': + parser = argparse.ArgumentParser( + description=__doc__, + formatter_class=argparse.RawDescriptionHelpFormatter) + subparsers = parser.add_subparsers(dest='command') + analyze_faces_parser = subparsers.add_parser( + 'faces', help=analyze_faces.__doc__) + analyze_faces_parser.add_argument('path') + analyze_labels_parser = subparsers.add_parser( + 'labels', help=analyze_labels.__doc__) + analyze_labels_parser.add_argument('path') + analyze_shots_parser = subparsers.add_parser( + 'shots', help=analyze_shots.__doc__) + analyze_shots_parser.add_argument('path') + + args = parser.parse_args() + + if args.command == 'faces': + analyze_faces(args.path) + if args.command == 'labels': + analyze_labels(args.path) + if args.command == 'shots': + analyze_shots(args.path) diff --git a/samples/analyze/analyze_test.py b/samples/analyze/analyze_test.py new file mode 100644 index 00000000..f3178319 --- /dev/null +++ b/samples/analyze/analyze_test.py @@ -0,0 +1,50 @@ +#!/usr/bin/env python + +# Copyright 2017 Google, Inc +# +# 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 +# +# http://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. + +import os + +import pytest + +import analyze + +BUCKET = os.environ['CLOUD_STORAGE_BUCKET'] +LABELS_FILE_PATH = '/video/cat.mp4' +FACES_FILE_PATH = '/video/googlework.mp4' +SHOTS_FILE_PATH = '/video/gbikes_dinosaur.mp4' + + +@pytest.mark.slow +def test_cat_video_shots(capsys): + analyze.analyze_shots( + 'gs://{}{}'.format(BUCKET, SHOTS_FILE_PATH)) + out, _ = capsys.readouterr() + assert 'Scene 1:' in out + + +@pytest.mark.slow +def test_work_video_faces(capsys): + analyze.analyze_faces( + 'gs://{}{}'.format(BUCKET, FACES_FILE_PATH)) + out, _ = capsys.readouterr() + assert 'Thumbnail' in out + + +@pytest.mark.slow +def test_dino_video_labels(capsys): + analyze.analyze_labels( + 'gs://{}{}'.format(BUCKET, LABELS_FILE_PATH)) + out, _ = capsys.readouterr() + assert 'Whiskers' in out diff --git a/samples/analyze/requirements.txt b/samples/analyze/requirements.txt new file mode 100644 index 00000000..ba92ac97 --- /dev/null +++ b/samples/analyze/requirements.txt @@ -0,0 +1 @@ +https://storage.googleapis.com/videointelligence-alpha/videointelligence-python.zip