From 2accb949720e684d0bea5a3b246555ee7ad4bb4f Mon Sep 17 00:00:00 2001 From: chouseknecht Date: Tue, 4 Jun 2013 19:12:28 -0400 Subject: [PATCH] Hosts side of inventory detail page now working through modal dialogs. Fixed pagination on modal list. Test Add/Edit/Delete host buttons. Only piece left is to fix the host name link, which should bring up the Edit dialog. --- ansibleworks/ui/static/js/app.js | 39 +- .../ui/static/js/controllers/Inventories.js | 33 +- ansibleworks/ui/static/js/forms/Hosts.js | 3 +- .../ui/static/js/forms/Inventories.js | 17 +- ansibleworks/ui/static/js/helpers/Groups.js | 17 +- ansibleworks/ui/static/js/helpers/Hosts.js | 428 ++++++++++++++++++ .../ui/static/js/helpers/related-search.js | 20 +- ansibleworks/ui/static/js/lists/Hosts.js | 3 +- .../ui/static/lib/ansible/list-generator.js | 2 +- ansibleworks/ui/templates/ui/index.html | 3 +- 10 files changed, 475 insertions(+), 90 deletions(-) create mode 100644 ansibleworks/ui/static/js/helpers/Hosts.js diff --git a/ansibleworks/ui/static/js/app.js b/ansibleworks/ui/static/js/app.js index 14bffc832b..c81efc66ae 100644 --- a/ansibleworks/ui/static/js/app.js +++ b/ansibleworks/ui/static/js/app.js @@ -50,7 +50,8 @@ angular.module('ansible', [ 'JobEventsListDefinition', 'JobEventFormDefinition', 'JobHostDefinition', - 'GroupsHelper' + 'GroupsHelper', + 'HostsHelper' ]) .config(['$routeProvider', function($routeProvider) { $routeProvider. @@ -96,42 +97,6 @@ angular.module('ansible', [ when('/inventories/:id', { templateUrl: urlPrefix + 'partials/inventories.html', controller: InventoriesEdit }). - when('/inventories/:inventory_id/hosts', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsList }). - - when('/inventories/:inventory_id/hosts/add', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsAdd }). - - when('/inventories/:inventory_id/hosts/:host_id', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsEdit }). - - when('/inventories/:inventory_id/groups', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsList }). - - when('/inventories/:inventory_id/groups/add', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsAdd }). - - when('/inventories/:inventory_id/groups/:group_id', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsEdit }). - - when('/inventories/:inventory_id/groups/:group_id/children', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsList }). - - when('/inventories/:inventory_id/groups/:group_id/children/add', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsAdd }). - - when('/inventories/:inventory_id/groups/:group_id/children/:child_id', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: GroupsEdit }). - - when('/inventories/:inventory_id/groups/:group_id/hosts', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsList }). - - when('/inventories/:inventory_id/groups/:group_id/hosts/add', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsAdd }). - - when('/inventories/:inventory_id/groups/:group_id/hosts/:host_id', - { templateUrl: urlPrefix + 'partials/inventories.html', controller: HostsEdit }). - when('/organizations', { templateUrl: urlPrefix + 'partials/organizations.html', controller: OrganizationsList }). diff --git a/ansibleworks/ui/static/js/controllers/Inventories.js b/ansibleworks/ui/static/js/controllers/Inventories.js index b311336e43..d81822a020 100644 --- a/ansibleworks/ui/static/js/controllers/Inventories.js +++ b/ansibleworks/ui/static/js/controllers/Inventories.js @@ -206,7 +206,7 @@ function InventoriesEdit ($scope, $rootScope, $compile, $location, $log, $routeP GenerateForm, Rest, Alert, ProcessErrors, LoadBreadCrumbs, RelatedSearchInit, RelatedPaginateInit, ReturnToCaller, ClearScope, LookUpInit, Prompt, OrganizationList, TreeInit, GetBasePath, GroupsList, GroupsEdit, LoadInventory, - GroupsDelete) + GroupsDelete, HostsList, HostsAdd, HostsEdit, HostsDelete) { ClearScope('htmlTemplate'); //Garbage collection. Don't leave behind any listeners/watchers from the prior //scope. @@ -302,13 +302,7 @@ function InventoriesEdit ($scope, $rootScope, $compile, $location, $log, $routeP }); }; - - function changePath(path) { - // For reasons unknown, calling $location.path() from inside - // treeController fails to work. This is the work-around. - window.location = '/#' + path; - }; - + scope.treeController = function($node) { var nodeType = $($node).attr('type'); if (nodeType == 'inventory') { @@ -325,14 +319,6 @@ function InventoriesEdit ($scope, $rootScope, $compile, $location, $log, $routeP label: 'Add Subgroup', action: function(obj) { GroupsList({ "inventory_id": id, group_id: $(obj).attr('group_id') }); } }, - /*addHost: { - label: 'Add Host', - action: function(obj) { - LoadBreadCrumbs({ path: '/groups/' + $(obj).attr('group_id'), title: $(obj).attr('name') }); - changePath($location.path() + '/groups/' + $(obj).attr('group_id') + '/hosts'); - }, - "_disabled": (nodeType == 'all-hosts-group') ? true : false - },*/ edit: { label: 'Edit Group', action: function(obj) { GroupsEdit({ "inventory_id": id, group_id: $(obj).attr('group_id') }); }, @@ -396,12 +382,25 @@ function InventoriesEdit ($scope, $rootScope, $compile, $location, $log, $routeP scope.deleteGroup = function() { GroupsDelete({ scope: scope, "inventory_id": id, group_id: scope.group_id }); } + + scope.addHost = function() { + HostsList({ scope: scope, "inventory_id": id, group_id: scope.group_id }); + } + + scope.editHost = function(host_id, host_name) { + HostsEdit({ scope: scope, "inventory_id": id, group_id: scope.group_id, host_id: host_id, host_name: host_name }); + } + + scope.deleteHost = function(host_id, host_name) { + HostsDelete({ scope: scope, "inventory_id": id, group_id: scope.group_id, host_id: host_id, host_name: host_name }); + } + } InventoriesEdit.$inject = [ '$scope', '$rootScope', '$compile', '$location', '$log', '$routeParams', 'InventoryForm', 'GenerateForm', 'Rest', 'Alert', 'ProcessErrors', 'LoadBreadCrumbs', 'RelatedSearchInit', 'RelatedPaginateInit', 'ReturnToCaller', 'ClearScope', 'LookUpInit', 'Prompt', 'OrganizationList', 'TreeInit', 'GetBasePath', 'GroupsList', 'GroupsEdit', 'LoadInventory', - 'GroupsDelete' + 'GroupsDelete', 'HostsList', 'HostsAdd', 'HostsEdit', 'HostsDelete' ]; \ No newline at end of file diff --git a/ansibleworks/ui/static/js/forms/Hosts.js b/ansibleworks/ui/static/js/forms/Hosts.js index 0afb0651ce..e08ed14ed0 100644 --- a/ansibleworks/ui/static/js/forms/Hosts.js +++ b/ansibleworks/ui/static/js/forms/Hosts.js @@ -13,7 +13,7 @@ angular.module('HostFormDefinition', []) addTitle: 'Create Host', //Legend in add mode editTitle: '{{ name }}', //Legend in edit mode name: 'host', //Form name attribute - well: true, //Wrap the form with TB well + well: false, //Wrap the form with TB well fields: { name: { @@ -39,7 +39,6 @@ angular.module('HostFormDefinition', []) addRequired: false, editRequird: false, rows: 10, - class: 'span12', default: "\{\}", awPopOver: "

Enter variables as JSON. Both the key and value must be wrapped in double quotes. " + "Separate variables with commas, and wrap the entire string with { }. " + diff --git a/ansibleworks/ui/static/js/forms/Inventories.js b/ansibleworks/ui/static/js/forms/Inventories.js index c6abdbd704..536e09dd47 100644 --- a/ansibleworks/ui/static/js/forms/Inventories.js +++ b/ansibleworks/ui/static/js/forms/Inventories.js @@ -76,17 +76,10 @@ angular.module('InventoryFormDefinition', []) iterator: 'host', actions: { add: { - ngClick: "add('hosts')", + ngClick: "addHost()", icon: 'icon-plus', - label: 'Create Host', - awToolTip: 'Create a new host', - ngHide: 'createButtonShow == false' - }, - select: { - ngClick: "select('hosts')", - icon: 'icon-th-large', - label: 'Select Existing Host', - awToolTip: 'Select an existing host', + label: 'Add Host', + awToolTip: 'Add a host', ngHide: 'createButtonShow == false' } }, @@ -104,14 +97,14 @@ angular.module('InventoryFormDefinition', []) fieldActions: { edit: { - ngClick: "edit('hosts', \{\{ host.id \}\}, '\{\{ host.name \}\}')", + ngClick: "editHost(\{\{ host.id \}\}, '\{\{ host.name \}\}')", icon: 'icon-edit', label: 'Edit', class: 'btn-success', awToolTip: 'Edit host' }, delete: { - ngClick: "delete('hosts', \{\{ host.id \}\}, '\{\{ host.name \}\}', 'hosts')", + ngClick: "deleteHost(\{\{ host.id \}\}, '\{\{ host.name \}\}')", icon: 'icon-remove', label: 'Delete', class: 'btn-danger', diff --git a/ansibleworks/ui/static/js/helpers/Groups.js b/ansibleworks/ui/static/js/helpers/Groups.js index b1194fffec..8d30f35146 100644 --- a/ansibleworks/ui/static/js/helpers/Groups.js +++ b/ansibleworks/ui/static/js/helpers/Groups.js @@ -1,10 +1,9 @@ /********************************************* * Copyright (c) 2013 AnsibleWorks, Inc. * - * InventoryHelper - * Routines for building the tree. Everything related to the tree is here except - * for the menu piece. The routine for building the menu is in InventoriesEdit controller - * (controllers/Inventories.js) + * GroupsHelper + * + * Routines that handle group add/edit/delete on the Inventory tree widget. * */ @@ -33,8 +32,8 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', 'ListGenerator', ' selectButton: false }); - scope.formModalActionLabel = 'Finished' - scope.formModalHeader = 'Add Group' + scope.formModalActionLabel = 'Finished'; + scope.formModalHeader = 'Add Group'; $('#form-modal').modal(); @@ -62,7 +61,7 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', 'ListGenerator', ' }); SearchInit({ scope: scope, set: 'groups', list: list, url: defaultUrl }); - PaginateInit({ scope: scope, list: list, url: defaultUrl }); + PaginateInit({ scope: scope, list: list, url: defaultUrl, mode: 'lookup' }); scope.search(list.iterator); if (!scope.$$phase) { @@ -276,7 +275,7 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', 'ListGenerator', ' .error( function(data, status, headers, config) { scope.variables = null; ProcessErrors(scope, data, status, form, - { hdr: 'Error!', msg: 'Failed to retrieve host variables. GET returned status: ' + status }); + { hdr: 'Error!', msg: 'Failed to retrieve group variables. GET returned status: ' + status }); }); } else { @@ -370,7 +369,7 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', 'ListGenerator', ' function($rootScope, $location, $log, $routeParams, Rest, Alert, GroupForm, GenerateForm, Prompt, ProcessErrors, GetBasePath) { return function(params) { - // Delete the selected group node. Disassociates it from + // Delete the selected group node. Disassociates it from its parent. var scope = params.scope; var group_id = params.group_id; var inventory_id = params.inventory_id; diff --git a/ansibleworks/ui/static/js/helpers/Hosts.js b/ansibleworks/ui/static/js/helpers/Hosts.js new file mode 100644 index 0000000000..364148dd8f --- /dev/null +++ b/ansibleworks/ui/static/js/helpers/Hosts.js @@ -0,0 +1,428 @@ +/********************************************* + * Copyright (c) 2013 AnsibleWorks, Inc. + * + * HostsHelper + * + * Routines that handle host add/edit/delete on the Inventory detail page. + * + */ + +angular.module('HostsHelper', [ 'RestServices', 'Utilities', 'ListGenerator', 'HostListDefinition', + 'SearchHelper', 'PaginateHelper', 'ListGenerator', 'AuthService', 'HostsHelper', + 'InventoryHelper', 'RelatedSearchHelper','RelatedPaginateHelper', + 'InventoryFormDefinition' + ]) + + .factory('HostsList', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'HostList', 'GenerateList', + 'Prompt', 'SearchInit', 'PaginateInit', 'ProcessErrors', 'GetBasePath', 'HostsAdd', 'HostsReload', + function($rootScope, $location, $log, $routeParams, Rest, Alert, HostList, GenerateList, LoadBreadCrumbs, SearchInit, + PaginateInit, ProcessErrors, GetBasePath, HostsAdd, HostsReload) { + return function(params) { + + var inventory_id = params.inventory_id; + var group_id = params.group_id; + + var list = HostList; + var defaultUrl = GetBasePath('inventory') + inventory_id + '/hosts/'; + var view = GenerateList; + + var scope = view.inject(HostList, { + id: 'form-modal-body', + mode: 'select', + breadCrumbs: false, + selectButton: false + }); + + scope.formModalActionLabel = 'Finished'; + scope.formModalHeader = 'Add Host'; + + $('#form-modal').modal(); + $('#form-modal').unbind('hidden'); + $('#form-modal').on('hidden', function () { HostsReload(params); }); + + scope.selected = []; + + if (scope.PostRefreshRemove) { + scope.PostRefreshRemove(); + } + scope.PostRefreshRemove = scope.$on('PostRefresh', function() { + $("tr.success").each(function(index) { + // Make sure no rows have a green background + var ngc = $(this).attr('ng-class'); + scope[ngc] = ""; + }); + if ($routeParams.group_id) { + // Remove the current group from the list of available groups, thus + // preventing a group from being added to itself + for (var i=0; i < scope.groups.length; i++) { + if (scope.groups[i].id == $routeParams.group_id) { + scope.groups.splice(i,1); + } + } + } + //scope.$digest(); + }); + + SearchInit({ scope: scope, set: 'hosts', list: list, url: defaultUrl }); + PaginateInit({ scope: scope, list: list, url: defaultUrl, mode: 'lookup' }); + scope.search(list.iterator); + + if (!scope.$$phase) { + scope.$digest(); + } + + scope.formModalAction = function() { + var url = GetBasePath('groups') + group_id + '/hosts/'; + Rest.setUrl(url); + scope.queue = []; + + if (scope.callFinishedRemove) { + scope.callFinishedRemove(); + } + scope.callFinishedRemove = scope.$on('callFinished', function() { + // We call the API for each selected item. We need to hang out until all the api + // calls are finished. + if (scope.queue.length == scope.selected.length) { + // All the api calls finished + $('input[type="checkbox"]').prop("checked",false); + scope.selected = []; + var errors = 0; + for (var i=0; i < scope.queue.length; i++) { + if (scope.queue[i].result == 'error') { + errors++; + } + } + if (errors > 0) { + Alert('Error', 'There was an error while adding one or more of the selected hosts.'); + } + else { + $('#form-modal').modal('hide'); + HostsReload(params); + } + } + }); + + if (scope.selected.length > 0 ) { + var group; + for (var i=0; i < scope.selected.length; i++) { + group = null; + for (var j=0; j < scope.groups.length; j++) { + if (scope.groups[j].id == scope.selected[i]) { + group = scope.groups[j]; + } + } + if (group !== null) { + Rest.post(group) + .success( function(data, status, headers, config) { + scope.queue.push({ result: 'success', data: data, status: status }); + scope.$emit('callFinished'); + }) + .error( function(data, status, headers, config) { + scope.queue.push({ result: 'error', data: data, status: status, headers: headers }); + scope.$emit('callFinished'); + }); + } + } + } + else { + $('#form-modal').modal('hide'); + } + } + + scope.toggle_host = function(id) { + if (scope[list.iterator + "_" + id + "_class"] == "success") { + scope[list.iterator + "_" + id + "_class"] = ""; + document.getElementById('check_' + id).checked = false; + if (scope.selected.indexOf(id) > -1) { + scope.selected.splice(scope.selected.indexOf(id),1); + } + } + else { + scope[list.iterator + "_" + id + "_class"] = "success"; + document.getElementById('check_' + id).checked = true; + if (scope.selected.indexOf(id) == -1) { + scope.selected.push(id); + } + } + } + + scope.createHost = function() { + $('#form-modal').modal('hide'); + HostsAdd({ scope: params.scope, inventory_id: inventory_id, group_id: group_id }); + } + + } + }]) + + + .factory('HostsAdd', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'HostForm', 'GenerateForm', + 'Prompt', 'ProcessErrors', 'GetBasePath', 'HostsReload', + function($rootScope, $location, $log, $routeParams, Rest, Alert, HostForm, GenerateForm, Prompt, ProcessErrors, + GetBasePath, HostsReload) { + return function(params) { + + var inventory_id = params.inventory_id; + var group_id = (params.group_id !== undefined) ? params.group_id : null; + + // Inject dynamic view + var defaultUrl = GetBasePath('groups') + group_id + '/hosts/'; + var form = HostForm; + var generator = GenerateForm; + var scope = generator.inject(form, {mode: 'add', modal: true, related: false}); + + scope.formModalActionLabel = 'Save' + scope.formModalHeader = 'Create Host' + + $('#form-modal').unbind('hidden'); + $('#form-modal').on('hidden', function () { HostsReload(params); }); + + generator.reset(); + var master={}; + + if (!scope.$$phase) { + scope.$digest(); + } + + // Save + scope.formModalAction = function() { + try { + // Make sure we have valid JSON + var myjson = JSON.parse(scope.variables); + + var data = {} + for (var fld in form.fields) { + if (fld != 'variables') { + data[fld] = scope[fld]; + } + } + data['inventory'] = inventory_id; + + Rest.setUrl(defaultUrl); + Rest.post(data) + .success( function(data, status, headers, config) { + if (scope.variables) { + Rest.setUrl(data.related.variable_data); + Rest.put({data: scope.variables}) + .success( function(data, status, headers, config) { + $('#form-modal').modal('hide'); + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to add host varaibles. PUT returned status: ' + status }); + }); + } + else { + $('#form-modal').modal('hide'); + } + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to add new group. Post returned status: ' + status }); + }); + } + catch(err) { + Alert("Error", "Error parsing host variables. Expecting valid JSON. Parser returned " + err); + } + } + + // Cancel + scope.formReset = function() { + // Defaults + generator.reset(); + }; + + } + }]) + + + .factory('HostsEdit', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'HostForm', 'GenerateForm', + 'Prompt', 'ProcessErrors', 'GetBasePath', 'HostsReload', + function($rootScope, $location, $log, $routeParams, Rest, Alert, HostForm, GenerateForm, Prompt, ProcessErrors, + GetBasePath, HostsReload) { + return function(params) { + + var host_id = params.host_id; + var inventory_id = params.inventory_id; + var group_id = params.group_id; + + var generator = GenerateForm; + var form = HostForm; + var defaultUrl = GetBasePath('hosts') + host_id + '/'; + var scope = generator.inject(form, { mode: 'edit', modal: true, related: false}); + generator.reset(); + var master = {}; + var relatedSets = {}; + + scope.formModalActionLabel = 'Save' + scope.formModalHeader = 'Edit Host' + + $('#form-modal').unbind('hidden'); + $('#form-modal').on('hidden', function () { HostsReload(params); }); + + // After the group record is loaded, retrieve any group variables + if (scope.hostLoadedRemove) { + scope.hostLoadedRemove(); + } + scope.hostLoadedRemove = scope.$on('hostLoaded', function() { + if (scope.variable_url) { + Rest.setUrl(scope.variable_url); + Rest.get() + .success( function(data, status, headers, config) { + if ($.isEmptyObject(data.data)) { + scope.variables = "\{\}"; + } + else { + scope.variables = data.data; + } + }) + .error( function(data, status, headers, config) { + scope.variables = null; + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to retrieve host variables. GET returned status: ' + status }); + }); + } + else { + scope.variables = "\{\}"; + } + }); + + // Retrieve detail record and prepopulate the form + Rest.setUrl(defaultUrl); + Rest.get() + .success( function(data, status, headers, config) { + for (var fld in form.fields) { + if (data[fld]) { + scope[fld] = data[fld]; + master[fld] = scope[fld]; + } + } + var related = data.related; + for (var set in form.related) { + if (related[set]) { + relatedSets[set] = { url: related[set], iterator: form.related[set].iterator }; + } + } + scope.variable_url = data.related.variable_data; + scope.$emit('hostLoaded'); + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to retrieve host: ' + id + '. GET status: ' + status }); + }); + + if (!scope.$$phase) { + scope.$digest(); + } + + // Save changes to the parent + scope.formModalAction = function() { + try { + // Make sure we have valid JSON + var myjson = JSON.parse(scope.variables); + + var data = {} + for (var fld in form.fields) { + data[fld] = scope[fld]; + } + data['inventory'] = inventory_id; + Rest.setUrl(defaultUrl); + Rest.put(data) + .success( function(data, status, headers, config) { + if (scope.variables) { + //update host variables + Rest.setUrl(GetBasePath('hosts') + data.id + '/variable_data/'); + Rest.put({data: scope.variables}) + .success( function(data, status, headers, config) { + $('#form-modal').modal('hide'); + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to update host varaibles. PUT returned status: ' + status }); + }); + } + else { + $('#form-modal').modal('hide'); + } + }) + .error( function(data, status, headers, config) { + ProcessErrors(scope, data, status, form, + { hdr: 'Error!', msg: 'Failed to update host: ' + host_id + '. PUT status: ' + status }); + }); + } + catch(err) { + Alert("Error", "Error parsing group variables. Expecting valid JSON. Parser returned " + err); + } + }; + + // Cancel + scope.formReset = function() { + generator.reset(); + for (var fld in master) { + scope[fld] = master[fld]; + } + } + } + }]) + + + .factory('HostsDelete', ['$rootScope', '$location', '$log', '$routeParams', 'Rest', 'Alert', 'Prompt', 'ProcessErrors', 'GetBasePath', + 'HostsReload', + function($rootScope, $location, $log, $routeParams, Rest, Alert, Prompt, ProcessErrors, GetBasePath, HostsReload) { + return function(params) { + + // Delete the selected host. Disassociates it from the group. + + var scope = params.scope; + var group_id = params.group_id; + var inventory_id = params.inventory_id; + var host_id = params.host_id; + var host_name = params.host_name; + var url = (group_id !== null) ? GetBasePath('groups') + group_id + '/hosts/' : GetBasePath('inventory') + inventory_id + '/hosts/'; + + var action_to_take = function() { + Rest.setUrl(url); + Rest.post({ id: host_id, disassociate: 1 }) + .success( function(data, status, headers, config) { + $('#prompt-modal').modal('hide'); + HostsReload(params); + }) + .error( function(data, status, headers, config) { + $('#prompt-modal').modal('hide'); + HostsReload(params); + ProcessErrors(scope, data, status, null, + { hdr: 'Error!', msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status }); + }); + }; + + //Force binds to work. Not working usual way. + $('#prompt-header').text('Delete Host'); + $('#prompt-body').text('Are you sure you want to delete host ' + host_name + '?'); + $('#prompt-action-btn').addClass('btn-danger'); + scope.promptAction = action_to_take; // for some reason this binds? + $('#prompt-modal').modal({ + backdrop: 'static', + keyboard: true, + show: true + }); + } + }]) + + + .factory('HostsReload', ['RelatedSearchInit', 'RelatedPaginateInit', 'InventoryForm', 'GetBasePath', + function(RelatedSearchInit, RelatedPaginateInit, InventoryForm, GetBasePath) { + return function(params) { + // Rerfresh the Hosts view on right side of page + var url = (params.group_id !== null) ? GetBasePath('groups') + params.group_id + '/hosts/' : + GetBasePath('inventory') + params.inventory_id + '/'; + var relatedSets = { hosts: { url: url, iterator: 'host' } }; + RelatedSearchInit({ scope: params.scope, form: InventoryForm, relatedSets: relatedSets }); + RelatedPaginateInit({ scope: params.scope, relatedSets: relatedSets }); + params.scope.search('host'); + if (!params.scope.$$phase) { + params.scope.$digest(); + } + } + }]); + + + diff --git a/ansibleworks/ui/static/js/helpers/related-search.js b/ansibleworks/ui/static/js/helpers/related-search.js index 602f91e1c2..71f36d073a 100644 --- a/ansibleworks/ui/static/js/helpers/related-search.js +++ b/ansibleworks/ui/static/js/helpers/related-search.js @@ -25,17 +25,19 @@ angular.module('RelatedSearchHelper', ['RestServices', 'Utilities','RefreshRelat // Set default values for (var set in form.related) { - for (var fld in form.related[set].fields) { - if (form.related[set].fields[fld].key) { - scope[form.related[set].iterator + 'SearchField'] = fld - scope[form.related[set].iterator + 'SearchFieldLabel'] = form.related[set].fields[fld].label; - break; + if (form.related[set].type != 'tree') { + for (var fld in form.related[set].fields) { + if (form.related[set].fields[fld].key) { + scope[form.related[set].iterator + 'SearchField'] = fld + scope[form.related[set].iterator + 'SearchFieldLabel'] = form.related[set].fields[fld].label; + break; + } } + scope[form.related[set].iterator + 'SearchType'] = 'contains'; + scope[form.related[set].iterator + 'SearchTypeLabel'] = 'Contains'; + scope[form.related[set].iterator + 'SelectShow'] = false; + scope[form.related[set].iterator + 'HideSearchType'] = false; } - scope[form.related[set].iterator + 'SearchType'] = 'contains'; - scope[form.related[set].iterator + 'SearchTypeLabel'] = 'Contains'; - scope[form.related[set].iterator + 'SelectShow'] = false; - scope[form.related[set].iterator + 'HideSearchType'] = false; } // Functions to handle search widget changes diff --git a/ansibleworks/ui/static/js/lists/Hosts.js b/ansibleworks/ui/static/js/lists/Hosts.js index ccaa94d7a1..b6afae64e5 100644 --- a/ansibleworks/ui/static/js/lists/Hosts.js +++ b/ansibleworks/ui/static/js/lists/Hosts.js @@ -16,6 +16,7 @@ angular.module('HostListDefinition', []) selectInstructions: 'Click on a row to select it, and click Finished when done. Use the green button to create a new row.', editTitle: 'Hosts', index: true, + well: true, fields: { name: { @@ -33,7 +34,7 @@ angular.module('HostListDefinition', []) icon: 'icon-plus', label: 'Add', mode: 'all', // One of: edit, select, all - ngClick: 'addHost()', + ngClick: 'createHost()', ngHide: 'showAddButton == false', class: 'btn-success btn-small', awToolTip: 'Create a new host' diff --git a/ansibleworks/ui/static/lib/ansible/list-generator.js b/ansibleworks/ui/static/lib/ansible/list-generator.js index 01c911d15c..8b7e3a503c 100644 --- a/ansibleworks/ui/static/lib/ansible/list-generator.js +++ b/ansibleworks/ui/static/lib/ansible/list-generator.js @@ -279,7 +279,7 @@ angular.module('ListGenerator', ['GeneratorHelpers',]) html += "\n"; //well } - if (options.mode == 'lookup') { + if ( options.mode == 'lookup' || (options.id && options.id == "form-modal-body") ) { html += PaginateWidget({ set: list.name, iterator: list.iterator, mini: true, mode: 'lookup' }); } else { diff --git a/ansibleworks/ui/templates/ui/index.html b/ansibleworks/ui/templates/ui/index.html index 4601fffa01..2464fc7ca5 100644 --- a/ansibleworks/ui/templates/ui/index.html +++ b/ansibleworks/ui/templates/ui/index.html @@ -31,8 +31,6 @@ - - @@ -73,6 +71,7 @@ +