Skip to content

Commit

Permalink
frontend: migrate API projects namespace to flask-restx
Browse files Browse the repository at this point in the history
  • Loading branch information
nikromen committed Jul 12, 2023
1 parent 46ae367 commit a4c578e
Show file tree
Hide file tree
Showing 4 changed files with 134 additions and 9 deletions.
11 changes: 11 additions & 0 deletions frontend/coprs_frontend/coprs/views/apiv3_ns/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import json
from http import HTTPStatus

import flask
import wtforms
import sqlalchemy
Expand Down Expand Up @@ -374,3 +376,12 @@ def rename_fields_helper(input_dict, replace):
for value in values:
output.add(new_key, value)
return output


def responser(result, status: HTTPStatus = HTTPStatus.OK):
"""
Make API response with status
"""
resp = flask.jsonify(result)
resp.status_code = status.value
return resp
2 changes: 0 additions & 2 deletions frontend/coprs_frontend/coprs/views/apiv3_ns/apiv3_builds.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,6 @@
from .json2form import get_form_compatible_data




apiv3_builds_ns = Namespace("build", description="Builds")
api.add_namespace(apiv3_builds_ns)

Expand Down
33 changes: 27 additions & 6 deletions frontend/coprs_frontend/coprs/views/apiv3_ns/apiv3_projects.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,16 @@
from http import HTTPStatus

import flask

from flask_restx import Namespace, Resource

from coprs.views.apiv3_ns import (query_params, get_copr, pagination, Paginator,
GET, POST, PUT, DELETE, set_defaults)
from coprs.views.apiv3_ns.json2form import get_form_compatible_data, get_input_dict
from coprs import db, models, forms, db_session_scope
from coprs.views.misc import api_login_required
from coprs.views.apiv3_ns import apiv3_ns, rename_fields_helper
from coprs.views.apiv3_ns import apiv3_ns, rename_fields_helper, api, responser
from coprs.views.apiv3_ns.schema import fullname_params, project_model, project_parser
from coprs.logic.actions_logic import ActionsLogic
from coprs.logic.coprs_logic import CoprsLogic, CoprChrootsLogic, MockChrootsLogic
from coprs.logic.complex_logic import ComplexLogic
Expand All @@ -16,6 +22,10 @@
from . import editable_copr


apiv3_projects_ns = Namespace("project", description="Projects")
api.add_namespace(apiv3_projects_ns)


def to_dict(copr):
return {
"id": copr.id,
Expand Down Expand Up @@ -77,11 +87,22 @@ def owner2tuple(ownername):
return user, group


@apiv3_ns.route("/project", methods=GET)
@query_params()
def get_project(ownername, projectname):
copr = get_copr(ownername, projectname)
return flask.jsonify(to_dict(copr))
@apiv3_projects_ns.route("")
class Project(Resource):

Check warning

Code scanning / vcs-diff-lint

Project: Missing class docstring Warning

Project: Missing class docstring
parser = project_parser()

@apiv3_projects_ns.doc(fullname_params)
@apiv3_projects_ns.marshall_with(project_model)
@apiv3_projects_ns.expect(parser)
@apiv3_projects_ns.response(HTTPStatus.OK.value, "OK, Project data follows...")
def get(self):
"""
Get a project
Get details for a single Copr project.
"""
args = self.parser.parse_args()
copr = get_copr(args.ownername, args.projectname)
return responser(to_dict(copr))


@apiv3_ns.route("/project/list", methods=GET)
Expand Down
97 changes: 96 additions & 1 deletion frontend/coprs_frontend/coprs/views/apiv3_ns/schema.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@
example="@copr",
)

fullname_field = String(
description="Full name of the project",
example="@copr/pull-requests",
)

projectname_field = String(
description="Name of the project",
example="copr-dev",
Expand Down Expand Up @@ -281,6 +286,56 @@
example="DESC",
)

homepage_field = Url(
description="Homepage URL of Copr project",
example="https://github.com/fedora-copr",
)

contact_field = String(
description="Contact email",
example="[email protected]",
)

description_field = String(
description="Description of Copr project",
)

instructions_field = String(
description="Instructions how to install and use Copr project",
)

persistent_field = Boolean(
description="Build and project is immune against deletion",
)

unlisted_on_hp_field = Boolean(
description="Don't list Copr project on home page",
)

auto_prune_field = Boolean(
description="Automatically delete builds in this project",
)

build_enable_net_field = Boolean(
description="Enable networking for the builds",
)

appstream_field = Boolean(
description="Enable Appstream for this project",
)

packit_forge_projects_allowed_field = String(
description="Whitespace separated list of forge projects that will be "
"allowed to build in the project via Packit",
example="github.com/fedora-copr/copr github.com/another/project",
)

follow_fedora_branching_field = Boolean(
description="If chroots for the new branch should be auto-enabled and populated from "
"rawhide ones",
)


pagination_schema = {
"limit_field": limit_field,
"offset_field": offset_field,
Expand Down Expand Up @@ -404,6 +459,33 @@
package_model = api.model("Package", package_schema)


project_schema = {
"id": id_field,
"name": projectname_field,
"ownername": ownername_field,
"full_name": fullname_field,
"homepage": homepage_field,
"contact": contact_field,
"description": description_field,
"instructions": instructions_field,
"devel_mode": Boolean,
"persistent": persistent_field,
"unlisted_on_hp": unlisted_on_hp_field,
"auto_prune": auto_prune_field,
"chroot_repos": Raw,
"additional_repos": additional_repos_field,
"enable_net": build_enable_net_field,
"bootstrap": String,
"isolation": isolation_field,
"module_hotfixes": module_hotfixes_field,
"appstream": appstream_field,
"packit_forge_projects_allowed": packit_forge_projects_allowed_field,
"follow_fedora_branching": follow_fedora_branching_field,
}

project_model = api.model("Project", project_schema)


def clone(field):
"""
Return a copy of a field
Expand All @@ -412,9 +494,13 @@ def clone(field):
return field.__class__(**kwargs)


add_package_params = {
fullname_params = {
"ownername": ownername_field.description,
"projectname": projectname_field.description,
}

add_package_params = {
**fullname_params,
"package_name": packagename_field.description,
"source_type_text": source_type_field.description,
}
Expand Down Expand Up @@ -551,3 +637,12 @@ def project_chroot_parser():
arg.required = True
parser.add_argument(arg)
return parser


def project_parser():
# pylint: disable=missing-function-docstring
parser = RequestParser()
parser.add_argument(field2arg("ownername", ownername_field, required=True))
parser.add_argument(field2arg("projectname", projectname_field, required=True))

return parser

0 comments on commit a4c578e

Please sign in to comment.