1
2
3 import flask
4 from flask import url_for, make_response
5 from flask_restful import Resource
6
7 from ... import db
8 from ...exceptions import (
9 ActionInProgressException,
10 ConflictingRequest,
11 InsufficientRightsException,
12 )
13 from ...logic.builds_logic import BuildsLogic
14 from ..common import get_project_safe
15 from ..exceptions import MalformedRequest, CannotProcessRequest, AccessForbidden
16 from ..common import render_build, rest_api_auth_required, render_build_task, get_build_safe, get_user_safe
17 from ..schemas import BuildSchema, BuildCreateSchema, BuildCreateFromUrlSchema
18 from ..util import mm_deserialize, get_request_parser, arg_bool
22
23 @classmethod
25
26 parser = get_request_parser()
27
28 parser.add_argument('owner', type=str,)
29 parser.add_argument('project_id', type=int)
30 parser.add_argument('group', type=str)
31
32 parser.add_argument('limit', type=int)
33 parser.add_argument('offset', type=int)
34
35 parser.add_argument('is_finished', type=arg_bool)
36
37
38 req_args = parser.parse_args()
39
40 if req_args["project_id"] is not None:
41 project = get_project_safe(req_args["project_id"])
42 query = BuildsLogic.get_multiple_by_copr(project)
43 elif req_args["owner"] is not None:
44 user = get_user_safe(req_args["owner"])
45 query = BuildsLogic.get_multiple_by_user(user)
46 else:
47 query = BuildsLogic.get_multiple()
48
49 if req_args["group"]:
50 query = BuildsLogic.filter_by_group_name(query, req_args["group"])
51
52 if req_args["is_finished"] is not None:
53 is_finished = req_args["is_finished"]
54 query = BuildsLogic.filter_is_finished(query, is_finished)
55
56 if req_args["limit"] is not None:
57 limit = req_args["limit"]
58 if limit <= 0 or limit > 100:
59 limit = 100
60 else:
61 limit = 100
62
63 query = query.limit(limit)
64
65 if req_args["offset"] is not None:
66 query = query.offset(req_args["offset"])
67
68 builds = query.all()
69
70 self_params = dict(req_args)
71 self_params["limit"] = limit
72 return {
73 "builds": [
74 render_build(build) for build in builds
75 ],
76 "_links": {
77 "self": {"href": url_for(".buildlistr", **self_params)},
78 },
79 }
80
81 @staticmethod
83 """
84 :return: if of the created build or raise Exception
85 """
86 build_params = mm_deserialize(BuildCreateFromUrlSchema(), req.data.decode("utf-8"))
87 project = get_project_safe(build_params["project_id"])
88
89 chroot_names = build_params.pop("chroots")
90 srpm_url = build_params.pop("srpm_url")
91 try:
92 build = BuildsLogic.create_new_from_url(
93 flask.g.user, project,
94 url=srpm_url,
95 chroot_names=chroot_names,
96 **build_params
97 )
98 db.session.commit()
99 except ActionInProgressException as err:
100 db.session.rollback()
101 raise CannotProcessRequest("Cannot create new build due to: {}"
102 .format(err))
103 except InsufficientRightsException as err:
104 db.session.rollback()
105 raise AccessForbidden("User {} cannot create build in project {}: {}"
106 .format(flask.g.user.username,
107 project.full_name, err))
108 return build.id
109
110 @staticmethod
112 """
113 :return: if of the created build or raise Exception
114 """
115 try:
116 metadata = req.form["metadata"]
117 except KeyError:
118 raise MalformedRequest("Missing build metadata in the request")
119
120 if "srpm" not in req.files:
121 raise MalformedRequest("Missing srpm file in the request")
122 srpm_handle = req.files["srpm"]
123
124 build_params = mm_deserialize(BuildCreateSchema(), metadata)
125 project_id = build_params["project_id"]
126
127 project = get_project_safe(project_id)
128
129 chroot_names = build_params.pop("chroots")
130 try:
131 build = BuildsLogic.create_new_from_upload(
132 flask.g.user, project,
133 f_uploader=lambda path: srpm_handle.save(path),
134 orig_filename=srpm_handle.filename,
135 chroot_names=chroot_names,
136 **build_params
137 )
138 db.session.commit()
139 except ActionInProgressException as err:
140 db.session.rollback()
141 raise CannotProcessRequest("Cannot create new build due to: {}"
142 .format(err))
143 except InsufficientRightsException as err:
144 db.session.rollback()
145 raise AccessForbidden("User {} cannon create build in project {}: {}"
146 .format(flask.g.user.username,
147 project.full_name, err))
148
149 return build.id
150
151 @rest_api_auth_required
153
154 req = flask.request
155 if req.content_type is None:
156 raise MalformedRequest("Got request without content type header")
157
158 if "application/json" in req.content_type:
159 build_id = self.handle_post_json(req)
160 elif "multipart/form-data" in req.content_type:
161 build_id = self.handle_post_multipart(req)
162 else:
163 raise MalformedRequest("Got unexpected content type: {}"
164 .format(req.content_type))
165 resp = make_response("", 201)
166 resp.headers["Location"] = url_for(".buildr", build_id=build_id)
167
168 return resp
169
172
173 @classmethod
174 - def get(cls, build_id):
193
194 @classmethod
195 @rest_api_auth_required
209
210 @classmethod
211 @rest_api_auth_required
212 - def put(self, build_id):
229