def loadDeployment(deploymentData): """Returns a Deployment object for the given data""" #check that the deploymentData is valid if not ("deploymentId" in deploymentData and type(deploymentData["deploymentId"])==str and len(deploymentData["deploymentId"])>0): raise errors.BadRequestError("Deployment must have attribute 'deploymentId' (type=str and length>0)") if not ("name" in deploymentData and type(deploymentData["name"])==str and len(deploymentData["name"])>0): raise errors.BadRequestError("Deployment must have attribute 'name' (type=str and length>0)") if not ("status" in deploymentData and type(deploymentData["status"])==str and len(deploymentData["status"])>0): raise errors.BadRequestError("Deployment must have attribute 'status' (type=str and length>0)") if not ("dateCreated" in deploymentData and type(deploymentData["dateCreated"])==str and len(deploymentData["dateCreated"])>0): raise errors.BadRequestError("Deployment must have attribute 'dateCreated' (type=str and length>0)") if not ("dateModified" in deploymentData and type(deploymentData["dateModified"])==str and len(deploymentData["dateModified"])>0): raise errors.BadRequestError("Deployment must have attribute 'dateCreated' (type=str and length>0)") if not ("archived" in deploymentData and type(deploymentData["archived"])==bool): raise errors.BadRequestError("Deployment must have attribute 'archived' (type=bool)") if not ("goalSampleSize" in deploymentData and type(deploymentData["goalSampleSize"]) in [int, Decimal] and deploymentData["goalSampleSize"]>0): raise errors.BadRequestError("Deployment must have attribute 'goalSampleSize' (type=int and value>0)") if not ("currentSampleSize" in deploymentData and type(deploymentData["currentSampleSize"]) in [int, Decimal] and deploymentData["currentSampleSize"]>=0): raise errors.BadRequestError("Deployment must have attribute 'currentSampleSize' (type=int and value>=0)") if not ("facility" in deploymentData and type(deploymentData["facility"]) in [str, dict] and len(deploymentData["facility"])>0): raise errors.BadRequestError("Deployment must have attribute 'facility' (type=str or dict and length>0)") #construct the deployment d = Deployment() d.deploymentId = deploymentData["deploymentId"] d.name = deploymentData["name"] if "description" in deploymentData: d.description = deploymentData["description"] d.status = deploymentData["status"] d.dateCreated = deploymentData["dateCreated"] d.dateModified = deploymentData["dateModified"] d.archived = deploymentData["archived"] d.goalSampleSize = int(deploymentData["goalSampleSize"]) d.currentSampleSize = int(deploymentData["currentSampleSize"]) d.facility = facility_db_access.loadFacility(deploymentData["facility"]) return d
def _process_request_body(self): """Parse the request body.""" try: request = json.loads(self.request.body) self._code = request.get('code') if not self._code: raise errors.BadRequestError('`code` attribute is required') self._timezone_offset = request.get( 'timezoneOffset', DEFAULT_TIMEZONE_OFFSET) except ValueError: raise errors.BadRequestError('Unsupported request body')
def createDeploymentForStudy(studyId, deployment): s = getStudy(studyId) if not (s.status in ["DESIGNED", "DEPLOYED", "PAUSED"]): raise errors.BadRequestError( "Deployments can only be created for DESIGNED, DEPLOYED, and PAUSED studies" ) if not facility_db_access.facilityContainsAllEquipment( deployment.facility, s.equipmentList): raise errors.BadRequestError( "Deployment 'facility' must have all of the equpiment required by its Study" ) s.deploymentList.append(deployment) s.modifyDate() StudyTable.put_item(Item=s.toDynamo()) return deployment
def downloadFile(studyId, fileName): study = study_db_access.getStudy(studyId) if fileName not in study.resourceList: raise errors.BadRequestError("No file named " +fileName+ " for study " + studyId) key = studyId+fileName file = s3.get_object(Bucket=BUCKET_NAME, Key=key) return file
def _get_user(self): userid = util.verify_token(self.request.headers.get('Authorization')) if not userid: raise errors.BadRequestError('Unknown client ID') self._user = UserSettings.get_by_key_name(userid) if not self._user: raise errors.NotFoundError('Unknown user')
def createDeployment(studyId, deploymentData): #check that deploymentData is valid if not ("name" in deploymentData and type(deploymentData["name"])==str and len(deploymentData["name"])>0): raise errors.BadRequestError("Deployment must have attribute 'name' (type=str and length>0)") if not ("goalSampleSize" in deploymentData and type(deploymentData["goalSampleSize"]) in [int, Decimal] and deploymentData["goalSampleSize"]>0): raise errors.BadRequestError("Deployment must have attribute 'goalSampleSize' (type=int and value>0)") if not ("facility" in deploymentData and type(deploymentData["facility"]) in [str, dict] and len(deploymentData["facility"])>0): raise errors.BadRequestError("Deployment must have attribute 'facility' (type=str or dict and length>0)") #construct the deployment d = Deployment() d.name = deploymentData["name"] if "description" in deploymentData: d.description = deploymentData["description"] d.goalSampleSize = int(deploymentData["goalSampleSize"]) d.facility = facility_db_access.loadFacility(deploymentData["facility"]) #create the deployment (by updating its parent study) return study_db_access.createDeploymentForStudy(studyId, d)
def createPermissionForStudy(studyId): validateUser(studyId) permissionData = request.get_json() if not ("userId" in permissionData and type(permissionData["userId"])==str and len(permissionData["userId"])>0): raise errors.BadRequestError("Permission must have attribute 'userId' (type=str and length>0)") userId = permissionData["userId"] userPermission = permission_db_access.createAdminForStudy(userId, studyId) return toJson(userPermission)
def updateStudy(studyId, studyData): oldStudy = getStudy(studyId) newStudy = loadStudy(studyData) #check that the study can be updated if not (oldStudy.studyId == newStudy.studyId): raise errors.BadRequestError( "studyId of the study to be updated must mach the studyId of the endpoint" ) if not (oldStudy.dateModified == newStudy.dateModified): raise errors.BadRequestError( "dateModifed on the study to be updated does not match the dateModified in the database." ) if not (newStudy.status in ["CREATED", "DESIGNED", "DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError( "status must be CREATED, DESIGNED, DEPLOYED, PAUSED, or TERMINATED" ) #The archived flag can always be updated regardless of status oldStudy.archived = newStudy.archived if (oldStudy.status == "CREATED"): if not (newStudy.status in ["CREATED", "DESIGNED", "TERMINATED"]): raise errors.BadRequestError( "status of a CREATED study can only be updated to DESIGNED or TERMINATED" ) oldStudy.name = newStudy.name oldStudy.description = newStudy.description oldStudy.equipmentList = newStudy.equipmentList oldStudy.resourceList = newStudy.resourceList if (oldStudy.status == "DESIGNED"): if not (newStudy.status in ["DESIGNED", "DEPLOYED", "TERMINATED"]): raise errors.BadRequestError( "status of a DESIGNED study can only be updated to DEPLOYED or TERMINATED" ) if (oldStudy.status == "DEPLOYED"): if not (newStudy.status in ["DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError( "status of a DEPLOYED study can only be updated to PAUSED or TERMINATED" ) if (oldStudy.status == "PAUSED"): if not (newStudy.status in ["DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError( "status of a PAUSED study can only be updated to DEPLOYED or TERMINATED" ) if (oldStudy.status == "TERMINATED"): if not (newStudy.status == "TERMINATED"): raise errors.BadRequestError( "Cannot change the status of a TERMINATED study") if (newStudy.status == "TERMINATED"): for d in oldStudy.deploymentList: if not d.status == "TERMINATED": d.status = "TERMINATED" d.modifyDate() oldStudy.status = newStudy.status oldStudy.modifyDate() StudyTable.put_item(Item=oldStudy.toDynamo()) return oldStudy
def uploadFile(studyId, file): study = study_db_access.getStudy(studyId) if not study.status == "CREATED": raise errors.BadRequestError("Files can only uploaded for CREATED studies") fileName =file.filename key = studyId+fileName s3.upload_fileobj(file, BUCKET_NAME, key) study.resourceList.append(fileName) study_db_access.updateStudy(studyId, study.toDynamo()) return fileName
def _process_request_body(self): """Parse the request body.""" try: data = json.loads(self.request.body) self._user.night_mode = data.get('nightMode', self._user.night_mode) self._user.frequency = data.get('frequency', self._user.frequency) self._user.timezone_offset = data.get( 'timezoneOffset', self._user.timezone_offset) self._user.put() except ValueError: raise errors.BadRequestError('Unsupported request body')
def updateDeploymentForStudy(studyId, deployment): s = getStudy(studyId) if not (s.status in ["DESIGNED", "DEPLOYED", "PAUSED"]): raise errors.BadRequestError( "Deployments can only be updated for DESIGNED, DEPLOYED, and PAUSED studies" ) if not facility_db_access.facilityContainsAllEquipment( deployment.facility, s.equipmentList): raise errors.BadRequestError( "Deployment 'facility' must have all of the equpiment required by its Study" ) allDeploymentsArePausedOrTerminated = True for i in range(len(s.deploymentList)): if s.deploymentList[i].deploymentId == deployment.deploymentId: s.deploymentList[i] = deployment if s.deploymentList[i].status not in ["PAUSED", "TERMINATED"]: allDeploymentsArePausedOrTerminated = False if allDeploymentsArePausedOrTerminated and s.status == "DEPLOYED": s.status = "PAUSED" s.modifyDate() StudyTable.put_item(Item=s.toDynamo()) return deployment
class OAuthCodeExchangeHandler(webapp2.RequestHandler): """Request handler for OAuth 2.0 code exchange.""" @errors.error_aware def post(self): """Handle code exchange.""" self._process_request_body() self._exchange_code() user = self._create_user() util.write_response(self, user.to_dict()) def _process_request_body(self): """Parse the request body.""" try: request = json.loads(self.request.body) self._code = request.get('code') if not self._code: raise errors.BadRequestError('`code` attribute is required') self._timezone_offset = request.get( 'timezoneOffset', DEFAULT_TIMEZONE_OFFSET) except ValueError: raise errors.BadRequestError('Unsupported request body') def _exchange_code(self): """Retrieve credentials for the current user.""" oauth_flow = self._create_oauth_flow() # Perform the exchange of the code. try: creds = oauth_flow.step2_exchange(self._code) except FlowExchangeError, e: raise errors.InternalServerError('Unable to exchange code: ', e.message) # Verify that the token has been issued for our application. self._userid = util.verify_token(creds.access_token) if not self._userid: raise errors.BadRequestError('Unknown client ID') # Verify that we can retrieve valid refresh token for the current user. if creds.refresh_token: # Store the credentials in the data store using the userid as the key. StorageByKeyName( model.UserSettings, self._userid, 'credentials').put(creds) else: # Look for existing credentials in our datastore. creds = StorageByKeyName( model.UserSettings, self._userid, 'credentials').get() if not creds or not creds.refresh_token: raise errors.UnauthorizedError('No refresh token') return creds
def createEquipment(equipmentData): #check that equipmentData is valid if not ("name" in equipmentData and type(equipmentData["name"]) == str and len(equipmentData["name"]) > 0): raise errors.BadRequestError( "Equipment must have attribute 'name' (type=str and length>0)") #construct the equipment e = Equipment() e.name = equipmentData["name"] if "abbreviation" in equipmentData: e.abbreviation = equipmentData["abbreviation"] #create the equipment EquipmentTable.put_item(Item=e.toDynamo()) return e
def createFacility(facilityData): #check that facilityData is valid if not ("name" in deploymentData and type(deploymentData["name"]) == str and len(deploymentData["name"]) > 0): raise errors.BadRequestError( "Facility must have attribute 'name' (type=str and length>0)") #construct the facility f = Facility() f.name = facilityData["name"] if "equipmentList" in facilityData: f.equipmentList = equipment_db_access.loadEquipmentList( facilityData["equipmentList"]) #create the facility FacilityTable.put_item(Item=f.toDynamo()) return f
def createStudy(studyData): #check that the studyData is valid if not ("name" in studyData and type(studyData["name"]) == str and len(studyData["name"]) > 0): raise errors.BadRequestError( "Study must have attribute 'name' (type=str and length>0)") #construct the study s = Study() s.name = studyData["name"] if "description" in studyData: s.description = studyData["description"] if "equipmentList" in studyData: s.equipmentList = equipment_db_access.loadEquipmentList( studyData["equipmentList"]) #create the study StudyTable.put_item(Item=s.toDynamo()) return s
def updateDeployment(studyId, deploymentId, deploymentData): oldDeployment = getDeployment(studyId, deploymentId) newDeployment = loadDeployment(deploymentData) #check that the deployment can be updated if not (oldDeployment.deploymentId==newDeployment.deploymentId): raise errors.BadRequestError("deploymentId of the deployment to be updated must mach the deploymentId of the endpoint") if not (oldDeployment.dateModified==newDeployment.dateModified): raise errors.BadRequestError("dateModifed on the deployment to be updated does not match the dateModified in the database.") if not (newDeployment.status in ["CREATED", "DESIGNED", "DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError("status must be CREATED, DESIGNED, DEPLOYED, PAUSED, or TERMINATED") #The archived flag can always be updated regardless of status oldDeployment.archived = newDeployment.archived if (oldDeployment.status=="CREATED"): if not (newDeployment.status in ["CREATED", "DESIGNED", "TERMINATED"]): raise errors.BadRequestError("status of a CREATED deployment can only be updated to DESIGNED or TERMINATED") oldDeployment.name = newDeployment.name oldDeployment.description = newDeployment.description oldDeployment.goalSampleSize = newDeployment.goalSampleSize oldDeployment.facility = newDeployment.facility if (oldDeployment.status=="DESIGNED"): if not (newDeployment.status in ["DESIGNED", "DEPLOYED", "TERMINATED"]): raise errors.BadRequestError("status of a DESIGNED deployment can only be updated to DEPLOYED or TERMINATED") if (oldDeployment.status=="DEPLOYED"): if not (newDeployment.status in ["DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError("status of a DEPLOYED deployment can only be updated to PAUSED or TERMINATED") if study_db_access.getStudy(studyId).status=="DEPLOYED": oldDeployment.currentSampleSize = newDeployment.currentSampleSize if (oldDeployment.status=="PAUSED"): if not (newDeployment.status in ["DEPLOYED", "PAUSED", "TERMINATED"]): raise errors.BadRequestError("status of a PAUSED study can only be updated to DEPLOYED or TERMINATED") if (oldDeployment.status=="TERMINATED"): if not (newDeployment.status=="TERMINATED"): raise errors.BadRequestError("Cannot change the status of a TERMINATED study") oldDeployment.status = newDeployment.status #if the goalSampleSize has been reached, automatically pause the deployment if (oldDeployment.currentSampleSize>=oldDeployment.goalSampleSize and oldDeployment.status not in ["PAUSED", "TERMINATED"]): oldDeployment.status = "PAUSED" oldDeployment.modifyDate() return study_db_access.updateDeploymentForStudy(studyId, oldDeployment)
def loadStudy(studyData): """Returns a Study object for the given data""" #check that the studyData is valid if not ("studyId" in studyData and type(studyData["studyId"]) == str and len(studyData["studyId"]) > 0): raise errors.BadRequestError( "Study must have attribute 'studyId' (type=str and length>0)") if not ("name" in studyData and type(studyData["name"]) == str and len(studyData["name"]) > 0): raise errors.BadRequestError( "Study must have attribute 'name' (type=str and length>0)") if not ("status" in studyData and type(studyData["status"]) == str and len(studyData["status"]) > 0): raise errors.BadRequestError( "Study must have attribute 'status' (type=str and length>0)") if not ("dateCreated" in studyData and type(studyData["dateCreated"]) == str and len(studyData["dateCreated"]) > 0): raise errors.BadRequestError( "Study must have attribute 'dateCreated' (type=str and length>0)") if not ("dateModified" in studyData and type(studyData["dateModified"]) == str and len(studyData["dateModified"]) > 0): raise errors.BadRequestError( "Study must have attribute 'dateModified' (type=str and length>0)") if not ("archived" in studyData and type(studyData["archived"]) == bool): raise errors.BadRequestError( "Study must have attribute 'archived' (type=bool)") #construct the study s = Study() s.studyId = studyData["studyId"] s.name = studyData["name"] if "description" in studyData: s.description = studyData["description"] s.status = studyData["status"] s.dateCreated = studyData["dateCreated"] s.dateModified = studyData["dateModified"] s.archived = studyData["archived"] if "deploymentList" in studyData: s.deploymentList = deployment_db_access.loadDeploymentList( studyData["deploymentList"]) if "equipmentList" in studyData: s.equipmentList = equipment_db_access.loadEquipmentList( studyData["equipmentList"]) if "resourceList" in studyData: s.resourceList = studyData["resourceList"] return s