diff --git a/awx/ui/static/js/app.js b/awx/ui/static/js/app.js index 63e6607485..7450b28805 100644 --- a/awx/ui/static/js/app.js +++ b/awx/ui/static/js/app.js @@ -51,6 +51,7 @@ angular.module('ansible', [ 'JobFormDefinition', 'JobEventsListDefinition', 'JobEventFormDefinition', + 'JobModalEventDefinition', 'JobHostDefinition', 'GroupsHelper', 'HostsHelper', diff --git a/awx/ui/static/js/controllers/JobEvents.js b/awx/ui/static/js/controllers/JobEvents.js index 043dc529b4..e0fe76491d 100644 --- a/awx/ui/static/js/controllers/JobEvents.js +++ b/awx/ui/static/js/controllers/JobEvents.js @@ -12,7 +12,7 @@ function JobEventsList ($scope, $rootScope, $location, $log, $routeParams, Rest, Alert, JobEventList, GenerateList, LoadBreadCrumbs, Prompt, SearchInit, PaginateInit, ReturnToCaller, - ClearScope, ProcessErrors, GetBasePath, LookUpInit, ToggleChildren, EventView, + ClearScope, ProcessErrors, GetBasePath, LookUpInit, ToggleChildren, FormatDate) { ClearScope('htmlTemplate'); @@ -153,7 +153,7 @@ function JobEventsList ($scope, $rootScope, $location, $log, $routeParams, Rest, LoadBreadCrumbs(); scope.viewJobEvent = function(id) { - EventView({"event_id": id }); + $location.path('/jobs/' + $routeParams.id + '/job_events/' + id); } scope.refresh = function() { @@ -173,15 +173,14 @@ function JobEventsList ($scope, $rootScope, $location, $log, $routeParams, Rest, JobEventsList.$inject = [ '$scope', '$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'JobEventList', 'GenerateList', 'LoadBreadCrumbs', 'Prompt', 'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope', - 'ProcessErrors','GetBasePath', 'LookUpInit', 'ToggleChildren', 'EventView', 'FormatDate' + 'ProcessErrors','GetBasePath', 'LookUpInit', 'ToggleChildren', 'FormatDate' ]; function JobEventsEdit ($scope, $rootScope, $compile, $location, $log, $routeParams, JobEventForm, GenerateForm, - Rest, Alert, ProcessErrors, LoadBreadCrumbs, ClearScope, GetBasePath, FormatDate) + Rest, Alert, ProcessErrors, LoadBreadCrumbs, ClearScope, GetBasePath, FormatDate, EventView) { ClearScope('htmlTemplate'); //Garbage collection. Don't leave behind any listeners/watchers from the prior //scope. - // Inject dynamic view var form = JobEventForm; var generator = GenerateForm; @@ -195,35 +194,82 @@ function JobEventsEdit ($scope, $rootScope, $compile, $location, $log, $routePar Rest.setUrl(defaultUrl); Rest.get() .success( function(data, status, headers, config) { - LoadBreadCrumbs({ path: '/job_events/' + $routeParams.event_id, title: data.event }); - for (var fld in form.fields) { - if (fld == 'status') { - scope['status'] = (data.failed) ? 'error' : 'success'; - } - else if (fld == 'event_data') { - scope['event_data'] = JSON.stringify(data['event_data'], undefined, '\t'); - } - else { - if (fld == 'created') { + scope['event_display'] = data['event_display'].replace(/^\u00a0*/g,''); + LoadBreadCrumbs({ path: '/jobs/' + $routeParams.job_id + '/job_events/' + $routeParams.event_id, + title: scope['event_display'] }); + for (var fld in form.fields) { + switch(fld) { + case 'status': + if (data['failed']) { + scope['status'] = 'error'; + } + else if (data['changed']) { + scope['status'] = 'changed'; + } + else { + scope['status'] = 'success'; + } + break; + case 'created': var cDate = new Date(data['created']); scope['created'] = FormatDate(cDate); - } - else { - if (data[fld]) { - scope[fld] = data[fld]; + break; + case 'host': + if (data['summary_fields'] && data['summary_fields']['host']) { + scope['host'] = data['summary_fields']['host']['name']; + } + break; + case 'id': + case 'task': + scope[fld] = data[fld]; + break; + case 'msg': + case 'stdout': + case 'stderr': + case 'start': + case 'end': + case 'delta': + case 'rc': + if (data['event_data'] && data['event_data']['res'] && data['event_data']['res'][fld] !== undefined) { + scope[fld] = data['event_data']['res'][fld]; + if (form.fields[fld].type == 'textarea') { + var n = data['event_data']['res'][fld].match(/\n/g); + rows = (n) ? n.length : 1; + rows = (rows > 15) ? 5 : rows; + $('textarea[name="' + fld + '"]').attr('rows',rows); + } } - } - } - } - }) - .error( function(data, status, headers, config) { - ProcessErrors(scope, data, status, form, - { hdr: 'Error!', msg: 'Failed to retrieve event detail: ' + $routeParams.event_id + '. GET status: ' + status }); - }); + break; + case 'conditional': + if (data['event_data']['res']) { + scope[fld] = data['event_data']['res']['is_conditional']; + } + break; + case 'module_name': + case 'module_args': + if (data['event_data']['res'] && data['event_data']['res']['invocation']) { + scope[fld] = data['event_data']['res']['invocation'][fld]; + } + break; + } + } + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, null, + { hdr: 'Error!', msg: 'Failed to retrieve host: ' + $routeParams.event_id + '. GET status: ' + status }); + }); + + scope.navigateBack = function() { + window.history.back(); + } + + scope.rawView = function() { + EventView({"event_id": scope.id }); + } } JobEventsEdit.$inject = [ '$scope', '$rootScope', '$compile', '$location', '$log', '$routeParams', 'JobEventForm', 'GenerateForm', 'Rest', 'Alert', 'ProcessErrors', 'LoadBreadCrumbs', 'ClearScope', 'GetBasePath', - 'FormatDate' + 'FormatDate', 'EventView' ]; diff --git a/awx/ui/static/js/forms/JobEvents.js b/awx/ui/static/js/forms/JobEvents.js index a7fc5e77ee..f9695b1232 100644 --- a/awx/ui/static/js/forms/JobEvents.js +++ b/awx/ui/static/js/forms/JobEvents.js @@ -10,9 +10,8 @@ angular.module('JobEventFormDefinition', []) .value( 'JobEventForm', { - editTitle: '{{ id }} - {{ event }}', //Legend in edit mode + editTitle: '{{ id }} - {{ event_display }}', //Legend in edit mode name: 'job_events', - "class": 'horizontal-narrow', well: false, fields: { @@ -66,7 +65,7 @@ angular.module('JobEventFormDefinition', []) type: 'textarea', readonly: true, section: 'Results', - 'class': 'modal-input-xlarge', + 'class': 'span12', rows: 1 }, stdout: { @@ -74,7 +73,7 @@ angular.module('JobEventFormDefinition', []) type: 'textarea', readonly: true, section: 'Results', - 'class': 'modal-input-xlarge', + 'class': 'span12', rows: 1 }, stderr: { @@ -82,7 +81,7 @@ angular.module('JobEventFormDefinition', []) type: 'textarea', readonly: true, section: 'Results', - 'class': 'modal-input-xlarge', + 'class': 'span12', rows: 1 }, start: { @@ -117,8 +116,31 @@ angular.module('JobEventFormDefinition', []) } }, - buttons: { + navigation: { + back_top: { + label: 'Back', + position: 'top', + 'class': 'btn-small pull-right', + icon: 'icon-arrow-left', + ngClick: 'navigateBack()' + }, + back_bottom: { + label: 'Back', + position: 'bottom', + 'class': 'btn-small pull-right', + icon: 'icon-arrow-left', + ngClick: 'navigateBack()' + }, + raw_view: { + label: 'View raw JSON results', + icon: 'icon-zoom-in', + position: 'bottom', + 'class': 'btn-small', + ngClick: 'rawView()' + } + }, + buttons: { }, related: { //related colletions (and maybe items?) diff --git a/awx/ui/static/js/forms/JobModalEvent.js b/awx/ui/static/js/forms/JobModalEvent.js new file mode 100644 index 0000000000..803abeb2f6 --- /dev/null +++ b/awx/ui/static/js/forms/JobModalEvent.js @@ -0,0 +1,35 @@ +/********************************************* + * Copyright (c) 2013 AnsibleWorks, Inc. + * + * JobModalEvent.js + * Form definition for Job Events model + * + * + */ +angular.module('JobModalEventDefinition', []) + .value( + 'JobModalEventForm', { + + editTitle: '{{ id }} - {{ event_display }}', //Legend in edit mode + name: 'job_events', + well: false, + 'class': 'horizontal-narrow', + + fields: { + event_data: { + label: 'Event Data', + type: 'textarea', + readonly: true, + rows: 10, + 'class': 'modal-input-xlarge' + } + }, + + buttons: { + }, + + related: { //related colletions (and maybe items?) + } + + }); //Form + diff --git a/awx/ui/static/js/helpers/Events.js b/awx/ui/static/js/helpers/Events.js index f3120758a1..57be20f66e 100644 --- a/awx/ui/static/js/helpers/Events.js +++ b/awx/ui/static/js/helpers/Events.js @@ -6,8 +6,8 @@ * EventView - show the job_events form in a modal dialog * */ -angular.module('EventsHelper', ['RestServices', 'Utilities', 'JobEventFormDefinition']) -.factory('EventView', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'JobEventForm', 'GenerateForm', +angular.module('EventsHelper', ['RestServices', 'Utilities', 'JobModalEventDefinition']) +.factory('EventView', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'JobModalEventForm', 'GenerateForm', 'Prompt', 'ProcessErrors', 'GetBasePath', 'FormatDate', function($rootScope, $location, $log, $routeParams, Rest, Alert, JobEventForm, GenerateForm, Prompt, ProcessErrors, GetBasePath, FormatDate) { @@ -25,7 +25,6 @@ angular.module('EventsHelper', ['RestServices', 'Utilities', 'JobEventFormDefini } scope.formModalActionLabel = 'OK'; - //scope.formModalHeader = 'View Event'; scope.formModalCancelShow = false; $('#form-modal .btn-success').removeClass('btn-success').addClass('btn-none'); @@ -34,67 +33,13 @@ angular.module('EventsHelper', ['RestServices', 'Utilities', 'JobEventFormDefini Rest.setUrl(defaultUrl); Rest.get() .success( function(data, status, headers, config) { - for (var fld in form.fields) { - switch(fld) { - case 'status': - if (data['failed']) { - scope['status'] = 'error'; - } - else if (data['changed']) { - scope['status'] = 'changed'; - } - else { - scope['status'] = 'success'; - } - break; - case 'created': - var cDate = new Date(data['created']); - scope['created'] = FormatDate(cDate); - break; - case 'host': - if (data['summary_fields'] && data['summary_fields']['host']) { - scope['host'] = data['summary_fields']['host']['name']; - } - break; - case 'id': - case 'task': - scope[fld] = data[fld]; - break; - case 'msg': - case 'stdout': - case 'stderr': - case 'start': - case 'end': - case 'delta': - case 'rc': - if (data['event_data'] && data['event_data']['res'] && data['event_data']['res'][fld] !== undefined) { - scope[fld] = data['event_data']['res'][fld]; - if (form.fields[fld].type == 'textarea') { - var n = data['event_data']['res'][fld].match(/\n/g); - rows = (n) ? n.length : 1; - rows = (rows > 5) ? 5 : rows; - $('textarea[name="' + fld + '"]').attr('rows',rows); - } - } - break; - case 'conditional': - if (data['event_data']['res']) { - scope[fld] = data['event_data']['res']['is_conditional']; - } - break; - case 'module_name': - case 'module_args': - if (data['event_data']['res'] && data['event_data']['res']['invocation']) { - scope[fld] = data['event_data']['res']['invocation'][fld]; - } - break; - } - } - scope['formModalHeader'] = data.event_display.replace(/^\u00a0*/g,''); + scope.formModalHeader = data['event_display']; + scope.event_data = JSON.stringify(data['event_data'], null, '\t'); }) .error( function(data, status, headers, config) { + $('#form-modal').modal("hide"); ProcessErrors(scope, data, status, form, - { hdr: 'Error!', msg: 'Failed to retrieve host: ' + event_id + '. GET status: ' + status }); + { hdr: 'Error!', msg: 'Failed to retrieve event: ' + event_id + '. GET status: ' + status }); }); if (!scope.$$phase) { diff --git a/awx/ui/static/lib/ansible/form-generator.js b/awx/ui/static/lib/ansible/form-generator.js index c15b3cc8b6..174efa49ee 100644 --- a/awx/ui/static/lib/ansible/form-generator.js +++ b/awx/ui/static/lib/ansible/form-generator.js @@ -181,6 +181,21 @@ angular.module('FormGenerator', ['GeneratorHelpers', 'ngCookies']) return html; }, + button: function(btn) { + // pass in a button object and get back an html string containing + // a