Applying requested changes

pull/47/head
Matheus Lima 2019-02-20 20:22:22 -03:00
parent af83a190db
commit 1ad957142a
5 changed files with 48 additions and 37 deletions

View File

@ -26,40 +26,43 @@ class AccountDeviceEndpoint(SeleneEndpoint):
def post(self, account_id): def post(self, account_id):
payload = json.loads(self.request.data) payload = json.loads(self.request.data)
device = AddDevice(payload) add_device = AddDevice(payload)
device.validate() add_device.validate()
code = self.request.args['code'] code = self.request.args['code']
# Checking if there's one pairing session for the pairing code # Checking if there's one pairing session for the pairing code
pairing_json = self.cache.get('pairing.code:{}'.format(code)) pairing_json = self.cache.get('pairing.code:{}'.format(code))
if pairing_json: if pairing_json:
device_id = self._finish_pairing(account_id, code, device, pairing_json) device_id = self._finish_pairing(account_id, code, add_device, pairing_json)
response = device_id, HTTPStatus.OK response = device_id, HTTPStatus.OK
else: else:
response = '', HTTPStatus.NO_CONTENT response = '', HTTPStatus.NO_CONTENT
return response return response
def _finish_pairing(self, account_id, code, device, pairing_json): def _finish_pairing(self, account_id, code, add_device, pairing_json):
pairing = json.loads(pairing_json) pairing = json.loads(pairing_json)
# Removing the pairing code from the cache # Removing the pairing code from the cache
self.cache.delete('pairing.code:{}'.format(code)) self.cache.delete('pairing.code:{}'.format(code))
# Finishing the pairing process # Finishing the pairing process
device_id = self._pair( device_id = self._pair(
account_id, account_id,
str(device.name), add_device,
str(device.wake_word_id),
str(device.text_to_speech_id),
pairing pairing
) )
return device_id return device_id
def _pair(self, account_id: str, name: str, wake_word_id: str, text_to_speech_id: str, pairing: dict): def _pair(self, account_id: str, add_device: AddDevice, pairing: dict):
"""Creates a device and associate it to a pairing session""" """Creates a device and associate it to a pairing session"""
with get_db_connection(self.config['DB_CONNECTION_POOL']) as db: with get_db_connection(self.config['DB_CONNECTION_POOL']) as db:
result = DeviceRepository(db).add_device(account_id, name, wake_word_id, text_to_speech_id) result = DeviceRepository(db).add_device(
pairing['uuid'] = result['id'] account_id,
self.cache.set_with_expiration( str(add_device.name),
'pairing.token:{}'.format(pairing['token']), str(add_device.wake_word_id),
json.dumps(pairing), str(add_device.text_to_speech_id)
self.device_pairing_time
) )
return pairing['uuid'] pairing['uuid'] = result['id']
self.cache.set_with_expiration(
'pairing.token:{}'.format(pairing['token']),
json.dumps(pairing),
self.device_pairing_time
)
return pairing['uuid']

View File

@ -37,12 +37,7 @@ class DeviceActivateEndpoint(SeleneEndpoint):
pairing = self._get_pairing_session(device_activate) pairing = self._get_pairing_session(device_activate)
if pairing: if pairing:
device_id = pairing['uuid'] device_id = pairing['uuid']
self._activate( self._activate(device_id, device_activate)
device_id,
str(device_activate.platform),
str(device_activate.enclosure_version),
str(device_activate.core_version)
)
response = self._generate_login(device_id), HTTPStatus.OK response = self._generate_login(device_id), HTTPStatus.OK
else: else:
response = '', HTTPStatus.NO_CONTENT response = '', HTTPStatus.NO_CONTENT
@ -61,22 +56,27 @@ class DeviceActivateEndpoint(SeleneEndpoint):
self.cache.delete(self._token_key(token)) self.cache.delete(self._token_key(token))
return pairing return pairing
def _activate(self, device_id: str, platform: str, enclosure_version: str, core_version: str): def _activate(self, device_id: str, device_activate: DeviceActivate):
"""Updates a device in the database with the core version, platform and enclosure_version fields""" """Updates a device in the database with the core version, platform and enclosure_version fields"""
with get_db_connection(self.config['DB_CONNECTION_POOL']) as db: with get_db_connection(self.config['DB_CONNECTION_POOL']) as db:
DeviceRepository(db).update_device(device_id, platform, enclosure_version, core_version) DeviceRepository(db).update_device(
device_id,
str(device_activate.platform),
str(device_activate.enclosure_version),
str(device_activate.core_version)
)
def _generate_login(self, device_id: str): def _generate_login(self, device_id: str):
self.sha512.update(bytes(str(uuid.uuid4()), 'utf-8')) self.sha512.update(bytes(str(uuid.uuid4()), 'utf-8'))
access = self.sha512.hexdigest() access = self.sha512.hexdigest()
self.sha512.update(bytes(str(uuid.uuid4()), 'utf-8')) self.sha512.update(bytes(str(uuid.uuid4()), 'utf-8'))
refresh = self.sha512.hexdigest() refresh = self.sha512.hexdigest()
login = { login = dict(
'uuid': device_id, uuid=device_id,
'accessToken': access, accessToken= access,
'refreshToken': refresh, refreshToken=refresh,
'expiration': self.ONE_DAY expiration=self.ONE_DAY
} )
login_json = json.dumps(login) login_json = json.dumps(login)
# Storing device access token for one: # Storing device access token for one:
self.cache.set_with_expiration('device.session:{uuid}'.format(uuid=device_id), login_json, self.ONE_DAY) self.cache.set_with_expiration('device.session:{uuid}'.format(uuid=device_id), login_json, self.ONE_DAY)

View File

@ -44,9 +44,10 @@ class DeviceCodeEndpoint(SeleneEndpoint):
if self.cache.set_if_not_exists_with_expiration(self._code_key(code), if self.cache.set_if_not_exists_with_expiration(self._code_key(code),
value=pairing_json, value=pairing_json,
expiration=self.device_pairing_time): expiration=self.device_pairing_time):
return pairing response = pairing
else: else:
return self._create(state) response = self._create(state)
return response
@staticmethod @staticmethod
def _code_key(code): def _code_key(code):

View File

@ -4,8 +4,14 @@ from datetime import date, timedelta
from behave import fixture, use_fixture from behave import fixture, use_fixture
from public_api.api import public from public_api.api import public
from selene.data.account import Account, AccountRepository, AccountAgreement, PRIVACY_POLICY, TERMS_OF_USE, Agreement, \ from selene.data.account import (
AgreementRepository Account,
AccountRepository,
AccountAgreement,
PRIVACY_POLICY,
TERMS_OF_USE,
Agreement,
AgreementRepository)
from selene.data.device import DeviceRepository from selene.data.device import DeviceRepository
from selene.data.device.entity.text_to_speech import TextToSpeech from selene.data.device.entity.text_to_speech import TextToSpeech
from selene.data.device.entity.wake_word import WakeWord from selene.data.device.entity.wake_word import WakeWord

View File

@ -20,10 +20,11 @@ def add_device(context):
'wake_word_id': context.wake_word_id, 'wake_word_id': context.wake_word_id,
'text_to_speech_id': context.text_to_speech_id 'text_to_speech_id': context.text_to_speech_id
} }
response = context.client.post('/api/account/{account_id}/device?code={code}' response = context.client.post(
.format(account_id=context.account.id, code=context.pairing['code']), '/api/account/{account_id}/device?code={code}'
data=json.dumps(device), .format(account_id=context.account.id, code=context.pairing['code']),
content_type='application_json') data=json.dumps(device),
content_type='application_json')
context.device_id = response.data.decode('utf-8') context.device_id = response.data.decode('utf-8')