blob: 1a6a54b0d9ccbd457497ccd83c17861afba2cbf5 [file] [log] [blame]
"""Utility class for sending requests to BonD, adding and controlling bots."""
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
import json
import logging
import requests
from datetime import datetime
from oauth2client.client import GoogleCredentials
_BOND_API_URL = 'https://bond-pa.sandbox.googleapis.com'
_HANGOUTS_API_URL = 'https://www.googleapis.com/hangouts/v1_meetings_preprod/'
_MEETINGS_API_URL = 'https://preprod-meetings.sandbox.googleapis.com'
_TOKEN_TTL_SECONDS = 3500
# See https://crbug.com/874835 for details on the credentials files.
_SERVICE_CREDS_FILE = '/creds/service_accounts/bond_service_account.json'
class BondHttpApi(object):
"""Utility class for sending requests to BonD for bots."""
def __init__(self):
self._last_token_request_time = None
self._last_token = None
def GetAvailableWorkers(self):
"""Gets the number of available workers for a conference."""
token = self._GetAccessToken()
resp = requests.get(
'%s/v1/workers:count' % _BOND_API_URL,
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer %s' % token
})
return json.loads(resp.text)["numOfAvailableWorkers"]
def CreateConference(self):
"""Creates a conference.
Returns:
The meeting code of the created conference.
"""
token = self._GetAccessToken()
request_data = {
'conference_type': 'THOR',
'backend_options': {
'mesi_apiary_url': _HANGOUTS_API_URL,
'mas_one_platform_url': _MEETINGS_API_URL
},
}
resp = requests.post(
'%s/v1/conferences:create' % _BOND_API_URL,
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer %s' % token,
},
data=json.dumps(request_data))
json_response = json.loads(resp.text)
logging.info("CreateConference response: %s", json_response)
return json_response["conference"]["conferenceCode"]
def ExecuteScript(self, script, meeting_code):
"""Executes the specified script.
Args:
script: Script to execute.
meeting_code: The meeting to execute the script for.
Returns:
RunScriptRequest denoting failure or success of the request.
"""
token = self._GetAccessToken()
request_data = {
'script': script,
'conference': {
'conference_code': meeting_code
}
}
resp = requests.post(
'%s/v1/conference/%s/script' % (_BOND_API_URL, meeting_code),
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer %s' % token,
},
data=json.dumps(request_data))
json_response = json.loads(resp.text)
logging.info("ExecuteScript response: %s", json_response)
return json_response['success']
def AddBotsRequest(self, meeting_code, number_of_bots, ttl_secs):
"""Adds a number of bots to a meeting for a specified period of time.
Args:
meeting_code: The meeting to join.
number_of_bots: The number of bots to add to the meeting.
ttl_secs: The time in seconds that the bots will stay in the meeting after
joining.
Returns:
List of IDs of the started bots.
"""
token = self._GetAccessToken()
request_data = {
'num_of_bots': number_of_bots,
'ttl_secs': ttl_secs,
'video_call_options': {},
'media_options': {
'audio_file_path': "audio_32bit_48k_stereo.raw",
'mute_audio': True,
'video_file_path': "jamboard_two_far_video_hd.1280_720.yuv",
'video_fps': 30,
'mute_video': False
},
'backend_options': {
'mesi_apiary_url': _HANGOUTS_API_URL,
'mas_one_platform_url': _MEETINGS_API_URL
},
'conference': {
'conference_code': meeting_code
},
'bot_type': "MEETINGS"
}
resp = requests.post(
'%s/v1/conference/%s/bots:add' % (_BOND_API_URL, meeting_code),
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer %s' % token
},
data=json.dumps(request_data))
json_response = json.loads(resp.text)
logging.info("AddBotsRequest response: %s", json_response)
return json_response["botIds"]
def _GetAccessToken(self):
if self._last_token is None or self._CheckTokenExpired():
credentials = self._CreateApiCredentials()
scope = 'https://www.googleapis.com/auth/meetings'
credentials = credentials.create_scoped(scope)
self._last_token_request_time = datetime.now()
self._last_token = credentials.get_access_token().access_token
return self._last_token
def _CreateApiCredentials(self):
return GoogleCredentials.from_stream(_SERVICE_CREDS_FILE)
def _CheckTokenExpired(self):
elapsed = datetime.now() - self._last_token_request_time
return elapsed.total_seconds() > _TOKEN_TTL_SECONDS