def get(self): """Refreshes an existing JWT by creating a new one that is a copy of the old except that it has a refreshed access expiration. .. :quickref: Authentication; Refresh a token. .. code-block:: bash $ curl http://localhost:5000/api/v1/auth/token/ -X GET \\ -H "Authorization: Bearer <your_token>" """ # old_token = praetorian.read_token_from_header() # new_token = praetorian.refresh_jwt_token(old_token) # response = {"access_token": new_token} user = current_user() response = { "access_token": praetorian.encode_jwt_token(user), "valid_for": praetorian.access_lifespan.total_seconds(), "user": { "id": user.id, "login": user.login, "full_name": user.full_name, "email": user.email, }, } return NestedResponse().dump(response)
def post(self) -> dict: """Creates a new project. .. :quickref: Projects; Create a new project. :param name: a name/title for the project :param description: a description of the project and it's purpose :param workspace_id: id of the workspace that contains this project :returns: a newly created project """ parser = reqparse.RequestParser() parser.add_argument("name", type=str, required=True, help="No name provided") parser.add_argument("description", type=str) parser.add_argument("workspace_id", type=int, required=True) args = parser.parse_args() workspace = Workspace.query.filter_by(id=args["workspace_id"]).first() if workspace: project = Project( name=args["name"], description=args["description"], workspace_id=args["workspace_id"], ) db.session.add(project) db.session.commit() return NestedResponse(schema=ProjectSchema).dump(project) return { "error": f"Workspace {args['workspace_id']} does not exist." }, 400
def post(self): """Logs the user in by parsing a POST request containing user credentials and issuing a JWT token. .. :quickref: Authentication; Log user in. .. code-block:: bash $ curl http://localhost:5000/api/v1/auth/login/ -X POST \\ -d '{"login":"******", "password":"******"}' """ parser = reqparse.RequestParser() parser.add_argument("login", type=str, required=True) parser.add_argument("password", type=str, required=True) args = parser.parse_args() user = praetorian.authenticate(args["login"], args["password"]) current_app.logger.info("user " + str(user.id) + " logged in successfully") response = { "access_token": praetorian.encode_jwt_token(user), "valid_for": praetorian.access_lifespan.total_seconds(), "user": { "id": user.id, "login": user.login, "full_name": user.full_name, "email": user.email, }, } return NestedResponse().dump(response)
def get(self, id: int) -> dict: workspace = Workspace.query.filter_by(id=id).first() if not workspace: abort(404) return NestedResponse(schema=WorkspaceSchema).dump(workspace)
def get(self, id: int) -> dict: project = Project.query.filter_by(id=id).first() if not project: abort(404) return NestedResponse(schema=ProjectSchema).dump(project)
def post(self) -> dict: """Creates a new user. .. :quickref: Users; Create a new user. :param login: login for the new user :param password: password for the new user :param full_name: full name for the new user (optional) :param email: an email address for the new user (optional) :returns: a newly created user """ parser = reqparse.RequestParser() parser.add_argument("login", type=str, required=True) parser.add_argument("password", type=str, required=True) parser.add_argument("full_name", type=str) parser.add_argument("email", type=str) args = parser.parse_args() new_user = User( login=args["login"], password=args["password"], full_name=args["full_name"], email=args["email"], ) db.session.add(new_user) db.session.commit() return NestedResponse(schema=UserSchema).dump(new_user)
def get(self) -> list: """Lists all models that satisfy certain conditions. Every parameter can be appeneded multiple times. :param workspace: search for models only in this workspace :param project: search for models only in this project :param hyperparam: search for models that have this hyperparameter :param param: search for models that have this parameter :returns: a list of objects """ parser = paginated_parser.copy() parser.add_argument("projects", type=str) args = parser.parse_args() # Initialize query builder query = Model.query paginated_query = query.paginate(args["page"], args["per_page"], False) return NestedResponse(schema=ModelLesserSchema, many=True, pagination=paginated_query).dump( paginated_query.items)
def get(self) -> list: parser = paginated_parser.copy() args = parser.parse_args() paginated_query = Project.query.paginate(args["page"], args["per_page"], False) return NestedResponse( schema=ProjectSchema, many=True, pagination=paginated_query ).dump(paginated_query.items)
def post(self) -> dict: parser = reqparse.RequestParser() parser.add_argument("name", type=str, required=True, help="No name provided") parser.add_argument("description", type=str, default="") args = parser.parse_args() workspace = Workspace(name=args["name"], description=args["description"]) db.session.add(workspace) db.session.commit() return NestedResponse(schema=WorkspaceSchema).dump(workspace)
def get(self, id: int) -> dict: """Returns data about a requested user. .. :quickref: Users; Get a single user. :param id: id of a requested user :returns: a single object """ user = User.query.filter_by(id=id).one_or_none() return NestedResponse(schema=UserSchema).dump(user)
def get(self) -> list: parser = paginated_parser.copy() args = parser.parse_args() # paginated_query = Tag.query.options(db.noload('models')).paginate(args["page"], args["per_page"], False) paginated_query = Tag.query.paginate(args["page"], args["per_page"], False) return NestedResponse(schema=TagSchema, exclude=("models", ), many=True, pagination=paginated_query).dump( paginated_query.items)
def delete(self, model_id: int, tag_id: int) -> dict: model = Model.query.filter_by(id=model_id).first() tag = Tag.query.filter_by(id=tag_id).first() if not (model and tag): abort(404) tag.models.remove(model) current_app.logger.info("tag " + str(tag_id) + " dropped from model " + str(model_id)) db.session.add(tag) db.session.commit() return NestedResponse(schema=ModelSchema).dump(model)
def get(self, id: int) -> dict: """Returns data about a requested tag. :param id: id of a requested tag :returns: a single object """ tag = Tag.query.filter_by(id=id).one_or_none() if not tag: abort(404) return NestedResponse(schema=TagSchema).dump(tag)
def get(self, id: int) -> dict: """Returns data about a requested model. :param id: id of a requested model :returns: a single object """ model = Model.query.filter_by(id=id).one_or_none() if not model: abort(404) return NestedResponse(schema=ModelSchema).dump(model)
def post(self) -> dict: parser = reqparse.RequestParser() parser.add_argument("name", type=str, required=True, help="No name provided") parser.add_argument("description", type=str) args = parser.parse_args() tag = Tag(name=args["name"], description=args["description"]) db.session.add(tag) db.session.commit() return NestedResponse(schema=TagSchema).dump(tag)
def get(self) -> list: """Lists all users. .. :quickref: Users; Get a collection of users. :return: a list of users """ parser = paginated_parser.copy() args = parser.parse_args() paginated_query = User.query.paginate(args["page"], args["per_page"], False) return NestedResponse(schema=UserSchema, many=True, pagination=paginated_query).dump( paginated_query.items)
def get(self, id: int) -> dict: """Returns data about a requested project. .. :quickref: Projects; Get a single project. :param id: id of a requested project :reqheader Authorization: Bearer JWT :status 200: when project exists :status 404: when requested project does not exist :returns: a single object """ project = Project.query.filter_by(id=id).first() if not project: abort(404) return NestedResponse(schema=ProjectSchema).dump(project)
def get(self) -> list: """Lists all projects. .. :quickref: Projects; Get a collection of projects. :param search: lists only projects that contain the name like `search` :return: a list of projects """ parser = paginated_parser.copy() args = parser.parse_args() paginated_query = Project.query.paginate(args["page"], args["per_page"], False) return NestedResponse(schema=ProjectSchema, many=True, pagination=paginated_query).dump( paginated_query.items)
def post(self) -> dict: parser = reqparse.RequestParser() parser.add_argument("login", type=str, required=True) parser.add_argument("password", type=str, required=True) parser.add_argument("full_name", type=str) parser.add_argument("email", type=str) args = parser.parse_args() new_user = User( login=args["login"], password=args["password"], full_name=args["full_name"], email=args["email"], ) db.session.add(new_user) db.session.commit() return NestedResponse(schema=UserSchema).dump(new_user)
def post(self) -> dict: parser = reqparse.RequestParser() parser.add_argument("name", type=str, required=True, help="No name provided") parser.add_argument("description", type=str) parser.add_argument("workspace_id", type=int, required=True) args = parser.parse_args() workspace = Workspace.query.filter_by(id=args["workspace_id"]).first() if workspace: project = Project( name=args["name"], description=args["description"], workspace_id=args["workspace_id"], ) db.session.add(project) db.session.commit() return NestedResponse(schema=ProjectSchema).dump(project) return {"error": f"Workspace {args['workspace_id']} does not exist."}, 400
def post(self) -> dict: parser = reqparse.RequestParser() parser.add_argument("name", type=str) parser.add_argument("dataset_name", type=str) parser.add_argument("dataset_description", type=str) parser.add_argument("project_id", type=int, required=True) parser.add_argument("user_id", type=int, required=True) parser.add_argument("hyperparameters", type=str, default="{}") parser.add_argument("parameters", type=str, default="{}") parser.add_argument("metrics", type=str, default="{}") parser.add_argument("git_active_branch", type=str, default=None) parser.add_argument("git_commit_hash", type=str, default=None) parser.add_argument("file", type=FileStorage, location="files", required=True) parser.add_argument("private", type=bool, default=False) args = parser.parse_args() if "file" in args: print("FILE:", args["file"]) filename = models_uploadset.save(args["file"], name=str(uuid.uuid4()) + ".") for arg_name in ["hyperparameters", "parameters", "metrics"]: args[arg_name] = json.loads(args[arg_name]) new_model = Model( user_id=args["user_id"], project_id=args["project_id"], hyperparameters=args["hyperparameters"], parameters=args["parameters"], metrics=args["metrics"], name=args["name"], path=filename, dataset_name=args["dataset_name"], dataset_description=args["dataset_description"], git_active_branch=args["git_active_branch"], git_commit_hash=args["git_commit_hash"], private=args["private"], ) db.session.add(new_model) db.session.commit() return NestedResponse(schema=ModelSchema).dump(new_model)
def post(self) -> dict: """Uploads a model. .. :quickref: Models; Upload a new model. :param name: human-readable name of the model :param dataset_name: name used to identify the dataset :param dataset_description: description used to provide more context :param project_id: id of the project the model belongs to :param hyperparameters: a dictionary of hyperparameters :param parameters: a dictionary of parameters :param metrics: a dictionary of metrics :param tags: a list of tags in form of a single string separated by commas :param git_active_branch: an active branch of the uploaded model :param git_commit_hash: hash of the most recent commit :param file: contents of the file selected to upload :param private: whether to mark the model as private :returns: a newly uploaded model """ parser = reqparse.RequestParser() parser.add_argument("name", type=str) parser.add_argument("dataset_name", type=str) parser.add_argument("dataset_description", type=str) parser.add_argument("project_id", type=int, required=True) # user_id : deprecated parser.add_argument("user_id", type=int, required=False) parser.add_argument("hyperparameters", type=str, default="{}") parser.add_argument("parameters", type=str, default="{}") parser.add_argument("metrics", type=str, default="{}") parser.add_argument("tags", type=str, default="") parser.add_argument("git_active_branch", type=str, default=None) parser.add_argument("git_commit_hash", type=str, default=None) parser.add_argument("file", type=FileStorage, location="files", required=True) parser.add_argument("private", type=bool, default=False) args = parser.parse_args() if "file" in args: print("FILE:", args["file"]) filename = models_uploadset.save(args["file"], name=str(uuid.uuid4()) + ".") for arg_name in ["hyperparameters", "parameters", "metrics"]: args[arg_name] = json.loads(args[arg_name]) user = current_user() new_model = Model( user_id=user.id, project_id=args["project_id"], hyperparameters=args["hyperparameters"], parameters=args["parameters"], metrics=args["metrics"], name=args["name"], path=filename, dataset_name=args["dataset_name"], dataset_description=args["dataset_description"], git_active_branch=args["git_active_branch"], git_commit_hash=args["git_commit_hash"], private=args["private"], ) db.session.add(new_model) db.session.commit() return NestedResponse(schema=ModelSchema).dump(new_model)
def get(self, id: int) -> dict: user = User.query.filter_by(id=id).one_or_none() return NestedResponse(schema=UserSchema).dump(user)
def get(self) -> list: """Lists all models that satisfy certain conditions. .. :quickref: Models; Get a collection of models. Every parameter can be appended multiple times. :param workspace: search for models only in this workspace :param project: search for models only in this project :param hyperparam: search for models that have this hyperparameter :param param: search for models that have this parameter :returns: a list of objects """ parser = paginated_parser.copy() parser.add_argument("workspace", type=int) parser.add_argument("projects", type=str) parser.add_argument("hyperparameters", type=str) parser.add_argument("parameters", type=str) parser.add_argument("metrics", type=str) parser.add_argument("users", type=str) args = parser.parse_args() # Initialize query builder query = Model.query if args["workspace"]: # TODO: add fetching models from multiple workspaces # query = query.filter() pass if args["projects"]: query = query.filter( Model.project_id.in_(args["projects"].split(","))) if args["users"]: query = query.filter(Model.user_id.in_(args["users"].split(","))) # if args["hyperparameters"]: # # Filtering through hyperparameters. # # Every result has to contain ALL of the requested keys # query = query.filter( # Model.hyperparameters.has_all( # postgres_array(args["hyperparameters"].split(",")) # ) # ) # if args["parameters"]: # # Filtering through parameters. # # Every result has to contain ALL of the requested keys # query = query.filter( # Model.parameters.has_all(postgres_array(args["parameters"].split(","))) # ) if args["metrics"]: # Filtering through metrics. # Every result has to contain ALL of the requested keys query = query.filter( Model.metrics.has_all( postgres_array(args["metrics"].split(",")))) paginated_query = query.paginate(args["page"], args["per_page"], False) return NestedResponse( schema=ModelSchema, exclude=("parameters", "hyperparameters", "metrics"), many=True, pagination=paginated_query, ).dump(paginated_query.items)