def apikey(): """ Verify OC membership and return an API key. The API key will be saved in the DB to verify use as well as returned upon subsequent calls to this endpoint with the same OC credentials. """ json = request.get_json() email = json.get('email') password = json.get('password') is_oc_member = is_user_oc_member(email, password) if not is_oc_member: return unauthorized_response() try: # We need to check the database for an existing key apikey = Key.query.filter_by(email=email).first() # Don't return success for blacklisted keys if apikey and apikey.blacklisted: return unauthorized_response() if not apikey: # Since they're already authenticated by is_oc_user(), we know we # can generate an API key for them if they don't already have one apikey = create_new_apikey(email, db.session) if not apikey: return utils.standardize_response(status_code=500) logger.info(apikey.serialize) return utils.standardize_response(payload=dict(data=apikey.serialize), datatype="credentials") except Exception as e: logger.exception(e) return utils.standardize_response(status_code=500)
def update_resource(id, json, db): resource = Resource.query.get(id) if not resource: return redirect('/404') langs, categ = get_attributes(json) index_object = {'objectID': id} try: logger.info(f"Updating resource. Old data: {resource.serialize}") if json.get('languages'): resource.languages = langs index_object['languages'] = resource.serialize['languages'] if json.get('category'): resource.category = categ index_object['category'] = categ.name if json.get('name'): resource.name = json.get('name') index_object['name'] = json.get('name') if json.get('url'): resource.url = json.get('url') index_object['url'] = json.get('url') if 'paid' in json: paid = json.get('paid') # Converts "false" and "true" to their bool if type(paid) is str and paid.lower() in ["true", "false"]: paid = paid.lower().strip() == "true" resource.paid = paid index_object['paid'] = paid if 'notes' in json: resource.notes = json.get('notes') index_object['notes'] = json.get('notes') try: index.partial_update_object(index_object) except (AlgoliaUnreachableHostException, AlgoliaException) as e: if environ.get("FLASK_ENV") != 'development': logger.exception(e) msg = f"Algolia failed to update index for resource '{resource.name}'" logger.warn(msg) error = {'errors': [{"algolia-failed": {"message": msg}}]} return utils.standardize_response(payload=error, status_code=500) # Wait to commit the changes until we know that Aloglia was updated db.session.commit() return utils.standardize_response(payload=dict( data=resource.serialize)) except IntegrityError as e: logger.exception(e) return utils.standardize_response(status_code=422) except Exception as e: logger.exception(e) return utils.standardize_response(status_code=500)
def update_resource(id, json, db): resource = Resource.query.get(id) api_key = g.auth_key.apikey if not resource: return redirect('/404') langs, categ = get_attributes(json) index_object = {'objectID': id} def get_unique_resource_categories_as_strings(): resources = Resource.query.all() return {resource.category.name for resource in resources} def get_unique_resource_languages_as_strings(): resources = Resource.query.all() return { language.name for resource in resources for language in resource.languages } try: logger.info(f"Updating resource. Old data: " f"{json_module.dumps(resource.serialize(api_key))}") if json.get('languages') is not None: old_languages = resource.languages[:] resource.languages = langs index_object['languages'] = resource.serialize( api_key)['languages'] resource_languages = get_unique_resource_languages_as_strings() for language in old_languages: if language.name not in resource_languages: db.session.delete(language) if json.get('category'): old_category = resource.category resource.category = categ index_object['category'] = categ.name resource_categories = get_unique_resource_categories_as_strings() if old_category.name not in resource_categories: db.session.delete(old_category) if json.get('name'): resource.name = json.get('name') index_object['name'] = json.get('name') if json.get('url'): resource.url = json.get('url') index_object['url'] = json.get('url') if 'free' in json: free = ensure_bool(json.get('free')) resource.free = free index_object['free'] = free if 'notes' in json: resource.notes = json.get('notes') index_object['notes'] = json.get('notes') try: index.partial_update_object(index_object) except (AlgoliaUnreachableHostException, AlgoliaException) as e: if environ.get("FLASK_ENV") != 'development': logger.exception(e) msg = f"Algolia failed to update index for resource '{resource.name}'" logger.warn(msg) error = {'errors': [{"algolia-failed": {"message": msg}}]} return utils.standardize_response(payload=error, status_code=500) # Wait to commit the changes until we know that Aloglia was updated db.session.commit() return utils.standardize_response( payload=dict(data=resource.serialize(api_key)), datatype="resource") except IntegrityError as e: logger.exception(e) return utils.standardize_response(status_code=422) except Exception as e: logger.exception(e) return utils.standardize_response(status_code=500)