Coverage for webapp/publisher/snaps/release_views.py: 91%

102 statements  

« prev     ^ index     » next       coverage.py v7.15.4, created at 2026-08-20 22:09 +0000

1# Packages 

2import flask 

3from canonicalwebteam.store_api.dashboard import Dashboard 

4from canonicalwebteam.exceptions import StoreApiResponseErrorList 

5 

6# Local 

7from cache.cache_utility import redis_cache 

8from webapp.endpoints.utils import get_auditable_map_cache_key 

9from webapp.helpers import api_publisher_session 

10from webapp.decorators import login_required 

11 

12dashboard = Dashboard(api_publisher_session) 

13 

14 

15@login_required 

16def redirect_get_release_history(snap_name): 

17 return flask.redirect( 

18 flask.url_for(".get_release_history", snap_name=snap_name) 

19 ) 

20 

21 

22@login_required 

23def get_releases(snap_name): 

24 # If this fails, the page will 404 

25 dashboard.get_snap_info(flask.session, snap_name) 

26 return flask.render_template("store/publisher.html") 

27 

28 

29@login_required 

30def get_release_status(snap_name): 

31 try: 

32 history = dashboard.snap_release_history(flask.session, snap_name, 1) 

33 except StoreApiResponseErrorList as api_response_error_list: 

34 if api_response_error_list.status_code == 404: 

35 return flask.abort(404, "No snap named {}".format(snap_name)) 

36 return flask.jsonify(api_response_error_list.errors), 400 

37 

38 revisions = [] 

39 if isinstance(history, dict): 

40 revisions = history.get("revisions") or [] 

41 elif isinstance(history, list): 

42 revisions = history 

43 

44 return flask.jsonify({"has_releases": bool(revisions)}) 

45 

46 

47@login_required 

48def redirect_post_release(snap_name): 

49 return flask.redirect( 

50 flask.url_for(".post_release", snap_name=snap_name), 307 

51 ) 

52 

53 

54@login_required 

55def get_release_history_json(snap_name): 

56 page = flask.request.args.get("page", default=1, type=int) 

57 

58 try: 

59 release_history = dashboard.snap_release_history( 

60 flask.session, snap_name, page 

61 ) 

62 except StoreApiResponseErrorList as api_response_error_list: 

63 if api_response_error_list.status_code == 404: 

64 return flask.abort(404, "No snap named {}".format(snap_name)) 

65 else: 

66 return flask.jsonify(api_response_error_list.errors), 400 

67 

68 return flask.jsonify(release_history) 

69 

70 

71@login_required 

72def post_release(snap_name): 

73 data = flask.request.json 

74 

75 if not data: 

76 response = {"errors": ["No changes were submitted"]} 

77 return flask.jsonify(response), 400 

78 

79 try: 

80 response = dashboard.post_snap_release(flask.session, data) 

81 except StoreApiResponseErrorList as api_response_error_list: 

82 if api_response_error_list.status_code == 404: 

83 return flask.abort(404, "No snap named {}".format(snap_name)) 

84 else: 

85 return ( 

86 flask.jsonify( 

87 { 

88 "errors": api_response_error_list.errors, 

89 } 

90 ), 

91 400, 

92 ) 

93 

94 redis_cache.delete(get_auditable_map_cache_key(snap_name)) 

95 

96 return flask.jsonify(response) 

97 

98 

99@login_required 

100def redirect_post_close_channel(snap_name): 

101 return flask.redirect( 

102 flask.url_for(".post_close_channel", snap_name=snap_name), 307 

103 ) 

104 

105 

106@login_required 

107def post_close_channel(snap_name): 

108 data = flask.request.json 

109 

110 if not data: 

111 return flask.jsonify({}), 400 

112 

113 try: 

114 snap_id = dashboard.get_snap_id(flask.session, snap_name) 

115 except StoreApiResponseErrorList as api_response_error_list: 

116 if api_response_error_list.status_code == 404: 

117 return flask.abort(404, "No snap named {}".format(snap_name)) 

118 else: 

119 return flask.jsonify(api_response_error_list.errors), 400 

120 

121 try: 

122 response = dashboard.post_close_channel(flask.session, snap_id, data) 

123 except StoreApiResponseErrorList as api_response_error_list: 

124 if api_response_error_list.status_code == 404: 

125 return flask.abort(404, "No snap named {}".format(snap_name)) 

126 else: 

127 response = { 

128 "errors": api_response_error_list.errors, 

129 "success": False, 

130 } 

131 return flask.jsonify(response), 400 

132 

133 response["success"] = True 

134 return flask.jsonify(response) 

135 

136 

137@login_required 

138def post_default_track(snap_name): 

139 data = flask.request.json 

140 

141 if not data: 

142 return flask.jsonify({}), 400 

143 

144 try: 

145 snap_id = dashboard.get_snap_id(flask.session, snap_name) 

146 except StoreApiResponseErrorList as api_response_error_list: 

147 if api_response_error_list.status_code == 404: 

148 return flask.abort(404, "No snap named {}".format(snap_name)) 

149 else: 

150 return flask.jsonify(api_response_error_list.errors), 400 

151 

152 try: 

153 dashboard.snap_metadata(flask.session, snap_id, data) 

154 except StoreApiResponseErrorList as api_response_error_list: 

155 if api_response_error_list.status_code == 404: 

156 return flask.abort(404, "No snap named {}".format(snap_name)) 

157 else: 

158 response = { 

159 "errors": api_response_error_list.errors, 

160 "success": False, 

161 } 

162 return flask.jsonify(response), 400 

163 

164 return flask.jsonify({"success": True}) 

165 

166 

167@login_required 

168def get_snap_revision_json(snap_name, revision): 

169 """ 

170 Return JSON object from the publisher API 

171 """ 

172 revision = dashboard.get_snap_revision(flask.session, snap_name, revision) 

173 

174 return flask.jsonify(revision)