1111from ibutsu_server .util .uuid import validate_uuid
1212
1313
14- def add_dashboard (dashboard = None , token_info = None , user = None ):
14+ def add_dashboard (dashboard = None , token_info = None , user = None ) -> tuple [ dict , int ] :
1515 """Create a dashboard
1616
1717 :param body: Dashboard
@@ -22,17 +22,30 @@ def add_dashboard(dashboard=None, token_info=None, user=None):
2222 if not connexion .request .is_json :
2323 return RESPONSE_JSON_REQ
2424 dashboard = Dashboard .from_dict (** connexion .request .get_json ())
25+
26+ if dashboard .portal_id and dashboard .project_id :
27+ return "Dashboard can only have one of project_id or portal_id" , HTTPStatus .BAD_REQUEST
28+
29+ if not (dashboard .portal_id or dashboard .project_id ):
30+ return "Dashboard needs either project_id or portal_id" , HTTPStatus .BAD_REQUEST
31+
2532 if dashboard .project_id and not project_has_user (dashboard .project_id , user ):
2633 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
34+
35+ # TODO utility function to resolve all users with at least one project set
36+ # compare to projects assigned to the portal? or portals are open to all projects
37+ # otherwise, limit to admin users or new portal_admin permission
38+
2739 if dashboard .user_id and not User .query .get (dashboard .user_id ):
2840 return f"User with ID { dashboard .user_id } doesn't exist" , HTTPStatus .BAD_REQUEST
41+
2942 session .add (dashboard )
3043 session .commit ()
3144 return dashboard .to_dict (), HTTPStatus .CREATED
3245
3346
3447@validate_uuid
35- def get_dashboard (id_ , token_info = None , user = None ):
48+ def get_dashboard (id_ , token_info = None , user = None ) -> dict :
3649 """Get a single dashboard by ID
3750
3851 :param id: ID of test dashboard
@@ -45,16 +58,19 @@ def get_dashboard(id_, token_info=None, user=None):
4558 return "Dashboard not found" , HTTPStatus .NOT_FOUND
4659 if dashboard and dashboard .project and not project_has_user (dashboard .project , user ):
4760 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
61+ # TODO test against dashboard with only portal set
4862 return dashboard .to_dict ()
4963
5064
5165def get_dashboard_list (
52- filter_ = None , project_id = None , page = 1 , page_size = 25 , token_info = None , user = None
53- ):
66+ filter_ = None , project_id = None , portal_id = None , page = 1 , page_size = 25 , token_info = None , user = None
67+ ) -> dict [ list [ dict ], dict ] :
5468 """Get a list of dashboards
5569
5670 :param project_id: Filter dashboards by project ID
5771 :type project_id: str
72+ :param portal_id: Filter dashboards by portal ID
73+ :type portal_id: str
5874 :param user_id: Filter dashboards by user ID
5975 :type user_id: str
6076 :param limit: Limit the dashboards
@@ -66,13 +82,24 @@ def get_dashboard_list(
6682 """
6783 query = Dashboard .query
6884 project = None
85+ if portal_id is not None and project_id is not None :
86+ return "Dashboard list can only have one of project_id or portal_id" , HTTPStatus .BAD_REQUEST
87+
88+ # Project filter injection
6989 if "project_id" in connexion .request .args :
7090 project = Project .query .get (connexion .request .args ["project_id" ])
7191 if project :
7292 if not project_has_user (project , user ):
7393 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
7494 query = query .filter (Dashboard .project_id == project_id )
7595
96+ # Portal filter injection
97+ if "portal_id" in connexion .request .args :
98+ portal = Project .query .get (connexion .request .args ["portal_id" ])
99+ if portal :
100+ query = query .filter (Dashboard .portal_id == portal_id )
101+
102+ # Other filters follow
76103 if filter_ :
77104 for filter_string in filter_ :
78105 filter_clause = convert_filter (filter_string , Dashboard )
@@ -96,10 +123,10 @@ def get_dashboard_list(
96123
97124
98125@validate_uuid
99- def update_dashboard (id_ , dashboard = None , token_info = None , user = None ):
126+ def update_dashboard (id_ , dashboard = None , token_info = None , user = None ) -> dict :
100127 """Update a dashboard
101128
102- :param id: ID of test dashboard
129+ :param id: ID of dashboard
103130 :type id: str
104131 :param body: Dashboard
105132 :type body: dict | bytes
@@ -113,19 +140,25 @@ def update_dashboard(id_, dashboard=None, token_info=None, user=None):
113140 dashboard_dict ["metadata" ]["project" ], user
114141 ):
115142 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
143+
144+ # TODO user/admin check for portal ref
145+
116146 dashboard = Dashboard .query .get (id_ )
117147 if not dashboard :
118148 return "Dashboard not found" , HTTPStatus .NOT_FOUND
119- if project_has_user (dashboard .project , user ):
149+ if dashboard . project_id is not None and project_has_user (dashboard .project , user ):
120150 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
151+
152+ # TODO user/admin check for portal ref
153+
121154 dashboard .update (connexion .request .get_json ())
122155 session .add (dashboard )
123156 session .commit ()
124157 return dashboard .to_dict ()
125158
126159
127160@validate_uuid
128- def delete_dashboard (id_ , token_info = None , user = None ):
161+ def delete_dashboard (id_ , token_info = None , user = None ) -> tuple [ str , int ] :
129162 """Deletes a dashboard
130163
131164 :param id: ID of the dashboard to delete
@@ -136,8 +169,9 @@ def delete_dashboard(id_, token_info=None, user=None):
136169 dashboard = Dashboard .query .get (id_ )
137170 if not dashboard :
138171 return HTTPStatus .NOT_FOUND .phrase , HTTPStatus .NOT_FOUND
139- if not project_has_user (dashboard .project , user ):
172+ if dashboard . project_id is not None and not project_has_user (dashboard .project , user ):
140173 return HTTPStatus .FORBIDDEN .phrase , HTTPStatus .FORBIDDEN
174+ # TODO user/admin check for portal ref
141175 widget_configs = WidgetConfig .query .filter (WidgetConfig .dashboard_id == dashboard .id ).all ()
142176 for widget_config in widget_configs :
143177 session .delete (widget_config )
0 commit comments