2 * Licensed under the Apache License, Version 2.0 (the "License");
3 * you may not use this file except in compliance with the License.
4 * You may obtain a copy of the License at
6 * http://www.apache.org/licenses/LICENSE-2.0
8 * Unless required by applicable law or agreed to in writing, software
9 * distributed under the License is distributed on an "AS IS" BASIS,
10 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 * See the License for the specific language governing permissions and
12 * limitations under the License.
20 .controller('ResultsController', ResultsController);
24 .directive('fileModel', ['$parse', function ($parse) {
27 link: function(scope, element, attrs) {
28 var model = $parse(attrs.fileModel);
29 var modelSetter = model.assign;
31 element.bind('change', function(){
32 scope.$apply(function(){
33 modelSetter(scope, element[0].files[0]);
40 ResultsController.$inject = [
41 '$scope', '$http', '$filter', '$state', 'testapiApiUrl','raiseAlert'
45 * TestAPI Results Controller
46 * This controller is for the '/results' page where a user can browse
47 * a listing of community uploaded results.
49 function ResultsController($scope, $http, $filter, $state, testapiApiUrl,
53 ctrl.uploadFile=uploadFile;
56 ctrl.clearFilters = clearFilters;
57 ctrl.associateMeta = associateMeta;
58 ctrl.getVersionList = getVersionList;
59 ctrl.getUserProducts = getUserProducts;
60 ctrl.associateProductVersion = associateProductVersion;
61 ctrl.getProductVersions = getProductVersions;
62 ctrl.prepVersionEdit = prepVersionEdit;
64 /** Mappings of Interop WG components to marketing program names. */
65 ctrl.targetMappings = {
66 'platform': 'Openstack Powered Platform',
67 'compute': 'OpenStack Powered Compute',
68 'object': 'OpenStack Powered Object Storage'
71 /** Initial page to be on. */
75 * How many results should display on each page. Since pagination
76 * is server-side implemented, this value should match the
77 * 'results_per_page' configuration of the TestAPI server which
80 ctrl.itemsPerPage = 20;
83 * How many page buttons should be displayed at max before adding
88 /** The upload date lower limit to be used in filtering results. */
91 /** The upload date upper limit to be used in filtering results. */
94 /** The date format for the date picker. */
95 ctrl.format = 'yyyy-MM-dd';
97 /** Check to see if this page should display user-specific results. */
98 // ctrl.isUserResults = $state.current.name === 'userResults';
99 // need auth to browse
100 ctrl.isUserResults = $state.current.name === 'userResults';
102 // Should only be on user-results-page if authenticated.
103 if (ctrl.isUserResults && !$scope.auth.isAuthenticated) {
107 ctrl.pageHeader = ctrl.isUserResults ?
108 'Private test results' : 'Community test results';
110 ctrl.pageParagraph = ctrl.isUserResults ?
111 'Your most recently uploaded test results are listed here.' :
112 'The most recently uploaded community test results are listed ' +
115 ctrl.uploadState = '';
117 ctrl.isPublic = false;
119 if (ctrl.isUserResults) {
120 ctrl.authRequest = $scope.auth.doSignCheck()
122 // ctrl.getUserProducts();
128 function uploadFileToUrl(file, uploadUrl){
129 var fd = new FormData();
130 fd.append('file', file);
131 fd.append('public', ctrl.isPublic)
133 $http.post(uploadUrl, fd, {
134 transformRequest: angular.identity,
135 headers: {'Content-Type': undefined}
138 .success(function(data){
139 var id = data.href.substr(data.href.lastIndexOf('/')+1);
140 ctrl.uploadState = "Upload succeed. Result id is " + id;
144 .error(function(data, status){
145 ctrl.uploadState = "Upload failed. Error code is " + status;
149 function uploadFile(){
150 var file = $scope.resultFile;
151 console.log('file is ' );
154 var uploadUrl = testapiApiUrl + "/results/upload";
155 uploadFileToUrl(file, uploadUrl);
159 * This will contact the TestAPI API to get a listing of test run
163 ctrl.showError = false;
164 // Construct the API URL based on user-specified filters.
165 var content_url = testapiApiUrl + '/results' +
166 '?page=' + ctrl.currentPage;
167 var start = $filter('date')(ctrl.startDate, 'yyyy-MM-dd');
170 content_url + '&from=' + start + ' 00:00:00';
172 var end = $filter('date')(ctrl.endDate, 'yyyy-MM-dd');
174 content_url = content_url + '&to=' + end + ' 23:59:59';
176 if (ctrl.isUserResults) {
177 content_url = content_url + '&signed';
179 ctrl.resultsRequest =
180 $http.get(content_url).success(function (data) {
182 ctrl.totalItems = ctrl.data.pagination.total_pages * ctrl.itemsPerPage;
183 ctrl.currentPage = ctrl.data.pagination.current_page;
184 }).error(function (error) {
187 ctrl.showError = true;
189 'Error retrieving results listing from server: ' +
190 angular.toJson(error);
195 * This is called when the date filter calendar is opened. It
196 * does some event handling, and sets a scope variable so the UI
197 * knows which calendar was opened.
198 * @param {Object} $event - The Event object
199 * @param {String} openVar - Tells which calendar was opened
201 function open($event, openVar) {
202 $event.preventDefault();
203 $event.stopPropagation();
204 ctrl[openVar] = true;
208 * This function will clear all filters and update the results
211 function clearFilters() {
212 ctrl.startDate = null;
218 * This will send an API request in order to associate a metadata
219 * key-value pair with the given testId
220 * @param {Number} index - index of the test object in the results list
221 * @param {String} key - metadata key
222 * @param {String} value - metadata value
224 function associateMeta(index, key, value) {
225 var testId = ctrl.data.results[index].id;
227 testapiApiUrl, '/results/', testId, '/meta/', key
230 var editFlag = key + 'Edit';
232 ctrl.associateRequest = $http.post(metaUrl, value)
233 .success(function () {
234 ctrl.data.results[index][editFlag] = false;
235 }).error(function (error) {
236 raiseAlert('danger', error.title, error.detail);
240 ctrl.unassociateRequest = $http.delete(metaUrl)
241 .success(function () {
242 ctrl.data.results[index][editFlag] = false;
243 }).error(function (error) {
244 if (error.code == 404) {
245 // Key doesn't exist, so count it as a success,
246 // and don't raise an alert.
247 ctrl.data.results[index][editFlag] = false;
250 raiseAlert('danger', error.title, error.detail);
257 * Retrieve an array of available capability files from the TestAPI
258 * API server, sort this array reverse-alphabetically, and store it in
260 * Sample API return array: ["2015.03.json", "2015.04.json"]
262 function getVersionList() {
263 if (ctrl.versionList) {
266 var content_url = testapiApiUrl + '/guidelines';
267 ctrl.versionsRequest =
268 $http.get(content_url).success(function (data) {
269 ctrl.versionList = data.sort().reverse();
270 }).error(function (error) {
271 raiseAlert('danger', error.title,
272 'Unable to retrieve version list');
277 * Get products user has management rights to or all products depending
278 * on the passed in parameter value.
280 function getUserProducts() {
284 var contentUrl = testapiApiUrl + '/products';
285 ctrl.productsRequest =
286 $http.get(contentUrl).success(function (data) {
288 angular.forEach(data.products, function(prod) {
289 if (prod.can_manage) {
290 ctrl.products[prod.id] = prod;
293 }).error(function (error) {
294 ctrl.products = null;
295 ctrl.showError = true;
297 'Error retrieving Products listing from server: ' +
298 angular.toJson(error);
303 * Send a PUT request to the API server to associate a product with
306 function associateProductVersion(result) {
307 var verId = (result.selectedVersion ?
308 result.selectedVersion.id : null);
309 var testId = result.id;
310 var url = testapiApiUrl + '/results/' + testId;
311 ctrl.associateRequest = $http.put(url, {'product_version_id':
313 .success(function (data) {
314 result.product_version = result.selectedVersion;
315 if (result.selectedVersion) {
316 result.product_version.product_info =
317 result.selectedProduct;
319 result.productEdit = false;
320 }).error(function (error) {
321 raiseAlert('danger', error.title, error.detail);
326 * Get all versions for a product.
328 function getProductVersions(result) {
329 if (!result.selectedProduct) {
330 result.productVersions = [];
331 result.selectedVersion = null;
335 var url = testapiApiUrl + '/products/' +
336 result.selectedProduct.id + '/versions';
337 ctrl.getVersionsRequest = $http.get(url)
338 .success(function (data) {
339 result.productVersions = data;
341 // If the test result isn't already associated to a
342 // version, default it to the null version.
343 if (!result.product_version) {
344 angular.forEach(data, function(ver) {
346 result.selectedVersion = ver;
350 }).error(function (error) {
351 raiseAlert('danger', error.title, error.detail);
356 * Instantiate variables needed for editing product/version
359 function prepVersionEdit(result) {
360 result.productEdit = true;
361 if (result.product_version) {
362 result.selectedProduct =
363 ctrl.products[result.product_version.product_info.id];
365 result.selectedVersion = result.product_version;
366 ctrl.getProductVersions(result);