mirror of
https://github.com/ansible/awx.git
synced 2026-01-12 02:19:58 -03:30
Boolean / Smart Search (#3631)
* Part 1: building new search components Directives: smart-search, column-sort, paginate Service: QuerySet Model: DjangoSearchModel * Part 2: Implementing new search components, de-implementing old search components Remove old code: * tagSearch directive * old pagination strategy * old column sorting strategy * lookup Add new directives to list/form generator: * smart-search, * paginate * column-sort Connect $state + dataset resolution * upgrade ui-router lib to v1.0.0-beta3 * Custom $urlMatcherFactory.type - queryset * Render lists, forms, related, lookups in named views * Provide html templates in list/form/lookup/related state definitions * Provide dataset through resolve block in state definitions Update utilities * isEmpty filter * use async validation strategy in awlookup directive * Part 3: State implementations (might split into per-module commits) * Support optional state definition flag: squashSearchUrl. *_search params are only URI-encoded if squashSearchUrl is falsey. * * Fix list badge counts * Clear search input after search term(s) applied * Chain of multiple search terms in one submission * Hook up activity stream * Hook up portal mode * Fix pagination range calculations * Hook up organization sub-list views * Hook up listDefinition.search defaults * Fix ng-disabled conditions reflecting RBAC access on form fields * Fix actively-editing indicator in generated lists * form generator - fix undefined span, remove dead event listeners * wrap hosts/groups lists in a panel, fix groups list error * Smart search directive: clear all search tags * Search tags - ‘Clear All’ text - 12px Search key - remove top padding/margin Search key - reverse bolding of relationship fields / label, add commas Search tags - remove padding-bottom Lookup modal - “X” close button styled incorrectly Lookup modal - List title not rendered Lookup modal - 20px margin between buttons * Portal Mode Fix default column-sort on jobs list Hide column-oort on job status column Apply custom search bar sizes * stateDefinition.factory Return ES6 Promise instead of $q promise. $q cannot be safely provided during module.config() phase Some generated state trees (inventory / inventoryManage) need to be reduced to one promise. Side-step issues caused by ui-router de-registering ALL registered states that match placeholder state name/url pattern. e.g. inventories.lazyLoad() would de-register inventoryManage states if a page refresh occured @ /#/inventories/** * Combine generated state trees: inventories + inventoryManage Hook up inventory sync schedule list/form add /form edit views * Hook up system job schedule list/add/edit states * Fix breadcrumb of generated states in /setup view Fix typo in scheduler search prefix * Remove old search system deritus from list definitions * Fix breadcrumb definitions in states registered in app.js config block * Transclude list action buttons in generated form lists * Lookup Modal passes acceptance criterea: Modal cancel/exit - don’t update form field’s ng-model Modal save - do update form field's ng-model Transclude generated list contents into <lookup-modal> directive Lookup modal test spec * Fix typo in merge conflict resolution * Disable failing unit tests pending revision * Integrate smart-search architechture into add-permissions modal * use a semicolon delimiter instead of comma to avoid collision with django __in comparator * Hook up Dashboard > Hosts states, update Dashboard Inventory/Project counts with new search filters * Misc bug splat Add 20px spacing around root ui-view Fix missing closing div in related views Remove dupe line in smart-search controller * Remove defunct LookupHelper code * Rebuild inventories list status tooltips on updates to dataset Code cleanup - remove defunct modules Remove LookupHelper / LookupInit code Remove pre-RBAC permissions module * Add mising stateTree / basePath properties to form definitions * Resolve i18n conflicts in list and form generator Freeze dependencies * Integrate sockets * Final bug splat: fix jobs > job details and jobs > scheduled routing fix mis-resolved merge conflicts swap console.info for $log.debug
This commit is contained in:
parent
defd271c90
commit
a49095bdbc
@ -729,64 +729,7 @@ legend {
|
||||
.navigation {
|
||||
margin: 15px 0 15px 0;
|
||||
}
|
||||
|
||||
.page-number {
|
||||
display: inline-block;
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.page-number-small {
|
||||
display: inline-block;
|
||||
margin-left: 10px;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
/* Pagination */
|
||||
.page-label {
|
||||
font-size: 12px;
|
||||
margin-top: 0;
|
||||
text-align: right;
|
||||
}
|
||||
|
||||
.pagination {
|
||||
margin-top: 0;
|
||||
margin-bottom: 7px;
|
||||
}
|
||||
|
||||
.pagination>li>a,
|
||||
.pagination>li>span {
|
||||
border: 1px solid @grey-border;
|
||||
padding: 3px 6px;
|
||||
font-size: 10px;
|
||||
}
|
||||
|
||||
.pagination li {
|
||||
a#next-page {
|
||||
border-radius: 0 4px 4px 0;
|
||||
}
|
||||
|
||||
a#previous-page {
|
||||
border-radius: 4px 0 0 4px;
|
||||
}
|
||||
}
|
||||
|
||||
.modal-body {
|
||||
.pagination {
|
||||
margin-top: 15px;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.pagination > li > a {
|
||||
border: none;
|
||||
padding-top: 0;
|
||||
padding-bottom: 0;
|
||||
}
|
||||
.pagination > .active > a {
|
||||
background-color: @default-bg;
|
||||
color: #428bca;
|
||||
border-color: none;
|
||||
border: 1px solid @default-link;
|
||||
}
|
||||
.alert {
|
||||
padding: 0;
|
||||
border: none;
|
||||
@ -1623,6 +1566,10 @@ a.btn-disabled:hover {
|
||||
|
||||
/* Sort link styles */
|
||||
|
||||
.list-header-noSort:hover.list-header:hover{
|
||||
cursor: default;
|
||||
}
|
||||
|
||||
.list-header:hover {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
@ -19,13 +19,7 @@
|
||||
}
|
||||
|
||||
.job-list {
|
||||
.pagination li {
|
||||
|
||||
}
|
||||
.pagination li a {
|
||||
font-size: 12px;
|
||||
padding: 3px 6px;
|
||||
}
|
||||
i[class*="icon-job-"] {
|
||||
font-size: 13px;
|
||||
}
|
||||
|
||||
@ -116,44 +116,6 @@ table, tbody {
|
||||
margin-left: 15px;
|
||||
}
|
||||
|
||||
/* -- Pagination -- */
|
||||
.List-pagination {
|
||||
margin-top: 20px;
|
||||
font-size: 12px;
|
||||
color: @list-pagin-text;
|
||||
text-transform: uppercase;
|
||||
height: 22px;
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.List-paginationPagerHolder {
|
||||
display: flex;
|
||||
flex: 1 0 auto;
|
||||
}
|
||||
|
||||
.List-paginationPager {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.List-paginationPager--pageof {
|
||||
line-height: 22px;
|
||||
margin-left: 10px;
|
||||
}
|
||||
|
||||
.List-paginationPager--item {
|
||||
border-color: @list-pagin-bord;
|
||||
}
|
||||
|
||||
.List-paginationPager--active {
|
||||
border-color: @list-pagin-bord-act!important;
|
||||
background-color: @list-pagin-bg-act!important;
|
||||
}
|
||||
|
||||
.List-paginationItemsOf {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.List-header {
|
||||
display: flex;
|
||||
min-height: 34px;
|
||||
|
||||
@ -11,23 +11,12 @@
|
||||
* Controller for handling permissions adding
|
||||
*/
|
||||
|
||||
export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'ProcessErrors', function (rootScope, scope, GetBasePath, Rest, $q, Wait, ProcessErrors) {
|
||||
var manuallyUpdateChecklists = function(list, id, isSelected) {
|
||||
var elemScope = angular
|
||||
.element("#" +
|
||||
list + "s_table #" + id + ".List-tableRow input")
|
||||
.scope();
|
||||
if (elemScope) {
|
||||
elemScope.isSelected = !!isSelected;
|
||||
}
|
||||
};
|
||||
export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'ProcessErrors', function(rootScope, scope, GetBasePath, Rest, $q, Wait, ProcessErrors) {
|
||||
|
||||
scope.allSelected = [];
|
||||
|
||||
// the object permissions are being added to
|
||||
scope.object = scope[scope.$parent.list
|
||||
.iterator + "_obj"];
|
||||
|
||||
scope.object = scope.resourceData.data;
|
||||
// array for all possible roles for the object
|
||||
scope.roles = Object
|
||||
.keys(scope.object.summary_fields.object_roles)
|
||||
@ -36,7 +25,8 @@ export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'Pr
|
||||
value: scope.object.summary_fields
|
||||
.object_roles[key].id,
|
||||
label: scope.object.summary_fields
|
||||
.object_roles[key].name };
|
||||
.object_roles[key].name
|
||||
};
|
||||
});
|
||||
|
||||
// TODO: get working with api
|
||||
@ -48,7 +38,8 @@ export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'Pr
|
||||
name: scope.object.summary_fields
|
||||
.object_roles[key].name,
|
||||
description: scope.object.summary_fields
|
||||
.object_roles[key].description };
|
||||
.object_roles[key].description
|
||||
};
|
||||
});
|
||||
|
||||
scope.showKeyPane = false;
|
||||
@ -63,90 +54,44 @@ export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'Pr
|
||||
scope.teamsSelected = !scope.usersSelected;
|
||||
};
|
||||
|
||||
// manually handle selection/deselection of user/team checkboxes
|
||||
scope.$on("selectedOrDeselected", function(e, val) {
|
||||
val = val.value;
|
||||
if (val.isSelected) {
|
||||
// deselected, so remove from the allSelected list
|
||||
scope.allSelected = scope.allSelected.filter(function(i) {
|
||||
// return all but the object who has the id and type
|
||||
// of the element to deselect
|
||||
return (!(val.id === i.id && val.type === i.type));
|
||||
});
|
||||
// pop/push into unified collection of selected users & teams
|
||||
scope.$on("selectedOrDeselected", function(e, value) {
|
||||
let item = value.value;
|
||||
|
||||
function buildName(user) {
|
||||
return (user.first_name &&
|
||||
user.last_name) ?
|
||||
user.first_name + " " +
|
||||
user.last_name :
|
||||
user.username;
|
||||
}
|
||||
|
||||
if (item.isSelected) {
|
||||
if (item.type === 'user') {
|
||||
item.name = buildName(item);
|
||||
}
|
||||
scope.allSelected.push(item);
|
||||
} else {
|
||||
// selected, so add to the allSelected list
|
||||
var getName = function(val) {
|
||||
if (val.type === "user") {
|
||||
return (val.first_name &&
|
||||
val.last_name) ?
|
||||
val.first_name + " " +
|
||||
val.last_name :
|
||||
val.username;
|
||||
} else {
|
||||
return val.name;
|
||||
}
|
||||
};
|
||||
scope.allSelected.push({
|
||||
name: getName(val),
|
||||
type: val.type,
|
||||
roles: [],
|
||||
id: val.id
|
||||
});
|
||||
scope.allSelected = _.remove(scope.allSelected, { id: item.id });
|
||||
}
|
||||
});
|
||||
|
||||
// used to handle changes to the itemsSelected scope var on "next page",
|
||||
// "sorting etc."
|
||||
scope.$on("itemsSelected", function(e, inList) {
|
||||
// compile a list of objects that needed to be checked in the lists
|
||||
scope.updateLists = scope.allSelected.filter(function(inMemory) {
|
||||
var notInList = true;
|
||||
inList.forEach(function(val) {
|
||||
// if the object is part of the allSelected list and is
|
||||
// selected,
|
||||
// you don't need to add it updateLists
|
||||
if (inMemory.id === val.id &&
|
||||
inMemory.type === val.type) {
|
||||
notInList = false;
|
||||
}
|
||||
});
|
||||
return notInList;
|
||||
});
|
||||
});
|
||||
|
||||
// handle changes to the updatedLists by manually selected those values in
|
||||
// the UI
|
||||
scope.$watch("updateLists", function(toUpdate) {
|
||||
(toUpdate || []).forEach(function(obj) {
|
||||
manuallyUpdateChecklists(obj.type, obj.id, true);
|
||||
});
|
||||
|
||||
delete scope.updateLists;
|
||||
});
|
||||
|
||||
// remove selected user/team
|
||||
scope.removeObject = function(obj) {
|
||||
manuallyUpdateChecklists(obj.type, obj.id, false);
|
||||
|
||||
scope.allSelected = scope.allSelected.filter(function(i) {
|
||||
return (!(obj.id === i.id && obj.type === i.type));
|
||||
});
|
||||
};
|
||||
|
||||
// update post url list
|
||||
scope.$watch("allSelected", function(val) {
|
||||
scope.posts = _
|
||||
.flatten((val || [])
|
||||
.map(function (owner) {
|
||||
var url = GetBasePath(owner.type + "s") + owner.id +
|
||||
"/roles/";
|
||||
.map(function(owner) {
|
||||
var url = GetBasePath(owner.type + "s") + owner.id +
|
||||
"/roles/";
|
||||
|
||||
return (owner.roles || [])
|
||||
.map(function (role) {
|
||||
return {url: url,
|
||||
id: role.value};
|
||||
});
|
||||
}));
|
||||
return (owner.roles || [])
|
||||
.map(function(role) {
|
||||
return {
|
||||
url: url,
|
||||
id: role.value
|
||||
};
|
||||
});
|
||||
}));
|
||||
}, true);
|
||||
|
||||
// post roles to api
|
||||
@ -156,22 +101,22 @@ export default ['$rootScope', '$scope', 'GetBasePath', 'Rest', '$q', 'Wait', 'Pr
|
||||
var requests = scope.posts
|
||||
.map(function(post) {
|
||||
Rest.setUrl(post.url);
|
||||
return Rest.post({"id": post.id});
|
||||
return Rest.post({ "id": post.id });
|
||||
});
|
||||
|
||||
$q.all(requests)
|
||||
.then(function () {
|
||||
.then(function() {
|
||||
Wait('stop');
|
||||
rootScope.$broadcast("refreshList", "permission");
|
||||
scope.closeModal();
|
||||
}, function (error) {
|
||||
}, function(error) {
|
||||
Wait('stop');
|
||||
rootScope.$broadcast("refreshList", "permission");
|
||||
scope.closeModal();
|
||||
ProcessErrors(null, error.data, error.status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to post role(s): POST returned status' +
|
||||
error.status
|
||||
error.status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
@ -6,55 +6,28 @@
|
||||
import addPermissionsController from './addPermissions.controller';
|
||||
|
||||
/* jshint unused: vars */
|
||||
export default
|
||||
[ 'templateUrl',
|
||||
'Wait',
|
||||
function(templateUrl, Wait) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
scope: true,
|
||||
controller: addPermissionsController,
|
||||
templateUrl: templateUrl('access/addPermissions/addPermissions'),
|
||||
link: function(scope, element, attrs, ctrl) {
|
||||
scope.withoutTeamPermissions = attrs.withoutTeamPermissions;
|
||||
scope.toggleFormTabs('users');
|
||||
export default ['templateUrl', '$state',
|
||||
'Wait', 'addPermissionsUsersList', 'addPermissionsTeamsList',
|
||||
function(templateUrl, $state, Wait, usersList, teamsList) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
scope: {
|
||||
usersDataset: '=',
|
||||
teamsDataset: '=',
|
||||
resourceData: '=',
|
||||
},
|
||||
controller: addPermissionsController,
|
||||
templateUrl: templateUrl('access/addPermissions/addPermissions'),
|
||||
link: function(scope, element, attrs) {
|
||||
scope.toggleFormTabs('users');
|
||||
$('#add-permissions-modal').modal('show');
|
||||
|
||||
$("body").addClass("is-modalOpen");
|
||||
scope.closeModal = function() {
|
||||
$state.go('^', null, {reload: true});
|
||||
};
|
||||
|
||||
$("body").append(element);
|
||||
|
||||
Wait('start');
|
||||
|
||||
|
||||
scope.$broadcast("linkLists");
|
||||
|
||||
setTimeout(function() {
|
||||
$('#add-permissions-modal').modal("show");
|
||||
}, 200);
|
||||
|
||||
$('.modal[aria-hidden=false]').each(function () {
|
||||
if ($(this).attr('id') !== 'add-permissions-modal') {
|
||||
$(this).modal('hide');
|
||||
}
|
||||
});
|
||||
|
||||
scope.closeModal = function() {
|
||||
$("body").removeClass("is-modalOpen");
|
||||
$('#add-permissions-modal').on('hidden.bs.modal',
|
||||
function () {
|
||||
$('.AddPermissions').remove();
|
||||
});
|
||||
$('#add-permissions-modal').modal('hide');
|
||||
};
|
||||
|
||||
scope.$on('closePermissionsModal', function() {
|
||||
scope.closeModal();
|
||||
});
|
||||
|
||||
Wait('stop');
|
||||
|
||||
window.scrollTo(0,0);
|
||||
}
|
||||
};
|
||||
}
|
||||
];
|
||||
window.scrollTo(0, 0);
|
||||
}
|
||||
};
|
||||
}
|
||||
];
|
||||
|
||||
@ -45,13 +45,11 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="AddPermissions-list" ng-show="usersSelected">
|
||||
<add-permissions-list all-selected="allSelected" type="users">
|
||||
</add-permissions-list>
|
||||
<div id="AddPermissions-users" class="AddPermissions-list" ng-show="usersSelected">
|
||||
<add-permissions-list view="Users" all-selected="allSelected" dataset="usersDataset"></add-permissions-list>
|
||||
</div>
|
||||
<div class="AddPermissions-list" ng-show="teamsSelected">
|
||||
<add-permissions-list all-selected="allSelected" type="teams">
|
||||
</add-permissions-list>
|
||||
<div id="AddPermissions-teams" class="AddPermissions-list" ng-show="teamsSelected">
|
||||
<add-permissions-list view="Teams" all-selected="allSelected" dataset="teamsDataset"></add-permissions-list>
|
||||
</div>
|
||||
|
||||
<div class="AddPermissions-separator"
|
||||
|
||||
@ -5,55 +5,43 @@
|
||||
*************************************************/
|
||||
|
||||
/* jshint unused: vars */
|
||||
export default
|
||||
['addPermissionsTeamsList', 'addPermissionsUsersList', 'generateList', 'GetBasePath', 'SelectionInit', 'SearchInit',
|
||||
'PaginateInit', function(addPermissionsTeamsList,
|
||||
addPermissionsUsersList, generateList,
|
||||
GetBasePath, SelectionInit, SearchInit, PaginateInit) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
scope: {
|
||||
allSelected: '='
|
||||
},
|
||||
template: "<div class='addPermissionsList-inner'></div>",
|
||||
link: function(scope, element, attrs, ctrl) {
|
||||
scope.$on("linkLists", function(e) {
|
||||
var generator = generateList,
|
||||
list = addPermissionsTeamsList,
|
||||
url = GetBasePath("teams"),
|
||||
set = "teams",
|
||||
id = "addPermissionsTeamsList",
|
||||
mode = "edit";
|
||||
export default ['addPermissionsTeamsList', 'addPermissionsUsersList', '$compile', 'generateList', 'GetBasePath', 'SelectionInit', function(addPermissionsTeamsList,
|
||||
addPermissionsUsersList, $compile, generateList,
|
||||
GetBasePath, SelectionInit) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
scope: {
|
||||
allSelected: '=',
|
||||
view: '@',
|
||||
dataset: '='
|
||||
},
|
||||
template: "<div class='addPermissionsList-inner'></div>",
|
||||
link: function(scope, element, attrs, ctrl) {
|
||||
let listMap, list, list_html;
|
||||
|
||||
if (attrs.type === 'users') {
|
||||
list = addPermissionsUsersList;
|
||||
url = GetBasePath("users") + "?is_superuser=false";
|
||||
set = "users";
|
||||
id = "addPermissionsUsersList";
|
||||
mode = "edit";
|
||||
}
|
||||
listMap = {Teams: addPermissionsTeamsList, Users: addPermissionsUsersList};
|
||||
list = listMap[scope.view];
|
||||
list_html = generateList.build({
|
||||
mode: 'edit',
|
||||
list: list
|
||||
});
|
||||
|
||||
scope.id = id;
|
||||
scope.list = listMap[scope.view];
|
||||
scope[`${list.iterator}_dataset`] = scope.dataset.data;
|
||||
scope[`${list.name}`] = scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
scope.$watch("selectedItems", function() {
|
||||
scope.$emit("itemsSelected", scope.selectedItems);
|
||||
});
|
||||
scope.$watch(list.name, function(){
|
||||
_.forEach(scope[`${list.name}`], isSelected);
|
||||
});
|
||||
|
||||
element.find(".addPermissionsList-inner")
|
||||
.attr("id", id);
|
||||
|
||||
generator.inject(list, { id: id,
|
||||
title: false, mode: mode, scope: scope });
|
||||
|
||||
SearchInit({ scope: scope, set: set,
|
||||
list: list, url: url });
|
||||
|
||||
PaginateInit({ scope: scope,
|
||||
list: list, url: url, pageSize: 5 });
|
||||
|
||||
scope.search(list.iterator);
|
||||
});
|
||||
function isSelected(item){
|
||||
if(_.find(scope.allSelected, {id: item.id})){
|
||||
item.isSelected = true;
|
||||
}
|
||||
};
|
||||
return item;
|
||||
}
|
||||
element.append(list_html);
|
||||
$compile(element.contents())(scope);
|
||||
}
|
||||
];
|
||||
};
|
||||
}];
|
||||
|
||||
@ -7,9 +7,14 @@
|
||||
|
||||
export default function() {
|
||||
return {
|
||||
searchSize: 'col-lg-12 col-md-12 col-sm-12 col-xs-12',
|
||||
name: 'users',
|
||||
iterator: 'user',
|
||||
defaultSearchParams: function(term){
|
||||
return {or__username__icontains: term,
|
||||
or__first_name__icontains: term,
|
||||
or__last_name__icontains: term
|
||||
};
|
||||
},
|
||||
title: false,
|
||||
listTitleBadge: false,
|
||||
multiSelect: true,
|
||||
@ -17,7 +22,6 @@
|
||||
index: false,
|
||||
hover: true,
|
||||
emptyListText : 'No Users exist',
|
||||
|
||||
fields: {
|
||||
first_name: {
|
||||
label: 'First Name',
|
||||
|
||||
@ -8,22 +8,31 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Activity Stream
|
||||
* @description This controller controls the activity stream.
|
||||
*/
|
||||
function activityStreamController($scope, $state, subTitle, Stream, GetTargetTitle) {
|
||||
*/
|
||||
function activityStreamController($scope, $state, subTitle, Stream, GetTargetTitle, list, Dataset) {
|
||||
|
||||
// subTitle is passed in via a resolve on the route. If there is no subtitle
|
||||
// generated in the resolve then we go get the targets generic title.
|
||||
init();
|
||||
|
||||
// Get the streams sub-title based on the target. This scope variable is leveraged
|
||||
// when we define the activity stream list. Specifically it is included in the list
|
||||
// title.
|
||||
$scope.streamSubTitle = subTitle ? subTitle : GetTargetTitle($state.params.target);
|
||||
function init() {
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
// Open the stream
|
||||
Stream({
|
||||
scope: $scope
|
||||
});
|
||||
// subTitle is passed in via a resolve on the route. If there is no subtitle
|
||||
// generated in the resolve then we go get the targets generic title.
|
||||
|
||||
// Get the streams sub-title based on the target. This scope variable is leveraged
|
||||
// when we define the activity stream list. Specifically it is included in the list
|
||||
// title.
|
||||
$scope.streamSubTitle = subTitle ? subTitle : GetTargetTitle($state.params.target);
|
||||
|
||||
// Open the stream
|
||||
Stream({
|
||||
scope: $scope
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default ['$scope', '$state', 'subTitle', 'Stream', 'GetTargetTitle', activityStreamController];
|
||||
export default ['$scope', '$state', 'subTitle', 'Stream', 'GetTargetTitle', 'StreamList', 'Dataset', activityStreamController];
|
||||
|
||||
@ -1,3 +0,0 @@
|
||||
<div class="Panel" id="stream-container">
|
||||
<div id="stream-content"></div>
|
||||
</div>
|
||||
@ -4,49 +4,73 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../shared/template-url/template-url.factory';
|
||||
|
||||
export default {
|
||||
name: 'activityStream',
|
||||
route: '/activity_stream?target&id',
|
||||
templateUrl: templateUrl('activity-stream/activitystream'),
|
||||
controller: 'activityStreamController',
|
||||
searchPrefix: 'activity',
|
||||
data: {
|
||||
activityStream: true
|
||||
},
|
||||
params: {
|
||||
activity_search: {
|
||||
value: {
|
||||
// default params will not generate search tags
|
||||
order_by: '-timestamp',
|
||||
or__object1: null,
|
||||
or__object2: null
|
||||
}
|
||||
}
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: "ACTIVITY STREAM"
|
||||
},
|
||||
onExit: function(){
|
||||
onExit: function() {
|
||||
$('#stream-detail-modal').modal('hide');
|
||||
$('.modal-backdrop').remove();
|
||||
$('body').removeClass('modal-open');
|
||||
},
|
||||
resolve: {
|
||||
features: ['FeaturesService', 'ProcessErrors', '$state', '$rootScope',
|
||||
function(FeaturesService, ProcessErrors, $state, $rootScope) {
|
||||
var features = FeaturesService.get();
|
||||
if(features){
|
||||
if(FeaturesService.featureEnabled('activity_streams')) {
|
||||
return features;
|
||||
}
|
||||
else {
|
||||
$state.go('dashboard');
|
||||
}
|
||||
views: {
|
||||
'list@': {
|
||||
controller: 'activityStreamController',
|
||||
templateProvider: function(StreamList, generateList) {
|
||||
let html = generateList.build({
|
||||
list: StreamList,
|
||||
mode: 'edit'
|
||||
});
|
||||
html = generateList.wrapPanel(html);
|
||||
return html;
|
||||
}
|
||||
$rootScope.featuresConfigured.promise.then(function(features){
|
||||
if(features){
|
||||
if(FeaturesService.featureEnabled('activity_streams')) {
|
||||
}
|
||||
},
|
||||
resolve: {
|
||||
Dataset: ['StreamList', 'QuerySet', '$stateParams', 'GetBasePath',
|
||||
function(list, qs, $stateParams, GetBasePath) {
|
||||
let path = GetBasePath(list.basePath) || GetBasePath(list.name);
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}
|
||||
],
|
||||
features: ['FeaturesService', 'ProcessErrors', '$state', '$rootScope',
|
||||
function(FeaturesService, ProcessErrors, $state, $rootScope) {
|
||||
var features = FeaturesService.get();
|
||||
if (features) {
|
||||
if (FeaturesService.featureEnabled('activity_streams')) {
|
||||
return features;
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
$state.go('dashboard');
|
||||
}
|
||||
}
|
||||
});
|
||||
}],
|
||||
subTitle:
|
||||
[ '$stateParams',
|
||||
$rootScope.featuresConfigured.promise.then(function(features) {
|
||||
if (features) {
|
||||
if (FeaturesService.featureEnabled('activity_streams')) {
|
||||
return features;
|
||||
} else {
|
||||
$state.go('dashboard');
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
],
|
||||
subTitle: ['$stateParams',
|
||||
'Rest',
|
||||
'ModelToBasePathKey',
|
||||
'GetBasePath',
|
||||
@ -65,15 +89,14 @@ export default {
|
||||
.then(function(data) {
|
||||
// Return the name or the username depending on which is available.
|
||||
return (data.data.name || data.data.username);
|
||||
}).catch(function (response) {
|
||||
ProcessErrors(null, response.data, response.status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to get title info. GET returned status: ' +
|
||||
response.status
|
||||
}).catch(function(response) {
|
||||
ProcessErrors(null, response.data, response.status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to get title info. GET returned status: ' +
|
||||
response.status
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@ -10,7 +10,7 @@ export default ['templateUrl', function(templateUrl) {
|
||||
scope: true,
|
||||
replace: true,
|
||||
templateUrl: templateUrl('activity-stream/streamDropdownNav/stream-dropdown-nav'),
|
||||
controller: ['$scope', '$state', 'CreateSelect2', function($scope, $state, CreateSelect2) {
|
||||
controller: ['$scope', '$state', '$stateParams','CreateSelect2', function($scope, $state, $stateParams, CreateSelect2) {
|
||||
|
||||
$scope.streamTarget = ($state.params && $state.params.target) ? $state.params.target : 'dashboard';
|
||||
|
||||
@ -35,14 +35,17 @@ export default ['templateUrl', function(templateUrl) {
|
||||
});
|
||||
|
||||
$scope.changeStreamTarget = function(){
|
||||
|
||||
if($scope.streamTarget && $scope.streamTarget === 'dashboard') {
|
||||
// Just navigate to the base activity stream
|
||||
$state.go('activityStream', {}, {inherit: false});
|
||||
$state.go('activityStream');
|
||||
}
|
||||
else {
|
||||
let search = _.merge($stateParams.activity_search, {
|
||||
or__object1: $scope.streamTarget,
|
||||
or__object2: $scope.streamTarget
|
||||
});
|
||||
// Attach the taget to the query parameters
|
||||
$state.go('activityStream', {target: $scope.streamTarget}, {inherit: false});
|
||||
$state.go('activityStream', {target: $scope.streamTarget, activity_search: search});
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
@ -15,6 +15,12 @@ import 'jquery.resize';
|
||||
import 'codemirror';
|
||||
import 'js-yaml';
|
||||
import 'select2';
|
||||
import uiRouter from 'angular-ui-router';
|
||||
// backwards compatibility for $stateChange* events
|
||||
import 'angular-ui-router/release/stateEvents';
|
||||
// ui-router debugging
|
||||
//import { trace } from 'angular-ui-router';
|
||||
//trace.enable();
|
||||
|
||||
// Configuration dependencies
|
||||
global.$AnsibleConfig = null;
|
||||
@ -27,7 +33,7 @@ if ($basePath) {
|
||||
|
||||
// Modules
|
||||
import './helpers';
|
||||
import './forms';
|
||||
import * as forms from './forms';
|
||||
import './lists';
|
||||
import './widgets';
|
||||
import './filters';
|
||||
@ -40,12 +46,10 @@ import systemTracking from './system-tracking/main';
|
||||
import inventories from './inventories/main';
|
||||
import inventoryScripts from './inventory-scripts/main';
|
||||
import organizations from './organizations/main';
|
||||
import permissions from './permissions/main';
|
||||
import managementJobs from './management-jobs/main';
|
||||
import jobDetail from './job-detail/main';
|
||||
import jobSubmission from './job-submission/main';
|
||||
import notifications from './notifications/main';
|
||||
import access from './access/main';
|
||||
import about from './about/main';
|
||||
import license from './license/main';
|
||||
import setupMenu from './setup-menu/main';
|
||||
@ -54,23 +58,17 @@ import breadCrumb from './bread-crumb/main';
|
||||
import browserData from './browser-data/main';
|
||||
import dashboard from './dashboard/main';
|
||||
import moment from './shared/moment/main';
|
||||
import templateUrl from './shared/template-url/main';
|
||||
import login from './login/main';
|
||||
import activityStream from './activity-stream/main';
|
||||
import standardOut from './standard-out/main';
|
||||
import JobTemplates from './job-templates/main';
|
||||
import search from './search/main';
|
||||
import credentials from './credentials/main';
|
||||
import { ProjectsList, ProjectsAdd, ProjectsEdit } from './controllers/Projects';
|
||||
import OrganizationsList from './organizations/list/organizations-list.controller';
|
||||
import OrganizationsAdd from './organizations/add/organizations-add.controller';
|
||||
import { UsersList, UsersAdd, UsersEdit } from './controllers/Users';
|
||||
import { TeamsList, TeamsAdd, TeamsEdit } from './controllers/Teams';
|
||||
|
||||
import RestServices from './rest/main';
|
||||
import './lookup/main';
|
||||
import './shared/api-loader';
|
||||
import './shared/form-generator';
|
||||
import access from './access/main';
|
||||
import './shared/Modal';
|
||||
import './shared/prompt-dialog';
|
||||
import './shared/directives';
|
||||
@ -80,7 +78,7 @@ import config from './shared/config/main';
|
||||
import './login/authenticationServices/pendo/ng-pendo';
|
||||
import footer from './footer/main';
|
||||
import scheduler from './scheduler/main';
|
||||
import {N_} from './i18n';
|
||||
import { N_ } from './i18n';
|
||||
|
||||
var tower = angular.module('Tower', [
|
||||
// how to add CommonJS / AMD third-party dependencies:
|
||||
@ -88,17 +86,17 @@ var tower = angular.module('Tower', [
|
||||
// 2. add package name to ./grunt-tasks/webpack.vendorFiles
|
||||
require('angular-breadcrumb'),
|
||||
require('angular-codemirror'),
|
||||
require('angular-cookies'),
|
||||
require('angular-drag-and-drop-lists'),
|
||||
require('angular-ui-router'),
|
||||
require('angular-sanitize'),
|
||||
require('angular-scheduler').name,
|
||||
require('angular-tz-extensions'),
|
||||
require('lr-infinite-scroll'),
|
||||
require('ng-toast'),
|
||||
|
||||
uiRouter,
|
||||
'ui.router.state.events',
|
||||
|
||||
about.name,
|
||||
access.name,
|
||||
license.name,
|
||||
RestServices.name,
|
||||
browserData.name,
|
||||
@ -106,14 +104,13 @@ var tower = angular.module('Tower', [
|
||||
inventories.name,
|
||||
inventoryScripts.name,
|
||||
organizations.name,
|
||||
permissions.name,
|
||||
//permissions.name,
|
||||
managementJobs.name,
|
||||
setupMenu.name,
|
||||
mainMenu.name,
|
||||
breadCrumb.name,
|
||||
dashboard.name,
|
||||
moment.name,
|
||||
templateUrl.name,
|
||||
login.name,
|
||||
activityStream.name,
|
||||
footer.name,
|
||||
@ -121,27 +118,19 @@ var tower = angular.module('Tower', [
|
||||
jobSubmission.name,
|
||||
notifications.name,
|
||||
standardOut.name,
|
||||
access.name,
|
||||
JobTemplates.name,
|
||||
portalMode.name,
|
||||
search.name,
|
||||
config.name,
|
||||
credentials.name,
|
||||
//'templates',
|
||||
'Utilities',
|
||||
'OrganizationFormDefinition',
|
||||
'UserFormDefinition',
|
||||
'FormGenerator',
|
||||
'OrganizationListDefinition',
|
||||
'jobTemplates',
|
||||
'UserListDefinition',
|
||||
'UserHelper',
|
||||
'PromptDialog',
|
||||
'ApiLoader',
|
||||
'RelatedSearchHelper',
|
||||
'SearchHelper',
|
||||
'PaginationHelpers',
|
||||
'RefreshHelper',
|
||||
'AWDirectives',
|
||||
'InventoriesListDefinition',
|
||||
'InventoryFormDefinition',
|
||||
@ -161,7 +150,6 @@ var tower = angular.module('Tower', [
|
||||
'TeamHelper',
|
||||
'CredentialsListDefinition',
|
||||
'CredentialFormDefinition',
|
||||
'LookUpHelper',
|
||||
'JobTemplatesListDefinition',
|
||||
'PortalJobTemplatesListDefinition',
|
||||
'JobTemplateFormDefinition',
|
||||
@ -223,10 +211,12 @@ var tower = angular.module('Tower', [
|
||||
timeout: 4000
|
||||
});
|
||||
}])
|
||||
.config(['$stateProvider', '$urlRouterProvider', '$breadcrumbProvider',
|
||||
'$urlMatcherFactoryProvider',
|
||||
function($stateProvider, $urlRouterProvider, $breadcrumbProvider,
|
||||
$urlMatcherFactoryProvider) {
|
||||
.config(['$urlRouterProvider', '$breadcrumbProvider', 'QuerySetProvider',
|
||||
'$urlMatcherFactoryProvider', 'stateDefinitionsProvider', '$stateProvider', '$stateExtenderProvider',
|
||||
function($urlRouterProvider, $breadcrumbProvider, QuerySet,
|
||||
$urlMatcherFactoryProvider, stateDefinitionsProvider, $stateProvider, $stateExtenderProvider) {
|
||||
let $stateExtender = $stateExtenderProvider.$get(),
|
||||
stateDefinitions = stateDefinitionsProvider.$get();
|
||||
$urlMatcherFactoryProvider.strictMode(false);
|
||||
$breadcrumbProvider.setOptions({
|
||||
templateUrl: urlPrefix + 'partials/breadcrumb.html'
|
||||
@ -234,202 +224,133 @@ var tower = angular.module('Tower', [
|
||||
|
||||
// route to the details pane of /job/:id/host-event/:eventId if no other child specified
|
||||
$urlRouterProvider.when('/jobs/*/host-event/*', '/jobs/*/host-event/*/details');
|
||||
$urlRouterProvider.otherwise('/home');
|
||||
|
||||
// $urlRouterProvider.otherwise("/home");
|
||||
$urlRouterProvider.otherwise(function($injector) {
|
||||
var $state = $injector.get("$state");
|
||||
$state.go('dashboard');
|
||||
$urlMatcherFactoryProvider.type('queryset', {
|
||||
// encoding
|
||||
// from {operator__key1__comparator=value, ... }
|
||||
// to "_search=operator:key:compator=value& ... "
|
||||
encode: function(item) {
|
||||
return QuerySet.$get().encodeArr(item);
|
||||
},
|
||||
// decoding
|
||||
// from "_search=operator:key:compator=value& ... "
|
||||
// to "_search=operator:key:compator=value& ... "
|
||||
decode: function(item) {
|
||||
return QuerySet.$get().decodeArr(item);
|
||||
},
|
||||
// directionality - are we encoding or decoding?
|
||||
is: function(item) {
|
||||
// true: encode to uri
|
||||
// false: decode to $stateParam
|
||||
return angular.isObject(item);
|
||||
}
|
||||
});
|
||||
|
||||
/* Mark translatable strings with N_() and
|
||||
* extract them by 'grunt nggettext_extract'
|
||||
* but angular.config() cannot get gettextCatalog.
|
||||
*/
|
||||
$stateProvider.
|
||||
state('teams', {
|
||||
url: '/teams',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: TeamsList,
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'team'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: N_("TEAMS")
|
||||
}
|
||||
}).
|
||||
|
||||
state('teams.add', {
|
||||
url: '/add',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: TeamsAdd,
|
||||
ncyBreadcrumb: {
|
||||
parent: "teams",
|
||||
label: N_("CREATE TEAM")
|
||||
}
|
||||
}).
|
||||
// Handy hook for debugging register/deregister of lazyLoad'd states
|
||||
// $stateProvider.stateRegistry.onStatesChanged((event, states) =>{
|
||||
// console.log(event, states)
|
||||
// })
|
||||
|
||||
state('teams.edit', {
|
||||
url: '/:team_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: TeamsEdit,
|
||||
data: {
|
||||
activityStreamId: 'team_id'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: "teams",
|
||||
label: "{{team_obj.name}}"
|
||||
}
|
||||
}).
|
||||
|
||||
state('teamUsers', {
|
||||
url: '/teams/:team_id/users',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: UsersList
|
||||
}).
|
||||
// lazily generate a tree of substates which will replace this node in ui-router's stateRegistry
|
||||
// see: stateDefinition.factory for usage documentation
|
||||
$stateProvider.state({
|
||||
name: 'projects',
|
||||
url: '/projects',
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
parent: 'projects', // top-most node in the generated tree (will replace this state definition)
|
||||
modes: ['add', 'edit'],
|
||||
list: 'ProjectList',
|
||||
form: 'ProjectsForm',
|
||||
controllers: {
|
||||
list: ProjectsList, // DI strings or objects
|
||||
add: ProjectsAdd,
|
||||
edit: ProjectsEdit
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'project',
|
||||
socket: {
|
||||
"groups": {
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
state('teamUserEdit', {
|
||||
url: '/teams/:team_id/users/:user_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: UsersEdit
|
||||
}).
|
||||
|
||||
state('teamProjects', {
|
||||
url: '/teams/:team_id/projects',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: ProjectsList
|
||||
}).
|
||||
|
||||
state('teamProjectAdd', {
|
||||
url: '/teams/:team_id/projects/add',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: ProjectsAdd
|
||||
}).
|
||||
|
||||
state('teamProjectEdit', {
|
||||
url: '/teams/:team_id/projects/:project_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: ProjectsEdit
|
||||
}).
|
||||
|
||||
state('teamCredentials', {
|
||||
url: '/teams/:team_id/credentials',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsList
|
||||
}).
|
||||
|
||||
state('teamCredentialAdd', {
|
||||
url: '/teams/:team_id/credentials/add',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsAdd
|
||||
}).
|
||||
|
||||
state('teamCredentialEdit', {
|
||||
url: '/teams/:team_id/credentials/:credential_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsEdit
|
||||
}).
|
||||
|
||||
state('credentials', {
|
||||
$stateProvider.state({
|
||||
name: 'credentials',
|
||||
url: '/credentials',
|
||||
templateUrl: urlPrefix + 'partials/credentials.html',
|
||||
controller: CredentialsList,
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'credential'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: N_("CREDENTIALS")
|
||||
}
|
||||
}).
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
parent: 'credentials',
|
||||
modes: ['add', 'edit'],
|
||||
list: 'CredentialList',
|
||||
form: 'CredentialForm',
|
||||
controllers: {
|
||||
list: CredentialsList,
|
||||
add: CredentialsAdd,
|
||||
edit: CredentialsEdit
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'credential'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: 'CREDENTIALS'
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
state('credentials.add', {
|
||||
url: '/add',
|
||||
templateUrl: urlPrefix + 'partials/credentials.html',
|
||||
controller: CredentialsAdd,
|
||||
ncyBreadcrumb: {
|
||||
parent: "credentials",
|
||||
label: N_("CREATE CREDENTIAL")
|
||||
}
|
||||
}).
|
||||
$stateProvider.state({
|
||||
name: 'teams',
|
||||
url: '/teams',
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
parent: 'teams',
|
||||
modes: ['add', 'edit'],
|
||||
list: 'TeamList',
|
||||
form: 'TeamForm',
|
||||
controllers: {
|
||||
list: TeamsList,
|
||||
add: TeamsAdd,
|
||||
edit: TeamsEdit
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'team'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: 'TEAMS'
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
state('credentials.edit', {
|
||||
url: '/:credential_id',
|
||||
templateUrl: urlPrefix + 'partials/credentials.html',
|
||||
controller: CredentialsEdit,
|
||||
data: {
|
||||
activityStreamId: 'credential_id'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: "credentials",
|
||||
label: "{{credential_obj.name}}"
|
||||
}
|
||||
}).
|
||||
|
||||
state('users', {
|
||||
$stateProvider.state({
|
||||
name: 'users',
|
||||
url: '/users',
|
||||
templateUrl: urlPrefix + 'partials/users.html',
|
||||
controller: UsersList,
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'user'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: N_("USERS")
|
||||
}
|
||||
}).
|
||||
|
||||
state('users.add', {
|
||||
url: '/add',
|
||||
templateUrl: urlPrefix + 'partials/users.html',
|
||||
controller: UsersAdd,
|
||||
ncyBreadcrumb: {
|
||||
parent: "users",
|
||||
label: N_("CREATE USER")
|
||||
}
|
||||
}).
|
||||
|
||||
state('users.edit', {
|
||||
url: '/:user_id',
|
||||
templateUrl: urlPrefix + 'partials/users.html',
|
||||
controller: UsersEdit,
|
||||
data: {
|
||||
activityStreamId: 'user_id'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: "users",
|
||||
label: "{{user_obj.username}}"
|
||||
}
|
||||
}).
|
||||
|
||||
state('userCredentials', {
|
||||
url: '/users/:user_id/credentials',
|
||||
templateUrl: urlPrefix + 'partials/users.html',
|
||||
controller: CredentialsList
|
||||
}).
|
||||
|
||||
state('userCredentialAdd', {
|
||||
url: '/users/:user_id/credentials/add',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsAdd
|
||||
}).
|
||||
|
||||
state('teamUserCredentialEdit', {
|
||||
url: '/teams/:user_id/credentials/:credential_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsEdit
|
||||
}).
|
||||
|
||||
state('sockets', {
|
||||
url: '/sockets',
|
||||
templateUrl: urlPrefix + 'partials/sockets.html',
|
||||
controller: SocketsController,
|
||||
ncyBreadcrumb: {
|
||||
label: N_("SOCKETS")
|
||||
}
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
parent: 'users',
|
||||
modes: ['add', 'edit'],
|
||||
list: 'UserList',
|
||||
form: 'UserForm',
|
||||
controllers: {
|
||||
list: UsersList,
|
||||
add: UsersAdd,
|
||||
edit: UsersEdit
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'user'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'setup',
|
||||
label: 'USERS'
|
||||
}
|
||||
})
|
||||
});
|
||||
}
|
||||
])
|
||||
@ -447,17 +368,23 @@ var tower = angular.module('Tower', [
|
||||
}]);
|
||||
}])
|
||||
|
||||
.run(['$stateExtender', '$q', '$compile', '$cookieStore', '$rootScope', '$log',
|
||||
.run(['$stateExtender', '$q', '$compile', '$cookieStore', '$rootScope', '$log', '$stateParams',
|
||||
'CheckLicense', '$location', 'Authorization', 'LoadBasePaths', 'Timer',
|
||||
'ClearScope', 'LoadConfig', 'Store', 'pendoService', 'Prompt', 'Rest',
|
||||
'Wait', 'ProcessErrors', '$state', 'GetBasePath', 'ConfigService',
|
||||
'FeaturesService', '$filter', 'SocketService', 'I18NInit',
|
||||
function($stateExtender, $q, $compile, $cookieStore, $rootScope, $log,
|
||||
function($stateExtender, $q, $compile, $cookieStore, $rootScope, $log, $stateParams,
|
||||
CheckLicense, $location, Authorization, LoadBasePaths, Timer,
|
||||
ClearScope, LoadConfig, Store, pendoService, Prompt, Rest, Wait,
|
||||
ProcessErrors, $state, GetBasePath, ConfigService, FeaturesService,
|
||||
$filter, SocketService, I18NInit) {
|
||||
|
||||
$rootScope.$state = $state;
|
||||
$rootScope.$state.matches = function(stateName) {
|
||||
return $state.current.name.search(stateName) > 0;
|
||||
};
|
||||
$rootScope.$stateParams = $stateParams;
|
||||
|
||||
I18NInit();
|
||||
$stateExtender.addState({
|
||||
name: 'dashboard',
|
||||
@ -465,14 +392,14 @@ var tower = angular.module('Tower', [
|
||||
templateUrl: urlPrefix + 'partials/home.html',
|
||||
controller: Home,
|
||||
params: { licenseMissing: null },
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
refreshButton: true
|
||||
refreshButton: true,
|
||||
socket: {
|
||||
"groups": {
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: N_("DASHBOARD")
|
||||
@ -491,94 +418,94 @@ var tower = angular.module('Tower', [
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
searchPrefix: 'job',
|
||||
name: 'jobs',
|
||||
url: '/jobs',
|
||||
templateUrl: urlPrefix + 'partials/jobs.html',
|
||||
controller: JobsListController,
|
||||
ncyBreadcrumb: {
|
||||
label: N_("JOBS")
|
||||
},
|
||||
params: {
|
||||
search: {
|
||||
value: {order_by:'-finished'}
|
||||
job_search: {
|
||||
value: { order_by: '-finished' }
|
||||
}
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"],
|
||||
"schedules": ["changed"]
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'projects',
|
||||
url: '/projects?{status}',
|
||||
templateUrl: urlPrefix + 'partials/projects.html',
|
||||
controller: ProjectsList,
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'project'
|
||||
socket: {
|
||||
"groups": {
|
||||
"jobs": ["status_changed"],
|
||||
"schedules": ["changed"]
|
||||
}
|
||||
}
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: N_("PROJECTS")
|
||||
resolve: {
|
||||
Dataset: ['AllJobsList', 'QuerySet', '$stateParams', 'GetBasePath', (list, qs, $stateParams, GetBasePath) => {
|
||||
let path = GetBasePath(list.basePath) || GetBasePath(list.name);
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}]
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
views: {
|
||||
'list@': {
|
||||
templateUrl: urlPrefix + 'partials/jobs.html',
|
||||
},
|
||||
'list@jobs': {
|
||||
templateProvider: function(AllJobsList, generateList) {
|
||||
let html = generateList.build({
|
||||
list: AllJobsList,
|
||||
mode: 'edit'
|
||||
});
|
||||
return html;
|
||||
},
|
||||
controller: JobsListController
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'projects.add',
|
||||
url: '/add',
|
||||
templateUrl: urlPrefix + 'partials/projects.html',
|
||||
controller: ProjectsAdd,
|
||||
ncyBreadcrumb: {
|
||||
parent: "projects",
|
||||
label: N_("CREATE PROJECT")
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
name: 'teamUsers',
|
||||
url: '/teams/:team_id/users',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: UsersList,
|
||||
resolve: {
|
||||
Users: ['UsersList', 'QuerySet', '$stateParams', 'GetBasePath', (list, qs, $stateParams, GetBasePath) => {
|
||||
let path = GetBasePath(list.basePath) || GetBasePath(list.name);
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}]
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'projects.edit',
|
||||
url: '/:id',
|
||||
templateUrl: urlPrefix + 'partials/projects.html',
|
||||
controller: ProjectsEdit,
|
||||
data: {
|
||||
activityStreamId: 'id'
|
||||
},
|
||||
name: 'userCredentials',
|
||||
url: '/users/:user_id/credentials',
|
||||
templateUrl: urlPrefix + 'partials/users.html',
|
||||
controller: CredentialsList
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'userCredentialAdd',
|
||||
url: '/users/:user_id/credentials/add',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsAdd
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'teamUserCredentialEdit',
|
||||
url: '/teams/:user_id/credentials/:credential_id',
|
||||
templateUrl: urlPrefix + 'partials/teams.html',
|
||||
controller: CredentialsEdit
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'sockets',
|
||||
url: '/sockets',
|
||||
templateUrl: urlPrefix + 'partials/sockets.html',
|
||||
controller: SocketsController,
|
||||
ncyBreadcrumb: {
|
||||
parent: 'projects',
|
||||
label: '{{name}}'
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
label: 'SOCKETS'
|
||||
}
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'projectOrganizations',
|
||||
url: '/projects/:project_id/organizations',
|
||||
templateUrl: urlPrefix + 'partials/projects.html',
|
||||
controller: OrganizationsList
|
||||
});
|
||||
|
||||
$stateExtender.addState({
|
||||
name: 'projectOrganizationAdd',
|
||||
url: '/projects/:project_id/organizations/add',
|
||||
templateUrl: urlPrefix + 'partials/projects.html',
|
||||
controller: OrganizationsAdd
|
||||
});
|
||||
|
||||
$rootScope.addPermission = function(scope) {
|
||||
$compile("<add-permissions class='AddPermissions'></add-permissions>")(scope);
|
||||
};
|
||||
@ -604,7 +531,7 @@ var tower = angular.module('Tower', [
|
||||
Rest.post({ "disassociate": true, "id": entry.id })
|
||||
.success(function() {
|
||||
Wait('stop');
|
||||
$rootScope.$broadcast("refreshList", "permission");
|
||||
$state.go('.', null, { reload: true });
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($rootScope, data, status, null, {
|
||||
|
||||
@ -25,18 +25,29 @@ export default
|
||||
if(streamConfig && streamConfig.activityStream) {
|
||||
if(streamConfig.activityStreamTarget) {
|
||||
stateGoParams.target = streamConfig.activityStreamTarget;
|
||||
stateGoParams.activity_search = {
|
||||
or__object1: streamConfig.activityStreamTarget,
|
||||
or__object2: streamConfig.activityStreamTarget,
|
||||
order_by: '-timestamp',
|
||||
page_size: '20',
|
||||
};
|
||||
}
|
||||
else {
|
||||
stateGoParams.activity_search = {
|
||||
order_by: '-timestamp',
|
||||
page_size: '20',
|
||||
};
|
||||
}
|
||||
if(streamConfig.activityStreamId) {
|
||||
stateGoParams.id = $state.params[streamConfig.activityStreamId];
|
||||
}
|
||||
|
||||
}
|
||||
originalRoute = $state.current;
|
||||
$state.go('activityStream', stateGoParams);
|
||||
}
|
||||
// The user is navigating away from the activity stream - take them back from whence they came
|
||||
else {
|
||||
// Pull the previous state out of local storage
|
||||
|
||||
if(originalRoute) {
|
||||
$state.go(originalRoute.name, originalRoute.fromParams);
|
||||
}
|
||||
@ -51,14 +62,13 @@ export default
|
||||
};
|
||||
|
||||
scope.$on("$stateChangeStart", function updateActivityStreamButton(event, toState, toParams, fromState, fromParams) {
|
||||
|
||||
if(fromState && !Empty(fromState.name)) {
|
||||
// Go ahead and attach the from params to the state object so that it can all be stored together
|
||||
fromState.fromParams = fromParams ? fromParams : {};
|
||||
|
||||
// Store the state that we're coming from in local storage to be accessed when navigating away from the
|
||||
// activity stream
|
||||
Store('previous_state', fromState);
|
||||
//Store('previous_state', fromState);
|
||||
}
|
||||
|
||||
streamConfig = (toState && toState.data) ? toState.data : {};
|
||||
|
||||
@ -8,114 +8,63 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Credentials
|
||||
* @description This controller's for the credentials page
|
||||
*/
|
||||
*/
|
||||
|
||||
|
||||
export function CredentialsList($scope, $rootScope, $location, $log,
|
||||
$stateParams, Rest, Alert, CredentialList, GenerateList, Prompt, SearchInit,
|
||||
PaginateInit, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath,
|
||||
SelectionInit, GetChoices, Wait, $state, $filter, rbacUiControlService) {
|
||||
$stateParams, Rest, Alert, CredentialList, Prompt, ClearScope,
|
||||
ProcessErrors, GetBasePath, Wait, $state, $filter, rbacUiControlService, Dataset) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
rbacUiControlService.canAdd('credentials')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
Wait('start');
|
||||
|
||||
var list = CredentialList,
|
||||
defaultUrl = GetBasePath('credentials'),
|
||||
view = GenerateList,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
mode = (base === 'credentials') ? 'edit' : 'select',
|
||||
url;
|
||||
defaultUrl = GetBasePath('credentials');
|
||||
|
||||
view.inject(list, { mode: mode, scope: $scope });
|
||||
init();
|
||||
|
||||
$scope.selected = [];
|
||||
$scope.credentialLoading = true;
|
||||
function init() {
|
||||
rbacUiControlService.canAdd('credentials')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
url = GetBasePath(base) + ( (base === 'users') ? $stateParams.user_id + '/credentials/' : $stateParams.team_id + '/credentials/' );
|
||||
if (mode === 'select') {
|
||||
SelectionInit({ scope: $scope, list: list, url: url, returnToCaller: 1 });
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
$scope.selected = [];
|
||||
}
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function () {
|
||||
var i, j;
|
||||
|
||||
// Cleanup after a delete
|
||||
Wait('stop');
|
||||
$('#prompt-modal').modal('hide');
|
||||
|
||||
list.fields.kind.searchOptions = $scope.credential_kind_options_list;
|
||||
|
||||
// Translate the kind value
|
||||
for (i = 0; i < $scope.credentials.length; i++) {
|
||||
for (j = 0; j < $scope.credential_kind_options_list.length; j++) {
|
||||
if ($scope.credential_kind_options_list[j].value === $scope.credentials[i].kind) {
|
||||
$scope.credentials[i].kind = $scope.credential_kind_options_list[j].label;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
$scope.removeChoicesReady();
|
||||
}
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReadyCredential', function () {
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'credentials',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
$scope.search(list.iterator);
|
||||
});
|
||||
|
||||
// Load the list of options for Kind
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'kind',
|
||||
variable: 'credential_kind_options_list',
|
||||
callback: 'choicesReadyCredential'
|
||||
});
|
||||
|
||||
$scope.addCredential = function () {
|
||||
$state.transitionTo('credentials.add');
|
||||
$scope.addCredential = function() {
|
||||
$state.go('credentials.add');
|
||||
};
|
||||
|
||||
$scope.editCredential = function (id) {
|
||||
$state.transitionTo('credentials.edit', {credential_id: id});
|
||||
$scope.editCredential = function(id) {
|
||||
$state.go('credentials.edit', { credential_id: id });
|
||||
};
|
||||
|
||||
$scope.deleteCredential = function (id, name) {
|
||||
var action = function () {
|
||||
$scope.deleteCredential = function(id, name) {
|
||||
var action = function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
Wait('start');
|
||||
var url = defaultUrl + id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.destroy()
|
||||
.success(function () {
|
||||
.success(function() {
|
||||
|
||||
if (parseInt($state.params.credential_id) === id) {
|
||||
$state.go("^", null, {reload: true});
|
||||
$state.go("^", null, { reload: true });
|
||||
} else {
|
||||
$scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(list.iterator);
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
@ -126,97 +75,74 @@ export function CredentialsList($scope, $rootScope, $location, $log,
|
||||
actionText: 'DELETE'
|
||||
});
|
||||
};
|
||||
|
||||
$scope.$emit('choicesReadyCredential');
|
||||
}
|
||||
|
||||
CredentialsList.$inject = ['$scope', '$rootScope', '$location', '$log',
|
||||
'$stateParams', 'Rest', 'Alert', 'CredentialList', 'generateList', 'Prompt',
|
||||
'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope',
|
||||
'ProcessErrors', 'GetBasePath', 'SelectionInit', 'GetChoices', 'Wait',
|
||||
'$state', '$filter', 'rbacUiControlService'
|
||||
'$stateParams', 'Rest', 'Alert', 'CredentialList', 'Prompt', 'ClearScope',
|
||||
'ProcessErrors', 'GetBasePath', 'Wait', '$state', '$filter', 'rbacUiControlService', 'Dataset'
|
||||
];
|
||||
|
||||
|
||||
export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, CredentialForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ReturnToCaller, ClearScope, GenerateList, SearchInit, PaginateInit,
|
||||
LookUpInit, OrganizationList, GetBasePath, GetChoices, Empty, KindChange,
|
||||
ClearScope, GetBasePath, GetChoices, Empty, KindChange,
|
||||
OwnerChange, FormSave, $state, CreateSelect2) {
|
||||
ClearScope();
|
||||
|
||||
// Inject dynamic view
|
||||
var form = CredentialForm,
|
||||
generator = GenerateForm,
|
||||
defaultUrl = GetBasePath('credentials'),
|
||||
url;
|
||||
|
||||
$scope.keyEntered = false;
|
||||
$scope.permissionsTooltip = 'Please save before assigning permissions';
|
||||
generator.inject(form, { mode: 'add', related: false, scope: $scope });
|
||||
generator.reset();
|
||||
init();
|
||||
|
||||
// Load the list of options for Kind
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'kind',
|
||||
variable: 'credential_kind_options'
|
||||
});
|
||||
function init() {
|
||||
// Load the list of options for Kind
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'kind',
|
||||
variable: 'credential_kind_options'
|
||||
});
|
||||
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'become_method',
|
||||
variable: 'become_options'
|
||||
});
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'become_method',
|
||||
variable: 'become_options'
|
||||
});
|
||||
|
||||
CreateSelect2({
|
||||
element: '#credential_become_method',
|
||||
multiple: false
|
||||
});
|
||||
CreateSelect2({
|
||||
element: '#credential_become_method',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
CreateSelect2({
|
||||
element: '#credential_kind',
|
||||
multiple: false
|
||||
});
|
||||
CreateSelect2({
|
||||
element: '#credential_kind',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
$scope.canShareCredential = false;
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
$rootScope.$watch('current_user', function(){
|
||||
try {
|
||||
if ($rootScope.current_user.is_superuser) {
|
||||
$scope.canShareCredential = true;
|
||||
} else {
|
||||
Rest.setUrl(`/api/v1/users/${$rootScope.current_user.id}/admin_of_organizations`);
|
||||
Rest.get()
|
||||
.success(function(data) {
|
||||
$scope.canShareCredential = (data.count) ? true : false;
|
||||
}).error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to find if users is admin of org' + status });
|
||||
});
|
||||
}
|
||||
$scope.keyEntered = false;
|
||||
$scope.permissionsTooltip = 'Please save before assigning permissions';
|
||||
|
||||
|
||||
var orgUrl = ($rootScope.current_user.is_superuser) ?
|
||||
GetBasePath("organizations") :
|
||||
$rootScope.current_user.url + "admin_of_organizations?";
|
||||
|
||||
// Create LookUpInit for organizations
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: orgUrl,
|
||||
form: form,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio',
|
||||
autopopulateLookup: false
|
||||
});
|
||||
// determine if the currently logged-in user may share this credential
|
||||
// previous commentary said: "$rootScope.current_user isn't available because a call to the config endpoint hasn't finished resolving yet"
|
||||
// I'm 99% sure this state's will never resolve block will be rejected if setup surrounding config endpoint hasn't completed
|
||||
if ($rootScope.current_user && $rootScope.current_user.is_superuser) {
|
||||
$scope.canShareCredential = true;
|
||||
} else {
|
||||
Rest.setUrl(`/api/v1/users/${$rootScope.current_user.id}/admin_of_organizations`);
|
||||
Rest.get()
|
||||
.success(function(data) {
|
||||
$scope.canShareCredential = (data.count) ? true : false;
|
||||
}).error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to find if users is admin of org' + status });
|
||||
});
|
||||
}
|
||||
catch(err){
|
||||
// $rootScope.current_user isn't available because a call to the config endpoint hasn't finished resolving yet
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
if (!Empty($stateParams.user_id)) {
|
||||
// Get the username based on incoming route
|
||||
@ -226,10 +152,10 @@ export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
url = GetBasePath('users') + $stateParams.user_id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
$scope.user_username = data.username;
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to retrieve user. GET status: ' + status });
|
||||
});
|
||||
} else if (!Empty($stateParams.team_id)) {
|
||||
@ -240,10 +166,10 @@ export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
url = GetBasePath('teams') + $stateParams.team_id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
$scope.team_name = data.name;
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to retrieve team. GET status: ' + status });
|
||||
});
|
||||
} else {
|
||||
@ -263,32 +189,30 @@ export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
});
|
||||
|
||||
// Handle Kind change
|
||||
$scope.kindChange = function () {
|
||||
$scope.kindChange = function() {
|
||||
KindChange({ scope: $scope, form: form, reset: true });
|
||||
};
|
||||
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
generator.clearApiErrors();
|
||||
generator.checkAutoFill();
|
||||
$scope.formSave = function() {
|
||||
if ($scope[form.name + '_form'].$valid) {
|
||||
FormSave({ scope: $scope, mode: 'add' });
|
||||
}
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('credentials');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('credentials');
|
||||
};
|
||||
|
||||
// Password change
|
||||
$scope.clearPWConfirm = function (fld) {
|
||||
$scope.clearPWConfirm = function(fld) {
|
||||
// If password value changes, make sure password_confirm must be re-entered
|
||||
$scope[fld] = '';
|
||||
$scope[form.name + '_form'][fld].$setValidity('awpassmatch', false);
|
||||
};
|
||||
|
||||
// Respond to 'Ask at runtime?' checkbox
|
||||
$scope.ask = function (fld, associated) {
|
||||
$scope.ask = function(fld, associated) {
|
||||
if ($scope[fld + '_ask']) {
|
||||
$scope[fld] = 'ASK';
|
||||
$("#" + form.name + "_" + fld + "_input").attr("type", "text");
|
||||
@ -313,7 +237,7 @@ export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
};
|
||||
|
||||
// Click clear button
|
||||
$scope.clear = function (fld, associated) {
|
||||
$scope.clear = function(fld, associated) {
|
||||
$scope[fld] = '';
|
||||
$scope[associated] = '';
|
||||
$scope[form.name + '_form'][associated].$setValidity('awpassmatch', true);
|
||||
@ -324,54 +248,88 @@ export function CredentialsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
|
||||
CredentialsAdd.$inject = ['$scope', '$rootScope', '$compile', '$location',
|
||||
'$log', '$stateParams', 'CredentialForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'generateList',
|
||||
'SearchInit', 'PaginateInit', 'LookUpInit', 'OrganizationList',
|
||||
'GetBasePath', 'GetChoices', 'Empty', 'KindChange', 'OwnerChange',
|
||||
'FormSave', '$state', 'CreateSelect2'
|
||||
'ProcessErrors', 'ClearScope', 'GetBasePath', 'GetChoices', 'Empty', 'KindChange',
|
||||
'OwnerChange', 'FormSave', '$state', 'CreateSelect2'
|
||||
];
|
||||
|
||||
|
||||
export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, CredentialForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
RelatedSearchInit, RelatedPaginateInit, ReturnToCaller, ClearScope, Prompt,
|
||||
GetBasePath, GetChoices, KindChange, OrganizationList, LookUpInit, Empty,
|
||||
OwnerChange, FormSave, Wait, $state, CreateSelect2, Authorization) {
|
||||
if (!$rootScope.current_user) {
|
||||
Authorization.restoreUserInfo();
|
||||
}
|
||||
$stateParams, CredentialForm, Rest, Alert, ProcessErrors, ClearScope, Prompt,
|
||||
GetBasePath, GetChoices, KindChange, Empty, OwnerChange, FormSave, Wait,
|
||||
$state, CreateSelect2, Authorization) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
var defaultUrl = GetBasePath('credentials'),
|
||||
generator = GenerateForm,
|
||||
form = CredentialForm,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
master = {},
|
||||
id = $stateParams.credential_id,
|
||||
relatedSets = {};
|
||||
id = $stateParams.credential_id;
|
||||
|
||||
generator.inject(form, { mode: 'edit', related: true, scope: $scope });
|
||||
generator.reset();
|
||||
$scope.id = id;
|
||||
init();
|
||||
|
||||
$scope.$watch('credential_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
function init() {
|
||||
$scope.id = id;
|
||||
$scope.$watch('credential_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
|
||||
$scope.canShareCredential = false;
|
||||
Wait('start');
|
||||
if (!$rootScope.current_user) {
|
||||
Authorization.restoreUserInfo();
|
||||
}
|
||||
});
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'kind',
|
||||
variable: 'credential_kind_options',
|
||||
callback: 'choicesReadyCredential'
|
||||
});
|
||||
|
||||
$scope.canShareCredential = false;
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'become_method',
|
||||
variable: 'become_options'
|
||||
});
|
||||
|
||||
if ($rootScope.current_user.is_superuser) {
|
||||
$scope.canShareCredential = true;
|
||||
} else {
|
||||
Rest.setUrl(`/api/v1/users/${$rootScope.current_user.id}/admin_of_organizations`);
|
||||
Rest.get()
|
||||
.success(function(data) {
|
||||
$scope.canShareCredential = (data.count) ? true : false;
|
||||
}).error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to find if users is admin of org' + status });
|
||||
});
|
||||
if ($rootScope.current_user && $rootScope.current_user.is_superuser) {
|
||||
$scope.canShareCredential = true;
|
||||
} else {
|
||||
Rest.setUrl(`/api/v1/users/${$rootScope.current_user.id}/admin_of_organizations`);
|
||||
Rest.get()
|
||||
.success(function(data) {
|
||||
$scope.canShareCredential = (data.count) ? true : false;
|
||||
}).error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to find if users is admin of org' + status });
|
||||
});
|
||||
}
|
||||
|
||||
// if the credential is assigned to an organization, allow permission delegation
|
||||
// do NOT use $scope.organization in a view directive to determine if a credential is associated with an org
|
||||
// @todo why not? ^ and what is this type check for a number doing - should this be a type check for undefined?
|
||||
$scope.disablePermissionAssignment = typeof($scope.organization) === 'number' ? false : true;
|
||||
if ($scope.disablePermissionAssignment) {
|
||||
$scope.permissionsTooltip = 'Credentials are only shared within an organization. Assign credentials to an organization to delegate credential permissions. The organization cannot be edited after credentials are assigned.';
|
||||
}
|
||||
setAskCheckboxes();
|
||||
KindChange({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
reset: false
|
||||
});
|
||||
OwnerChange({ scope: $scope });
|
||||
$scope.$watch("ssh_key_data", function(val) {
|
||||
if (val === "" || val === null || val === undefined) {
|
||||
$scope.keyEntered = false;
|
||||
$scope.ssh_key_unlock_ask = false;
|
||||
$scope.ssh_key_unlock = "";
|
||||
} else {
|
||||
$scope.keyEntered = true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function setAskCheckboxes() {
|
||||
@ -398,64 +356,14 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ($scope.removeCredentialLoaded) {
|
||||
$scope.removeCredentialLoaded();
|
||||
}
|
||||
$scope.removeCredentialLoaded = $scope.$on('credentialLoaded', function () {
|
||||
// if the credential is assigned to an organization, allow permission delegation
|
||||
// do NOT use $scope.organization in a view directive to determine if a credential is associated with an org
|
||||
$scope.disablePermissionAssignment = typeof($scope.organization) === 'number' ? false : true;
|
||||
if ($scope.disablePermissionAssignment){
|
||||
$scope.permissionsTooltip = 'Credentials are only shared within an organization. Assign credentials to an organization to delegate credential permissions. The organization cannot be edited after credentials are assigned.';
|
||||
}
|
||||
var set;
|
||||
for (set in relatedSets) {
|
||||
$scope.search(relatedSets[set].iterator);
|
||||
}
|
||||
var orgUrl = ($rootScope.current_user.is_superuser) ?
|
||||
GetBasePath("organizations") :
|
||||
$rootScope.current_user.url + "admin_of_organizations?";
|
||||
|
||||
// create LookUpInit for organizations
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: orgUrl,
|
||||
form: form,
|
||||
current_item: $scope.organization,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio',
|
||||
autopopulateLookup: false
|
||||
});
|
||||
|
||||
setAskCheckboxes();
|
||||
KindChange({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
reset: false
|
||||
});
|
||||
OwnerChange({ scope: $scope });
|
||||
$scope.$watch("ssh_key_data", function(val) {
|
||||
if (val === "" || val === null || val === undefined) {
|
||||
$scope.keyEntered = false;
|
||||
$scope.ssh_key_unlock_ask = false;
|
||||
$scope.ssh_key_unlock = "";
|
||||
} else {
|
||||
$scope.keyEntered = true;
|
||||
}
|
||||
});
|
||||
Wait('stop');
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
$scope.removeChoicesReady();
|
||||
}
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReadyCredential', function () {
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReadyCredential', function() {
|
||||
// Retrieve detail record and prepopulate the form
|
||||
Rest.setUrl(defaultUrl + ':id/');
|
||||
Rest.get({ params: { id: id } })
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
if (data && data.summary_fields &&
|
||||
data.summary_fields.organization &&
|
||||
data.summary_fields.organization.id) {
|
||||
@ -481,7 +389,6 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField];
|
||||
}
|
||||
}
|
||||
relatedSets = form.relatedSets(data.related);
|
||||
|
||||
if (!Empty($scope.user)) {
|
||||
$scope.owner = 'user';
|
||||
@ -530,118 +437,93 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
});
|
||||
|
||||
switch (data.kind) {
|
||||
case 'aws':
|
||||
$scope.access_key = data.username;
|
||||
$scope.secret_key = data.password;
|
||||
master.access_key = $scope.access_key;
|
||||
master.secret_key = $scope.secret_key;
|
||||
break;
|
||||
case 'ssh':
|
||||
$scope.ssh_password = data.password;
|
||||
master.ssh_password = $scope.ssh_password;
|
||||
break;
|
||||
case 'rax':
|
||||
$scope.api_key = data.password;
|
||||
master.api_key = $scope.api_key;
|
||||
break;
|
||||
case 'gce':
|
||||
$scope.email_address = data.username;
|
||||
$scope.project = data.project;
|
||||
break;
|
||||
case 'azure':
|
||||
$scope.subscription = data.username;
|
||||
break;
|
||||
case 'aws':
|
||||
$scope.access_key = data.username;
|
||||
$scope.secret_key = data.password;
|
||||
master.access_key = $scope.access_key;
|
||||
master.secret_key = $scope.secret_key;
|
||||
break;
|
||||
case 'ssh':
|
||||
$scope.ssh_password = data.password;
|
||||
master.ssh_password = $scope.ssh_password;
|
||||
break;
|
||||
case 'rax':
|
||||
$scope.api_key = data.password;
|
||||
master.api_key = $scope.api_key;
|
||||
break;
|
||||
case 'gce':
|
||||
$scope.email_address = data.username;
|
||||
$scope.project = data.project;
|
||||
break;
|
||||
case 'azure':
|
||||
$scope.subscription = data.username;
|
||||
break;
|
||||
}
|
||||
$scope.credential_obj = data;
|
||||
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
$scope.$emit('credentialLoaded');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to retrieve Credential: ' + $stateParams.id + '. GET status: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to retrieve Credential: ' + $stateParams.id + '. GET status: ' + status
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
Wait('start');
|
||||
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'kind',
|
||||
variable: 'credential_kind_options',
|
||||
callback: 'choicesReadyCredential'
|
||||
});
|
||||
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'become_method',
|
||||
variable: 'become_options'
|
||||
});
|
||||
|
||||
// Save changes to the parent
|
||||
$scope.formSave = function () {
|
||||
generator.clearApiErrors();
|
||||
generator.checkAutoFill({ scope: $scope });
|
||||
$scope.formSave = function() {
|
||||
if ($scope[form.name + '_form'].$valid) {
|
||||
FormSave({ scope: $scope, mode: 'edit' });
|
||||
}
|
||||
};
|
||||
|
||||
// Handle Owner change
|
||||
$scope.ownerChange = function () {
|
||||
$scope.ownerChange = function() {
|
||||
OwnerChange({ scope: $scope });
|
||||
};
|
||||
|
||||
// Handle Kind change
|
||||
$scope.kindChange = function () {
|
||||
$scope.kindChange = function() {
|
||||
KindChange({ scope: $scope, form: form, reset: true });
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$scope.formCancel = function() {
|
||||
$state.transitionTo('credentials');
|
||||
};
|
||||
|
||||
// Related set: Add button
|
||||
$scope.add = function (set) {
|
||||
$scope.add = function(set) {
|
||||
$rootScope.flashMessage = null;
|
||||
$location.path('/' + base + '/' + $stateParams.id + '/' + set + '/add');
|
||||
};
|
||||
|
||||
// Related set: Edit button
|
||||
$scope.edit = function (set, id) {
|
||||
$scope.edit = function(set, id) {
|
||||
$rootScope.flashMessage = null;
|
||||
$location.path('/' + base + '/' + $stateParams.id + '/' + set + '/' + id);
|
||||
};
|
||||
|
||||
// Related set: Delete button
|
||||
$scope['delete'] = function (set, itm_id, name, title) {
|
||||
$scope['delete'] = function(set, itm_id, name, title) {
|
||||
$rootScope.flashMessage = null;
|
||||
|
||||
var action = function () {
|
||||
var action = function() {
|
||||
var url = defaultUrl + id + '/' + set + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.post({
|
||||
id: itm_id,
|
||||
disassociate: 1
|
||||
})
|
||||
.success(function () {
|
||||
$('#prompt-modal').modal('hide');
|
||||
$scope.search(form.related[set].iterator);
|
||||
id: itm_id,
|
||||
disassociate: 1
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.success(function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(form.related[set].iterator);
|
||||
})
|
||||
.error(function(data, status) {
|
||||
$('#prompt-modal').modal('hide');
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. POST returned status: ' + status
|
||||
});
|
||||
});
|
||||
@ -657,14 +539,14 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
};
|
||||
|
||||
// Password change
|
||||
$scope.clearPWConfirm = function (fld) {
|
||||
$scope.clearPWConfirm = function(fld) {
|
||||
// If password value changes, make sure password_confirm must be re-entered
|
||||
$scope[fld] = '';
|
||||
$scope[form.name + '_form'][fld].$setValidity('awpassmatch', false);
|
||||
};
|
||||
|
||||
// Respond to 'Ask at runtime?' checkbox
|
||||
$scope.ask = function (fld, associated) {
|
||||
$scope.ask = function(fld, associated) {
|
||||
if ($scope[fld + '_ask']) {
|
||||
$scope[fld] = 'ASK';
|
||||
$("#" + form.name + "_" + fld + "_input").attr("type", "text");
|
||||
@ -688,7 +570,7 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
};
|
||||
|
||||
$scope.clear = function (fld, associated) {
|
||||
$scope.clear = function(fld, associated) {
|
||||
$scope[fld] = '';
|
||||
$scope[associated] = '';
|
||||
$scope[form.name + '_form'][associated].$setValidity('awpassmatch', true);
|
||||
@ -698,9 +580,8 @@ export function CredentialsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
|
||||
CredentialsEdit.$inject = ['$scope', '$rootScope', '$compile', '$location',
|
||||
'$log', '$stateParams', 'CredentialForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'RelatedSearchInit', 'RelatedPaginateInit',
|
||||
'ReturnToCaller', 'ClearScope', 'Prompt', 'GetBasePath', 'GetChoices',
|
||||
'KindChange', 'OrganizationList', 'LookUpInit', 'Empty', 'OwnerChange',
|
||||
'$log', '$stateParams', 'CredentialForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ClearScope', 'Prompt', 'GetBasePath', 'GetChoices',
|
||||
'KindChange', 'Empty', 'OwnerChange',
|
||||
'FormSave', 'Wait', '$state', 'CreateSelect2', 'Authorization'
|
||||
];
|
||||
|
||||
@ -12,15 +12,17 @@
|
||||
|
||||
|
||||
export function JobEventsList($sce, $filter, $scope, $rootScope, $location, $log, $stateParams, Rest, Alert, JobEventList, GenerateList,
|
||||
Prompt, SearchInit, PaginateInit, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath, LookUpInit, ToggleChildren,
|
||||
FormatDate, EventView, Refresh, Wait) {
|
||||
Prompt, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath, LookUpInit, ToggleChildren,
|
||||
FormatDate, EventView, Wait) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
var list = JobEventList,
|
||||
defaultUrl = GetBasePath('jobs') + $stateParams.id + '/job_events/', //?parent__isnull=1';
|
||||
generator = GenerateList,
|
||||
page;
|
||||
generator = GenerateList;
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// var defaultUrl = GetBasePath('jobs') + $stateParams.id + '/job_events/', //?parent__isnull=1';
|
||||
// page;
|
||||
|
||||
list.base = $location.path();
|
||||
$scope.job_id = $stateParams.id;
|
||||
@ -191,30 +193,31 @@ export function JobEventsList($sce, $filter, $scope, $rootScope, $location, $log
|
||||
});
|
||||
});
|
||||
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'jobevents',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
page = ($stateParams.page) ? parseInt($stateParams.page,10) - 1 : null;
|
||||
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl,
|
||||
page: page
|
||||
});
|
||||
|
||||
// Called from Inventories tab, host failed events link:
|
||||
if ($stateParams.host) {
|
||||
$scope[list.iterator + 'SearchField'] = 'host';
|
||||
$scope[list.iterator + 'SearchValue'] = $stateParams.host;
|
||||
$scope[list.iterator + 'SearchFieldLabel'] = list.fields.host.label;
|
||||
}
|
||||
|
||||
$scope.search(list.iterator, $stateParams.page);
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: $scope,
|
||||
// set: 'jobevents',
|
||||
// list: list,
|
||||
// url: defaultUrl
|
||||
// });
|
||||
//
|
||||
// page = ($stateParams.page) ? parseInt($stateParams.page,10) - 1 : null;
|
||||
//
|
||||
// PaginateInit({
|
||||
// scope: $scope,
|
||||
// list: list,
|
||||
// url: defaultUrl,
|
||||
// page: page
|
||||
// });
|
||||
//
|
||||
// // Called from Inventories tab, host failed events link:
|
||||
// if ($stateParams.host) {
|
||||
// $scope[list.iterator + 'SearchField'] = 'host';
|
||||
// $scope[list.iterator + 'SearchValue'] = $stateParams.host;
|
||||
// $scope[list.iterator + 'SearchFieldLabel'] = list.fields.host.label;
|
||||
// }
|
||||
//
|
||||
// $scope.search(list.iterator, $stateParams.page);
|
||||
|
||||
$scope.toggle = function (id) {
|
||||
ToggleChildren({
|
||||
@ -231,21 +234,24 @@ export function JobEventsList($sce, $filter, $scope, $rootScope, $location, $log
|
||||
};
|
||||
|
||||
$scope.refresh = function () {
|
||||
$scope.jobSearchSpin = true;
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.jobSearchSpin = true;
|
||||
$scope.jobLoading = true;
|
||||
Wait('start');
|
||||
Refresh({
|
||||
scope: $scope,
|
||||
set: 'jobevents',
|
||||
iterator: 'jobevent',
|
||||
url: $scope.current_url
|
||||
});
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// Refresh({
|
||||
// scope: $scope,
|
||||
// set: 'jobevents',
|
||||
// iterator: 'jobevent',
|
||||
// url: $scope.current_url
|
||||
// });
|
||||
};
|
||||
}
|
||||
|
||||
JobEventsList.$inject = ['$sce', '$filter', '$scope', '$rootScope', '$location', '$log', '$stateParams', 'Rest', 'Alert', 'JobEventList',
|
||||
'generateList', 'Prompt', 'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope', 'ProcessErrors',
|
||||
'GetBasePath', 'LookUpInit', 'ToggleChildren', 'FormatDate', 'EventView', 'Refresh', 'Wait'
|
||||
'generateList', 'Prompt', 'ReturnToCaller', 'ClearScope', 'ProcessErrors',
|
||||
'GetBasePath', 'LookUpInit', 'ToggleChildren', 'FormatDate', 'EventView', 'Wait'
|
||||
];
|
||||
|
||||
export function JobEventsEdit($scope, $rootScope, $compile, $location, $log, $stateParams, JobEventsForm, GenerateForm,
|
||||
|
||||
@ -12,13 +12,14 @@
|
||||
|
||||
|
||||
export function JobHostSummaryList($scope, $rootScope, $location, $log, $stateParams, Rest, Alert, JobHostList, GenerateList,
|
||||
Prompt, SearchInit, PaginateInit, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath, Refresh,
|
||||
Prompt, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath,
|
||||
JobStatusToolTip) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
var list = JobHostList,
|
||||
defaultUrl = GetBasePath('jobs') + $stateParams.id + '/job_host_summaries/',
|
||||
// @issue: OLD SEARCH
|
||||
// defaultUrl = GetBasePath('jobs') + $stateParams.id + '/job_host_summaries/',
|
||||
view = GenerateList,
|
||||
inventory;
|
||||
|
||||
@ -58,26 +59,27 @@ export function JobHostSummaryList($scope, $rootScope, $location, $log, $statePa
|
||||
$scope.removeJobReady = $scope.$on('JobReady', function() {
|
||||
view.inject(list, { mode: 'edit', scope: $scope });
|
||||
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'jobhosts',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
// Called from Inventories tab, host failed events link:
|
||||
if ($stateParams.host_name) {
|
||||
$scope[list.iterator + 'SearchField'] = 'host';
|
||||
$scope[list.iterator + 'SearchValue'] = $stateParams.host_name;
|
||||
$scope[list.iterator + 'SearchFieldLabel'] = list.fields.host.label;
|
||||
}
|
||||
$scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: $scope,
|
||||
// set: 'jobhosts',
|
||||
// list: list,
|
||||
// url: defaultUrl
|
||||
// });
|
||||
//
|
||||
// PaginateInit({
|
||||
// scope: $scope,
|
||||
// list: list,
|
||||
// url: defaultUrl
|
||||
// });
|
||||
//
|
||||
// // Called from Inventories tab, host failed events link:
|
||||
// if ($stateParams.host_name) {
|
||||
// $scope[list.iterator + 'SearchField'] = 'host';
|
||||
// $scope[list.iterator + 'SearchValue'] = $stateParams.host_name;
|
||||
// $scope[list.iterator + 'SearchFieldLabel'] = list.fields.host.label;
|
||||
// }
|
||||
// $scope.search(list.iterator);
|
||||
});
|
||||
|
||||
Rest.setUrl(GetBasePath('jobs') + $scope.job_id);
|
||||
@ -107,12 +109,13 @@ export function JobHostSummaryList($scope, $rootScope, $location, $log, $statePa
|
||||
};
|
||||
|
||||
$scope.refresh = function () {
|
||||
$scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(list.iterator);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
JobHostSummaryList.$inject = ['$scope', '$rootScope', '$location', '$log', '$stateParams', 'Rest', 'Alert', 'JobHostList',
|
||||
'generateList', 'Prompt', 'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope', 'ProcessErrors',
|
||||
'GetBasePath', 'Refresh', 'JobStatusToolTip', 'Wait'
|
||||
'generateList', 'Prompt', 'ReturnToCaller', 'ClearScope', 'ProcessErrors',
|
||||
'GetBasePath', 'JobStatusToolTip', 'Wait'
|
||||
];
|
||||
|
||||
@ -8,148 +8,105 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Jobs
|
||||
* @description This controller's for the jobs page
|
||||
*/
|
||||
*/
|
||||
|
||||
|
||||
export function JobsListController ($rootScope, $log, $scope, $compile, $stateParams,
|
||||
ClearScope, LoadSchedulesScope,
|
||||
LoadJobsScope, AllJobsList, ScheduledJobsList, GetChoices, GetBasePath, Wait, $state) {
|
||||
|
||||
export function JobsListController($state, $rootScope, $log, $scope, $compile, $stateParams,
|
||||
ClearScope, Find, DeleteJob, RelaunchJob, AllJobsList, ScheduledJobsList, GetBasePath, Dataset) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
var jobs_scope, scheduled_scope,
|
||||
choicesCount = 0,
|
||||
listCount = 0,
|
||||
api_complete = false,
|
||||
scheduledJobsList = _.cloneDeep(ScheduledJobsList);
|
||||
var list = AllJobsList;
|
||||
|
||||
$scope.jobsSelected = true;
|
||||
init();
|
||||
|
||||
if ($scope.removeListLoaded) {
|
||||
$scope.removeListLoaded();
|
||||
function init() {
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
$scope.showJobType = true;
|
||||
|
||||
_.forEach($scope[list.name], buildTooltips);
|
||||
}
|
||||
$scope.removeListLoaded = $scope.$on('listLoaded', function() {
|
||||
listCount++;
|
||||
if (listCount === 2) {
|
||||
api_complete = true;
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
|
||||
// After all choices are ready, load up the lists and populate the page
|
||||
if ($scope.removeBuildJobsList) {
|
||||
$scope.removeBuildJobsList();
|
||||
function buildTooltips(job) {
|
||||
job.status_tip = 'Job ' + job.status + ". Click for details.";
|
||||
}
|
||||
$scope.removeBuildJobsList = $scope.$on('buildJobsList', function() {
|
||||
var opt, search_params={};
|
||||
|
||||
if (AllJobsList.fields.type) {
|
||||
AllJobsList.fields.type.searchOptions = $scope.type_choices;
|
||||
}
|
||||
if ($stateParams.status) {
|
||||
search_params[AllJobsList.iterator + 'SearchField'] = 'status';
|
||||
search_params[AllJobsList.iterator + 'SelectShow'] = true;
|
||||
search_params[AllJobsList.iterator + 'SearchSelectOpts'] = AllJobsList.fields.status.searchOptions;
|
||||
search_params[AllJobsList.iterator + 'SearchFieldLabel'] = AllJobsList.fields.status.label.replace(/<br\>/g,' ');
|
||||
search_params[AllJobsList.iterator + 'SearchType'] = '';
|
||||
for (opt in AllJobsList.fields.status.searchOptions) {
|
||||
if (AllJobsList.fields.status.searchOptions[opt].value === $stateParams.status) {
|
||||
search_params[AllJobsList.iterator + 'SearchSelectValue'] = AllJobsList.fields.status.searchOptions[opt];
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
jobs_scope = $scope.$new(true);
|
||||
$scope.deleteJob = function(id) {
|
||||
DeleteJob({ scope: $scope, id: id });
|
||||
};
|
||||
|
||||
jobs_scope.viewJob = function (id) {
|
||||
$state.transitionTo('jobDetail', {id: id});
|
||||
$scope.relaunchJob = function(event, id) {
|
||||
var list, job, typeId;
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
} catch (e) {
|
||||
//ignore
|
||||
}
|
||||
|
||||
job = Find({ list: list, key: 'id', val: id });
|
||||
if (job.type === 'inventory_update') {
|
||||
typeId = job.inventory_source;
|
||||
} else if (job.type === 'project_update') {
|
||||
typeId = job.project;
|
||||
} else if (job.type === 'job' || job.type === "system_job" || job.type === 'ad_hoc_command') {
|
||||
typeId = job.id;
|
||||
}
|
||||
RelaunchJob({ scope: $scope, id: typeId, type: job.type, name: job.name });
|
||||
};
|
||||
|
||||
$scope.refreshJobs = function() {
|
||||
$state.go('.', null, { reload: true });
|
||||
};
|
||||
|
||||
$scope.viewJobDetails = function(job) {
|
||||
|
||||
var goToJobDetails = function(state) {
|
||||
$state.go(state, { id: job.id }, { reload: true });
|
||||
};
|
||||
|
||||
jobs_scope.showJobType = true;
|
||||
LoadJobsScope({
|
||||
parent_scope: $scope,
|
||||
scope: jobs_scope,
|
||||
list: AllJobsList,
|
||||
id: 'active-jobs',
|
||||
url: GetBasePath('unified_jobs') + '?status__in=pending,waiting,running,completed,failed,successful,error,canceled,new&order_by=-finished',
|
||||
pageSize: 20,
|
||||
searchParams: search_params,
|
||||
spinner: false
|
||||
});
|
||||
|
||||
|
||||
scheduled_scope = $scope.$new(true);
|
||||
scheduledJobsList.basePath = GetBasePath('schedules') + '?next_run__isnull=false';
|
||||
LoadSchedulesScope({
|
||||
parent_scope: $scope,
|
||||
scope: scheduled_scope,
|
||||
list: scheduledJobsList,
|
||||
pageSize: 20,
|
||||
id: 'scheduled-jobs-tab',
|
||||
searchSize: 'col-lg-4 col-md-4 col-sm-4 col-xs-12',
|
||||
url: scheduledJobsList.basePath
|
||||
});
|
||||
|
||||
$scope.refreshJobs = function() {
|
||||
jobs_scope.search('all_job');
|
||||
scheduled_scope.search('schedule');
|
||||
};
|
||||
|
||||
function clearTabs() {
|
||||
$scope.jobsSelected = false;
|
||||
$scope.schedulesSelected = false;
|
||||
}
|
||||
|
||||
$scope.toggleTab = function(tab) {
|
||||
clearTabs();
|
||||
if (tab === "jobs") {
|
||||
$scope.jobsSelected = true;
|
||||
} else if (tab === "scheduled") {
|
||||
$scope.schedulesSelected = true;
|
||||
}
|
||||
};
|
||||
|
||||
$scope.$on('ws-jobs', function() {
|
||||
$scope.refreshJobs();
|
||||
});
|
||||
|
||||
$scope.$on('ws-schedules', function() {
|
||||
if (api_complete) {
|
||||
scheduled_scope.search('schedule');
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
$scope.removeChoicesReady();
|
||||
}
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReady', function() {
|
||||
choicesCount++;
|
||||
if (choicesCount === 2) {
|
||||
$scope.$emit('buildJobsList');
|
||||
switch (job.type) {
|
||||
case 'job':
|
||||
goToJobDetails('jobDetail');
|
||||
break;
|
||||
case 'ad_hoc_command':
|
||||
goToJobDetails('adHocJobStdout');
|
||||
break;
|
||||
case 'system_job':
|
||||
goToJobDetails('managementJobStdout');
|
||||
break;
|
||||
case 'project_update':
|
||||
goToJobDetails('scmUpdateStdout');
|
||||
break;
|
||||
case 'inventory_update':
|
||||
goToJobDetails('inventorySyncStdout');
|
||||
break;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
$scope.refreshJobs = function() {
|
||||
$state.reload();
|
||||
};
|
||||
|
||||
if ($rootScope.removeJobStatusChange) {
|
||||
$rootScope.removeJobStatusChange();
|
||||
}
|
||||
$rootScope.removeJobStatusChange = $rootScope.$on('JobStatusChange-jobs', function() {
|
||||
$scope.refreshJobs();
|
||||
});
|
||||
|
||||
Wait('start');
|
||||
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: GetBasePath('unified_jobs'),
|
||||
field: 'status',
|
||||
variable: 'status_choices',
|
||||
callback: 'choicesReady'
|
||||
});
|
||||
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: GetBasePath('unified_jobs'),
|
||||
field: 'type',
|
||||
variable: 'type_choices',
|
||||
callback: 'choicesReady'
|
||||
if ($rootScope.removeScheduleStatusChange) {
|
||||
$rootScope.removeScheduleStatusChange();
|
||||
}
|
||||
$rootScope.removeScheduleStatusChange = $rootScope.$on('ScheduleStatusChange', function() {
|
||||
$state.reload();
|
||||
});
|
||||
}
|
||||
|
||||
JobsListController.$inject = ['$rootScope', '$log', '$scope', '$compile', '$stateParams',
|
||||
'ClearScope', 'LoadSchedulesScope', 'LoadJobsScope',
|
||||
'AllJobsList', 'ScheduledJobsList', 'GetChoices', 'GetBasePath', 'Wait', '$state'];
|
||||
JobsListController.$inject = ['$state', '$rootScope', '$log', '$scope', '$compile', '$stateParams',
|
||||
'ClearScope', 'Find', 'DeleteJob', 'RelaunchJob', 'AllJobsList', 'ScheduledJobsList', 'GetBasePath', 'Dataset'
|
||||
];
|
||||
|
||||
@ -8,85 +8,64 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Projects
|
||||
* @description This controller's for the projects page
|
||||
*/
|
||||
*/
|
||||
|
||||
|
||||
export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
Rest, Alert, ProjectList, GenerateList, Prompt, SearchInit,
|
||||
PaginateInit, ReturnToCaller, ClearScope, ProcessErrors, GetBasePath,
|
||||
SelectionInit, ProjectUpdate, Refresh, Wait, GetChoices, Empty,
|
||||
Find, GetProjectIcon, GetProjectToolTip, $filter, $state, rbacUiControlService,
|
||||
i18n) {
|
||||
ClearScope();
|
||||
|
||||
$scope.canAdd = false;
|
||||
|
||||
rbacUiControlService.canAdd('projects')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
Wait('start');
|
||||
export function ProjectsList($scope, $rootScope, $location, $log, $stateParams,
|
||||
Rest, Alert, ProjectList, Prompt, ReturnToCaller, ClearScope, ProcessErrors,
|
||||
GetBasePath, ProjectUpdate, Wait, GetChoices, Empty, Find, GetProjectIcon,
|
||||
GetProjectToolTip, $filter, $state, rbacUiControlService, Dataset, i18n) {
|
||||
|
||||
var list = ProjectList,
|
||||
defaultUrl = GetBasePath('projects') + ($stateParams.status ? '?status__in=' + $stateParams.status : ''),
|
||||
view = GenerateList,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
mode = (base === 'projects') ? 'edit' : 'select',
|
||||
url = (base === 'teams') ? GetBasePath('teams') + $stateParams.team_id + '/projects/' : defaultUrl,
|
||||
choiceCount = 0;
|
||||
view.inject(list, { mode: mode, scope: $scope });
|
||||
defaultUrl = GetBasePath('projects');
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
$scope.projectLoading = true;
|
||||
init();
|
||||
|
||||
if (mode === 'select') {
|
||||
SelectionInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: url,
|
||||
returnToCaller: 1
|
||||
});
|
||||
}
|
||||
function init() {
|
||||
$scope.canAdd = false;
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function () {
|
||||
Wait('stop');
|
||||
if ($scope.projects) {
|
||||
$scope.projects.forEach(function(project, i) {
|
||||
$scope.projects[i].statusIcon = GetProjectIcon(project.status);
|
||||
$scope.projects[i].statusTip = GetProjectToolTip(project.status);
|
||||
$scope.projects[i].scm_update_tooltip = i18n._("Start an SCM update");
|
||||
$scope.projects[i].scm_schedule_tooltip = i18n._("Schedule future SCM updates");
|
||||
$scope.projects[i].scm_type_class = "";
|
||||
|
||||
if (project.status === 'failed' && project.summary_fields.last_update && project.summary_fields.last_update.status === 'canceled') {
|
||||
$scope.projects[i].statusTip = i18n._('Canceled. Click for details');
|
||||
}
|
||||
|
||||
if (project.status === 'running' || project.status === 'updating') {
|
||||
$scope.projects[i].scm_update_tooltip = i18n._("SCM update currently running");
|
||||
$scope.projects[i].scm_type_class = "btn-disabled";
|
||||
}
|
||||
|
||||
$scope.project_scm_type_options.forEach(function(type) {
|
||||
if (type.value === project.scm_type) {
|
||||
$scope.projects[i].scm_type = type.label;
|
||||
if (type.label === 'Manual') {
|
||||
$scope.projects[i].scm_update_tooltip = i18n._('Manual projects do not require an SCM update');
|
||||
$scope.projects[i].scm_schedule_tooltip = i18n._('Manual projects do not require a schedule');
|
||||
$scope.projects[i].scm_type_class = 'btn-disabled';
|
||||
$scope.projects[i].statusTip = i18n._('Not configured for SCM');
|
||||
$scope.projects[i].statusIcon = 'none';
|
||||
}
|
||||
}
|
||||
});
|
||||
rbacUiControlService.canAdd('projects')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
}
|
||||
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
_.forEach($scope[list.name], buildTooltips);
|
||||
$rootScope.flashMessage = null;
|
||||
}
|
||||
|
||||
$scope.$watch(`${list.name}`, function() {
|
||||
_.forEach($scope[list.name], buildTooltips);
|
||||
});
|
||||
|
||||
function buildTooltips(project) {
|
||||
project.statusIcon = GetProjectIcon(project.status);
|
||||
project.statusTip = GetProjectToolTip(project.status);
|
||||
project.scm_update_tooltip = "Start an SCM update";
|
||||
project.scm_schedule_tooltip = i18n._("Schedule future SCM updates");
|
||||
project.scm_type_class = "";
|
||||
|
||||
if (project.status === 'failed' && project.summary_fields.last_update && project.summary_fields.last_update.status === 'canceled') {
|
||||
project.statusTip = i18n._('Canceled. Click for details');
|
||||
}
|
||||
|
||||
if (project.status === 'running' || project.status === 'updating') {
|
||||
project.scm_update_tooltip = i18n._("SCM update currently running");
|
||||
project.scm_type_class = "btn-disabled";
|
||||
}
|
||||
if (project.scm_type === 'manual') {
|
||||
project.scm_update_tooltip = i18n._('Manual projects do not require an SCM update');
|
||||
project.scm_schedule_tooltip = i18n._('Manual projects do not require a schedule');
|
||||
project.scm_type_class = 'btn-disabled';
|
||||
project.statusTip = i18n._('Not configured for SCM');
|
||||
project.statusIcon = 'none';
|
||||
}
|
||||
}
|
||||
|
||||
$scope.$on(`ws-jobs`, function(e, data) {
|
||||
var project;
|
||||
$log.debug(data);
|
||||
@ -98,9 +77,9 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
$log.debug('Received event for project: ' + project.name);
|
||||
$log.debug('Status changed to: ' + data.status);
|
||||
if (data.status === 'successful' || data.status === 'failed') {
|
||||
$scope.search(list.iterator, null, null, null, null, false);
|
||||
}
|
||||
else {
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(list.iterator, null, null, null, null, false);
|
||||
} else {
|
||||
project.scm_update_tooltip = "SCM update currently running";
|
||||
project.scm_type_class = "btn-disabled";
|
||||
}
|
||||
@ -111,95 +90,12 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
}
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesHere) {
|
||||
$scope.removeChoicesHere();
|
||||
}
|
||||
$scope.removeChoicesHere = $scope.$on('choicesCompleteProjectList', function () {
|
||||
var opt;
|
||||
|
||||
list.fields.scm_type.searchOptions = $scope.project_scm_type_options;
|
||||
list.fields.status.searchOptions = $scope.project_status_options;
|
||||
|
||||
if ($stateParams.scm_type && $stateParams.status) {
|
||||
// Request coming from home page. User wants all errors for an scm_type
|
||||
defaultUrl += '?status=' + $stateParams.status;
|
||||
}
|
||||
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'projects',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
if ($stateParams.scm_type) {
|
||||
$scope[list.iterator + 'SearchType'] = '';
|
||||
$scope[list.iterator + 'SearchField'] = 'scm_type';
|
||||
$scope[list.iterator + 'SelectShow'] = true;
|
||||
$scope[list.iterator + 'SearchSelectOpts'] = list.fields.scm_type.searchOptions;
|
||||
$scope[list.iterator + 'SearchFieldLabel'] = list.fields.scm_type.label.replace(/<br\>/g, ' ');
|
||||
for (opt in list.fields.scm_type.searchOptions) {
|
||||
if (list.fields.scm_type.searchOptions[opt].value === $stateParams.scm_type) {
|
||||
$scope[list.iterator + 'SearchSelectValue'] = list.fields.scm_type.searchOptions[opt];
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else if ($stateParams.status) {
|
||||
$scope[list.iterator + 'SearchType'] = '';
|
||||
$scope[list.iterator + 'SearchValue'] = $stateParams.status;
|
||||
$scope[list.iterator + 'SearchField'] = 'status';
|
||||
$scope[list.iterator + 'SelectShow'] = true;
|
||||
$scope[list.iterator + 'SearchFieldLabel'] = list.fields.status.label;
|
||||
$scope[list.iterator + 'SearchSelectOpts'] = list.fields.status.searchOptions;
|
||||
for (opt in list.fields.status.searchOptions) {
|
||||
if (list.fields.status.searchOptions[opt].value === $stateParams.status) {
|
||||
$scope[list.iterator + 'SearchSelectValue'] = list.fields.status.searchOptions[opt];
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
$scope.search(list.iterator);
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesReadyList) {
|
||||
$scope.removeChoicesReadyList();
|
||||
}
|
||||
$scope.removeChoicesReadyList = $scope.$on('choicesReadyProjectList', function () {
|
||||
choiceCount++;
|
||||
if (choiceCount === 2) {
|
||||
$scope.$emit('choicesCompleteProjectList');
|
||||
}
|
||||
});
|
||||
|
||||
// Load options for status --used in search
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'status',
|
||||
variable: 'project_status_options',
|
||||
callback: 'choicesReadyProjectList'
|
||||
});
|
||||
|
||||
// Load the list of options for Kind
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: defaultUrl,
|
||||
field: 'scm_type',
|
||||
variable: 'project_scm_type_options',
|
||||
callback: 'choicesReadyProjectList'
|
||||
});
|
||||
|
||||
$scope.addProject = function () {
|
||||
$state.transitionTo('projects.add');
|
||||
$scope.addProject = function() {
|
||||
$state.go('projects.add');
|
||||
};
|
||||
|
||||
$scope.editProject = function (id) {
|
||||
$state.transitionTo('projects.edit', {id: id});
|
||||
$scope.editProject = function(id) {
|
||||
$state.go('projects.edit', { project_id: id });
|
||||
};
|
||||
|
||||
if ($scope.removeGoToJobDetails) {
|
||||
@ -213,7 +109,7 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
// Grab the id from summary_fields
|
||||
var id = (data.summary_fields.current_update) ? data.summary_fields.current_update.id : data.summary_fields.last_update.id;
|
||||
|
||||
$state.go('scmUpdateStdout', {id: id});
|
||||
$state.go('scmUpdateStdout', { id: id });
|
||||
|
||||
} else {
|
||||
Alert(i18n._('No Updates Available'), i18n._('There is no SCM update information available for this project. An update has not yet been ' +
|
||||
@ -221,7 +117,7 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
}
|
||||
});
|
||||
|
||||
$scope.showSCMStatus = function (id) {
|
||||
$scope.showSCMStatus = function(id) {
|
||||
// Refresh the project list
|
||||
var project = Find({ list: $scope.projects, key: 'id', val: id });
|
||||
if (Empty(project.scm_type) || project.scm_type === 'Manual') {
|
||||
@ -241,18 +137,19 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
}
|
||||
};
|
||||
|
||||
$scope.deleteProject = function (id, name) {
|
||||
var action = function () {
|
||||
$scope.deleteProject = function(id, name) {
|
||||
var action = function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
Wait('start');
|
||||
var url = defaultUrl + id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.destroy()
|
||||
.success(function () {
|
||||
if (parseInt($state.params.id) === id) {
|
||||
$state.go("^", null, {reload: true});
|
||||
.success(function() {
|
||||
if (parseInt($state.params.project_id) === id) {
|
||||
$state.go("^", null, { reload: true });
|
||||
} else {
|
||||
$scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(list.iterator);
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
@ -272,7 +169,7 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
if ($scope.removeCancelUpdate) {
|
||||
$scope.removeCancelUpdate();
|
||||
}
|
||||
$scope.removeCancelUpdate = $scope.$on('Cancel_Update', function (e, url) {
|
||||
$scope.removeCancelUpdate = $scope.$on('Cancel_Update', function(e, url) {
|
||||
// Cancel the project update process
|
||||
Rest.setUrl(url);
|
||||
Rest.post()
|
||||
@ -288,12 +185,12 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
if ($scope.removeCheckCancel) {
|
||||
$scope.removeCheckCancel();
|
||||
}
|
||||
$scope.removeCheckCancel = $scope.$on('Check_Cancel', function (e, data) {
|
||||
$scope.removeCheckCancel = $scope.$on('Check_Cancel', function(e, data) {
|
||||
// Check that we 'can' cancel the update
|
||||
var url = data.related.cancel;
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
if (data.can_cancel) {
|
||||
$scope.$emit('Cancel_Update', url);
|
||||
} else {
|
||||
@ -306,14 +203,14 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
});
|
||||
});
|
||||
|
||||
$scope.cancelUpdate = function (id, name) {
|
||||
$scope.cancelUpdate = function(id, name) {
|
||||
Rest.setUrl(GetBasePath("projects") + id);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
if (data.related.current_update) {
|
||||
Rest.setUrl(data.related.current_update);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
$scope.$emit('Check_Cancel', data);
|
||||
})
|
||||
.error(function (data, status) {
|
||||
@ -331,15 +228,10 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
});
|
||||
};
|
||||
|
||||
$scope.refresh = function () {
|
||||
$scope.search(list.iterator);
|
||||
};
|
||||
|
||||
$scope.SCMUpdate = function (project_id, event) {
|
||||
$scope.SCMUpdate = function(project_id, event) {
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
}
|
||||
catch(e) {
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
$scope.projects.every(function(project) {
|
||||
@ -362,62 +254,52 @@ export function ProjectsList ($scope, $rootScope, $location, $log, $stateParams,
|
||||
$scope.editSchedules = function(id) {
|
||||
var project = Find({ list: $scope.projects, key: 'id', val: id });
|
||||
if (!(project.scm_type === "Manual" || Empty(project.scm_type)) && !(project.status === 'updating' || project.status === 'running' || project.status === 'pending')) {
|
||||
$state.go('projectSchedules', {id: id});
|
||||
$state.go('projectSchedules', { id: id });
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
ProjectsList.$inject = ['$scope', '$rootScope', '$location', '$log',
|
||||
'$stateParams', 'Rest', 'Alert', 'ProjectList', 'generateList', 'Prompt',
|
||||
'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope',
|
||||
'ProcessErrors', 'GetBasePath', 'SelectionInit', 'ProjectUpdate',
|
||||
'Refresh', 'Wait', 'GetChoices', 'Empty', 'Find',
|
||||
'GetProjectIcon', 'GetProjectToolTip', '$filter', '$state', 'rbacUiControlService',
|
||||
'i18n'
|
||||
ProjectsList.$inject = ['$scope', '$rootScope', '$location', '$log', '$stateParams',
|
||||
'Rest', 'Alert', 'ProjectList', 'Prompt', 'ReturnToCaller', 'ClearScope', 'ProcessErrors',
|
||||
'GetBasePath', 'ProjectUpdate', 'Wait', 'GetChoices', 'Empty', 'Find', 'GetProjectIcon',
|
||||
'GetProjectToolTip', '$filter', '$state', 'rbacUiControlService', 'Dataset', 'i18n'
|
||||
];
|
||||
|
||||
export function ProjectsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, GenerateForm, ProjectsForm, Rest, Alert, ProcessErrors,
|
||||
GetBasePath, GetProjectPath, GetChoices, Wait, $state, CreateSelect2) {
|
||||
|
||||
export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, ProjectsForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ClearScope, GetBasePath, ReturnToCaller, GetProjectPath, LookUpInit,
|
||||
OrganizationList, CredentialList, GetChoices, DebugForm, Wait, $state,
|
||||
CreateSelect2, i18n) {
|
||||
|
||||
Rest.setUrl(GetBasePath('projects'));
|
||||
Rest.options()
|
||||
.success(function(data) {
|
||||
if (!data.actions.POST) {
|
||||
$state.go("^");
|
||||
Alert('Permission Error', 'You do not have permission to add a project.', 'alert-info');
|
||||
}
|
||||
});
|
||||
|
||||
ClearScope();
|
||||
|
||||
// Inject dynamic view
|
||||
var form = ProjectsForm(),
|
||||
generator = GenerateForm,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
defaultUrl = GetBasePath('projects'),
|
||||
master = {};
|
||||
|
||||
// remove "type" field from search options
|
||||
CredentialList = _.cloneDeep(CredentialList);
|
||||
CredentialList.fields.kind.noSearch = true;
|
||||
init();
|
||||
|
||||
generator.inject(form, { mode: 'add', related: false, scope: $scope });
|
||||
generator.reset();
|
||||
function init() {
|
||||
Rest.setUrl(GetBasePath('projects'));
|
||||
Rest.options()
|
||||
.success(function(data) {
|
||||
if (!data.actions.POST) {
|
||||
$state.go("^");
|
||||
Alert('Permission Error', 'You do not have permission to add a project.', 'alert-info');
|
||||
}
|
||||
});
|
||||
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
}
|
||||
|
||||
GetProjectPath({ scope: $scope, master: master });
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
$scope.removeChoicesReady();
|
||||
}
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReady', function () {
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReady', function() {
|
||||
var i;
|
||||
for (i = 0; i < $scope.scm_type_options.length; i++) {
|
||||
if ($scope.scm_type_options[i].value === '') {
|
||||
$scope.scm_type_options[i].value="manual";
|
||||
$scope.scm_type_options[i].value = "manual";
|
||||
//$scope.scm_type = $scope.scm_type_options[i];
|
||||
break;
|
||||
}
|
||||
@ -440,33 +322,14 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
variable: 'scm_type_options',
|
||||
callback: 'choicesReady'
|
||||
});
|
||||
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('credentials') + '?kind=scm',
|
||||
form: form,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
|
||||
CreateSelect2({
|
||||
element: '#local-path-select',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
var i, fld, url, data={};
|
||||
generator.clearApiErrors();
|
||||
$scope.formSave = function() {
|
||||
var i, fld, url, data = {};
|
||||
data = {};
|
||||
for (fld in form.fields) {
|
||||
if (form.fields[fld].type === 'checkbox_group') {
|
||||
@ -480,8 +343,8 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
}
|
||||
}
|
||||
|
||||
if($scope.scm_type.value === "manual"){
|
||||
data.scm_type = "" ;
|
||||
if ($scope.scm_type.value === "manual") {
|
||||
data.scm_type = "";
|
||||
data.local_path = $scope.local_path.value;
|
||||
} else {
|
||||
data.scm_type = $scope.scm_type.value;
|
||||
@ -492,26 +355,18 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
Wait('start');
|
||||
Rest.setUrl(url);
|
||||
Rest.post(data)
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
$scope.addedItem = data.id;
|
||||
|
||||
Refresh({
|
||||
scope: $scope,
|
||||
set: 'projects',
|
||||
iterator: 'project',
|
||||
url: $scope.current_url
|
||||
});
|
||||
|
||||
$state.go('projects.edit', {id: data.id}, {reload: true});
|
||||
$state.go('projects.edit', { id: data.id }, { reload: true });
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, form, { hdr: i18n._('Error!'),
|
||||
msg: i18n._('Failed to create new project. POST returned status: ') + status });
|
||||
});
|
||||
};
|
||||
|
||||
$scope.scmChange = function () {
|
||||
$scope.scmChange = function() {
|
||||
// When an scm_type is set, path is not required
|
||||
if ($scope.scm_type) {
|
||||
$scope.pathRequired = ($scope.scm_type.value === 'manual') ? true : false;
|
||||
@ -520,7 +375,7 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
}
|
||||
|
||||
// Dynamically update popover values
|
||||
if($scope.scm_type.value) {
|
||||
if ($scope.scm_type.value) {
|
||||
switch ($scope.scm_type.value) {
|
||||
case 'git':
|
||||
$scope.urlPopover = i18n._('<p>Example URLs for GIT SCM include:</p><ul class=\"no-bullets\"><li>https://github.com/ansible/ansible.git</li>' +
|
||||
@ -528,7 +383,7 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
'<p><strong>Note:</strong> When using SSH protocol for GitHub or Bitbucket, enter an SSH key only, ' +
|
||||
'do not enter a username (other than git). Additionally, GitHub and Bitbucket do not support password authentication when using ' +
|
||||
'SSH. GIT read only protocol (git://) does not use username or password information.');
|
||||
break;
|
||||
break;
|
||||
case 'svn':
|
||||
$scope.urlPopover = i18n._('<p>Example URLs for Subversion SCM include:</p>' +
|
||||
'<ul class=\"no-bullets\"><li>https://github.com/ansible/ansible</li><li>svn://servername.example.com/path</li>' +
|
||||
@ -548,89 +403,47 @@ export function ProjectsAdd(Refresh, $scope, $rootScope, $compile, $location, $l
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('projects');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('projects');
|
||||
};
|
||||
}
|
||||
|
||||
ProjectsAdd.$inject = ['Refresh', '$scope', '$rootScope', '$compile', '$location', '$log',
|
||||
'$stateParams', 'ProjectsForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ClearScope', 'GetBasePath', 'ReturnToCaller',
|
||||
'GetProjectPath', 'LookUpInit', 'OrganizationList', 'CredentialList',
|
||||
'GetChoices', 'DebugForm', 'Wait', '$state', 'CreateSelect2', 'i18n'
|
||||
];
|
||||
ProjectsAdd.$inject = ['$scope', '$rootScope', '$compile', '$location', '$log',
|
||||
'$stateParams', 'GenerateForm', 'ProjectsForm', 'Rest', 'Alert', 'ProcessErrors', 'GetBasePath',
|
||||
'GetProjectPath', 'GetChoices', 'Wait', '$state', 'CreateSelect2', 'i18n'];
|
||||
|
||||
|
||||
export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, ProjectsForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
RelatedSearchInit, RelatedPaginateInit, Prompt, ClearScope, GetBasePath,
|
||||
ReturnToCaller, GetProjectPath, Authorization, CredentialList, LookUpInit,
|
||||
GetChoices, Empty, DebugForm, Wait, SchedulesControllerInit,
|
||||
SchedulesListInit, SchedulesList, ProjectUpdate, $state, CreateSelect2,
|
||||
OrganizationList, NotificationsListInit, ToggleNotification, i18n) {
|
||||
$stateParams, ProjectsForm, Rest, Alert, ProcessErrors,
|
||||
Prompt, ClearScope, GetBasePath, GetProjectPath, Authorization,
|
||||
GetChoices, Empty, DebugForm, Wait, ProjectUpdate, $state, CreateSelect2, ToggleNotification, i18n) {
|
||||
|
||||
ClearScope('htmlTemplate');
|
||||
|
||||
var form = ProjectsForm(),
|
||||
defaultUrl = GetBasePath('projects') + $stateParams.project_id + '/',
|
||||
master = {},
|
||||
id = $stateParams.project_id;
|
||||
|
||||
init();
|
||||
|
||||
function init() {
|
||||
$scope.project_local_paths = [];
|
||||
$scope.base_dir = '';
|
||||
}
|
||||
|
||||
$scope.$watch('project_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
|
||||
// Inject dynamic view
|
||||
var form = ProjectsForm(),
|
||||
generator = GenerateForm,
|
||||
defaultUrl = GetBasePath('projects') + $stateParams.id + '/',
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
master = {}, i,
|
||||
id = $stateParams.id,
|
||||
relatedSets = {};
|
||||
|
||||
// remove "type" field from search options
|
||||
CredentialList = _.cloneDeep(CredentialList);
|
||||
CredentialList.fields.kind.noSearch = true;
|
||||
|
||||
|
||||
SchedulesList.well = false;
|
||||
generator.inject(form, {
|
||||
mode: 'edit',
|
||||
related: true,
|
||||
scope: $scope
|
||||
});
|
||||
generator.reset();
|
||||
|
||||
$scope.project_local_paths = [];
|
||||
$scope.base_dir = '';
|
||||
|
||||
if ($scope.removerelatedschedules) {
|
||||
$scope.removerelatedschedules();
|
||||
}
|
||||
$scope.removerelatedschedules = $scope.$on('relatedschedules', function() {
|
||||
SchedulesListInit({
|
||||
scope: $scope,
|
||||
list: SchedulesList,
|
||||
choices: null,
|
||||
related: true
|
||||
});
|
||||
});
|
||||
|
||||
// After the project is loaded, retrieve each related set
|
||||
if ($scope.projectLoadedRemove) {
|
||||
$scope.projectLoadedRemove();
|
||||
}
|
||||
$scope.projectLoadedRemove = $scope.$on('projectLoaded', function () {
|
||||
var set, opts=[];
|
||||
|
||||
for (set in relatedSets) {
|
||||
$scope.search(relatedSets[set].iterator);
|
||||
}
|
||||
|
||||
SchedulesControllerInit({
|
||||
scope: $scope,
|
||||
parent_scope: $scope,
|
||||
iterator: 'schedule'
|
||||
});
|
||||
$scope.projectLoadedRemove = $scope.$on('projectLoaded', function() {
|
||||
var opts = [];
|
||||
|
||||
if (Authorization.getUserInfo('is_superuser') === true) {
|
||||
GetProjectPath({ scope: $scope, master: master });
|
||||
@ -644,42 +457,19 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
$scope.base_dir = 'You do not have access to view this property';
|
||||
}
|
||||
|
||||
LookUpInit({
|
||||
url: GetBasePath('credentials') + '?kind=scm',
|
||||
scope: $scope,
|
||||
form: form,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: $scope.organization,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
$scope.pathRequired = ($scope.scm_type.value === 'manual') ? true : false;
|
||||
$scope.scmRequired = ($scope.scm_type.value !== 'manual') ? true : false;
|
||||
$scope.scmBranchLabel = ($scope.scm_type.value === 'svn') ? 'Revision #' : 'SCM Branch';
|
||||
Wait('stop');
|
||||
|
||||
NotificationsListInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('projects'),
|
||||
id: $scope.project_obj.id
|
||||
});
|
||||
|
||||
$scope.scmChange();
|
||||
});
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
$scope.removeChoicesReady();
|
||||
}
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReady', function () {
|
||||
$scope.removeChoicesReady = $scope.$on('choicesReady', function() {
|
||||
let i;
|
||||
for (i = 0; i < $scope.scm_type_options.length; i++) {
|
||||
if ($scope.scm_type_options[i].value === '') {
|
||||
$scope.scm_type_options[i].value = "manual";
|
||||
@ -689,7 +479,7 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
// Retrieve detail record and prepopulate the form
|
||||
Rest.setUrl(defaultUrl);
|
||||
Rest.get({ params: { id: id } })
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
var fld, i;
|
||||
for (fld in form.fields) {
|
||||
if (form.fields[fld].type === 'checkbox_group') {
|
||||
@ -705,15 +495,12 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
if (form.fields[fld].sourceModel && data.summary_fields &&
|
||||
data.summary_fields[form.fields[fld].sourceModel]) {
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
master[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
}
|
||||
}
|
||||
relatedSets = form.relatedSets(data.related);
|
||||
|
||||
|
||||
|
||||
data.scm_type = (Empty(data.scm_type)) ? 'manual' : data.scm_type;
|
||||
for (i = 0; i < $scope.scm_type_options.length; i++) {
|
||||
@ -743,18 +530,6 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
});
|
||||
|
||||
$scope.scmBranchLabel = ($scope.scm_type.value === 'svn') ? 'Revision #' : 'SCM Branch';
|
||||
|
||||
// Initialize related search functions. Doing it here to make sure relatedSets object is populated.
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
$scope.scm_update_tooltip = "Start an SCM update";
|
||||
$scope.scm_type_class = "";
|
||||
if (data.status === 'running' || data.status === 'updating') {
|
||||
@ -791,14 +566,12 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
var notifier = this.notification;
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
}
|
||||
catch(e) {
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
ToggleNotification({
|
||||
scope: $scope,
|
||||
url: $scope.project_url,
|
||||
id: $scope.project_obj.id,
|
||||
url: $scope.project_obj.url,
|
||||
notifier: notifier,
|
||||
column: column,
|
||||
callback: 'NotificationRefresh'
|
||||
@ -806,9 +579,9 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
};
|
||||
|
||||
// Save changes to the parent
|
||||
$scope.formSave = function () {
|
||||
$scope.formSave = function() {
|
||||
var fld, i, params;
|
||||
generator.clearApiErrors();
|
||||
//generator.clearApiErrors();
|
||||
Wait('start');
|
||||
$rootScope.flashMessage = null;
|
||||
params = {};
|
||||
@ -824,8 +597,8 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
}
|
||||
|
||||
if($scope.scm_type.value === "manual"){
|
||||
params.scm_type = "" ;
|
||||
if ($scope.scm_type.value === "manual") {
|
||||
params.scm_type = "";
|
||||
params.local_path = $scope.local_path.value;
|
||||
} else {
|
||||
params.scm_type = $scope.scm_type.value;
|
||||
@ -836,37 +609,26 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
Rest.put(params)
|
||||
.success(function() {
|
||||
Wait('stop');
|
||||
$state.go($state.current, {}, {reload: true});
|
||||
$state.go($state.current, {}, { reload: true });
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!', msg: 'Failed to update project: ' + id + '. PUT status: ' + status });
|
||||
});
|
||||
};
|
||||
|
||||
// Related set: Add button
|
||||
$scope.add = function (set) {
|
||||
$rootScope.flashMessage = null;
|
||||
$location.path('/' + base + '/' + $stateParams.id + '/' + set);
|
||||
};
|
||||
|
||||
// Related set: Edit button
|
||||
$scope.edit = function (set, id) {
|
||||
$rootScope.flashMessage = null;
|
||||
$location.path('/' + set + '/' + id);
|
||||
};
|
||||
|
||||
// Related set: Delete button
|
||||
$scope['delete'] = function (set, itm_id, name, title) {
|
||||
var action = function () {
|
||||
$scope['delete'] = function(set, itm_id, name, title) {
|
||||
var action = function() {
|
||||
var url = GetBasePath('projects') + id + '/' + set + '/';
|
||||
$rootScope.flashMessage = null;
|
||||
Rest.setUrl(url);
|
||||
Rest.post({ id: itm_id, disassociate: 1 })
|
||||
.success(function () {
|
||||
.success(function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
$scope.search(form.related[set].iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(form.related[set].iterator);
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
$('#prompt-modal').modal('hide');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Call to ' + url + ' failed. POST returned status: ' + status });
|
||||
});
|
||||
@ -880,7 +642,7 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
});
|
||||
};
|
||||
|
||||
$scope.scmChange = function () {
|
||||
$scope.scmChange = function() {
|
||||
if ($scope.scm_type) {
|
||||
$scope.pathRequired = ($scope.scm_type.value === 'manual') ? true : false;
|
||||
$scope.scmRequired = ($scope.scm_type.value !== 'manual') ? true : false;
|
||||
@ -888,7 +650,7 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
|
||||
// Dynamically update popover values
|
||||
if($scope.scm_type.value) {
|
||||
if ($scope.scm_type.value) {
|
||||
switch ($scope.scm_type.value) {
|
||||
case 'git':
|
||||
$scope.urlPopover = i18n._('<p>Example URLs for GIT SCM include:</p><ul class=\"no-bullets\"><li>https://github.com/ansible/ansible.git</li>' +
|
||||
@ -896,7 +658,7 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
'<p><strong>Note:</strong> When using SSH protocol for GitHub or Bitbucket, enter an SSH key only, ' +
|
||||
'do not enter a username (other than git). Additionally, GitHub and Bitbucket do not support password authentication when using ' +
|
||||
'SSH. GIT read only protocol (git://) does not use username or password information.');
|
||||
break;
|
||||
break;
|
||||
case 'svn':
|
||||
$scope.urlPopover = i18n._('<p>Example URLs for Subversion SCM include:</p>' +
|
||||
'<ul class=\"no-bullets\"><li>https://github.com/ansible/ansible</li><li>svn://servername.example.com/path</li>' +
|
||||
@ -916,7 +678,7 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
};
|
||||
|
||||
$scope.SCMUpdate = function () {
|
||||
$scope.SCMUpdate = function() {
|
||||
if ($scope.project_obj.scm_type === "Manual" || Empty($scope.project_obj.scm_type)) {
|
||||
// ignore
|
||||
} else if ($scope.project_obj.status === 'updating' || $scope.project_obj.status === 'running' || $scope.project_obj.status === 'pending') {
|
||||
@ -926,17 +688,12 @@ export function ProjectsEdit($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$scope.formCancel = function() {
|
||||
$state.transitionTo('projects');
|
||||
};
|
||||
}
|
||||
|
||||
ProjectsEdit.$inject = ['$scope', '$rootScope', '$compile', '$location', '$log',
|
||||
'$stateParams', 'ProjectsForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'RelatedSearchInit', 'RelatedPaginateInit', 'Prompt',
|
||||
'ClearScope', 'GetBasePath', 'ReturnToCaller', 'GetProjectPath',
|
||||
'Authorization', 'CredentialList', 'LookUpInit', 'GetChoices', 'Empty',
|
||||
'DebugForm', 'Wait', 'SchedulesControllerInit', 'SchedulesListInit',
|
||||
'SchedulesList', 'ProjectUpdate', '$state', 'CreateSelect2',
|
||||
'OrganizationList', 'NotificationsListInit', 'ToggleNotification', 'i18n'
|
||||
];
|
||||
'$stateParams', 'ProjectsForm', 'Rest', 'Alert', 'ProcessErrors', 'Prompt',
|
||||
'ClearScope', 'GetBasePath', 'GetProjectPath', 'Authorization', 'GetChoices', 'Empty',
|
||||
'DebugForm', 'Wait', 'ProjectUpdate', '$state', 'CreateSelect2', 'ToggleNotification', 'i18n'];
|
||||
|
||||
@ -18,33 +18,33 @@ GetBasePath, Wait, Find, LoadSchedulesScope, GetChoices) {
|
||||
|
||||
var base, id, url, parentObject;
|
||||
|
||||
base = $location.path().replace(/^\//, '').split('/')[0];
|
||||
// base = $location.path().replace(/^\//, '').split('/')[0];
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function() {
|
||||
var list = $scope.schedules;
|
||||
list.forEach(function(element, idx) {
|
||||
list[idx].play_tip = (element.enabled) ? 'Schedule is Active. Click to temporarily stop.' : 'Schedule is temporarily stopped. Click to activate.';
|
||||
});
|
||||
});
|
||||
// if ($scope.removePostRefresh) {
|
||||
// $scope.removePostRefresh();
|
||||
// }
|
||||
// $scope.removePostRefresh = $scope.$on('PostRefresh', function() {
|
||||
// var list = $scope.schedules;
|
||||
// list.forEach(function(element, idx) {
|
||||
// list[idx].play_tip = (element.enabled) ? 'Schedule is Active. Click to temporarily stop.' : 'Schedule is temporarily stopped. Click to activate.';
|
||||
// });
|
||||
// });
|
||||
|
||||
if ($scope.removeParentLoaded) {
|
||||
$scope.removeParentLoaded();
|
||||
}
|
||||
$scope.removeParentLoaded = $scope.$on('ParentLoaded', function() {
|
||||
url += "schedules/";
|
||||
SchedulesList.well = true;
|
||||
LoadSchedulesScope({
|
||||
parent_scope: $scope,
|
||||
scope: $scope,
|
||||
list: SchedulesList,
|
||||
id: 'schedule-list-target',
|
||||
url: url,
|
||||
pageSize: 20
|
||||
});
|
||||
});
|
||||
// if ($scope.removeParentLoaded) {
|
||||
// $scope.removeParentLoaded();
|
||||
// }
|
||||
// $scope.removeParentLoaded = $scope.$on('ParentLoaded', function() {
|
||||
// url += "schedules/";
|
||||
// SchedulesList.well = true;
|
||||
// LoadSchedulesScope({
|
||||
// parent_scope: $scope,
|
||||
// scope: $scope,
|
||||
// list: SchedulesList,
|
||||
// id: 'schedule-list-target',
|
||||
// url: url,
|
||||
// pageSize: 20
|
||||
// });
|
||||
// });
|
||||
|
||||
|
||||
if ($scope.removeChoicesReady) {
|
||||
@ -67,7 +67,8 @@ GetBasePath, Wait, Find, LoadSchedulesScope, GetChoices) {
|
||||
});
|
||||
|
||||
$scope.refreshJobs = function() {
|
||||
$scope.search(SchedulesList.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(SchedulesList.iterator);
|
||||
};
|
||||
|
||||
Wait('start');
|
||||
|
||||
@ -8,108 +8,62 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Teams
|
||||
* @description This controller's for teams
|
||||
*/
|
||||
*/
|
||||
|
||||
export function TeamsList($scope, $rootScope, $log, $stateParams,
|
||||
Rest, Alert, TeamList, Prompt, ClearScope, ProcessErrors,
|
||||
GetBasePath, Wait, $state, $filter, rbacUiControlService, Dataset) {
|
||||
|
||||
export function TeamsList($scope, $rootScope, $location, $log, $stateParams,
|
||||
Rest, Alert, TeamList, GenerateList, Prompt, SearchInit, PaginateInit,
|
||||
ReturnToCaller, ClearScope, ProcessErrors, SetTeamListeners, GetBasePath,
|
||||
SelectionInit, Wait, $state, Refresh, $filter, rbacUiControlService) {
|
||||
ClearScope();
|
||||
|
||||
$scope.canAdd = false;
|
||||
|
||||
rbacUiControlService.canAdd('teams')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
var list = TeamList,
|
||||
defaultUrl = GetBasePath('teams'),
|
||||
generator = GenerateList,
|
||||
paths = $location.path().replace(/^\//, '').split('/'),
|
||||
mode = (paths[0] === 'teams') ? 'edit' : 'select',
|
||||
url;
|
||||
defaultUrl = GetBasePath('teams');
|
||||
|
||||
var injectForm = function() {
|
||||
generator.inject(list, { mode: mode, scope: $scope });
|
||||
};
|
||||
init();
|
||||
|
||||
injectForm();
|
||||
function init() {
|
||||
$scope.canAdd = false;
|
||||
|
||||
$scope.$on("RefreshTeamsList", function() {
|
||||
injectForm();
|
||||
Refresh({
|
||||
scope: $scope,
|
||||
set: 'teams',
|
||||
iterator: 'team',
|
||||
url: GetBasePath('teams') + "?order_by=name&page_size=" + $scope.team_page_size
|
||||
rbacUiControlService.canAdd('teams')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
_.forEach($scope[list.name], (team) => {
|
||||
team.organization_name = team.summary_fields.organization.name;
|
||||
});
|
||||
});
|
||||
|
||||
$scope.selected = [];
|
||||
|
||||
url = GetBasePath('base') + $location.path() + '/';
|
||||
SelectionInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: url,
|
||||
returnToCaller: 1
|
||||
});
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
$scope.selected = [];
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function () {
|
||||
// After a refresh, populate the organization name on each row
|
||||
var i;
|
||||
if ($scope.teams) {
|
||||
for (i = 0; i < $scope.teams.length; i++) {
|
||||
if ($scope.teams[i].summary_fields.organization) {
|
||||
$scope.teams[i].organization_name = $scope.teams[i].summary_fields.organization.name;
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'teams',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
$scope.search(list.iterator);
|
||||
|
||||
$scope.addTeam = function () {
|
||||
$state.transitionTo('teams.add');
|
||||
$scope.addTeam = function() {
|
||||
$state.go('teams.add');
|
||||
};
|
||||
|
||||
$scope.editTeam = function (id) {
|
||||
$state.transitionTo('teams.edit', {team_id: id});
|
||||
$scope.editTeam = function(id) {
|
||||
$state.go('teams.edit', { team_id: id });
|
||||
};
|
||||
|
||||
$scope.deleteTeam = function (id, name) {
|
||||
$scope.deleteTeam = function(id, name) {
|
||||
|
||||
var action = function () {
|
||||
var action = function() {
|
||||
Wait('start');
|
||||
var url = defaultUrl + id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.destroy()
|
||||
.success(function () {
|
||||
.success(function() {
|
||||
Wait('stop');
|
||||
$('#prompt-modal').modal('hide');
|
||||
if (parseInt($state.params.team_id) === id) {
|
||||
$state.go("^", null, {reload: true});
|
||||
$state.go('^', null, { reload: true });
|
||||
} else {
|
||||
$scope.search(list.iterator);
|
||||
$state.go('.', null, { reload: true });
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
Wait('stop');
|
||||
$('#prompt-modal').modal('hide');
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
@ -128,18 +82,15 @@ export function TeamsList($scope, $rootScope, $location, $log, $stateParams,
|
||||
};
|
||||
}
|
||||
|
||||
TeamsList.$inject = ['$scope', '$rootScope', '$location', '$log',
|
||||
'$stateParams', 'Rest', 'Alert', 'TeamList', 'generateList', 'Prompt',
|
||||
'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope',
|
||||
'ProcessErrors', 'SetTeamListeners', 'GetBasePath', 'SelectionInit', 'Wait',
|
||||
'$state', 'Refresh', '$filter', 'rbacUiControlService'
|
||||
|
||||
TeamsList.$inject = ['$scope', '$rootScope', '$log',
|
||||
'$stateParams', 'Rest', 'Alert', 'TeamList', 'Prompt', 'ClearScope',
|
||||
'ProcessErrors', 'GetBasePath', 'Wait', '$state', '$filter', 'rbacUiControlService', 'Dataset'
|
||||
];
|
||||
|
||||
|
||||
export function TeamsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, TeamForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ReturnToCaller, ClearScope, GenerateList, OrganizationList, SearchInit,
|
||||
PaginateInit, GetBasePath, LookUpInit, Wait, $state) {
|
||||
export function TeamsAdd($scope, $rootScope, $stateParams, TeamForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ClearScope, GetBasePath, Wait, $state) {
|
||||
ClearScope('htmlTemplate'); //Garbage collection. Don't leave behind any listeners/watchers from the prior
|
||||
//$scope.
|
||||
|
||||
@ -155,176 +106,128 @@ export function TeamsAdd($scope, $rootScope, $compile, $location, $log,
|
||||
// Inject dynamic view
|
||||
var defaultUrl = GetBasePath('teams'),
|
||||
form = TeamForm,
|
||||
generator = GenerateForm,
|
||||
scope = generator.inject(form, { mode: 'add', related: false });
|
||||
generator = GenerateForm;
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
generator.reset();
|
||||
init();
|
||||
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: null,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
function init() {
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
}
|
||||
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
$scope.formSave = function() {
|
||||
var fld, data;
|
||||
generator.clearApiErrors();
|
||||
Wait('start');
|
||||
Rest.setUrl(defaultUrl);
|
||||
data = {};
|
||||
for (fld in form.fields) {
|
||||
data[fld] = scope[fld];
|
||||
data[fld] = $scope[fld];
|
||||
}
|
||||
Rest.post(data)
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
Wait('stop');
|
||||
$rootScope.flashMessage = "New team successfully created!";
|
||||
$rootScope.$broadcast("EditIndicatorChange", "users", data.id);
|
||||
$state.go('teams.edit', {team_id: data.id}, {reload: true});
|
||||
$state.go('teams.edit', { team_id: data.id }, { reload: true });
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!', msg: 'Failed to add new team. Post returned status: ' +
|
||||
status });
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to add new team. Post returned status: ' +
|
||||
status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('teams');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('teams');
|
||||
};
|
||||
}
|
||||
|
||||
TeamsAdd.$inject = ['$scope', '$rootScope', '$compile', '$location', '$log',
|
||||
'$stateParams', 'TeamForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'generateList',
|
||||
'OrganizationList', 'SearchInit', 'PaginateInit', 'GetBasePath',
|
||||
'LookUpInit', 'Wait', '$state'
|
||||
TeamsAdd.$inject = ['$scope', '$rootScope', '$stateParams', 'TeamForm', 'GenerateForm',
|
||||
'Rest', 'Alert', 'ProcessErrors', 'ClearScope', 'GetBasePath', 'Wait', '$state'
|
||||
];
|
||||
|
||||
|
||||
export function TeamsEdit($scope, $rootScope, $location,
|
||||
$stateParams, TeamForm, GenerateForm, Rest, ProcessErrors,
|
||||
RelatedSearchInit, RelatedPaginateInit, ClearScope,
|
||||
LookUpInit, GetBasePath, OrganizationList, Wait, $state) {
|
||||
export function TeamsEdit($scope, $rootScope, $stateParams,
|
||||
TeamForm, Rest, ProcessErrors, ClearScope, GetBasePath, Wait, $state) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
var defaultUrl = GetBasePath('teams'),
|
||||
generator = GenerateForm,
|
||||
form = TeamForm,
|
||||
var form = TeamForm,
|
||||
id = $stateParams.team_id,
|
||||
relatedSets = {},
|
||||
set;
|
||||
defaultUrl = GetBasePath('teams') + id;
|
||||
|
||||
$scope.team_id = id;
|
||||
init();
|
||||
|
||||
$scope.$watch('team_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
function init() {
|
||||
$scope.team_id = id;
|
||||
Rest.setUrl(defaultUrl);
|
||||
Wait('start');
|
||||
Rest.get(defaultUrl).success(function(data) {
|
||||
setScopeFields(data);
|
||||
$scope.organization_name = data.summary_fields.organization.name;
|
||||
|
||||
$scope.team_obj = data;
|
||||
});
|
||||
|
||||
$scope.$watch('team_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
generator.inject(form, { mode: 'edit', related: true, scope: $scope });
|
||||
generator.reset();
|
||||
}
|
||||
|
||||
var setScopeFields = function(data){
|
||||
// @issue I think all this really want to do is _.forEach(form.fields, (field) =>{ $scope[field] = data[field]})
|
||||
function setScopeFields(data) {
|
||||
_(data)
|
||||
.pick(function(value, key){
|
||||
return form.fields.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key){
|
||||
$scope[key] = value;
|
||||
})
|
||||
.value();
|
||||
.pick(function(value, key) {
|
||||
return form.fields.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key) {
|
||||
$scope[key] = value;
|
||||
})
|
||||
.value();
|
||||
return;
|
||||
};
|
||||
var setScopeRelated = function(data, related){
|
||||
_(related)
|
||||
.pick(function(value, key){
|
||||
return data.related.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key){
|
||||
relatedSets[key] = {
|
||||
url: data.related[key],
|
||||
iterator: value.iterator
|
||||
};
|
||||
})
|
||||
.value();
|
||||
};
|
||||
}
|
||||
|
||||
// prepares a data payload for a PUT request to the API
|
||||
var processNewData = function(fields){
|
||||
function processNewData(fields) {
|
||||
var data = {};
|
||||
_.forEach(fields, function(value, key){
|
||||
if ($scope[key] !== '' && $scope[key] !== null && $scope[key] !== undefined){
|
||||
data[key] = $scope[key];
|
||||
_.forEach(fields, function(value, key) {
|
||||
if ($scope[key] !== '' && $scope[key] !== null && $scope[key] !== undefined) {
|
||||
data[key] = $scope[key];
|
||||
}
|
||||
});
|
||||
return data;
|
||||
}
|
||||
|
||||
$scope.formCancel = function() {
|
||||
$state.go('teams', null, { reload: true });
|
||||
};
|
||||
|
||||
var init = function(){
|
||||
var url = defaultUrl + id;
|
||||
Rest.setUrl(url);
|
||||
Wait('start');
|
||||
Rest.get(url).success(function(data){
|
||||
setScopeFields(data);
|
||||
setScopeRelated(data, form.related);
|
||||
$scope.organization_name = data.summary_fields.organization.name;
|
||||
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
for (set in relatedSets) {
|
||||
$scope.search(relatedSets[set].iterator);
|
||||
}
|
||||
|
||||
$scope.team_obj = data;
|
||||
|
||||
LookUpInit({
|
||||
url: GetBasePath('organizations'),
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: $scope.organization,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
$scope.formCancel = function(){
|
||||
$state.go('teams', null, {reload: true});
|
||||
};
|
||||
|
||||
$scope.formSave = function(){
|
||||
generator.clearApiErrors();
|
||||
generator.checkAutoFill();
|
||||
$scope.formSave = function() {
|
||||
$rootScope.flashMessage = null;
|
||||
if ($scope[form.name + '_form'].$valid){
|
||||
if ($scope[form.name + '_form'].$valid) {
|
||||
Rest.setUrl(defaultUrl + id + '/');
|
||||
var data = processNewData(form.fields);
|
||||
Rest.put(data).success(function(){
|
||||
$state.go($state.current, null, {reload: true});
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status });
|
||||
});
|
||||
Rest.put(data).success(function() {
|
||||
$state.go($state.current, null, { reload: true });
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status
|
||||
});
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
@ -337,13 +240,8 @@ export function TeamsEdit($scope, $rootScope, $location,
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
/* Related Set implementation TDB */
|
||||
}
|
||||
|
||||
TeamsEdit.$inject = ['$scope', '$rootScope', '$location',
|
||||
'$stateParams', 'TeamForm', 'GenerateForm', 'Rest',
|
||||
'ProcessErrors', 'RelatedSearchInit', 'RelatedPaginateInit',
|
||||
'ClearScope', 'LookUpInit', 'GetBasePath',
|
||||
'OrganizationList', 'Wait', '$state'
|
||||
TeamsEdit.$inject = ['$scope', '$rootScope', '$stateParams', 'TeamForm', 'Rest',
|
||||
'ProcessErrors', 'ClearScope', 'GetBasePath', 'Wait', '$state'
|
||||
];
|
||||
|
||||
@ -8,14 +8,14 @@
|
||||
* @ngdoc function
|
||||
* @name controllers.function:Users
|
||||
* @description This controller's the Users page
|
||||
*/
|
||||
*/
|
||||
|
||||
import {N_} from "../i18n";
|
||||
import { N_ } from "../i18n";
|
||||
|
||||
const user_type_options = [
|
||||
{type: 'normal' , label: N_('Normal User') },
|
||||
{type: 'system_auditor' , label: N_('System Auditor') },
|
||||
{type: 'system_administrator', label: N_('System Administrator') },
|
||||
{ type: 'normal', label: N_('Normal User') },
|
||||
{ type: 'system_auditor', label: N_('System Auditor') },
|
||||
{ type: 'system_administrator', label: N_('System Administrator') },
|
||||
];
|
||||
|
||||
function user_type_sync($scope) {
|
||||
@ -25,18 +25,17 @@ function user_type_sync($scope) {
|
||||
switch (type_option.type) {
|
||||
case 'system_administrator':
|
||||
$scope.is_superuser = true;
|
||||
break;
|
||||
break;
|
||||
case 'system_auditor':
|
||||
$scope.is_system_auditor = true;
|
||||
break;
|
||||
break;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
export function UsersList($scope, $rootScope, $location, $log, $stateParams,
|
||||
Rest, Alert, UserList, GenerateList, Prompt, SearchInit, PaginateInit,
|
||||
ReturnToCaller, ClearScope, ProcessErrors, GetBasePath, SelectionInit,
|
||||
Wait, $state, Refresh, $filter, rbacUiControlService, i18n) {
|
||||
export function UsersList($scope, $rootScope, $stateParams,
|
||||
Rest, Alert, UserList, Prompt, ClearScope, ProcessErrors, GetBasePath,
|
||||
Wait, $state, $filter, rbacUiControlService, Dataset, i18n) {
|
||||
|
||||
for (var i = 0; i < user_type_options.length; i++) {
|
||||
user_type_options[i].label = i18n._(user_type_options[i].label);
|
||||
@ -44,95 +43,57 @@ export function UsersList($scope, $rootScope, $location, $log, $stateParams,
|
||||
|
||||
ClearScope();
|
||||
|
||||
$scope.canAdd = false;
|
||||
|
||||
rbacUiControlService.canAdd('users')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
var list = UserList,
|
||||
defaultUrl = GetBasePath('users'),
|
||||
generator = GenerateList,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
mode = (base === 'users') ? 'edit' : 'select',
|
||||
url = (base === 'organizations') ? GetBasePath('organizations') + $stateParams.organization_id + '/users/' :
|
||||
GetBasePath('teams') + $stateParams.team_id + '/users/';
|
||||
defaultUrl = GetBasePath('users');
|
||||
|
||||
var injectForm = function() {
|
||||
generator.inject(UserList, { mode: mode, scope: $scope });
|
||||
};
|
||||
init();
|
||||
|
||||
injectForm();
|
||||
function init() {
|
||||
$scope.canAdd = false;
|
||||
|
||||
$scope.$on("RefreshUsersList", function() {
|
||||
injectForm();
|
||||
Refresh({
|
||||
scope: $scope,
|
||||
set: 'users',
|
||||
iterator: 'user',
|
||||
url: GetBasePath('users') + "?order_by=username&page_size=" + $scope.user_page_size
|
||||
});
|
||||
});
|
||||
rbacUiControlService.canAdd('users')
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
$scope.selected = [];
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
if (mode === 'select') {
|
||||
SelectionInit({ scope: $scope, list: list, url: url, returnToCaller: 1 });
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
$scope.selected = [];
|
||||
}
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function () {
|
||||
// Cleanup after a delete
|
||||
Wait('stop');
|
||||
$('#prompt-modal').modal('hide');
|
||||
});
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'users',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
$scope.search(list.iterator);
|
||||
|
||||
$scope.addUser = function () {
|
||||
$state.transitionTo('users.add');
|
||||
$scope.addUser = function() {
|
||||
$state.go('users.add');
|
||||
};
|
||||
|
||||
$scope.editUser = function (id) {
|
||||
$state.transitionTo('users.edit', {user_id: id});
|
||||
$scope.editUser = function(id) {
|
||||
$state.go('users.edit', { user_id: id });
|
||||
};
|
||||
|
||||
$scope.deleteUser = function (id, name) {
|
||||
$scope.deleteUser = function(id, name) {
|
||||
|
||||
var action = function () {
|
||||
//$('#prompt-modal').on('hidden.bs.modal', function () {
|
||||
// Wait('start');
|
||||
//});
|
||||
var action = function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
Wait('start');
|
||||
var url = defaultUrl + id + '/';
|
||||
Rest.setUrl(url);
|
||||
Rest.destroy()
|
||||
.success(function () {
|
||||
.success(function() {
|
||||
if (parseInt($state.params.user_id) === id) {
|
||||
$state.go("^", null, {reload: true});
|
||||
$state.go('^', null, { reload: true });
|
||||
} else {
|
||||
$scope.search(list.iterator);
|
||||
$state.go('.', null, { reload: true });
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
@ -145,91 +106,54 @@ export function UsersList($scope, $rootScope, $location, $log, $stateParams,
|
||||
};
|
||||
}
|
||||
|
||||
UsersList.$inject = ['$scope', '$rootScope', '$location', '$log',
|
||||
'$stateParams', 'Rest', 'Alert', 'UserList', 'generateList', 'Prompt',
|
||||
'SearchInit', 'PaginateInit', 'ReturnToCaller', 'ClearScope',
|
||||
'ProcessErrors', 'GetBasePath', 'SelectionInit', 'Wait', '$state',
|
||||
'Refresh', '$filter', 'rbacUiControlService', 'i18n'
|
||||
UsersList.$inject = ['$scope', '$rootScope', '$stateParams',
|
||||
'Rest', 'Alert', 'UserList', 'Prompt', 'ClearScope', 'ProcessErrors', 'GetBasePath',
|
||||
'Wait', '$state', '$filter', 'rbacUiControlService', 'Dataset', 'i18n'
|
||||
];
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
export function UsersAdd($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, UserForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ReturnToCaller, ClearScope, GetBasePath, LookUpInit, OrganizationList,
|
||||
ResetForm, Wait, CreateSelect2, $state, i18n) {
|
||||
|
||||
for (var i = 0; i < user_type_options.length; i++) {
|
||||
user_type_options[i].label = i18n._(user_type_options[i].label);
|
||||
}
|
||||
|
||||
Rest.setUrl(GetBasePath('users'));
|
||||
Rest.options()
|
||||
.success(function(data) {
|
||||
if (!data.actions.POST) {
|
||||
$state.go("^");
|
||||
Alert('Permission Error', 'You do not have permission to add a user.', 'alert-info');
|
||||
}
|
||||
});
|
||||
export function UsersAdd($scope, $rootScope, $stateParams, UserForm,
|
||||
GenerateForm, Rest, Alert, ProcessErrors, ReturnToCaller, ClearScope,
|
||||
GetBasePath, ResetForm, Wait, CreateSelect2, $state, i18n) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
// Inject dynamic view
|
||||
var defaultUrl = GetBasePath('organizations'),
|
||||
form = UserForm,
|
||||
generator = GenerateForm;
|
||||
form = UserForm;
|
||||
|
||||
generator.inject(form, { mode: 'add', related: false, scope: $scope });
|
||||
ResetForm();
|
||||
init();
|
||||
|
||||
$scope.ldap_user = false;
|
||||
$scope.not_ldap_user = !$scope.ldap_user;
|
||||
$scope.ldap_dn = null;
|
||||
$scope.socialAuthUser = false;
|
||||
$scope.external_account = null;
|
||||
function init() {
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
generator.reset();
|
||||
$scope.ldap_user = false;
|
||||
$scope.not_ldap_user = !$scope.ldap_user;
|
||||
$scope.ldap_dn = null;
|
||||
$scope.socialAuthUser = false;
|
||||
$scope.external_account = null;
|
||||
|
||||
$scope.user_type_options = user_type_options;
|
||||
$scope.user_type = user_type_options[0];
|
||||
$scope.$watch('user_type', user_type_sync($scope));
|
||||
|
||||
CreateSelect2({
|
||||
element: '#user_user_type',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
// Configure the lookup dialog. If we're adding a user through the Organizations tab,
|
||||
// default the Organization value.
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: ($stateParams.organization_id !== undefined) ? $stateParams.organization_id : null,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
if ($stateParams.organization_id) {
|
||||
$scope.organization = $stateParams.organization_id;
|
||||
Rest.setUrl(GetBasePath('organizations') + $stateParams.organization_id + '/');
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
$scope.organization_name = data.name;
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to lookup Organization: ' + data.id + '. GET returned status: ' + status });
|
||||
Rest.setUrl(GetBasePath('users'));
|
||||
Rest.options()
|
||||
.success(function(data) {
|
||||
if (!data.actions.POST) {
|
||||
$state.go("^");
|
||||
Alert('Permission Error', 'You do not have permission to add a user.', 'alert-info');
|
||||
}
|
||||
});
|
||||
|
||||
$scope.user_type_options = user_type_options;
|
||||
$scope.user_type = user_type_options[0];
|
||||
$scope.$watch('user_type', user_type_sync($scope));
|
||||
CreateSelect2({
|
||||
element: '#user_user_type',
|
||||
multiple: false
|
||||
});
|
||||
}
|
||||
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
$scope.formSave = function() {
|
||||
var fld, data = {};
|
||||
generator.clearApiErrors();
|
||||
generator.checkAutoFill();
|
||||
if ($scope[form.name + '_form'].$valid) {
|
||||
if ($scope.organization !== undefined && $scope.organization !== null && $scope.organization !== '') {
|
||||
Rest.setUrl(defaultUrl + $scope.organization + '/users/');
|
||||
@ -244,18 +168,17 @@ export function UsersAdd($scope, $rootScope, $compile, $location, $log,
|
||||
data.is_system_auditor = $scope.is_system_auditor;
|
||||
Wait('start');
|
||||
Rest.post(data)
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
var base = $location.path().replace(/^\//, '').split('/')[0];
|
||||
if (base === 'users') {
|
||||
$rootScope.flashMessage = 'New user successfully created!';
|
||||
$rootScope.$broadcast("EditIndicatorChange", "users", data.id);
|
||||
$state.go('users.edit', {user_id: data.id}, {reload: true});
|
||||
}
|
||||
else {
|
||||
$state.go('users.edit', { user_id: data.id }, { reload: true });
|
||||
} else {
|
||||
ReturnToCaller(1);
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!', msg: 'Failed to add new user. POST returned status: ' + status });
|
||||
});
|
||||
} else {
|
||||
@ -264,69 +187,102 @@ export function UsersAdd($scope, $rootScope, $compile, $location, $log,
|
||||
}
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('users');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('users');
|
||||
};
|
||||
|
||||
// Password change
|
||||
$scope.clearPWConfirm = function (fld) {
|
||||
$scope.clearPWConfirm = function(fld) {
|
||||
// If password value changes, make sure password_confirm must be re-entered
|
||||
$scope[fld] = '';
|
||||
$scope[form.name + '_form'][fld].$setValidity('awpassmatch', false);
|
||||
};
|
||||
}
|
||||
|
||||
UsersAdd.$inject = ['$scope', '$rootScope', '$compile', '$location', '$log',
|
||||
'$stateParams', 'UserForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'GetBasePath',
|
||||
'LookUpInit', 'OrganizationList', 'ResetForm', 'Wait', 'CreateSelect2', '$state',
|
||||
'i18n'
|
||||
UsersAdd.$inject = ['$scope', '$rootScope', '$stateParams', 'UserForm', 'GenerateForm',
|
||||
'Rest', 'Alert', 'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'GetBasePath',
|
||||
'ResetForm', 'Wait', 'CreateSelect2', '$state', 'i18n'
|
||||
];
|
||||
|
||||
|
||||
export function UsersEdit($scope, $rootScope, $location,
|
||||
$stateParams, UserForm, GenerateForm, Rest, ProcessErrors,
|
||||
RelatedSearchInit, RelatedPaginateInit, ClearScope,
|
||||
GetBasePath, ResetForm, Wait, CreateSelect2 ,$state, i18n) {
|
||||
$stateParams, UserForm, Rest, ProcessErrors,
|
||||
ClearScope, GetBasePath, ResetForm, Wait, CreateSelect2, $state, i18n) {
|
||||
|
||||
for (var i = 0; i < user_type_options.length; i++) {
|
||||
user_type_options[i].label = i18n._(user_type_options[i].label);
|
||||
}
|
||||
|
||||
ClearScope();
|
||||
|
||||
var defaultUrl = GetBasePath('users'),
|
||||
generator = GenerateForm,
|
||||
form = UserForm,
|
||||
var form = UserForm,
|
||||
master = {},
|
||||
id = $stateParams.user_id,
|
||||
relatedSets = {},
|
||||
set;
|
||||
defaultUrl = GetBasePath('users') + id;
|
||||
|
||||
generator.inject(form, { mode: 'edit', related: true, scope: $scope });
|
||||
generator.reset();
|
||||
init();
|
||||
|
||||
$scope.user_type_options = user_type_options;
|
||||
$scope.user_type = user_type_options[0];
|
||||
$scope.$watch('user_type', user_type_sync($scope));
|
||||
function init() {
|
||||
$scope.user_type_options = user_type_options;
|
||||
$scope.user_type = user_type_options[0];
|
||||
$scope.$watch('user_type', user_type_sync($scope));
|
||||
Rest.setUrl(defaultUrl);
|
||||
Wait('start');
|
||||
Rest.get(defaultUrl).success(function(data) {
|
||||
$scope.user_id = id;
|
||||
$scope.ldap_user = (data.ldap_dn !== null && data.ldap_dn !== undefined && data.ldap_dn !== '') ? true : false;
|
||||
$scope.not_ldap_user = !$scope.ldap_user;
|
||||
master.ldap_user = $scope.ldap_user;
|
||||
$scope.socialAuthUser = (data.auth.length > 0) ? true : false;
|
||||
$scope.external_account = data.external_account;
|
||||
|
||||
$scope.$watch('user_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
$scope.user_type = $scope.user_type_options[0];
|
||||
$scope.is_system_auditor = false;
|
||||
$scope.is_superuser = false;
|
||||
if (data.is_system_auditor) {
|
||||
$scope.user_type = $scope.user_type_options[1];
|
||||
$scope.is_system_auditor = true;
|
||||
}
|
||||
if (data.is_superuser) {
|
||||
$scope.user_type = $scope.user_type_options[2];
|
||||
$scope.is_superuser = true;
|
||||
}
|
||||
|
||||
var setScopeFields = function(data){
|
||||
$scope.user_obj = data;
|
||||
|
||||
CreateSelect2({
|
||||
element: '#user_user_type',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
$scope.$watch('user_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
|
||||
setScopeFields(data);
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
function setScopeFields(data) {
|
||||
_(data)
|
||||
.pick(function(value, key){
|
||||
return form.fields.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key){
|
||||
$scope[key] = value;
|
||||
})
|
||||
.value();
|
||||
.pick(function(value, key) {
|
||||
return form.fields.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key) {
|
||||
$scope[key] = value;
|
||||
})
|
||||
.value();
|
||||
return;
|
||||
};
|
||||
}
|
||||
|
||||
$scope.convertApiUrl = function(str) {
|
||||
if (str) {
|
||||
@ -336,25 +292,12 @@ export function UsersEdit($scope, $rootScope, $location,
|
||||
}
|
||||
};
|
||||
|
||||
var setScopeRelated = function(data, related){
|
||||
_(related)
|
||||
.pick(function(value, key){
|
||||
return data.related.hasOwnProperty(key) === true;
|
||||
})
|
||||
.forEach(function(value, key){
|
||||
relatedSets[key] = {
|
||||
url: data.related[key],
|
||||
iterator: value.iterator
|
||||
};
|
||||
})
|
||||
.value();
|
||||
};
|
||||
// prepares a data payload for a PUT request to the API
|
||||
var processNewData = function(fields){
|
||||
var processNewData = function(fields) {
|
||||
var data = {};
|
||||
_.forEach(fields, function(value, key){
|
||||
if ($scope[key] !== '' && $scope[key] !== null && $scope[key] !== undefined){
|
||||
data[key] = $scope[key];
|
||||
_.forEach(fields, function(value, key) {
|
||||
if ($scope[key] !== '' && $scope[key] !== null && $scope[key] !== undefined) {
|
||||
data[key] = $scope[key];
|
||||
}
|
||||
});
|
||||
data.is_superuser = $scope.is_superuser;
|
||||
@ -362,98 +305,37 @@ export function UsersEdit($scope, $rootScope, $location,
|
||||
return data;
|
||||
};
|
||||
|
||||
var init = function(){
|
||||
var url = defaultUrl + id;
|
||||
Rest.setUrl(url);
|
||||
Wait('start');
|
||||
Rest.get(url).success(function(data){
|
||||
$scope.user_id = id;
|
||||
$scope.ldap_user = (data.ldap_dn !== null && data.ldap_dn !== undefined && data.ldap_dn !== '') ? true : false;
|
||||
$scope.not_ldap_user = !$scope.ldap_user;
|
||||
master.ldap_user = $scope.ldap_user;
|
||||
$scope.socialAuthUser = (data.auth.length > 0) ? true : false;
|
||||
$scope.external_account = data.external_account;
|
||||
|
||||
$scope.user_type = $scope.user_type_options[0];
|
||||
$scope.is_system_auditor = false;
|
||||
$scope.is_superuser = false;
|
||||
if (data.is_system_auditor) {
|
||||
$scope.user_type = $scope.user_type_options[1];
|
||||
$scope.is_system_auditor = true;
|
||||
}
|
||||
if (data.is_superuser) {
|
||||
$scope.user_type = $scope.user_type_options[2];
|
||||
$scope.is_superuser = true;
|
||||
}
|
||||
|
||||
$scope.user_obj = data;
|
||||
|
||||
CreateSelect2({
|
||||
element: '#user_user_type',
|
||||
multiple: false
|
||||
});
|
||||
|
||||
|
||||
setScopeFields(data);
|
||||
setScopeRelated(data, form.related);
|
||||
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
for (set in relatedSets) {
|
||||
$scope.search(relatedSets[set].iterator);
|
||||
}
|
||||
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status });
|
||||
});
|
||||
$scope.formCancel = function() {
|
||||
$state.go('users', null, { reload: true });
|
||||
};
|
||||
|
||||
$scope.formCancel = function(){
|
||||
$state.go('users', null, {reload: true});
|
||||
};
|
||||
|
||||
$scope.formSave = function(){
|
||||
generator.clearApiErrors();
|
||||
generator.checkAutoFill();
|
||||
$scope.formSave = function() {
|
||||
$rootScope.flashMessage = null;
|
||||
if ($scope[form.name + '_form'].$valid){
|
||||
if ($scope[form.name + '_form'].$valid) {
|
||||
Rest.setUrl(defaultUrl + id + '/');
|
||||
var data = processNewData(form.fields);
|
||||
Rest.put(data).success(function(){
|
||||
$state.go($state.current, null, {reload: true});
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!', msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status });
|
||||
});
|
||||
Rest.put(data).success(function() {
|
||||
$state.go($state.current, null, { reload: true });
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to retrieve user: ' +
|
||||
$stateParams.id + '. GET status: ' + status
|
||||
});
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
$scope.clearPWConfirm = function (fld) {
|
||||
$scope.clearPWConfirm = function(fld) {
|
||||
// If password value changes, make sure password_confirm must be re-entered
|
||||
$scope[fld] = '';
|
||||
$scope[form.name + '_form'][fld].$setValidity('awpassmatch', false);
|
||||
$rootScope.flashMessage = null;
|
||||
};
|
||||
|
||||
init();
|
||||
|
||||
/* Related Set implementation TDB */
|
||||
}
|
||||
|
||||
UsersEdit.$inject = ['$scope', '$rootScope', '$location',
|
||||
'$stateParams', 'UserForm', 'GenerateForm', 'Rest', 'ProcessErrors',
|
||||
'RelatedSearchInit', 'RelatedPaginateInit', 'ClearScope', 'GetBasePath',
|
||||
'$stateParams', 'UserForm', 'Rest', 'ProcessErrors', 'ClearScope', 'GetBasePath',
|
||||
'ResetForm', 'Wait', 'CreateSelect2', '$state', 'i18n'
|
||||
];
|
||||
|
||||
@ -39,7 +39,7 @@ export default
|
||||
label: i18n._("Hosts")
|
||||
},
|
||||
{
|
||||
url: "/#/home/hosts?active-failures=true",
|
||||
url: "/#/home/hosts?host_search=has_active_failures:true",
|
||||
number: scope.data.hosts.failed,
|
||||
label: i18n._("Failed Hosts"),
|
||||
isFailureCount: true
|
||||
@ -50,7 +50,7 @@ export default
|
||||
label: i18n._("Inventories"),
|
||||
},
|
||||
{
|
||||
url: "/#/inventories?status=sync-failed",
|
||||
url: "/#/inventories?inventory_search=inventory_sources_with_failures__gt:0",
|
||||
number: scope.data.inventories.inventory_failed,
|
||||
label: i18n._("Inventory Sync Failures"),
|
||||
isFailureCount: true
|
||||
@ -61,7 +61,7 @@ export default
|
||||
label: i18n._("Projects")
|
||||
},
|
||||
{
|
||||
url: "/#/projects?status=failed,canceled",
|
||||
url: "/#/projects?project_search=status__in:failed,canceled",
|
||||
number: scope.data.projects.failed,
|
||||
label: i18n._("Project Sync Failures"),
|
||||
isFailureCount: true
|
||||
|
||||
@ -1,4 +0,0 @@
|
||||
<div class="tab-pane" id="organizations">
|
||||
<div ui-view></div>
|
||||
<div ng-cloak id="htmlTemplate" class="Panel"></div>
|
||||
</div>
|
||||
@ -4,86 +4,52 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$scope', '$state', '$stateParams', 'PageRangeSetup', 'GetBasePath', 'DashboardHostsList',
|
||||
'generateList', 'PaginateInit', 'SetStatus', 'DashboardHostService', 'hosts', '$rootScope', 'SearchInit',
|
||||
function($scope, $state, $stateParams, PageRangeSetup, GetBasePath, DashboardHostsList, GenerateList, PaginateInit, SetStatus, DashboardHostService, hosts, $rootScope, SearchInit){
|
||||
var setJobStatus = function(){
|
||||
_.forEach($scope.hosts, function(value){
|
||||
SetStatus({
|
||||
scope: $scope,
|
||||
host: value
|
||||
});
|
||||
});
|
||||
};
|
||||
var generator = GenerateList,
|
||||
list = DashboardHostsList,
|
||||
defaultUrl = GetBasePath('hosts');
|
||||
$scope.hostPageSize = 10;
|
||||
$scope.editHost = function(id){
|
||||
$state.go('dashboardHosts.edit', {id: id});
|
||||
};
|
||||
$scope.toggleHostEnabled = function(host){
|
||||
DashboardHostService.setHostStatus(host, !host.enabled)
|
||||
.then(function(res){
|
||||
var index = _.findIndex($scope.hosts, function(o) {return o.id === res.data.id;});
|
||||
$scope.hosts[index].enabled = res.data.enabled;
|
||||
});
|
||||
};
|
||||
$scope.$on('PostRefresh', function(){
|
||||
$scope.hosts = _.map($scope.hosts, function(value){
|
||||
value.inventory_name = value.summary_fields.inventory.name;
|
||||
value.inventory_id = value.summary_fields.inventory.id;
|
||||
return value;
|
||||
});
|
||||
setJobStatus();
|
||||
});
|
||||
var cleanUpStateChangeListener = $rootScope.$on('$stateChangeSuccess', function(event, toState, toParams) {
|
||||
if (toState.name === "dashboardHosts.edit") {
|
||||
$scope.rowBeingEdited = toParams.id;
|
||||
$scope.listBeingEdited = "hosts";
|
||||
}
|
||||
else {
|
||||
delete $scope.rowBeingEdited;
|
||||
delete $scope.listBeingEdited;
|
||||
}
|
||||
});
|
||||
// Remove the listener when the scope is destroyed to avoid a memory leak
|
||||
$scope.$on('$destroy', function() {
|
||||
cleanUpStateChangeListener();
|
||||
});
|
||||
var init = function(){
|
||||
$scope.list = list;
|
||||
$scope.host_active_search = false;
|
||||
$scope.host_total_rows = hosts.results.length;
|
||||
$scope.hosts = hosts.results;
|
||||
setJobStatus();
|
||||
generator.inject(list, {mode: 'edit', scope: $scope});
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'hosts',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl,
|
||||
pageSize: 10
|
||||
});
|
||||
PageRangeSetup({
|
||||
scope: $scope,
|
||||
count: hosts.count,
|
||||
next: hosts.next,
|
||||
previous: hosts.previous,
|
||||
iterator: list.iterator
|
||||
export default ['$scope', '$state', '$stateParams', 'GetBasePath', 'DashboardHostsList',
|
||||
'generateList', 'SetStatus', 'DashboardHostService', '$rootScope', 'Dataset',
|
||||
function($scope, $state, $stateParams, GetBasePath, DashboardHostsList,
|
||||
GenerateList, SetStatus, DashboardHostService, $rootScope, Dataset) {
|
||||
|
||||
let list = DashboardHostsList;
|
||||
init();
|
||||
|
||||
function init() {
|
||||
// search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
$scope.$watchCollection(list.name, function() {
|
||||
$scope[list.name] = _.map($scope.hosts, function(value) {
|
||||
value.inventory_name = value.summary_fields.inventory.name;
|
||||
value.inventory_id = value.summary_fields.inventory.id;
|
||||
return value;
|
||||
});
|
||||
setJobStatus();
|
||||
});
|
||||
$scope.hostLoading = false;
|
||||
if($state.current.name === "dashboardHosts.edit") {
|
||||
$scope.rowBeingEdited = $state.params.id;
|
||||
$scope.listBeingEdited = "hosts";
|
||||
}
|
||||
$scope.search(list.iterator);
|
||||
};
|
||||
init();
|
||||
}];
|
||||
}
|
||||
|
||||
|
||||
function setJobStatus(){
|
||||
_.forEach($scope.hosts, function(value) {
|
||||
SetStatus({
|
||||
scope: $scope,
|
||||
host: value
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
$scope.editHost = function(id) {
|
||||
$state.go('dashboardHosts.edit', { id: id });
|
||||
};
|
||||
|
||||
$scope.toggleHostEnabled = function(host) {
|
||||
DashboardHostService.setHostStatus(host, !host.enabled)
|
||||
.then(function(res) {
|
||||
var index = _.findIndex($scope.hosts, function(o) {
|
||||
return o.id === res.data.id;
|
||||
});
|
||||
$scope.hosts[index].enabled = res.data.enabled;
|
||||
});
|
||||
};
|
||||
}
|
||||
];
|
||||
|
||||
@ -1,4 +0,0 @@
|
||||
<div class="tab-pane" id="HomeHosts">
|
||||
<div ui-view></div>
|
||||
<div ng-cloak id="htmlTemplate" class="Panel"></div>
|
||||
</div>
|
||||
@ -18,7 +18,7 @@ export default function(){
|
||||
class: 'Form-header-field',
|
||||
ngClick: 'toggleHostEnabled()',
|
||||
type: 'toggle',
|
||||
editRequired: false,
|
||||
|
||||
awToolTip: "<p>Indicates if a host is available and should be included in running jobs.</p><p>For hosts that " +
|
||||
"are part of an external inventory, this flag cannot be changed. It will be set by the inventory sync process.</p>",
|
||||
dataTitle: 'Host Enabled'
|
||||
@ -28,7 +28,7 @@ export default function(){
|
||||
name: {
|
||||
label: 'Host Name',
|
||||
type: 'text',
|
||||
editRequired: true,
|
||||
|
||||
value: '{{name}}',
|
||||
awPopOver: "<p>Provide a host name, ip address, or ip address:port. Examples include:</p>" +
|
||||
"<blockquote>myserver.domain.com<br/>" +
|
||||
@ -43,12 +43,10 @@ export default function(){
|
||||
description: {
|
||||
label: 'Description',
|
||||
type: 'text',
|
||||
editRequired: false
|
||||
},
|
||||
variables: {
|
||||
label: 'Variables',
|
||||
type: 'textarea',
|
||||
editRequired: false,
|
||||
rows: 6,
|
||||
class: 'modal-input-xlarge Form-textArea Form-formGroup--fullWidth',
|
||||
dataTitle: 'Host Variables',
|
||||
|
||||
@ -21,11 +21,7 @@ export default [ 'i18n', function(i18n){
|
||||
basePath: 'unified_jobs',
|
||||
label: '',
|
||||
iconOnly: true,
|
||||
searchable: false,
|
||||
searchType: 'select',
|
||||
nosort: true,
|
||||
searchOptions: [],
|
||||
searchLabel: 'Job Status',
|
||||
icon: 'icon-job-{{ host.active_failures }}',
|
||||
awToolTip: '{{ host.badgeToolTip }}',
|
||||
awTipPlacement: 'right',
|
||||
@ -54,24 +50,9 @@ export default [ 'i18n', function(i18n){
|
||||
columnClass: 'List-staticColumn--toggle',
|
||||
type: 'toggle',
|
||||
ngClick: 'toggleHostEnabled(host)',
|
||||
searchable: false,
|
||||
nosort: true,
|
||||
awToolTip: "<p>Indicates if a host is available and should be included in running jobs.</p><p>For hosts that are part of an external inventory, this flag cannot be changed. It will be set by the inventory sync process.</p>",
|
||||
dataTitle: 'Host Enabled',
|
||||
},
|
||||
has_active_failures: {
|
||||
label: 'Has failed jobs?',
|
||||
searchSingleValue: true,
|
||||
searchType: 'boolean',
|
||||
searchValue: 'true',
|
||||
searchOnly: true
|
||||
},
|
||||
has_inventory_sources: {
|
||||
label: 'Has external source?',
|
||||
searchSingleValue: true,
|
||||
searchType: 'boolean',
|
||||
searchValue: 'true',
|
||||
searchOnly: true
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@ -1,61 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
import listController from './dashboard-hosts-list.controller';
|
||||
import editController from './dashboard-hosts-edit.controller';
|
||||
|
||||
var dashboardHostsList = {
|
||||
name: 'dashboardHosts',
|
||||
url: '/home/hosts?:active-failures',
|
||||
controller: listController,
|
||||
templateUrl: templateUrl('dashboard/hosts/dashboard-hosts-list'),
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'host'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'dashboard',
|
||||
label: "HOSTS"
|
||||
},
|
||||
resolve: {
|
||||
hosts: ['Rest', 'GetBasePath', '$stateParams', function(Rest, GetBasePath, $stateParams){
|
||||
var defaultUrl = GetBasePath('hosts') + '?page_size=10' + ($stateParams['active-failures'] ? '&has_active_failures=true' : '' );
|
||||
Rest.setUrl(defaultUrl);
|
||||
return Rest.get().then(function(res){
|
||||
var results = _.map(res.data.results, function(value){
|
||||
value.inventory_name = value.summary_fields.inventory.name;
|
||||
value.inventory_id = value.summary_fields.inventory.id;
|
||||
return value;
|
||||
});
|
||||
res.data.results = results;
|
||||
return res.data;
|
||||
});
|
||||
}]
|
||||
}
|
||||
};
|
||||
|
||||
var dashboardHostsEdit = {
|
||||
name: 'dashboardHosts.edit',
|
||||
url: '/:id',
|
||||
controller: editController,
|
||||
templateUrl: templateUrl('dashboard/hosts/dashboard-hosts-edit'),
|
||||
ncyBreadcrumb: {
|
||||
parent: 'dashboardHosts',
|
||||
label: "{{host.name}}"
|
||||
},
|
||||
resolve: {
|
||||
host: ['$stateParams', 'Rest', 'GetBasePath', function($stateParams, Rest, GetBasePath){
|
||||
var defaultUrl = GetBasePath('hosts') + '?id=' + $stateParams.id;
|
||||
Rest.setUrl(defaultUrl);
|
||||
return Rest.get().then(function(res){
|
||||
return res.data.results[0];
|
||||
});
|
||||
}]
|
||||
}
|
||||
};
|
||||
|
||||
export {dashboardHostsList, dashboardHostsEdit};
|
||||
@ -4,17 +4,43 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {dashboardHostsList, dashboardHostsEdit} from './dashboard-hosts.route';
|
||||
import list from './dashboard-hosts.list';
|
||||
import form from './dashboard-hosts.form';
|
||||
import listController from './dashboard-hosts-list.controller';
|
||||
import editController from './dashboard-hosts-edit.controller';
|
||||
import service from './dashboard-hosts.service';
|
||||
|
||||
export default
|
||||
angular.module('dashboardHosts', [])
|
||||
angular.module('dashboardHosts', [])
|
||||
.service('DashboardHostService', service)
|
||||
.factory('DashboardHostsList', list)
|
||||
.factory('DashboardHostsForm', form)
|
||||
.run(['$stateExtender', function($stateExtender){
|
||||
$stateExtender.addState(dashboardHostsList);
|
||||
$stateExtender.addState(dashboardHostsEdit);
|
||||
}]);
|
||||
.config(['$stateProvider', 'stateDefinitionsProvider',
|
||||
function($stateProvider, stateDefinitionsProvider) {
|
||||
let stateDefinitions = stateDefinitionsProvider.$get();
|
||||
|
||||
$stateProvider.state({
|
||||
name: 'dashboardHosts',
|
||||
url: '/home/hosts',
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
url: '/home/hosts',
|
||||
parent: 'dashboardHosts',
|
||||
modes: ['edit'],
|
||||
list: 'DashboardHostsList',
|
||||
form: 'DashboardHostsForm',
|
||||
controllers: {
|
||||
list: listController,
|
||||
edit: editController
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'host'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'dashboard',
|
||||
label: "HOSTS"
|
||||
},
|
||||
})
|
||||
});
|
||||
}
|
||||
]);
|
||||
|
||||
@ -18,6 +18,8 @@ export default
|
||||
addTitle: i18n._('Create Credential'), //Legend in add mode
|
||||
editTitle: '{{ name }}', //Legend in edit mode
|
||||
name: 'credential',
|
||||
// the top-most node of generated state tree
|
||||
stateTree: 'credentials',
|
||||
forceListeners: true,
|
||||
subFormTitles: {
|
||||
credentialSubForm: i18n._('Type Details'),
|
||||
@ -31,24 +33,22 @@ export default
|
||||
name: {
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
autocomplete: false,
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
description: {
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
organization: {
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
// interpolated with $rootScope
|
||||
basePath: "{{$rootScope.current_user.is_superuser ? 'api/v1/organizations' : $rootScope.current_user.url + 'admin_of_organizations'}}",
|
||||
ngShow: 'canShareCredential',
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
list: 'OrganizationList',
|
||||
sourceModel: 'organization',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpOrganization()',
|
||||
@ -56,7 +56,7 @@ export default
|
||||
dataTitle: i18n._('Organization') + ' ',
|
||||
dataPlacement: 'bottom',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
kind: {
|
||||
label: i18n._('Type'),
|
||||
@ -64,8 +64,7 @@ export default
|
||||
type: 'select',
|
||||
ngOptions: 'kind.label for kind in credential_kind_options track by kind.value', // select as label for value in array 'kind.label for kind in credential_kind_options',
|
||||
ngChange: 'kindChange()',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
awPopOver: i18n._('<dl>\n' +
|
||||
'<dt>Machine</dt>\n' +
|
||||
'<dd>Authentication for remote machine access. This can include SSH keys, usernames, passwords, ' +
|
||||
@ -88,7 +87,7 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
hasSubForm: true,
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
access_key: {
|
||||
label: i18n._('Access Key'),
|
||||
@ -101,7 +100,7 @@ export default
|
||||
autocomplete: false,
|
||||
apiField: 'username',
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
secret_key: {
|
||||
label: i18n._('Secret Key'),
|
||||
@ -130,7 +129,7 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"host": {
|
||||
labelBind: 'hostLabel',
|
||||
@ -147,7 +146,7 @@ export default
|
||||
init: false
|
||||
},
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"subscription": {
|
||||
label: i18n._("Subscription ID"),
|
||||
@ -157,15 +156,15 @@ export default
|
||||
reqExpression: 'subscription_required',
|
||||
init: false
|
||||
},
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
autocomplete: false,
|
||||
awPopOver: i18n._('<p>Subscription ID is an Azure construct, which is mapped to a username.</p>'),
|
||||
dataTitle: i18n._('Subscription ID'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"username": {
|
||||
labelBind: 'usernameLabel',
|
||||
@ -178,7 +177,7 @@ export default
|
||||
},
|
||||
autocomplete: false,
|
||||
subForm: "credentialSubForm",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"email_address": {
|
||||
labelBind: 'usernameLabel',
|
||||
@ -194,7 +193,7 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"api_key": {
|
||||
label: i18n._('API Key'),
|
||||
@ -208,7 +207,7 @@ export default
|
||||
hasShowInputButton: true,
|
||||
clear: false,
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"password": {
|
||||
labelBind: 'passwordLabel',
|
||||
@ -222,15 +221,13 @@ export default
|
||||
init: false
|
||||
},
|
||||
subForm: "credentialSubForm",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"ssh_password": {
|
||||
label: i18n._('Password'),
|
||||
type: 'sensitive',
|
||||
ngShow: "kind.value == 'ssh'",
|
||||
ngDisabled: "ssh_password_ask || !(credential_obj.summary_fields.user_capabilities.edit || canAdd)",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
subCheckbox: {
|
||||
variable: 'ssh_password_ask',
|
||||
text: i18n._('Ask at runtime?'),
|
||||
@ -251,8 +248,8 @@ export default
|
||||
},
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
elementClass: 'Form-monospace',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
awDropFile: true,
|
||||
rows: 10,
|
||||
awPopOver: i18n._("SSH key description"),
|
||||
@ -261,14 +258,12 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
subForm: "credentialSubForm",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"ssh_key_unlock": {
|
||||
label: i18n._('Private Key Passphrase'),
|
||||
type: 'sensitive',
|
||||
ngShow: "kind.value == 'ssh' || kind.value == 'scm'",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: "keyEntered === false || ssh_key_unlock_ask || !(credential_obj.summary_fields.user_capabilities.edit || canAdd)",
|
||||
subCheckbox: {
|
||||
variable: 'ssh_key_unlock_ask',
|
||||
@ -293,25 +288,23 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"become_username": {
|
||||
labelBind: 'becomeUsernameLabel',
|
||||
type: 'text',
|
||||
ngShow: "(kind.value == 'ssh' && (become_method && become_method.value)) ",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
autocomplete: false,
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"become_password": {
|
||||
labelBind: 'becomePasswordLabel',
|
||||
type: 'sensitive',
|
||||
ngShow: "(kind.value == 'ssh' && (become_method && become_method.value)) ",
|
||||
ngDisabled: "become_password_ask || !(credential_obj.summary_fields.user_capabilities.edit || canAdd)",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
subCheckbox: {
|
||||
variable: 'become_password_ask',
|
||||
text: i18n._('Ask at runtime?'),
|
||||
@ -326,7 +319,7 @@ export default
|
||||
label: i18n._('Client ID'),
|
||||
subForm: 'credentialSubForm',
|
||||
ngShow: "kind.value === 'azure_rm'",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
secret:{
|
||||
type: 'sensitive',
|
||||
@ -335,14 +328,14 @@ export default
|
||||
label: i18n._('Client Secret'),
|
||||
subForm: 'credentialSubForm',
|
||||
ngShow: "kind.value === 'azure_rm'",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
tenant: {
|
||||
type: 'text',
|
||||
label: i18n._('Tenant ID'),
|
||||
subForm: 'credentialSubForm',
|
||||
ngShow: "kind.value === 'azure_rm'",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
authorize: {
|
||||
label: i18n._('Authorize'),
|
||||
@ -350,7 +343,7 @@ export default
|
||||
ngChange: "toggleCallback('host_config_key')",
|
||||
subForm: 'credentialSubForm',
|
||||
ngShow: "kind.value === 'net'",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
authorize_password: {
|
||||
label: i18n._('Authorize Password'),
|
||||
@ -359,7 +352,7 @@ export default
|
||||
autocomplete: false,
|
||||
subForm: 'credentialSubForm',
|
||||
ngShow: "authorize && authorize !== 'false'",
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"project": {
|
||||
labelBind: 'projectLabel',
|
||||
@ -370,14 +363,12 @@ export default
|
||||
dataTitle: i18n._('Project Name'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awRequiredWhen: {
|
||||
reqExpression: 'project_required',
|
||||
init: false
|
||||
},
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
"domain": {
|
||||
labelBind: 'domainLabel',
|
||||
@ -391,18 +382,14 @@ export default
|
||||
dataTitle: i18n._('Domain Name'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
subForm: 'credentialSubForm',
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
subForm: 'credentialSubForm'
|
||||
},
|
||||
"vault_password": {
|
||||
label: i18n._("Vault Password"),
|
||||
type: 'sensitive',
|
||||
ngShow: "kind.value == 'ssh'",
|
||||
ngDisabled: "vault_password_ask || !(credential_obj.summary_fields.user_capabilities.edit || canAdd)",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
subCheckbox: {
|
||||
variable: 'vault_password_ask',
|
||||
text: i18n._('Ask at runtime?'),
|
||||
@ -417,17 +404,17 @@ export default
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
label: 'Save',
|
||||
ngClick: 'formSave()', //$scope.function to call on click, optional
|
||||
ngDisabled: true,
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || canAdd)' //Disable when $pristine or $invalid, optional
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || !canAdd)' //Disable when $pristine or $invalid, optional
|
||||
}
|
||||
},
|
||||
|
||||
@ -437,24 +424,25 @@ export default
|
||||
awToolTip: '{{permissionsTooltip}}',
|
||||
dataTipWatch: 'permissionsTooltip',
|
||||
dataPlacement: 'top',
|
||||
basePath: 'credentials/:id/access_list/',
|
||||
basePath: 'api/v1/credentials/{{$stateParams.credential_id}}/access_list/',
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
type: 'collection',
|
||||
title: i18n._('Permissions'),
|
||||
iterator: 'permission',
|
||||
index: false,
|
||||
open: false,
|
||||
searchType: 'select',
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermission",
|
||||
ngClick: "$state.go('.add')",
|
||||
label: 'Add',
|
||||
awToolTip: i18n._('Add a permission'),
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: i18n._('+ ADD'),
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(credential_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
fields: {
|
||||
username: {
|
||||
key: true,
|
||||
|
||||
@ -18,31 +18,31 @@ export default
|
||||
editTitle: '{{ name }}',
|
||||
showTitle: true,
|
||||
name: 'group',
|
||||
basePath: 'groups',
|
||||
// the parent node this generated state definition tree expects to attach to
|
||||
stateTree: 'inventoryManage',
|
||||
// form generator inspects the current state name to determine whether or not to set an active (.is-selected) class on a form tab
|
||||
// this setting is optional on most forms, except where the form's edit state name is not parentStateName.edit
|
||||
activeEditState: 'inventoryManage.editGroup',
|
||||
well: false,
|
||||
|
||||
fields: {
|
||||
name: {
|
||||
label: 'Name',
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
tab: 'properties',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '(!group_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
tab: 'properties'
|
||||
},
|
||||
description: {
|
||||
label: 'Description',
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
tab: 'properties',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '(!group_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
tab: 'properties'
|
||||
},
|
||||
variables: {
|
||||
label: 'Variables',
|
||||
type: 'textarea',
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
rows: 12,
|
||||
'default': '---',
|
||||
dataTitle: 'Group Variables',
|
||||
@ -65,23 +65,23 @@ export default
|
||||
type: 'select',
|
||||
ngOptions: 'source.label for source in source_type_options track by source.value',
|
||||
ngChange: 'sourceChange(source)',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngModel: 'source',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '(!group_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
ngModel: 'source'
|
||||
},
|
||||
credential: {
|
||||
label: 'Cloud Credential',
|
||||
type: 'lookup',
|
||||
list: 'CredentialList',
|
||||
basePath: 'credentials',
|
||||
ngShow: "source && source.value !== '' && source.value !== 'custom'",
|
||||
sourceModel: 'credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpCredential()',
|
||||
ngClick: 'lookupCredential()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "cloudCredentialRequired",
|
||||
init: "false"
|
||||
},
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '(!group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
source_regions: {
|
||||
label: 'Regions',
|
||||
@ -89,22 +89,20 @@ export default
|
||||
ngOptions: 'source.label for source in source_region_choices track by source.value',
|
||||
multiSelect: true,
|
||||
ngShow: "source && (source.value == 'rax' || source.value == 'ec2' || source.value == 'gce' || source.value == 'azure' || source.value == 'azure_rm')",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
dataTitle: 'Source Regions',
|
||||
dataPlacement: 'right',
|
||||
awPopOver: "<p>Click on the regions field to see a list of regions for your cloud provider. You can select multiple regions, " +
|
||||
"or choose <em>All</em> to include all regions. Tower will only be updated with Hosts associated with the selected regions." +
|
||||
"</p>",
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
instance_filters: {
|
||||
label: 'Instance Filters',
|
||||
type: 'text',
|
||||
ngShow: "source && source.value == 'ec2'",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
dataTitle: 'Instance Filters',
|
||||
dataPlacement: 'right',
|
||||
awPopOver: "<p>Provide a comma-separated list of filter expressions. " +
|
||||
@ -118,15 +116,13 @@ export default
|
||||
"<p>View the <a href=\"http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html\" target=\"_blank\">Describe Instances documentation</a> " +
|
||||
"for a complete list of supported filters.</p>",
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
group_by: {
|
||||
label: 'Only Group By',
|
||||
type: 'select',
|
||||
ngShow: "source && source.value == 'ec2'",
|
||||
ngOptions: 'source.label for source in group_by_choices track by source.value',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
multiSelect: true,
|
||||
dataTitle: 'Only Group By',
|
||||
dataPlacement: 'right',
|
||||
@ -144,19 +140,19 @@ export default
|
||||
"<li>Tag None: <strong>tags » tag_none</strong></li>" +
|
||||
"</ul><p>If blank, all groups above are created except <em>Instance ID</em>.</p>",
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
inventory_script: {
|
||||
label : "Custom Inventory Script",
|
||||
type: 'lookup',
|
||||
basePath: 'inventory_scripts',
|
||||
list: 'InventoryScriptList',
|
||||
ngShow: "source && source.value === 'custom'",
|
||||
sourceModel: 'inventory_script',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpInventory_script()' ,
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
ngRequired: "source && source.value === 'custom'",
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
},
|
||||
custom_variables: {
|
||||
id: 'custom_variables',
|
||||
@ -164,8 +160,6 @@ export default
|
||||
ngShow: "source && source.value=='custom' ",
|
||||
type: 'textarea',
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
rows: 6,
|
||||
'default': '---',
|
||||
parseTypeName: 'envParseType',
|
||||
@ -187,8 +181,6 @@ export default
|
||||
ngShow: "source && source.value == 'ec2'",
|
||||
type: 'textarea',
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
rows: 6,
|
||||
'default': '---',
|
||||
parseTypeName: 'envParseType',
|
||||
@ -209,12 +201,9 @@ export default
|
||||
vmware_variables: {
|
||||
id: 'vmware_variables',
|
||||
label: 'Source Variables', //"{{vars_label}}" ,
|
||||
|
||||
ngShow: "source && source.value == 'vmware'",
|
||||
type: 'textarea',
|
||||
addRequired: false,
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
editRequird: false,
|
||||
rows: 6,
|
||||
'default': '---',
|
||||
parseTypeName: 'envParseType',
|
||||
@ -235,12 +224,9 @@ export default
|
||||
openstack_variables: {
|
||||
id: 'openstack_variables',
|
||||
label: 'Source Variables', //"{{vars_label}}" ,
|
||||
|
||||
ngShow: "source && source.value == 'openstack'",
|
||||
type: 'textarea',
|
||||
addRequired: false,
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
editRequird: false,
|
||||
rows: 6,
|
||||
'default': '---',
|
||||
parseTypeName: 'envParseType',
|
||||
@ -263,14 +249,13 @@ export default
|
||||
type: 'checkbox_group',
|
||||
ngShow: "source && (source.value !== '' && source.value !== null)",
|
||||
class: 'Form-checkbox--stacked',
|
||||
|
||||
fields: [{
|
||||
name: 'overwrite',
|
||||
label: 'Overwrite',
|
||||
type: 'checkbox',
|
||||
ngShow: "source.value !== '' && source.value !== null",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
awPopOver: '<p>If checked, all child groups and hosts not found on the external source will be deleted from ' +
|
||||
'the local inventory.</p><p>When not checked, local child hosts and groups not found on the external source will ' +
|
||||
'remain untouched by the inventory update process.</p>',
|
||||
@ -278,14 +263,14 @@ export default
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}, {
|
||||
name: 'overwrite_vars',
|
||||
label: 'Overwrite Variables',
|
||||
type: 'checkbox',
|
||||
ngShow: "source.value !== '' && source.value !== null",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
awPopOver: '<p>If checked, all variables for child groups and hosts will be removed and replaced by those ' +
|
||||
'found on the external source.</p><p>When not checked, a merge will be performed, combining local variables with ' +
|
||||
'those found on the external source.</p>',
|
||||
@ -293,21 +278,19 @@ export default
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}, {
|
||||
name: 'update_on_launch',
|
||||
label: 'Update on Launch',
|
||||
type: 'checkbox',
|
||||
ngShow: "source.value !== '' && source.value !== null",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: '<p>Each time a job runs using this inventory, refresh the inventory from the selected source before ' +
|
||||
'executing job tasks.</p>',
|
||||
dataTitle: 'Update on Launch',
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options',
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}]
|
||||
},
|
||||
update_cache_timeout: {
|
||||
@ -319,8 +302,6 @@ export default
|
||||
ngShow: "source && source.value !== '' && update_on_launch",
|
||||
spinner: true,
|
||||
"default": 0,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: '<p>Time in seconds to consider an inventory sync to be current. During job runs and callbacks the task system will ' +
|
||||
'evaluate the timestamp of the latest sync. If it is older than Cache Timeout, it is not considered current, ' +
|
||||
'and a new inventory sync will be performed.</p>',
|
||||
@ -333,16 +314,16 @@ export default
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(group_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(group_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@ -26,8 +26,7 @@ export default
|
||||
type: 'select',
|
||||
multiple: true,
|
||||
ngOptions: 'group.name for group in inventory_groups track by group.value',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
awPopOver: "<p>Provide a host name, ip address, or ip address:port. Examples include:</p>" +
|
||||
"<blockquote>myserver.domain.com<br/>" +
|
||||
"127.0.0.1<br />" +
|
||||
|
||||
@ -17,6 +17,7 @@ export default
|
||||
addTitle: 'Create Host',
|
||||
editTitle: '{{ host.name }}',
|
||||
name: 'host',
|
||||
basePath: 'hosts',
|
||||
well: false,
|
||||
formLabelSize: 'col-lg-3',
|
||||
formFieldSize: 'col-lg-9',
|
||||
@ -26,7 +27,6 @@ export default
|
||||
class: 'Form-header-field',
|
||||
ngClick: 'toggleHostEnabled(host)',
|
||||
type: 'toggle',
|
||||
editRequired: false,
|
||||
awToolTip: "<p>Indicates if a host is available and should be included in running jobs.</p><p>For hosts that " +
|
||||
"are part of an external inventory, this flag cannot be changed. It will be set by the inventory sync process.</p>",
|
||||
dataTitle: 'Host Enabled',
|
||||
@ -36,8 +36,7 @@ export default
|
||||
name: {
|
||||
label: 'Host Name',
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
awPopOver: "<p>Provide a host name, ip address, or ip address:port. Examples include:</p>" +
|
||||
"<blockquote>myserver.domain.com<br/>" +
|
||||
"127.0.0.1<br />" +
|
||||
@ -47,22 +46,18 @@ export default
|
||||
dataTitle: 'Host Name',
|
||||
dataPlacement: 'right',
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(host.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(host.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
description: {
|
||||
label: 'Description',
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(host.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(host.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
type: 'text'
|
||||
},
|
||||
variables: {
|
||||
label: 'Variables',
|
||||
type: 'textarea',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
rows: 6,
|
||||
"class": "modal-input-xlarge Form-textArea Form-formGroup--fullWidth",
|
||||
class: 'Form-formGroup--fullWidth',
|
||||
"default": "---",
|
||||
awPopOver: "<p>Enter variables using either JSON or YAML syntax. Use the radio button to toggle between the two.</p>" +
|
||||
"JSON:<br />\n" +
|
||||
@ -85,19 +80,16 @@ export default
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(host.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(host.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(host.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(host.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(host.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(host.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {}
|
||||
|
||||
});
|
||||
|
||||
@ -4,91 +4,136 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name forms.function:Inventories
|
||||
* @description This form is for adding/editing an inventory
|
||||
*/
|
||||
*/
|
||||
|
||||
export default
|
||||
angular.module('InventoryFormDefinition', ['ScanJobsListDefinition'])
|
||||
.factory('InventoryFormObject', ['i18n', function(i18n) {
|
||||
angular.module('InventoryFormDefinition', ['ScanJobsListDefinition'])
|
||||
.factory('InventoryFormObject', ['i18n', function(i18n) {
|
||||
return {
|
||||
|
||||
addTitle: i18n._('New Inventory'),
|
||||
editTitle: '{{ inventory_name }}',
|
||||
name: 'inventory',
|
||||
tabs: true,
|
||||
addTitle: 'New Inventory',
|
||||
editTitle: '{{ inventory_name }}',
|
||||
name: 'inventory',
|
||||
basePath: 'inventory',
|
||||
// the top-most node of this generated state tree
|
||||
stateTree: 'inventories',
|
||||
tabs: true,
|
||||
|
||||
fields: {
|
||||
inventory_name: {
|
||||
realName: 'name',
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: false,
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
fields: {
|
||||
inventory_name: {
|
||||
realName: 'name',
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
required: true,
|
||||
capitalize: false,
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
inventory_description: {
|
||||
realName: 'description',
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
organization: {
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
basePath: 'organizations',
|
||||
list: 'OrganizationList',
|
||||
sourceModel: 'organization',
|
||||
sourceField: 'name',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "organizationrequired",
|
||||
init: "true"
|
||||
},
|
||||
inventory_description: {
|
||||
realName: 'description',
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
variables: {
|
||||
label: i18n._('Variables'),
|
||||
type: 'textarea',
|
||||
class: 'Form-formGroup--fullWidth',
|
||||
rows: 6,
|
||||
"default": "---",
|
||||
awPopOver: "<p>Enter inventory variables using either JSON or YAML syntax. Use the radio button to toggle between the two.</p>" +
|
||||
"JSON:<br />\n" +
|
||||
"<blockquote>{<br /> \"somevar\": \"somevalue\",<br /> \"password\": \"magic\"<br /> }</blockquote>\n" +
|
||||
"YAML:<br />\n" +
|
||||
"<blockquote>---<br />somevar: somevalue<br />password: magic<br /></blockquote>\n" +
|
||||
'<p>View JSON examples at <a href="http://www.json.org" target="_blank">www.json.org</a></p>' +
|
||||
'<p>View YAML examples at <a href="http://docs.ansible.com/YAMLSyntax.html" target="_blank">docs.ansible.com</a></p>',
|
||||
dataTitle: 'Inventory Variables',
|
||||
dataPlacement: 'right',
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)' // TODO: get working
|
||||
}
|
||||
},
|
||||
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngHide: '(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
related: {
|
||||
permissions: {
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
dataPlacement: 'top',
|
||||
basePath: 'api/v1/inventories/{{$stateParams.inventory_id}}/access_list/',
|
||||
type: 'collection',
|
||||
title: 'Permissions',
|
||||
iterator: 'permission',
|
||||
index: false,
|
||||
open: false,
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
organization: {
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
sourceModel: 'organization',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpOrganization()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "organizationrequired",
|
||||
init: "true"
|
||||
actions: {
|
||||
add: {
|
||||
label: i18n._('Add'),
|
||||
ngClick: "$state.go('.add')",
|
||||
awToolTip: 'Add a permission',
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: '+ ADD',
|
||||
ngShow: '(inventory_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
|
||||
}
|
||||
},
|
||||
fields: {
|
||||
username: {
|
||||
label: i18n._('User'),
|
||||
linkBase: 'users',
|
||||
class: 'col-lg-3 col-md-3 col-sm-3 col-xs-4'
|
||||
},
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
},
|
||||
variables: {
|
||||
label: i18n._('Variables'),
|
||||
type: 'textarea',
|
||||
class: 'Form-formGroup--fullWidth',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
rows: 6,
|
||||
"default": "---",
|
||||
awPopOver: i18n._("<p>Enter inventory variables using either JSON or YAML syntax. Use the radio button to toggle between the two.</p>" +
|
||||
"JSON:<br />\n" +
|
||||
"<blockquote>{<br /> \"somevar\": \"somevalue\",<br /> \"password\": \"magic\"<br /> }</blockquote>\n" +
|
||||
"YAML:<br />\n" +
|
||||
"<blockquote>---<br />somevar: somevalue<br />password: magic<br /></blockquote>\n" +
|
||||
'<p>View JSON examples at <a href="http://www.json.org" target="_blank">www.json.org</a></p>' +
|
||||
'<p>View YAML examples at <a href="http://docs.ansible.com/YAMLSyntax.html" target="_blank">docs.ansible.com</a></p>'),
|
||||
dataTitle: i18n._('Inventory Variables'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(inventory_obj.summary_fields.user_capabilities.edit || canAdd)' // TODO: get working
|
||||
role: {
|
||||
label: i18n._('Role'),
|
||||
type: 'role',
|
||||
noSort: true,
|
||||
class: 'col-lg-4 col-md-4 col-sm-4 col-xs-4',
|
||||
},
|
||||
team_roles: {
|
||||
label: i18n._('Team Roles'),
|
||||
type: 'team_roles',
|
||||
noSort: true,
|
||||
class: 'col-lg-5 col-md-5 col-sm-5 col-xs-4',
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
},
|
||||
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngHide: '(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(inventory_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {
|
||||
relatedSets: function(urls) {
|
||||
return {
|
||||
permissions: {
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
dataPlacement: 'top',
|
||||
@ -102,7 +147,7 @@ export default
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermission",
|
||||
label: 'Add',
|
||||
label: i18n._('Add'),
|
||||
awToolTip: i18n._('Add a permission'),
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: i18n._('+ ADD'),
|
||||
@ -133,28 +178,22 @@ export default
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
relatedSets: function(urls) {
|
||||
return {
|
||||
permissions: {
|
||||
iterator: 'permission',
|
||||
url: urls.access_list
|
||||
}
|
||||
};
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
};}])
|
||||
.factory('InventoryForm', ['InventoryFormObject', 'ScanJobsList',
|
||||
|
||||
.factory('InventoryForm', ['InventoryFormObject', 'ScanJobsList',
|
||||
function(InventoryFormObject, ScanJobsList) {
|
||||
return function() {
|
||||
var itm;
|
||||
for (itm in InventoryFormObject.related) {
|
||||
if (InventoryFormObject.related[itm].include === "ScanJobsList") {
|
||||
InventoryFormObject.related[itm] = ScanJobsList;
|
||||
InventoryFormObject.related[itm].generateList = true; // tell form generator to call list generator and inject a list
|
||||
InventoryFormObject.related[itm] = ScanJobsList;
|
||||
InventoryFormObject.related[itm].generateList = true; // tell form generator to call list generator and inject a list
|
||||
}
|
||||
}
|
||||
return InventoryFormObject;
|
||||
};
|
||||
}]);
|
||||
}
|
||||
]);
|
||||
|
||||
@ -19,26 +19,27 @@ export default
|
||||
|
||||
addTitle: i18n._('New Job Template'),
|
||||
editTitle: '{{ name }}',
|
||||
name: 'job_templates',
|
||||
base: 'job_templates',
|
||||
name: 'job_template',
|
||||
basePath: 'job_templates',
|
||||
// the top-most node of generated state tree
|
||||
stateTree: 'jobTemplates',
|
||||
tabs: true,
|
||||
// (optional) array of supporting templates to ng-include inside generated html
|
||||
include: ['/static/partials/survey-maker-modal.html'],
|
||||
|
||||
fields: {
|
||||
name: {
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
column: 1,
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
column: 1
|
||||
},
|
||||
description: {
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
column: 1,
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
job_type: {
|
||||
label: i18n._('Job Type'),
|
||||
@ -46,8 +47,7 @@ export default
|
||||
ngOptions: 'type.label for type in job_type_options track by type.value',
|
||||
ngChange: 'jobTypeChange()',
|
||||
"default": 0,
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
column: 1,
|
||||
awPopOver: i18n._("<p>When this template is submitted as a job, setting the type to <em>run</em> will execute the playbook, running tasks " +
|
||||
" on the selected hosts.</p> <p>Setting the type to <em>check</em> will not execute the playbook. Instead, <code>ansible</code> will check playbook " +
|
||||
@ -61,14 +61,15 @@ export default
|
||||
ngShow: "!job_type.value || job_type.value !== 'scan'",
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
inventory: {
|
||||
label: i18n._('Inventory'),
|
||||
type: 'lookup',
|
||||
basePath: 'inventory',
|
||||
list: 'InventoryList',
|
||||
sourceModel: 'inventory',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpInventory()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: '!ask_inventory_on_launch',
|
||||
alwaysShowAsterisk: true
|
||||
@ -84,7 +85,7 @@ export default
|
||||
ngShow: "!job_type.value || job_type.value !== 'scan'",
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
project: {
|
||||
label: i18n._('Project'),
|
||||
@ -94,9 +95,10 @@ export default
|
||||
'class': "{{!(job_type.value === 'scan' && project_name !== 'Default') ? 'hidden' : ''}}",
|
||||
},
|
||||
type: 'lookup',
|
||||
list: 'ProjectList',
|
||||
basePath: 'projects',
|
||||
sourceModel: 'project',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpProject()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "projectrequired",
|
||||
init: "true"
|
||||
@ -106,7 +108,7 @@ export default
|
||||
dataTitle: i18n._('Project'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
playbook: {
|
||||
label: i18n._('Playbook'),
|
||||
@ -128,9 +130,13 @@ export default
|
||||
credential: {
|
||||
label: i18n._('Machine Credential'),
|
||||
type: 'lookup',
|
||||
list: 'CredentialList',
|
||||
basePath: 'credentials',
|
||||
search: {
|
||||
kind: 'ssh'
|
||||
},
|
||||
sourceModel: 'credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpCredential()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: '!ask_credential_on_launch',
|
||||
alwaysShowAsterisk: true
|
||||
@ -146,38 +152,42 @@ export default
|
||||
variable: 'ask_credential_on_launch',
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
cloud_credential: {
|
||||
label: i18n._('Cloud Credential'),
|
||||
type: 'lookup',
|
||||
list: 'CredentialList',
|
||||
basePath: 'credentials',
|
||||
search: {
|
||||
cloud: 'true'
|
||||
},
|
||||
sourceModel: 'cloud_credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpCloudcredential()',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
column: 1,
|
||||
awPopOver: i18n._("<p>Selecting an optional cloud credential in the job template will pass along the access credentials to the " +
|
||||
"running playbook, allowing provisioning into the cloud without manually passing parameters to the included modules.</p>"),
|
||||
dataTitle: i18n._('Cloud Credential'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
network_credential: {
|
||||
label: i18n._('Network Credential'),
|
||||
type: 'lookup',
|
||||
list: 'CredentialList',
|
||||
basePath: 'credentials',
|
||||
search: {
|
||||
kind: 'net'
|
||||
},
|
||||
sourceModel: 'network_credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpNetworkcredential()',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
column: 1,
|
||||
awPopOver: i18n._("<p>Network credentials are used by Ansible networking modules to connect to and manage networking devices.</p>"),
|
||||
dataTitle: i18n._('Network Credential'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
forks: {
|
||||
label: i18n._('Forks'),
|
||||
@ -187,8 +197,6 @@ export default
|
||||
min: 0,
|
||||
spinner: true,
|
||||
"default": '0',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
'class': "input-small",
|
||||
column: 1,
|
||||
awPopOver: i18n._('<p>The number of parallel or simultaneous processes to use while executing the playbook. 0 signifies ' +
|
||||
@ -197,13 +205,11 @@ export default
|
||||
dataTitle: i18n._('Forks'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)' // TODO: get working
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)' // TODO: get working
|
||||
},
|
||||
limit: {
|
||||
label: i18n._('Limit'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
column: 1,
|
||||
awPopOver: i18n._("<p>Provide a host pattern to further constrain the list of hosts that will be managed or affected by the playbook. " +
|
||||
"Multiple patterns can be separated by ; : or ,</p><p>For more information and examples see " +
|
||||
@ -215,28 +221,25 @@ export default
|
||||
variable: 'ask_limit_on_launch',
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
verbosity: {
|
||||
label: i18n._('Verbosity'),
|
||||
type: 'select',
|
||||
ngOptions: 'v.label for v in verbosity_options track by v.value',
|
||||
"default": 1,
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
column: 1,
|
||||
awPopOver: i18n._("<p>Control the level of output ansible will produce as the playbook executes.</p>"),
|
||||
dataTitle: i18n._('Verbosity'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
job_tags: {
|
||||
label: i18n._('Job Tags'),
|
||||
type: 'textarea',
|
||||
rows: 5,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
'elementClass': 'Form-textInput',
|
||||
column: 2,
|
||||
awPopOver: i18n._("<p>Provide a comma separated list of tags.</p>\n" +
|
||||
@ -249,14 +252,12 @@ export default
|
||||
variable: 'ask_tags_on_launch',
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
skip_tags: {
|
||||
label: i18n._('Skip Tags'),
|
||||
type: 'textarea',
|
||||
rows: 5,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
'elementClass': 'Form-textInput',
|
||||
column: 2,
|
||||
awPopOver: i18n._("<p>Provide a comma separated list of tags.</p>\n" +
|
||||
@ -269,7 +270,7 @@ export default
|
||||
variable: 'ask_skip_tags_on_launch',
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
checkbox_group: {
|
||||
label: i18n._('Options'),
|
||||
@ -278,21 +279,17 @@ export default
|
||||
name: 'become_enabled',
|
||||
label: i18n._('Enable Privilege Escalation'),
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
column: 2,
|
||||
awPopOver: i18n._("<p>If enabled, run this playbook as an administrator. This is the equivalent of passing the <code>--become</code> option to the <code>ansible-playbook</code> command. </p>"),
|
||||
dataPlacement: 'right',
|
||||
dataTitle: i18n._('Become Privilege Escalation'),
|
||||
dataContainer: "body",
|
||||
labelClass: 'stack-inline',
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}, {
|
||||
name: 'allow_callbacks',
|
||||
label: i18n._('Allow Provisioning Callbacks'),
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
editRequird: false,
|
||||
ngChange: "toggleCallback('host_config_key')",
|
||||
column: 2,
|
||||
awPopOver: i18n._("<p>Enables creation of a provisioning callback URL. Using the URL a host can contact Tower and request a configuration update " +
|
||||
@ -301,14 +298,12 @@ export default
|
||||
dataTitle: i18n._('Allow Provisioning Callbacks'),
|
||||
dataContainer: "body",
|
||||
labelClass: 'stack-inline',
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}]
|
||||
},
|
||||
callback_url: {
|
||||
label: i18n._('Provisioning Callback URL'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
readonly: true,
|
||||
ngShow: "allow_callbacks && allow_callbacks !== 'false'",
|
||||
column: 2,
|
||||
@ -317,7 +312,7 @@ export default
|
||||
dataPlacement: 'top',
|
||||
dataTitle: i18n._('Provisioning Callback URL'),
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
host_config_key: {
|
||||
label: i18n._('Host Config Key'),
|
||||
@ -331,7 +326,7 @@ export default
|
||||
dataPlacement: 'right',
|
||||
dataTitle: i18n._("Host Config Key"),
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
labels: {
|
||||
label: i18n._('Labels'),
|
||||
@ -339,21 +334,17 @@ export default
|
||||
class: 'Form-formGroup--fullWidth',
|
||||
ngOptions: 'label.label for label in labelOptions track by label.value',
|
||||
multiSelect: true,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
dataTitle: i18n._('Labels'),
|
||||
dataPlacement: 'right',
|
||||
awPopOver: i18n._("<p>Optional labels that describe this job template, such as 'dev' or 'test'. Labels can be used to group and filter job templates and completed jobs in the Tower display.</p>"),
|
||||
dataContainer: 'body',
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
variables: {
|
||||
label: i18n._('Extra Variables'),
|
||||
type: 'textarea',
|
||||
class: 'Form-textAreaLabel Form-formGroup--fullWidth',
|
||||
rows: 6,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
"default": "---",
|
||||
column: 2,
|
||||
awPopOver: i18n._("<p>Pass extra command line variables to the playbook. This is the <code>-e</code> or <code>--extra-vars</code> command line parameter " +
|
||||
@ -369,14 +360,14 @@ export default
|
||||
variable: 'ask_variables_on_launch',
|
||||
text: i18n._('Prompt on launch')
|
||||
},
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)' // TODO: get working
|
||||
ngDisabled: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)' // TODO: get working
|
||||
}
|
||||
},
|
||||
|
||||
buttons: { //for now always generates <button> tags
|
||||
add_survey: {
|
||||
ngClick: 'addSurvey()',
|
||||
ngShow: 'job_type.value !== "scan" && !survey_exists && (job_template_obj.summary_fields.user_capabilities.edit || canAdd)',
|
||||
ngShow: 'job_type.value !== "scan" && !survey_exists && (job_template_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
awFeature: 'surveys',
|
||||
awToolTip: 'Surveys allow users to be prompted at job launch with a series of questions related to the job. This allows for variables to be defined that affect the playbook run at time of launch.',
|
||||
dataPlacement: 'top'
|
||||
@ -384,25 +375,25 @@ export default
|
||||
edit_survey: {
|
||||
ngClick: 'editSurvey()',
|
||||
awFeature: 'surveys',
|
||||
ngShow: 'job_type.value !== "scan" && survey_exists && (job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: 'job_type.value !== "scan" && survey_exists && (job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
view_survey: {
|
||||
ngClick: 'editSurvey()',
|
||||
awFeature: 'surveys',
|
||||
ngShow: 'job_type.value !== "scan" && survey_exists && !(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: 'job_type.value !== "scan" && survey_exists && !(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()', //$scope.function to call on click, optional
|
||||
ngDisabled: "job_templates_form.$invalid",//true //Disable when $pristine or $invalid, optional and when can_edit = false, for permission reasons
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
@ -413,21 +404,23 @@ export default
|
||||
permissions: {
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
dataPlacement: 'top',
|
||||
basePath: 'job_templates/:id/access_list/',
|
||||
basePath: 'api/v1/job_templates/{{$stateParams.job_template_id}}/access_list/',
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
type: 'collection',
|
||||
title: i18n._('Permissions'),
|
||||
iterator: 'permission',
|
||||
index: false,
|
||||
open: false,
|
||||
searchType: 'select',
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermission",
|
||||
ngClick: "$state.go('.add')",
|
||||
label: 'Add',
|
||||
awToolTip: 'Add a permission',
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: '+ ADD',
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(job_template_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
@ -443,14 +436,12 @@ export default
|
||||
type: 'role',
|
||||
noSort: true,
|
||||
class: 'col-lg-4 col-md-4 col-sm-4 col-xs-4',
|
||||
searchable: false
|
||||
},
|
||||
team_roles: {
|
||||
label: 'Team Roles',
|
||||
type: 'team_roles',
|
||||
noSort: true,
|
||||
class: 'col-lg-5 col-md-5 col-sm-5 col-xs-4',
|
||||
searchable: false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@ -3,7 +3,7 @@
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name forms.function:JobVarsPrompt
|
||||
@ -27,8 +27,8 @@ export default
|
||||
label: null,
|
||||
type: 'textarea',
|
||||
rows: 6,
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
|
||||
|
||||
"default": "---"
|
||||
}
|
||||
},
|
||||
|
||||
@ -17,6 +17,7 @@ export default
|
||||
addTitle: 'Create Job',
|
||||
editTitle: '{{ id }} - {{ name }}',
|
||||
name: 'jobs',
|
||||
stateTree: 'jobs',
|
||||
well: true,
|
||||
base: 'jobs',
|
||||
tabs: true,
|
||||
|
||||
@ -18,46 +18,47 @@ export default
|
||||
addTitle: i18n._('New Organization'), //Title in add mode
|
||||
editTitle: '{{ name }}', //Title in edit mode
|
||||
name: 'organization', //entity or model name in singular form
|
||||
stateTree: 'organizations',
|
||||
tabs: true,
|
||||
|
||||
fields: {
|
||||
name: {
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: false,
|
||||
ngDisabled: '!(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(organization_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
capitalize: false
|
||||
},
|
||||
description: {
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(organization_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
buttons: { //for now always generates <button> tags
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(organization_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()', //$scope.function to call on click, optional
|
||||
ngDisabled: true,
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {
|
||||
permissions: {
|
||||
basePath: 'organizations/:id/access_list/',
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
basePath: 'api/v1/organizations/{{$stateParams.organization_id}}/access_list/',
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
dataPlacement: 'top',
|
||||
type: 'collection',
|
||||
title: i18n._('Permissions'),
|
||||
@ -68,11 +69,11 @@ export default
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermission",
|
||||
label: 'Add',
|
||||
label: i18n._('Add'),
|
||||
awToolTip: i18n._('Add a permission'),
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: i18n._('+ ADD'),
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(organization_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@ -18,43 +18,39 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
addTitle: i18n._('New Project'),
|
||||
editTitle: '{{ name }}',
|
||||
name: 'project',
|
||||
basePath: 'projects',
|
||||
// the top-most node of generated state tree
|
||||
stateTree: 'projects',
|
||||
forceListeners: true,
|
||||
tabs: true,
|
||||
subFormTitles: {
|
||||
sourceSubForm: i18n._('Source Details'),
|
||||
},
|
||||
|
||||
|
||||
fields: {
|
||||
name: {
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: false,
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
capitalize: false
|
||||
},
|
||||
description: {
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
organization: {
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
list: 'OrganizationList',
|
||||
sourceModel: 'organization',
|
||||
basePath: 'organizations',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpOrganization()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "organizationrequired",
|
||||
init: "true"
|
||||
},
|
||||
dataTitle: i18n._('Organization'),
|
||||
required: true,
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
scm_type: {
|
||||
label: i18n._('SCM Type'),
|
||||
@ -62,10 +58,9 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
class: 'Form-dropDown--scmType',
|
||||
ngOptions: 'type.label for type in scm_type_options track by type.value',
|
||||
ngChange: 'scmChange()',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
required: true,
|
||||
hasSubForm: true,
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
missing_path_alert: {
|
||||
type: 'alertblock',
|
||||
@ -88,7 +83,7 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
dataTitle: i18n._('Project Base Path'),
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
local_path: {
|
||||
label: i18n._('Playbook Directory'),
|
||||
@ -106,7 +101,7 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
dataTitle: i18n._('Project Path'),
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
scm_url: {
|
||||
label: 'SCM URL',
|
||||
@ -123,28 +118,29 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
dataTitle: 'SCM URL',
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
scm_branch: {
|
||||
labelBind: "scmBranchLabel",
|
||||
type: 'text',
|
||||
ngShow: "scm_type && scm_type.value !== 'manual'",
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
subForm: 'sourceSubForm',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
},
|
||||
credential: {
|
||||
label: i18n._('SCM Credential'),
|
||||
type: 'lookup',
|
||||
basePath: 'credentials',
|
||||
list: 'CredentialList',
|
||||
// apply a default search filter to show only scm credentials
|
||||
search: {
|
||||
kind: 'scm'
|
||||
},
|
||||
ngShow: "scm_type && scm_type.value !== 'manual'",
|
||||
sourceModel: 'credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpCredential()',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
subForm: 'sourceSubForm',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
subForm: 'sourceSubForm'
|
||||
},
|
||||
checkbox_group: {
|
||||
label: i18n._('SCM Update Options'),
|
||||
@ -155,39 +151,33 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
name: 'scm_clean',
|
||||
label: i18n._('Clean'),
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: i18n._('<p>Remove any local modifications prior to performing an update.</p>'),
|
||||
dataTitle: i18n._('SCM Clean'),
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options stack-inline',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}, {
|
||||
name: 'scm_delete_on_update',
|
||||
label: i18n._('Delete on Update'),
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: i18n._('<p>Delete the local repository in its entirety prior to performing an update.</p><p>Depending on the size of the ' +
|
||||
'repository this may significantly increase the amount of time required to complete an update.</p>'),
|
||||
dataTitle: i18n._('SCM Delete'),
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options stack-inline',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}, {
|
||||
name: 'scm_update_on_launch',
|
||||
label: i18n._('Update on Launch'),
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: i18n._('<p>Each time a job runs using this project, perform an update to the local repository prior to starting the job.</p>'),
|
||||
dataTitle: i18n._('SCM Update'),
|
||||
dataContainer: 'body',
|
||||
dataPlacement: 'right',
|
||||
labelClass: 'checkbox-options stack-inline',
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}]
|
||||
},
|
||||
scm_update_cache_timeout: {
|
||||
@ -199,61 +189,61 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
ngShow: "scm_update_on_launch && projectSelected && scm_type.value !== 'manual'",
|
||||
spinner: true,
|
||||
"default": '0',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
awPopOver: i18n._('<p>Time in seconds to consider a project to be current. During job runs and callbacks the task system will ' +
|
||||
'evaluate the timestamp of the latest project update. If it is older than Cache Timeout, it is not considered current, ' +
|
||||
'and a new project update will be performed.</p>'),
|
||||
dataTitle: i18n._('Cache Timeout'),
|
||||
dataPlacement: 'right',
|
||||
dataContainer: "body",
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)' // TODO: get working
|
||||
ngDisabled: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {
|
||||
permissions: {
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
djangoModel: 'access_list',
|
||||
dataPlacement: 'top',
|
||||
basePath: 'projects/:id/access_list/',
|
||||
basePath: 'api/v1/projects/{{$stateParams.project_id}}/access_list/',
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
type: 'collection',
|
||||
title: i18n._('Permissions'),
|
||||
iterator: 'permission',
|
||||
index: false,
|
||||
open: false,
|
||||
searchType: 'select',
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermission",
|
||||
ngClick: "$state.go('.add')",
|
||||
label: 'Add',
|
||||
awToolTip: i18n._('Add a permission'),
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: i18n._('+ ADD'),
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(project_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
fields: {
|
||||
username: {
|
||||
key: true,
|
||||
label: 'User',
|
||||
linkBase: 'users',
|
||||
uiSref: 'users({user_id: field.id})',
|
||||
class: 'col-lg-3 col-md-3 col-sm-3 col-xs-4'
|
||||
},
|
||||
role: {
|
||||
@ -261,14 +251,12 @@ angular.module('ProjectFormDefinition', ['SchedulesListDefinition'])
|
||||
type: 'role',
|
||||
noSort: true,
|
||||
class: 'col-lg-4 col-md-4 col-sm-4 col-xs-4',
|
||||
noSearch: true
|
||||
},
|
||||
team_roles: {
|
||||
label: 'Team Roles',
|
||||
type: 'team_roles',
|
||||
noSort: true,
|
||||
class: 'col-lg-5 col-md-5 col-sm-5 col-xs-4',
|
||||
noSearch: true
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@ -18,75 +18,73 @@ export default
|
||||
addTitle: i18n._('New Team'), //Legend in add mode
|
||||
editTitle: '{{ name }}', //Legend in edit mode
|
||||
name: 'team',
|
||||
// the top-most node of generated state tree
|
||||
stateTree: 'teams',
|
||||
tabs: true,
|
||||
|
||||
fields: {
|
||||
name: {
|
||||
label: i18n._('Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: false,
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
capitalize: false
|
||||
},
|
||||
description: {
|
||||
label: i18n._('Description'),
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
editRequired: false,
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
organization: {
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
list: 'OrganizationsList',
|
||||
sourceModel: 'organization',
|
||||
basePath: 'organizations',
|
||||
sourceField: 'name',
|
||||
addRequired: true,
|
||||
editRequire: false,
|
||||
ngClick: 'lookUpOrganization()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "orgrequired",
|
||||
init: true
|
||||
},
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(team_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
}
|
||||
},
|
||||
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(team_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {
|
||||
access_list: {
|
||||
permissions: {
|
||||
dataPlacement: 'top',
|
||||
awToolTip: i18n._('Please save before adding users'),
|
||||
basePath: 'teams/:id/access_list/',
|
||||
basePath: 'api/v1/teams/{{$stateParams.team_id}}/access_list/',
|
||||
search: {
|
||||
order_by: 'username'
|
||||
},
|
||||
type: 'collection',
|
||||
title: i18n._('Users'),
|
||||
iterator: 'permission',
|
||||
index: false,
|
||||
open: false,
|
||||
searchType: 'select',
|
||||
actions: {
|
||||
add: {
|
||||
ngClick: "addPermissionWithoutTeamTab",
|
||||
// @issue https://github.com/ansible/ansible-tower/issues/3487
|
||||
//ngClick: "addPermissionWithoutTeamTab",
|
||||
label: 'Add',
|
||||
awToolTip: i18n._('Add user to team'),
|
||||
actionClass: 'btn List-buttonSubmit',
|
||||
buttonContent: i18n._('+ ADD'),
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(team_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
@ -110,7 +108,12 @@ export default
|
||||
hideSearchAndActions: true,
|
||||
dataPlacement: 'top',
|
||||
awToolTip: i18n._('Please save before assigning permissions'),
|
||||
basePath: 'teams/:id/roles/',
|
||||
basePath: 'api/v1/teams/{{$stateParams.team_id}}/roles/',
|
||||
search: {
|
||||
page_size: '10',
|
||||
// @todo ask about name field / serializer on this endpoint
|
||||
order_by: 'id'
|
||||
},
|
||||
type: 'collection',
|
||||
title: i18n._('Granted Permissions'),
|
||||
iterator: 'role',
|
||||
@ -147,7 +150,7 @@ export default
|
||||
ngShow: 'permission.summary_fields.user_capabilities.unattach'
|
||||
}
|
||||
},
|
||||
hideOnSuperuser: true
|
||||
//hideOnSuperuser: true // defunct with RBAC
|
||||
}
|
||||
},
|
||||
};}]); //InventoryForm
|
||||
|
||||
@ -18,6 +18,8 @@ export default
|
||||
addTitle: i18n._('New User'),
|
||||
editTitle: '{{ username }}',
|
||||
name: 'user',
|
||||
// the top-most node of generated state tree
|
||||
stateTree: 'users',
|
||||
forceListeners: true,
|
||||
tabs: true,
|
||||
|
||||
@ -25,26 +27,23 @@ export default
|
||||
first_name: {
|
||||
label: i18n._('First Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: true,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
capitalize: true
|
||||
},
|
||||
last_name: {
|
||||
label: i18n._('Last Name'),
|
||||
type: 'text',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
capitalize: true,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
capitalize: true
|
||||
},
|
||||
email: {
|
||||
label: i18n._('Email'),
|
||||
type: 'email',
|
||||
addRequired: true,
|
||||
editRequired: true,
|
||||
autocomplete: false,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)',
|
||||
required: true,
|
||||
autocomplete: false
|
||||
},
|
||||
username: {
|
||||
label: i18n._('Username'),
|
||||
@ -54,46 +53,42 @@ export default
|
||||
init: true
|
||||
},
|
||||
autocomplete: false,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
organization: {
|
||||
label: i18n._('Organization'),
|
||||
type: 'lookup',
|
||||
list: 'OrganizationList',
|
||||
basePath: 'organizations',
|
||||
sourceModel: 'organization',
|
||||
sourceField: 'name',
|
||||
addRequired: true,
|
||||
editRequired: false,
|
||||
required: true,
|
||||
excludeMode: 'edit',
|
||||
ngClick: 'lookUpOrganization()',
|
||||
awRequiredWhen: {
|
||||
reqExpression: "orgrequired",
|
||||
init: true
|
||||
},
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
password: {
|
||||
label: i18n._('Password'),
|
||||
type: 'sensitive',
|
||||
hasShowInputButton: true,
|
||||
ngShow: 'ldap_user == false && socialAuthUser === false && external_account === null',
|
||||
addRequired: true,
|
||||
editRequired: false,
|
||||
ngRequired: "$state.match('add')",
|
||||
labelNGClass: "{'prepend-asterisk' : $state.matches('add')}",
|
||||
ngChange: "clearPWConfirm('password_confirm')",
|
||||
autocomplete: false,
|
||||
chkPass: true,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
password_confirm: {
|
||||
label: i18n._('Confirm Password'),
|
||||
type: 'sensitive',
|
||||
hasShowInputButton: true,
|
||||
ngShow: 'ldap_user == false && socialAuthUser === false && external_account === null',
|
||||
addRequired: true,
|
||||
editRequired: false,
|
||||
ngRequired: "$state.match('add')",
|
||||
labelNGClass: "{'prepend-asterisk' : $state.matches('add')}",
|
||||
awPassMatch: true,
|
||||
associated: 'password',
|
||||
autocomplete: false,
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
user_type: {
|
||||
label: i18n._('User Type'),
|
||||
@ -102,30 +97,33 @@ export default
|
||||
disableChooseOption: true,
|
||||
ngModel: 'user_type',
|
||||
ngShow: 'current_user["is_superuser"]',
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngDisabled: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
},
|
||||
|
||||
buttons: {
|
||||
cancel: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
close: {
|
||||
ngClick: 'formCancel()',
|
||||
ngShow: '!(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '!(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
},
|
||||
save: {
|
||||
ngClick: 'formSave()',
|
||||
ngDisabled: true,
|
||||
ngShow: '(user_obj.summary_fields.user_capabilities.edit || canAdd)'
|
||||
ngShow: '(user_obj.summary_fields.user_capabilities.edit || !canAdd)'
|
||||
}
|
||||
},
|
||||
|
||||
related: {
|
||||
organizations: {
|
||||
basePath: 'users/:id/organizations',
|
||||
awToolTip: i18n._('Please save before assigning to organizations'),
|
||||
basePath: 'api/v1/users/{{$stateParams.user_id}}/organizations',
|
||||
search: {
|
||||
page_size: '10'
|
||||
},
|
||||
dataPlacement: 'top',
|
||||
type: 'collection',
|
||||
title: i18n._('Organizations'),
|
||||
@ -144,11 +142,14 @@ export default
|
||||
label: 'Description'
|
||||
}
|
||||
},
|
||||
hideOnSuperuser: true
|
||||
//hideOnSuperuser: true // RBAC defunct
|
||||
},
|
||||
teams: {
|
||||
basePath: 'users/:id/teams',
|
||||
awToolTip: i18n._('Please save before assigning to teams'),
|
||||
basePath: 'api/v1/users/{{$stateParams.user_id}}/teams',
|
||||
search: {
|
||||
page_size: '10'
|
||||
},
|
||||
dataPlacement: 'top',
|
||||
type: 'collection',
|
||||
title: i18n._('Teams'),
|
||||
@ -166,9 +167,15 @@ export default
|
||||
label: 'Description'
|
||||
}
|
||||
},
|
||||
hideOnSuperuser: true
|
||||
//hideOnSuperuser: true // RBAC defunct
|
||||
},
|
||||
roles: {
|
||||
permissions: {
|
||||
basePath: 'api/v1/users/{{$stateParams.user_id}}/roles/',
|
||||
search: {
|
||||
page_size: '10',
|
||||
// @todo ask about name field / serializer on this endpoint
|
||||
order_by: 'id'
|
||||
},
|
||||
awToolTip: i18n._('Please save before assigning to organizations'),
|
||||
dataPlacement: 'top',
|
||||
hideSearchAndActions: true,
|
||||
@ -196,6 +203,12 @@ export default
|
||||
noSort: true
|
||||
},
|
||||
},
|
||||
// @issue https://github.com/ansible/ansible-tower/issues/3487
|
||||
// actions: {
|
||||
// add: {
|
||||
|
||||
// }
|
||||
// }
|
||||
fieldActions: {
|
||||
"delete": {
|
||||
label: i18n._('Remove'),
|
||||
@ -205,7 +218,7 @@ export default
|
||||
ngShow: 'permission.summary_fields.user_capabilities.unattach'
|
||||
}
|
||||
},
|
||||
hideOnSuperuser: true
|
||||
//hideOnSuperuser: true // RBAC defunct
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -17,7 +17,6 @@ import JobSubmission from "./helpers/JobSubmission";
|
||||
import JobTemplates from "./helpers/JobTemplates";
|
||||
import Jobs from "./helpers/Jobs";
|
||||
import LoadConfig from "./helpers/LoadConfig";
|
||||
import PaginationHelpers from "./helpers/PaginationHelpers";
|
||||
import Parse from "./helpers/Parse";
|
||||
import ProjectPath from "./helpers/ProjectPath";
|
||||
import Projects from "./helpers/Projects";
|
||||
@ -28,10 +27,6 @@ import Variables from "./helpers/Variables";
|
||||
import ApiDefaults from "./helpers/api-defaults";
|
||||
import inventory from "./helpers/inventory";
|
||||
import MD5 from "./helpers/md5";
|
||||
import RefreshRelated from "./helpers/refresh-related";
|
||||
import Refresh from "./helpers/refresh";
|
||||
import RelatedSearch from "./helpers/related-search";
|
||||
import Search from "./helpers/search";
|
||||
import Teams from "./helpers/teams";
|
||||
import AdhocHelper from "./helpers/Adhoc";
|
||||
import ApiModelHelper from "./helpers/ApiModel";
|
||||
@ -48,7 +43,6 @@ export
|
||||
JobTemplates,
|
||||
Jobs,
|
||||
LoadConfig,
|
||||
PaginationHelpers,
|
||||
Parse,
|
||||
ProjectPath,
|
||||
Projects,
|
||||
@ -59,10 +53,6 @@ export
|
||||
ApiDefaults,
|
||||
inventory,
|
||||
MD5,
|
||||
RefreshRelated,
|
||||
Refresh,
|
||||
RelatedSearch,
|
||||
Search,
|
||||
Teams,
|
||||
AdhocHelper,
|
||||
ApiModelHelper,
|
||||
|
||||
@ -41,7 +41,7 @@
|
||||
|
||||
export default
|
||||
angular.module('AdhocHelper', ['RestServices', 'Utilities',
|
||||
'CredentialFormDefinition', 'CredentialsListDefinition', 'LookUpHelper',
|
||||
'CredentialFormDefinition', 'CredentialsListDefinition',
|
||||
'JobSubmissionHelper', 'JobTemplateFormDefinition', 'ModalDialog',
|
||||
'FormGenerator', 'JobVarsPromptFormDefinition'])
|
||||
|
||||
|
||||
@ -223,8 +223,8 @@ angular.module('CredentialsHelper', ['Utilities'])
|
||||
}
|
||||
])
|
||||
|
||||
.factory('FormSave', ['$rootScope', 'Refresh', '$location', 'Alert', 'Rest', 'ProcessErrors', 'Empty', 'GetBasePath', 'CredentialForm', 'ReturnToCaller', 'Wait', '$state',
|
||||
function ($rootScope, Refresh, $location, Alert, Rest, ProcessErrors, Empty, GetBasePath, CredentialForm, ReturnToCaller, Wait, $state) {
|
||||
.factory('FormSave', ['$rootScope', '$location', 'Alert', 'Rest', 'ProcessErrors', 'Empty', 'GetBasePath', 'CredentialForm', 'ReturnToCaller', 'Wait', '$state',
|
||||
function ($rootScope, $location, Alert, Rest, ProcessErrors, Empty, GetBasePath, CredentialForm, ReturnToCaller, Wait, $state) {
|
||||
return function (params) {
|
||||
var scope = params.scope,
|
||||
mode = params.mode,
|
||||
@ -279,12 +279,13 @@ angular.module('CredentialsHelper', ['Utilities'])
|
||||
.success(function (data) {
|
||||
scope.addedItem = data.id;
|
||||
|
||||
Refresh({
|
||||
scope: scope,
|
||||
set: 'credentials',
|
||||
iterator: 'credential',
|
||||
url: url
|
||||
});
|
||||
// @issue: OLD SEARCH
|
||||
// Refresh({
|
||||
// scope: scope,
|
||||
// set: 'credentials',
|
||||
// iterator: 'credential',
|
||||
// url: url
|
||||
// });
|
||||
|
||||
Wait('stop');
|
||||
var base = $location.path().replace(/^\//, '').split('/')[0];
|
||||
|
||||
@ -15,9 +15,8 @@
|
||||
import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('GroupsHelper', [ 'RestServices', 'Utilities', listGenerator.name, 'GroupListDefinition', 'SearchHelper',
|
||||
'PaginationHelpers', listGenerator.name, 'GroupsHelper', 'InventoryHelper', 'SelectionHelper',
|
||||
'JobSubmissionHelper', 'RefreshHelper', 'PromptDialog', 'CredentialsListDefinition',
|
||||
angular.module('GroupsHelper', [ 'RestServices', 'Utilities', listGenerator.name, 'GroupListDefinition', listGenerator.name, 'GroupsHelper', 'InventoryHelper', 'SelectionHelper',
|
||||
'JobSubmissionHelper', 'PromptDialog', 'CredentialsListDefinition',
|
||||
'InventoryStatusDefinition', 'VariablesHelper', 'SchedulesListDefinition', 'StandardOutHelper',
|
||||
'SchedulesHelper'
|
||||
])
|
||||
@ -325,10 +324,10 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', listGenerator.name
|
||||
*/
|
||||
.factory('GroupsEdit', ['$filter', '$rootScope', '$location', '$log', '$stateParams', '$compile', 'Rest', 'Alert', 'GroupForm', 'GenerateForm',
|
||||
'Prompt', 'ProcessErrors', 'GetBasePath', 'SetNodeName', 'ParseTypeChange', 'GetSourceTypeOptions', 'InventoryUpdate',
|
||||
'LookUpInit', 'Empty', 'Wait', 'GetChoices', 'UpdateGroup', 'SourceChange', 'Find',
|
||||
'Empty', 'Wait', 'GetChoices', 'UpdateGroup', 'SourceChange', 'Find',
|
||||
'ParseVariableString', 'ToJSON', 'GroupsScheduleListInit', 'SetSchedulesInnerDialogSize', 'CreateSelect2',
|
||||
function ($filter, $rootScope, $location, $log, $stateParams, $compile, Rest, Alert, GroupForm, GenerateForm, Prompt, ProcessErrors,
|
||||
GetBasePath, SetNodeName, ParseTypeChange, GetSourceTypeOptions, InventoryUpdate, LookUpInit, Empty, Wait,
|
||||
GetBasePath, SetNodeName, ParseTypeChange, GetSourceTypeOptions, InventoryUpdate, Empty, Wait,
|
||||
GetChoices, UpdateGroup, SourceChange, Find, ParseVariableString, ToJSON, GroupsScheduleListInit,
|
||||
SetSchedulesInnerDialogSize, CreateSelect2) {
|
||||
return function (params) {
|
||||
@ -842,9 +841,11 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', listGenerator.name
|
||||
// Clean up
|
||||
Wait('stop');
|
||||
|
||||
if (modal_scope.searchCleanUp) {
|
||||
modal_scope.searchCleanup();
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (modal_scope.searchCleanUp) {
|
||||
// modal_scope.searchCleanup();
|
||||
// }
|
||||
|
||||
try {
|
||||
$('#group-modal-dialog').dialog('close');
|
||||
}
|
||||
@ -947,15 +948,19 @@ angular.module('GroupsHelper', [ 'RestServices', 'Utilities', listGenerator.name
|
||||
catch(e) {
|
||||
//ignore
|
||||
}
|
||||
if (modal_scope.searchCleanup) {
|
||||
modal_scope.searchCleanup();
|
||||
}
|
||||
if (parent_scope.restoreSearch) {
|
||||
parent_scope.restoreSearch();
|
||||
}
|
||||
else {
|
||||
Wait('stop');
|
||||
}
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// if (modal_scope.searchCleanup) {
|
||||
// modal_scope.searchCleanup();
|
||||
// }
|
||||
// if (parent_scope.restoreSearch) {
|
||||
// parent_scope.restoreSearch();
|
||||
// }
|
||||
// else {
|
||||
// Wait('stop');
|
||||
// }
|
||||
|
||||
Wait('stop');
|
||||
};
|
||||
|
||||
// Save
|
||||
|
||||
@ -18,8 +18,8 @@ import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('HostsHelper', [ 'RestServices', 'Utilities', listGenerator.name, 'HostListDefinition',
|
||||
'SearchHelper', 'PaginationHelpers', listGenerator.name, 'HostsHelper',
|
||||
'InventoryHelper', 'RelatedSearchHelper', 'InventoryFormDefinition', 'SelectionHelper',
|
||||
listGenerator.name, 'HostsHelper',
|
||||
'InventoryHelper', 'InventoryFormDefinition', 'SelectionHelper',
|
||||
'HostGroupsFormDefinition', 'VariablesHelper', 'ModalDialog', 'StandardOutHelper',
|
||||
'GroupListDefinition'
|
||||
])
|
||||
@ -160,23 +160,26 @@ angular.module('HostsHelper', [ 'RestServices', 'Utilities', listGenerator.name,
|
||||
};
|
||||
}])
|
||||
|
||||
.factory('HostsReload', [ '$stateParams', 'Empty', 'InventoryHosts', 'GetBasePath', 'SearchInit', 'PaginateInit', 'Wait',
|
||||
.factory('HostsReload', [ '$stateParams', 'Empty', 'InventoryHosts', 'GetBasePath', 'Wait',
|
||||
'SetHostStatus', 'SetStatus', 'ApplyEllipsis',
|
||||
function($stateParams, Empty, InventoryHosts, GetBasePath, SearchInit, PaginateInit, Wait, SetHostStatus, SetStatus,
|
||||
function($stateParams, Empty, InventoryHosts, GetBasePath, Wait, SetHostStatus, SetStatus,
|
||||
ApplyEllipsis) {
|
||||
return function(params) {
|
||||
|
||||
var scope = params.scope,
|
||||
parent_scope = params.parent_scope,
|
||||
group_id = params.group_id,
|
||||
inventory_id = params.inventory_id,
|
||||
list = InventoryHosts,
|
||||
pageSize = (params.pageSize) ? params.pageSize : 20,
|
||||
parent_scope = params.parent_scope;
|
||||
|
||||
url = ( !Empty(group_id) ) ? GetBasePath('groups') + group_id + '/all_hosts/' :
|
||||
GetBasePath('inventory') + inventory_id + '/hosts/';
|
||||
// @issue: OLD SEARCH
|
||||
// var list = InventoryHosts,
|
||||
// group_id = params.group_id,
|
||||
// inventory_id = params.inventory_id;
|
||||
// pageSize = (params.pageSize) ? params.pageSize : 20,
|
||||
//
|
||||
// url = ( !Empty(group_id) ) ? GetBasePath('groups') + group_id + '/all_hosts/' :
|
||||
// GetBasePath('inventory') + inventory_id + '/hosts/';
|
||||
|
||||
scope.search_place_holder='Search ' + scope.selected_group_name;
|
||||
// @issue: OLD SEARCH
|
||||
// scope.search_place_holder='Search ' + scope.selected_group_name;
|
||||
|
||||
if (scope.removeHostsReloadPostRefresh) {
|
||||
scope.removeHostsReloadPostRefresh();
|
||||
@ -196,31 +199,31 @@ angular.module('HostsHelper', [ 'RestServices', 'Utilities', listGenerator.name,
|
||||
}
|
||||
});
|
||||
|
||||
SearchInit({ scope: scope, set: 'hosts', list: list, url: url });
|
||||
PaginateInit({ scope: scope, list: list, url: url, pageSize: pageSize });
|
||||
|
||||
if ($stateParams.host_name) {
|
||||
scope[list.iterator + 'InputDisable'] = false;
|
||||
scope[list.iterator + 'SearchValue'] = $stateParams.host_name;
|
||||
scope[list.iterator + 'SearchField'] = 'name';
|
||||
scope[list.iterator + 'SearchFieldLabel'] = list.fields.name.label;
|
||||
scope[list.iterator + 'SearchSelectValue'] = null;
|
||||
}
|
||||
|
||||
if (scope.show_failures) {
|
||||
scope[list.iterator + 'InputDisable'] = true;
|
||||
scope[list.iterator + 'SearchValue'] = 'true';
|
||||
scope[list.iterator + 'SearchField'] = 'has_active_failures';
|
||||
scope[list.iterator + 'SearchFieldLabel'] = list.fields.has_active_failures.label;
|
||||
scope[list.iterator + 'SearchSelectValue'] = { value: 1 };
|
||||
}
|
||||
scope.search(list.iterator, null, true);
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({ scope: scope, set: 'hosts', list: list, url: url });
|
||||
// PaginateInit({ scope: scope, list: list, url: url, pageSize: pageSize });
|
||||
//
|
||||
// if ($stateParams.host_name) {
|
||||
// scope[list.iterator + 'InputDisable'] = false;
|
||||
// scope[list.iterator + 'SearchValue'] = $stateParams.host_name;
|
||||
// scope[list.iterator + 'SearchField'] = 'name';
|
||||
// scope[list.iterator + 'SearchFieldLabel'] = list.fields.name.label;
|
||||
// scope[list.iterator + 'SearchSelectValue'] = null;
|
||||
// }
|
||||
//
|
||||
// if (scope.show_failures) {
|
||||
// scope[list.iterator + 'InputDisable'] = true;
|
||||
// scope[list.iterator + 'SearchValue'] = 'true';
|
||||
// scope[list.iterator + 'SearchField'] = 'has_active_failures';
|
||||
// scope[list.iterator + 'SearchFieldLabel'] = list.fields.has_active_failures.label;
|
||||
// scope[list.iterator + 'SearchSelectValue'] = { value: 1 };
|
||||
// }
|
||||
// scope.search(list.iterator, null, true);
|
||||
};
|
||||
}])
|
||||
|
||||
.factory('HostsCopy', ['$compile', 'Rest', 'ProcessErrors', 'CreateDialog', 'GetBasePath', 'Wait', 'generateList', 'GroupList', 'SearchInit',
|
||||
'PaginateInit',
|
||||
function($compile, Rest, ProcessErrors, CreateDialog, GetBasePath, Wait, GenerateList, GroupList, SearchInit, PaginateInit) {
|
||||
.factory('HostsCopy', ['$compile', 'Rest', 'ProcessErrors', 'CreateDialog', 'GetBasePath', 'Wait', 'generateList', 'GroupList',
|
||||
function($compile, Rest, ProcessErrors, CreateDialog, GetBasePath, Wait, GenerateList, GroupList) {
|
||||
return function(params) {
|
||||
|
||||
var host_id = params.host_id,
|
||||
@ -271,7 +274,9 @@ return function(params) {
|
||||
scope.removeHostCopyDialogReady();
|
||||
}
|
||||
scope.removeCopyDialogReady = scope.$on('HostCopyDialogReady', function() {
|
||||
var url = GetBasePath('inventory') + group_scope.inventory.id + '/groups/';
|
||||
// @issue: OLD SEARCH
|
||||
// var url = GetBasePath('inventory') + group_scope.inventory.id + '/groups/';
|
||||
|
||||
GenerateList.inject(GroupList, {
|
||||
mode: 'lookup',
|
||||
id: 'copy-host-select-container',
|
||||
@ -279,19 +284,21 @@ return function(params) {
|
||||
//,
|
||||
//instructions: instructions
|
||||
});
|
||||
SearchInit({
|
||||
scope: scope,
|
||||
set: GroupList.name,
|
||||
list: GroupList,
|
||||
url: url
|
||||
});
|
||||
PaginateInit({
|
||||
scope: scope,
|
||||
list: GroupList,
|
||||
url: url,
|
||||
mode: 'lookup'
|
||||
});
|
||||
scope.search(GroupList.iterator, null, true, false);
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: scope,
|
||||
// set: GroupList.name,
|
||||
// list: GroupList,
|
||||
// url: url
|
||||
// });
|
||||
// PaginateInit({
|
||||
// scope: scope,
|
||||
// list: GroupList,
|
||||
// url: url,
|
||||
// mode: 'lookup'
|
||||
// });
|
||||
// scope.search(GroupList.iterator, null, true, false);
|
||||
});
|
||||
|
||||
if (scope.removeShowDialog) {
|
||||
@ -341,8 +348,12 @@ return function(params) {
|
||||
catch(e) {
|
||||
// ignore
|
||||
}
|
||||
scope.searchCleanup();
|
||||
group_scope.restoreSearch(); // Restore all parent search stuff and refresh hosts and groups lists
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// scope.searchCleanup();
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// group_scope.restoreSearch(); // Restore all parent search stuff and refresh hosts and groups lists
|
||||
scope.$destroy();
|
||||
};
|
||||
|
||||
|
||||
@ -686,9 +686,11 @@ export default
|
||||
|
||||
scope.plays = [];
|
||||
|
||||
url = scope.job.url + 'job_plays/?page_size=' + scope.playsMaxRows + '&order=id';
|
||||
url += (scope.search_play_name) ? '&play__icontains=' + encodeURIComponent(scope.search_play_name) : '';
|
||||
url += (scope.search_play_status === 'failed') ? '&failed=true' : '';
|
||||
// @issue: OLD SEARCH - factory needs refactoring! will be completely rehauled for job details 3.1 update
|
||||
// url = scope.job.url + 'job_plays/?page_size=' + scope.playsMaxRows + '&order=id';
|
||||
// url += (scope.search_play_name) ? '&play__icontains=' + encodeURIComponent(scope.search_play_name) : '';
|
||||
// url += (scope.search_play_status === 'failed') ? '&failed=true' : '';
|
||||
|
||||
scope.playsLoading = true;
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
@ -786,9 +788,12 @@ export default
|
||||
scope.tasks = [];
|
||||
if (scope.selectedPlay) {
|
||||
url = scope.job.url + 'job_tasks/?event_id=' + scope.selectedPlay;
|
||||
url += (scope.search_task_name) ? '&task__icontains=' + encodeURIComponent(scope.search_task_name) : '';
|
||||
url += (scope.search_task_status === 'failed') ? '&failed=true' : '';
|
||||
url += '&page_size=' + scope.tasksMaxRows + '&order=id';
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// url += (scope.search_task_name) ? '&task__icontains=' + encodeURIComponent(scope.search_task_name) : '';
|
||||
// url += (scope.search_task_status === 'failed') ? '&failed=true' : '';
|
||||
// url += '&page_size=' + scope.tasksMaxRows + '&order=id';
|
||||
|
||||
scope.plays.every(function(p, idx) {
|
||||
if (p.id === scope.selectedPlay) {
|
||||
play = scope.plays[idx];
|
||||
@ -918,9 +923,12 @@ export default
|
||||
page_size: scope.hostResultsMaxRows,
|
||||
order: 'host_name,counter',
|
||||
};
|
||||
if (scope.search_host_status === 'failed'){
|
||||
params.failed = true;
|
||||
}
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_host_status === 'failed'){
|
||||
// params.failed = true;
|
||||
// }
|
||||
|
||||
JobDetailService.getRelatedJobEvents(scope.job.id, params).success(function(res){
|
||||
scope.hostResults = JobDetailService.processHostEvents(res.results);
|
||||
scope.hostResultsLoading = false;
|
||||
@ -1052,27 +1060,30 @@ export default
|
||||
filteredListX[key] = plays[key];
|
||||
}
|
||||
}
|
||||
if (scope.search_play_name) {
|
||||
for (key in plays) {
|
||||
if (filteredListX[key].name.indexOf(scope.search_play_name) > 0) {
|
||||
filteredListA[key] = filteredListX[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListA = filteredListX;
|
||||
}
|
||||
|
||||
if (scope.search_play_status === 'failed') {
|
||||
for (key in filteredListA) {
|
||||
if (filteredListA[key].status === 'failed') {
|
||||
filteredListB[key] = plays[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListB = filteredListA;
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_play_name) {
|
||||
// for (key in plays) {
|
||||
// if (filteredListX[key].name.indexOf(scope.search_play_name) > 0) {
|
||||
// filteredListA[key] = filteredListX[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListA = filteredListX;
|
||||
// }
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_play_status === 'failed') {
|
||||
// for (key in filteredListA) {
|
||||
// if (filteredListA[key].status === 'failed') {
|
||||
// filteredListB[key] = plays[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListB = filteredListA;
|
||||
// }
|
||||
|
||||
keys = Object.keys(filteredListB);
|
||||
keys.sort(function(a,b) { return listSort(a,b); }).reverse();
|
||||
@ -1130,27 +1141,29 @@ export default
|
||||
}
|
||||
}
|
||||
|
||||
if (scope.search_task_name) {
|
||||
for (key in filteredListX) {
|
||||
if (filteredListX[key].name.indexOf(scope.search_task_name) > 0) {
|
||||
filteredListA[key] = filteredListX[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListA = filteredListX;
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_task_name) {
|
||||
// for (key in filteredListX) {
|
||||
// if (filteredListX[key].name.indexOf(scope.search_task_name) > 0) {
|
||||
// filteredListA[key] = filteredListX[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListA = filteredListX;
|
||||
// }
|
||||
|
||||
if (scope.search_task_status === 'failed') {
|
||||
for (key in filteredListA) {
|
||||
if (filteredListA[key].status === 'failed') {
|
||||
filteredListB[key] = tasks[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListB = filteredListA;
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_task_status === 'failed') {
|
||||
// for (key in filteredListA) {
|
||||
// if (filteredListA[key].status === 'failed') {
|
||||
// filteredListB[key] = tasks[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListB = filteredListA;
|
||||
// }
|
||||
|
||||
keys = Object.keys(filteredListB);
|
||||
keys.sort(function(a,b) { return listSort(a,b); }).reverse();
|
||||
@ -1196,27 +1209,30 @@ export default
|
||||
//hostResults = JSON.parse(JSON.stringify(scope.jobData.plays[scope.activePlay].tasks[scope.activeTask].hostResults));
|
||||
hostResults = scope.jobData.plays[scope.activePlay].tasks[scope.activeTask].hostResults;
|
||||
|
||||
if (scope.search_host_name) {
|
||||
for (key in hostResults) {
|
||||
if (hostResults[key].name.indexOf(scope.search_host_name) > 0) {
|
||||
filteredListA[key] = hostResults[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListA = hostResults;
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_host_name) {
|
||||
// for (key in hostResults) {
|
||||
// if (hostResults[key].name.indexOf(scope.search_host_name) > 0) {
|
||||
// filteredListA[key] = hostResults[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListA = hostResults;
|
||||
// }
|
||||
|
||||
if (scope.search_host_status === 'failed' || scope.search_host_status === 'unreachable') {
|
||||
for (key in filteredListA) {
|
||||
if (filteredListA[key].status === 'failed') {
|
||||
filteredListB[key] = filteredListA[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
filteredListB = filteredListA;
|
||||
}
|
||||
// @issue: OLD SEARCH
|
||||
// if (scope.search_host_status === 'failed' || scope.search_host_status === 'unreachable') {
|
||||
// for (key in filteredListA) {
|
||||
// if (filteredListA[key].status === 'failed') {
|
||||
// filteredListB[key] = filteredListA[key];
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// filteredListB = filteredListA;
|
||||
// }
|
||||
|
||||
keys = Object.keys(filteredListB);
|
||||
keys.sort(function compare(a, b) {
|
||||
if (filteredListB[a].name === filteredListB[b].name) {
|
||||
|
||||
@ -8,7 +8,7 @@
|
||||
|
||||
export default
|
||||
angular.module('JobSubmissionHelper', [ 'RestServices', 'Utilities', 'CredentialFormDefinition', 'CredentialsListDefinition',
|
||||
'LookUpHelper', 'JobSubmissionHelper', 'JobTemplateFormDefinition', 'ModalDialog', 'FormGenerator', 'JobVarsPromptFormDefinition'])
|
||||
'JobSubmissionHelper', 'JobTemplateFormDefinition', 'ModalDialog', 'FormGenerator', 'JobVarsPromptFormDefinition'])
|
||||
|
||||
.factory('CreateLaunchDialog', ['$compile', 'CreateDialog', 'Wait', 'ParseTypeChange',
|
||||
function($compile, CreateDialog, Wait, ParseTypeChange) {
|
||||
|
||||
@ -19,9 +19,9 @@ angular.module('JobTemplatesHelper', ['Utilities'])
|
||||
*/
|
||||
|
||||
.factory('CallbackHelpInit', ['$location', 'GetBasePath', 'Rest', 'JobTemplateForm', 'GenerateForm', '$stateParams', 'ProcessErrors', 'ParseTypeChange',
|
||||
'ParseVariableString', 'Empty', 'LookUpInit', 'InventoryList', 'CredentialList','ProjectList', 'RelatedSearchInit', 'RelatedPaginateInit', 'Wait',
|
||||
function($location, GetBasePath, Rest, JobTemplateForm, GenerateForm, $stateParams, ProcessErrors,ParseTypeChange,
|
||||
ParseVariableString, Empty, LookUpInit, InventoryList, CredentialList, ProjectList, RelatedSearchInit, RelatedPaginateInit, Wait) {
|
||||
'ParseVariableString', 'Empty', 'InventoryList', 'CredentialList','ProjectList', 'Wait',
|
||||
function($location, GetBasePath, Rest, JobTemplateForm, GenerateForm, $stateParams, ProcessErrors, ParseTypeChange,
|
||||
ParseVariableString, Empty, InventoryList, CredentialList, ProjectList, Wait) {
|
||||
return function(params) {
|
||||
|
||||
var scope = params.scope,
|
||||
@ -31,7 +31,7 @@ angular.module('JobTemplatesHelper', ['Utilities'])
|
||||
// loadingFinishedCount = 0,
|
||||
// base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
master = {},
|
||||
id = $stateParams.id,
|
||||
id = $stateParams.job_template_id,
|
||||
relatedSets = {};
|
||||
// checkSCMStatus, getPlaybooks, callback,
|
||||
// choicesCount = 0;
|
||||
@ -158,74 +158,11 @@ angular.module('JobTemplatesHelper', ['Utilities'])
|
||||
|
||||
scope.can_edit = data.summary_fields.can_edit;
|
||||
|
||||
LookUpInit({
|
||||
scope: scope,
|
||||
form: form,
|
||||
current_item: data.inventory,
|
||||
list: InventoryList,
|
||||
field: 'inventory',
|
||||
input_type: "radio"
|
||||
});
|
||||
|
||||
CredentialList.basePath = GetBasePath('credentials') + '?kind=ssh';
|
||||
// remove "type" field from search options
|
||||
CredentialList.fields.kind.noSearch = true;
|
||||
|
||||
LookUpInit({
|
||||
url: GetBasePath('credentials') + '?kind=ssh',
|
||||
scope: scope,
|
||||
form: form,
|
||||
current_item: data.credential,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
hdr: 'Select Machine Credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
|
||||
var NetworkCredentialList = {};
|
||||
// Clone the CredentialList object for use with network_credential. Cloning
|
||||
// and changing properties to avoid collision.
|
||||
jQuery.extend(true, NetworkCredentialList, CredentialList);
|
||||
NetworkCredentialList.name = 'networkcredentials';
|
||||
NetworkCredentialList.iterator = 'networkcredential';
|
||||
NetworkCredentialList.basePath = '/api/v1/credentials?kind=net';
|
||||
|
||||
LookUpInit({
|
||||
url: GetBasePath('credentials') + '?kind=net',
|
||||
scope: scope,
|
||||
form: form,
|
||||
current_item: data.network_credential,
|
||||
list: NetworkCredentialList,
|
||||
field: 'network_credential',
|
||||
hdr: 'Select Network Credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
|
||||
LookUpInit({
|
||||
scope: scope,
|
||||
form: form,
|
||||
current_item: data.project,
|
||||
list: ProjectList,
|
||||
field: 'project',
|
||||
input_type: "radio"
|
||||
});
|
||||
|
||||
|
||||
if (scope.project === "" && scope.playbook === "") {
|
||||
scope.resetProjectToDefault();
|
||||
}
|
||||
|
||||
RelatedSearchInit({
|
||||
scope: scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
RelatedPaginateInit({
|
||||
scope: scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
scope.$emit('jobTemplateLoaded', data.related.cloud_credential, master, relatedSets);
|
||||
})
|
||||
.error(function (data, status) {
|
||||
|
||||
@ -14,92 +14,7 @@ import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('JobsHelper', ['Utilities', 'RestServices', 'FormGenerator', 'JobSummaryDefinition', 'InventoryHelper', 'GeneratorHelpers',
|
||||
'JobSubmissionHelper', 'StandardOutHelper', 'SearchHelper', 'PaginationHelpers', 'AdhocHelper', listGenerator.name])
|
||||
|
||||
/**
|
||||
* JobsControllerInit({ scope: $scope });
|
||||
*
|
||||
* Initialize calling scope with all the bits required to support a jobs list
|
||||
*
|
||||
*/
|
||||
.factory('JobsControllerInit', ['$state', 'Find', 'DeleteJob', 'RelaunchJob',
|
||||
function($state, Find, DeleteJob, RelaunchJob) {
|
||||
return function(params) {
|
||||
var scope = params.scope,
|
||||
iterator = (params.iterator) ? params.iterator : scope.iterator;
|
||||
|
||||
scope.deleteJob = function(id) {
|
||||
DeleteJob({ scope: scope, id: id });
|
||||
};
|
||||
|
||||
scope.relaunchJob = function(event, id) {
|
||||
var list, job, typeId;
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
}
|
||||
catch(e) {
|
||||
//ignore
|
||||
}
|
||||
if (scope.completed_jobs) {
|
||||
list = scope.completed_jobs;
|
||||
}
|
||||
else if (scope.running_jobs) {
|
||||
list = scope.running_jobs;
|
||||
}
|
||||
else if (scope.queued_jobs) {
|
||||
list = scope.queued_jobs;
|
||||
}
|
||||
else if (scope.jobs) {
|
||||
list = scope.jobs;
|
||||
}
|
||||
else if(scope.all_jobs){
|
||||
list = scope.all_jobs;
|
||||
}
|
||||
job = Find({ list: list, key: 'id', val: id });
|
||||
if (job.type === 'inventory_update') {
|
||||
typeId = job.inventory_source;
|
||||
}
|
||||
else if (job.type === 'project_update') {
|
||||
typeId = job.project;
|
||||
}
|
||||
else if (job.type === 'job' || job.type === "system_job" || job.type === 'ad_hoc_command') {
|
||||
typeId = job.id;
|
||||
}
|
||||
RelaunchJob({ scope: scope, id: typeId, type: job.type, name: job.name });
|
||||
};
|
||||
|
||||
scope.refreshJobs = function() {
|
||||
scope.search(iterator);
|
||||
};
|
||||
|
||||
scope.viewJobDetails = function(job) {
|
||||
|
||||
var goToJobDetails = function(state) {
|
||||
$state.go(state, {id: job.id}, {reload:true});
|
||||
};
|
||||
|
||||
switch(job.type) {
|
||||
case 'job':
|
||||
goToJobDetails('jobDetail');
|
||||
break;
|
||||
case 'ad_hoc_command':
|
||||
goToJobDetails('adHocJobStdout');
|
||||
break;
|
||||
case 'system_job':
|
||||
goToJobDetails('managementJobStdout');
|
||||
break;
|
||||
case 'project_update':
|
||||
goToJobDetails('scmUpdateStdout');
|
||||
break;
|
||||
case 'inventory_update':
|
||||
goToJobDetails('inventorySyncStdout');
|
||||
break;
|
||||
}
|
||||
|
||||
};
|
||||
};
|
||||
}
|
||||
])
|
||||
'JobSubmissionHelper', 'StandardOutHelper', 'AdhocHelper', listGenerator.name])
|
||||
|
||||
.factory('RelaunchJob', ['RelaunchInventory', 'RelaunchPlaybook', 'RelaunchSCM', 'RelaunchAdhoc',
|
||||
function(RelaunchInventory, RelaunchPlaybook, RelaunchSCM, RelaunchAdhoc) {
|
||||
@ -210,83 +125,6 @@ export default
|
||||
};
|
||||
}])
|
||||
|
||||
/**
|
||||
*
|
||||
* Called from JobsList controller to load each section or list on the page
|
||||
*
|
||||
*/
|
||||
.factory('LoadJobsScope', ['$stateParams', '$location', '$compile',
|
||||
'SearchInit', 'PaginateInit', 'generateList', 'JobsControllerInit',
|
||||
'JobsListUpdate',
|
||||
function($stateParams, $location, $compile, SearchInit, PaginateInit,
|
||||
GenerateList, JobsControllerInit, JobsListUpdate) {
|
||||
return function(params) {
|
||||
var parent_scope = params.parent_scope,
|
||||
scope = params.scope,
|
||||
list = params.list,
|
||||
id = params.id,
|
||||
url = params.url,
|
||||
pageSize = params.pageSize || 10,
|
||||
base = $location.path().replace(/^\//, '').split('/')[0],
|
||||
search_params = params.searchParams,
|
||||
spinner = (params.spinner === undefined) ? true : params.spinner, key;
|
||||
|
||||
var buildTooltips = function(data){
|
||||
data.forEach((val) => {
|
||||
val.status_tip = 'Job ' + val.status + ". Click for details.";
|
||||
});
|
||||
};
|
||||
|
||||
GenerateList.inject(list, {
|
||||
mode: 'edit',
|
||||
id: id,
|
||||
scope: scope,
|
||||
title: false
|
||||
});
|
||||
|
||||
SearchInit({
|
||||
scope: scope,
|
||||
set: list.name,
|
||||
list: list,
|
||||
url: url
|
||||
});
|
||||
|
||||
PaginateInit({
|
||||
scope: scope,
|
||||
list: list,
|
||||
url: url,
|
||||
pageSize: pageSize
|
||||
});
|
||||
|
||||
scope.iterator = list.iterator;
|
||||
|
||||
if (scope.removePostRefresh) {
|
||||
scope.removePostRefresh();
|
||||
}
|
||||
scope.$on('PostRefresh', function(){
|
||||
JobsControllerInit({ scope: scope, parent_scope: parent_scope });
|
||||
JobsListUpdate({ scope: scope, parent_scope: parent_scope, list: list });
|
||||
buildTooltips(scope.jobs);
|
||||
parent_scope.$emit('listLoaded');
|
||||
});
|
||||
|
||||
if (base === 'jobs' && list.name === 'all_jobs') {
|
||||
if ($stateParams.id__int) {
|
||||
scope[list.iterator + 'SearchField'] = 'id';
|
||||
scope[list.iterator + 'SearchValue'] = $stateParams.id__int;
|
||||
scope[list.iterator + 'SearchFieldLabel'] = 'Job ID';
|
||||
}
|
||||
}
|
||||
|
||||
if (search_params) {
|
||||
for (key in search_params) {
|
||||
scope[key] = search_params[key];
|
||||
}
|
||||
}
|
||||
scope.search(list.iterator, null, null, null, null, spinner);
|
||||
};
|
||||
}])
|
||||
|
||||
.factory('DeleteJob', ['Find', 'GetBasePath', 'Rest', 'Wait',
|
||||
'ProcessErrors', 'Prompt', 'Alert', '$filter',
|
||||
function(Find, GetBasePath, Rest, Wait, ProcessErrors, Prompt, Alert,
|
||||
@ -338,7 +176,8 @@ export default
|
||||
scope.$emit(callback, action_label);
|
||||
}
|
||||
else {
|
||||
scope.search(scope.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// scope.search(scope.iterator);
|
||||
}
|
||||
})
|
||||
.error(function(obj, status) {
|
||||
@ -359,7 +198,8 @@ export default
|
||||
scope.$emit(callback, action_label);
|
||||
}
|
||||
else {
|
||||
scope.search(scope.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// scope.search(scope.iterator);
|
||||
}
|
||||
})
|
||||
.error(function (obj, status) {
|
||||
|
||||
@ -1,182 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:PaginationHelpers
|
||||
* @description pagination
|
||||
*/
|
||||
|
||||
export default
|
||||
angular.module('PaginationHelpers', ['Utilities', 'RefreshHelper', 'RefreshRelatedHelper'])
|
||||
|
||||
.factory('PageRangeSetup', ['Empty',
|
||||
function (Empty) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
count = params.count,
|
||||
next = params.next,
|
||||
previous = params.previous,
|
||||
iterator = params.iterator,
|
||||
i, first, last;
|
||||
|
||||
scope[iterator + '_page'] = 1;
|
||||
scope[iterator + '_num_pages'] = Math.ceil((count / scope[iterator + '_page_size']));
|
||||
scope[iterator + '_num_pages'] = (scope[iterator + '_num_pages'] <= 0) ? 1 : scope[iterator + '_num_pages'];
|
||||
scope[iterator + '_total_rows'] = count;
|
||||
$('#'+iterator+'-pagination #pagination-links li:eq(1)').removeAttr('class');
|
||||
// Which page are we on?
|
||||
if (Empty(next) && previous) {
|
||||
// no next page, but there is a previous page
|
||||
scope[iterator + '_page'] = /page=\d+/.test(previous) ? parseInt(previous.match(/page=(\d+)/)[1]) + 1 : 2;
|
||||
} else if (next && Empty(previous)) {
|
||||
// next page available, but no previous page
|
||||
scope[iterator + '_page'] = 1;
|
||||
$('#'+iterator+'-pagination #pagination-links li:eq(1)').attr('class', 'disabled');
|
||||
} else if (next && previous) {
|
||||
// we're in between next and previous
|
||||
scope[iterator + '_page'] = /page=\d+/.test(previous) ? parseInt(previous.match(/page=(\d+)/)[1]) + 1 : 2;
|
||||
}
|
||||
|
||||
// Calc the range of up to 10 pages to show
|
||||
scope[iterator + '_page_range'] = [];
|
||||
first = (scope[iterator + '_page'] > 5) ? scope[iterator + '_page'] - 5 : 1;
|
||||
if (scope[iterator + '_page'] < 6) {
|
||||
last = (10 <= scope[iterator + '_num_pages']) ? 10 : scope[iterator + '_num_pages'];
|
||||
} else {
|
||||
last = (scope[iterator + '_page'] + 4 < scope[iterator + '_num_pages']) ?
|
||||
scope[iterator + '_page'] + 4 : scope[iterator + '_num_pages'];
|
||||
}
|
||||
for (i = first; i <= last; i++) {
|
||||
scope[iterator + '_page_range'].push(i);
|
||||
}
|
||||
};
|
||||
}
|
||||
])
|
||||
|
||||
.factory('RelatedPaginateInit', ['RefreshRelated', '$cookieStore', 'Wait',
|
||||
function (RefreshRelated, $cookieStore, Wait) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
relatedSets = params.relatedSets,
|
||||
pageSize = (params.pageSize) ? params.pageSize : 10,
|
||||
key;
|
||||
|
||||
for (key in relatedSets) {
|
||||
scope[relatedSets[key].iterator + '_url'] = relatedSets[key].url;
|
||||
scope[relatedSets[key].iterator + '_page'] = 0;
|
||||
scope[relatedSets[key].iterator + '_page_size'] = pageSize;
|
||||
}
|
||||
|
||||
scope.getPage = function (page, set, iterator) {
|
||||
var new_url = scope[iterator + '_url'].replace(/.page\=\d+/, ''),
|
||||
connect = (/\/$/.test(new_url)) ? '?' : '&';
|
||||
if(scope[iterator + '_page'] === 1 && page === 0){
|
||||
return;
|
||||
}
|
||||
new_url += connect + 'page=' + page;
|
||||
if (scope[iterator + 'SearchFilters']){
|
||||
new_url += _.reduce(scope[iterator+'SearchFilters'], (result, filter) => result + '&' + filter.url, '');
|
||||
}
|
||||
if (scope[iterator + 'SearchParams']){
|
||||
new_url += '&' + scope[iterator + 'SearchParams'];
|
||||
}
|
||||
new_url += '&page_size=' + scope[iterator + '_page_size'];
|
||||
Wait('start');
|
||||
RefreshRelated({ scope: scope, set: set, iterator: iterator, url: new_url });
|
||||
};
|
||||
|
||||
scope.pageIsActive = function (page, iterator) {
|
||||
return (page === scope[iterator + '_page']) ? 'active' : '';
|
||||
};
|
||||
|
||||
scope.changePageSize = function (set, iterator) {
|
||||
// Called when a new page size is selected
|
||||
|
||||
scope[iterator + '_page'] = 1;
|
||||
var url = scope[iterator + '_url'];
|
||||
|
||||
// Using the session cookie, keep track of user rows per page selection
|
||||
$cookieStore.put(iterator + '_page_size', scope[iterator + '_page_size']);
|
||||
|
||||
url = url.replace(/\/\?.*$/, '/');
|
||||
url += (scope[iterator + 'SearchParams']) ? '?' + scope[iterator + 'SearchParams'] + '&page_size=' + scope[iterator + '_page_size'] :
|
||||
'?page_size=' + scope[iterator + '_page_size'];
|
||||
|
||||
RefreshRelated({
|
||||
scope: scope,
|
||||
set: set,
|
||||
iterator: iterator,
|
||||
url: url
|
||||
});
|
||||
};
|
||||
};
|
||||
}
|
||||
])
|
||||
|
||||
|
||||
.factory('PaginateInit', ['Refresh', '$cookieStore', 'Wait',
|
||||
function (Refresh, $cookieStore, Wait) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
list = params.list,
|
||||
iterator = (params.iterator) ? params.iterator : list.iterator,
|
||||
pageSize = params.pageSize,
|
||||
mode = (params.mode) ? params.mode : null;
|
||||
|
||||
scope[iterator + '_page'] = (params.page) ? params.page : 1;
|
||||
scope[iterator + '_url'] = params.url;
|
||||
scope[iterator + '_mode'] = mode;
|
||||
|
||||
if (pageSize) {
|
||||
scope[iterator + '_page_size'] = params.pageSize;
|
||||
} else if (mode === 'lookup') {
|
||||
scope[iterator + '_page_size'] = 5;
|
||||
} else {
|
||||
scope[iterator + '_page_size'] = 20;
|
||||
}
|
||||
|
||||
scope.getPage = function (page, set, iterator) {
|
||||
var new_url = scope[iterator + '_url'].replace(/.page\=\d+/, ''),
|
||||
connect = (/\/$/.test(new_url)) ? '?' : '&';
|
||||
if(scope[iterator + '_page'] === 1 && page === 0){
|
||||
return;
|
||||
}
|
||||
new_url += connect + 'page=' + page;
|
||||
if (scope[iterator + 'SearchFilters']){
|
||||
new_url += _.reduce(scope[iterator+'SearchFilters'], (result, filter) => result + '&' + filter.url, '');
|
||||
}
|
||||
if (scope[iterator + 'SearchParams']){
|
||||
new_url += '&' + scope[iterator + 'SearchParams'];
|
||||
}
|
||||
new_url += '&page_size=' + scope[iterator + '_page_size'];
|
||||
Wait('start');
|
||||
scope.getNewPage = true;
|
||||
Refresh({ scope: scope, set: set, iterator: iterator, url: new_url });
|
||||
};
|
||||
|
||||
scope.pageIsActive = function (page, iterator) {
|
||||
return (page === scope[iterator + '_page']) ? 'active' : '';
|
||||
};
|
||||
|
||||
scope.changePageSize = function (set, iterator, spinner) {
|
||||
// Called whenever a new page size is selected
|
||||
scope[iterator + '_page'] = 1;
|
||||
var new_url = scope[iterator + '_url'].replace(/\?page_size\=\d+/, ''),
|
||||
connect = (/\/$/.test(new_url)) ? '?' : '&';
|
||||
new_url += (scope[iterator + 'SearchParams']) ? connect + scope[iterator + 'SearchParams'] + '&page_size=' + scope[iterator + '_page_size'] :
|
||||
connect + 'page_size=' + scope[iterator + '_page_size'];
|
||||
if (spinner === undefined || spinner === true) {
|
||||
Wait('start');
|
||||
}
|
||||
Refresh({ scope: scope, set: set, iterator: iterator, url: new_url });
|
||||
};
|
||||
};
|
||||
}
|
||||
]);
|
||||
@ -17,7 +17,7 @@
|
||||
import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('SchedulesHelper', [ 'Utilities', 'RestServices', 'SchedulesHelper', 'SearchHelper', 'PaginationHelpers', listGenerator.name, 'ModalDialog',
|
||||
angular.module('SchedulesHelper', [ 'Utilities', 'RestServices', 'SchedulesHelper', listGenerator.name, 'ModalDialog',
|
||||
'GeneratorHelpers'])
|
||||
|
||||
.factory('EditSchedule', ['SchedulerInit', '$rootScope', 'Wait', 'Rest',
|
||||
@ -272,7 +272,7 @@ export default
|
||||
if (callback) {
|
||||
scope.$emit(callback, data);
|
||||
}
|
||||
$state.go("^");
|
||||
$state.go("^", null, {reload: true});
|
||||
});
|
||||
scope.saveSchedule = function() {
|
||||
SchedulePost({
|
||||
@ -376,7 +376,8 @@ export default
|
||||
* });
|
||||
*
|
||||
*/
|
||||
.factory('ToggleSchedule', ['Wait', 'GetBasePath', 'ProcessErrors', 'Rest', function(Wait, GetBasePath, ProcessErrors, Rest) {
|
||||
.factory('ToggleSchedule', ['Wait', 'GetBasePath', 'ProcessErrors', 'Rest', '$state',
|
||||
function(Wait, GetBasePath, ProcessErrors, Rest, $state) {
|
||||
return function(params) {
|
||||
var scope = params.scope,
|
||||
id = params.id,
|
||||
@ -391,12 +392,8 @@ export default
|
||||
data.enabled = (data.enabled) ? false : true;
|
||||
Rest.put(data)
|
||||
.success( function() {
|
||||
if (callback) {
|
||||
scope.$emit(callback, id);
|
||||
}
|
||||
else {
|
||||
Wait('stop');
|
||||
}
|
||||
Wait('stop');
|
||||
$state.go('.', null, {reload: true});
|
||||
})
|
||||
.error( function(data, status) {
|
||||
ProcessErrors(scope, data, status, null, { hdr: 'Error!',
|
||||
@ -429,9 +426,9 @@ export default
|
||||
* })
|
||||
*
|
||||
*/
|
||||
.factory('DeleteSchedule', ['GetBasePath','Rest', 'Wait',
|
||||
.factory('DeleteSchedule', ['GetBasePath','Rest', 'Wait', '$state',
|
||||
'ProcessErrors', 'Prompt', 'Find', '$location', '$filter',
|
||||
function(GetBasePath, Rest, Wait, ProcessErrors, Prompt, Find,
|
||||
function(GetBasePath, Rest, Wait, $state, ProcessErrors, Prompt, Find,
|
||||
$location, $filter) {
|
||||
return function(params) {
|
||||
|
||||
@ -461,6 +458,9 @@ export default
|
||||
if (new RegExp('/' + id + '$').test($location.$$url)) {
|
||||
$location.url($location.url().replace(/[/][0-9]+$/, "")); // go to list view
|
||||
}
|
||||
else{
|
||||
$state.go('.', null, {reload: true});
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
try {
|
||||
@ -497,214 +497,4 @@ export default
|
||||
});
|
||||
return response;
|
||||
};
|
||||
}])
|
||||
|
||||
.factory('SchedulesControllerInit', ['$state', '$location',
|
||||
'ToggleSchedule', 'DeleteSchedule', 'ParamPass',
|
||||
function($state, $location, ToggleSchedule, DeleteSchedule,
|
||||
ParamPass) {
|
||||
return function(params) {
|
||||
var scope = params.scope,
|
||||
parent_scope = params.parent_scope,
|
||||
iterator = (params.iterator) ? params.iterator : scope.iterator,
|
||||
base = params.base || $location.path().replace(/^\//, '').split('/')[0];
|
||||
|
||||
scope.toggleSchedule = function(event, id) {
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
}
|
||||
catch(e) {
|
||||
// ignore
|
||||
}
|
||||
ToggleSchedule({
|
||||
scope: scope,
|
||||
id: id,
|
||||
callback: 'SchedulesRefresh'
|
||||
});
|
||||
};
|
||||
|
||||
scope.deleteSchedule = function(id) {
|
||||
DeleteSchedule({
|
||||
scope: scope,
|
||||
id: id,
|
||||
callback: 'SchedulesRefresh'
|
||||
});
|
||||
};
|
||||
|
||||
scope.editSchedule = function(id) {
|
||||
if ($state.includes('inventoryManage')){
|
||||
$state.go('inventoryManage.schedules.edit', {schedule_id: id});
|
||||
}
|
||||
else if ($state.current.name === 'jobs'){
|
||||
// id === schedule object in this case
|
||||
var stateDictionary = {
|
||||
// type: stateName
|
||||
job: 'jobTemplateSchedules.edit',
|
||||
system_job: 'managementJobSchedules.edit',
|
||||
project_update: 'projectSchedules.edit',
|
||||
};
|
||||
$state.go(stateDictionary[id.type], {schedule_id: id.id, id: id.summary_fields.unified_job_template.id});
|
||||
}
|
||||
else{
|
||||
var base = $state.current.name.split(".")[0];
|
||||
$state.go(base + ".edit", {schedule_id: id});
|
||||
}
|
||||
};
|
||||
|
||||
scope.addSchedule = function() {
|
||||
if ($state.includes('inventoryManage')){
|
||||
scope.schedule_url = parent_scope.current_url.split('?')[0];
|
||||
ParamPass.set(scope.schedule_url);
|
||||
$state.go('inventoryManage.schedules.add');
|
||||
}
|
||||
else{
|
||||
var base = $state.current.name.split(".")[0];
|
||||
ParamPass.set(scope.schedule_url);
|
||||
$state.go(base + ".add");
|
||||
}
|
||||
};
|
||||
|
||||
scope.refreshSchedules = function() {
|
||||
if (base === 'jobs') {
|
||||
parent_scope.refreshJobs();
|
||||
}
|
||||
else {
|
||||
scope.search(iterator);
|
||||
}
|
||||
};
|
||||
|
||||
if (scope.removeSchedulesRefresh) {
|
||||
scope.removeSchedulesRefresh();
|
||||
}
|
||||
scope.removeSchedulesRefresh = scope.$on('SchedulesRefresh', function() {
|
||||
scope.search(iterator);
|
||||
});
|
||||
};
|
||||
}])
|
||||
|
||||
.factory('SchedulesListInit', [ function() {
|
||||
return function(params) {
|
||||
var scope = params.scope,
|
||||
list = params.list,
|
||||
choices = params.choices;
|
||||
scope[list.name].forEach(function(item, item_idx) {
|
||||
var fld,
|
||||
field,
|
||||
itm = scope[list.name][item_idx],
|
||||
job = item.summary_fields.unified_job_template;
|
||||
|
||||
itm.enabled = (itm.enabled) ? true : false;
|
||||
if (itm.enabled) {
|
||||
itm.play_tip = 'Schedule is active. Click to stop.';
|
||||
itm.status = 'active';
|
||||
itm.status_tip = 'Schedule is active. Click to stop.';
|
||||
}
|
||||
else {
|
||||
itm.play_tip = 'Schedule is stopped. Click to activate.';
|
||||
itm.status = 'stopped';
|
||||
itm.status_tip = 'Schedule is stopped. Click to activate.';
|
||||
}
|
||||
itm.nameTip = item.name;
|
||||
// include the word schedule if the schedule name does not include the word schedule
|
||||
if (item.name.indexOf("schedule") === -1 && item.name.indexOf("Schedule") === -1) {
|
||||
itm.nameTip += " schedule";
|
||||
}
|
||||
itm.nameTip += " for ";
|
||||
if (job.name.indexOf("job") === -1 && job.name.indexOf("Job") === -1) {
|
||||
itm.nameTip += "job ";
|
||||
}
|
||||
itm.nameTip += job.name;
|
||||
itm.nameTip += ". Click to edit schedule.";
|
||||
// Copy summary_field values
|
||||
for (field in list.fields) {
|
||||
fld = list.fields[field];
|
||||
if (fld.sourceModel) {
|
||||
if (itm.summary_fields[fld.sourceModel]) {
|
||||
itm[field] = itm.summary_fields[fld.sourceModel][fld.sourceField];
|
||||
}
|
||||
}
|
||||
}
|
||||
// Set the item type label
|
||||
if (list.fields.type) {
|
||||
choices.every(function(choice) {
|
||||
if (choice.value === item.type) {
|
||||
itm.type_label = choice.label;
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
});
|
||||
}
|
||||
});
|
||||
};
|
||||
}])
|
||||
|
||||
/**
|
||||
*
|
||||
* Called from a controller to setup the scope for a schedules list
|
||||
*
|
||||
*/
|
||||
.factory('LoadSchedulesScope', ['$compile', '$location', '$stateParams','SearchInit', 'PaginateInit', 'generateList', 'SchedulesControllerInit',
|
||||
'SchedulesListInit',
|
||||
function($compile, $location, $stateParams, SearchInit, PaginateInit, GenerateList, SchedulesControllerInit, SchedulesListInit) {
|
||||
return function(params) {
|
||||
var parent_scope = params.parent_scope,
|
||||
scope = params.scope,
|
||||
list = params.list,
|
||||
id = params.id,
|
||||
url = params.url,
|
||||
searchSize = params.searchSize,
|
||||
pageSize = params.pageSize || 10,
|
||||
spinner = (params.spinner === undefined) ? true : params.spinner;
|
||||
|
||||
|
||||
GenerateList.inject(list, {
|
||||
mode: 'edit',
|
||||
id: id,
|
||||
scope: scope,
|
||||
searchSize: (searchSize) ? searchSize : 'col-lg-6 col-md-6 col-sm-6 col-xs-12',
|
||||
showSearch: true,
|
||||
title: true,
|
||||
});
|
||||
|
||||
SearchInit({
|
||||
scope: scope,
|
||||
set: list.name,
|
||||
list: list,
|
||||
url: url
|
||||
});
|
||||
|
||||
PaginateInit({
|
||||
scope: scope,
|
||||
list: list,
|
||||
url: url,
|
||||
pageSize: pageSize
|
||||
});
|
||||
|
||||
scope.iterator = list.iterator;
|
||||
|
||||
if (scope.removePostRefresh) {
|
||||
scope.removePostRefresh();
|
||||
}
|
||||
scope.$on('PostRefresh', function(){
|
||||
SchedulesControllerInit({
|
||||
scope: scope,
|
||||
parent_scope: parent_scope,
|
||||
list: list
|
||||
});
|
||||
SchedulesListInit({
|
||||
scope: scope,
|
||||
list: list,
|
||||
choices: parent_scope.type_choices
|
||||
});
|
||||
parent_scope.$emit('listLoaded');
|
||||
});
|
||||
|
||||
if ($stateParams.id__int) {
|
||||
scope[list.iterator + 'SearchField'] = 'id';
|
||||
scope[list.iterator + 'SearchValue'] = $stateParams.id__int;
|
||||
scope[list.iterator + 'SearchFieldLabel'] = 'ID';
|
||||
}
|
||||
|
||||
scope.search(list.iterator, null, null, null, null, spinner);
|
||||
};
|
||||
}]);
|
||||
|
||||
@ -17,12 +17,12 @@ import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('InventoryHelper', ['RestServices', 'Utilities', 'OrganizationListDefinition', listGenerator.name,
|
||||
'InventoryHelper', 'InventoryFormDefinition', 'ParseHelper', 'SearchHelper', 'VariablesHelper',
|
||||
'InventoryHelper', 'InventoryFormDefinition', 'ParseHelper', 'VariablesHelper',
|
||||
])
|
||||
|
||||
.factory('SaveInventory', ['InventoryForm', 'Rest', 'Alert', 'ProcessErrors', 'LookUpInit', 'OrganizationList',
|
||||
.factory('SaveInventory', ['InventoryForm', 'Rest', 'Alert', 'ProcessErrors', 'OrganizationList',
|
||||
'GetBasePath', 'ParseTypeChange', 'Wait', 'ToJSON',
|
||||
function (InventoryForm, Rest, Alert, ProcessErrors, LookUpInit, OrganizationList, GetBasePath, ParseTypeChange, Wait,
|
||||
function (InventoryForm, Rest, Alert, ProcessErrors, OrganizationList, GetBasePath, ParseTypeChange, Wait,
|
||||
ToJSON) {
|
||||
return function (params) {
|
||||
|
||||
|
||||
@ -1,59 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:refresh-related
|
||||
* @description
|
||||
* discussion
|
||||
* RefreshRelatedHelper
|
||||
*
|
||||
* Used to refresh a related set whenever pagination or filter options change.
|
||||
*
|
||||
* RefreshRelated({
|
||||
* scope: <current scope>,
|
||||
* set: <model>,
|
||||
* iterator: <model name in singular form (i.e. organization),
|
||||
* url: <the api url to call>
|
||||
* });
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
export default
|
||||
angular.module('RefreshRelatedHelper', ['RestServices', 'Utilities', 'PaginationHelpers'])
|
||||
.factory('RefreshRelated', ['ProcessErrors', 'Rest', 'Wait', 'PageRangeSetup',
|
||||
function (ProcessErrors, Rest, Wait, PageRangeSetup) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
set = params.set,
|
||||
iterator = params.iterator,
|
||||
url = params.url;
|
||||
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
PageRangeSetup({
|
||||
scope: scope,
|
||||
count: data.count,
|
||||
next: data.next,
|
||||
previous: data.previous,
|
||||
iterator: iterator
|
||||
});
|
||||
scope[set] = data.results;
|
||||
scope[iterator + 'Loading'] = false;
|
||||
scope[iterator + 'HoldInput'] = false;
|
||||
Wait('stop');
|
||||
scope.$emit('related' + set);
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors(scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Failed to retrieve ' + set + '. GET returned status: ' + status });
|
||||
});
|
||||
};
|
||||
}
|
||||
]);
|
||||
@ -1,104 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:refresh
|
||||
* @description
|
||||
* RefreshHelper
|
||||
*
|
||||
* Used to refresh a related set whenever pagination or filter options change.
|
||||
*
|
||||
* RefreshRelated({
|
||||
* scope: <current scope>,
|
||||
* set: <model>,
|
||||
* iterator: <model name in singular form (i.e. organization),
|
||||
* url: <the api url to call>
|
||||
* });
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
export default
|
||||
angular.module('RefreshHelper', ['RestServices', 'Utilities', 'PaginationHelpers'])
|
||||
.factory('Refresh', ['$rootScope', '$location', 'ProcessErrors', 'Rest', 'Wait', 'Empty', 'PageRangeSetup', 'pagination', function ($rootScope, $location, ProcessErrors, Rest, Wait, Empty, PageRangeSetup, pagination) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
set = params.set,
|
||||
iterator = params.iterator,
|
||||
deferWaitStop = params.deferWaitStop;
|
||||
|
||||
var getPage = function(url) {
|
||||
scope.current_url = url;
|
||||
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
var i, modifier;
|
||||
PageRangeSetup({
|
||||
scope: scope,
|
||||
count: data.count,
|
||||
next: data.next,
|
||||
previous: data.previous,
|
||||
iterator: iterator
|
||||
});
|
||||
for (i = 1; i <= 3; i++) {
|
||||
modifier = (i === 1) ? '' : i;
|
||||
scope[iterator + 'HoldInput' + modifier] = false;
|
||||
}
|
||||
scope[set] = data.results;
|
||||
scope[iterator + 'Loading'] = false;
|
||||
scope[iterator + 'HidePaginator'] = false;
|
||||
if (!deferWaitStop) {
|
||||
Wait('stop');
|
||||
}
|
||||
scope.$emit('PostRefresh', set);
|
||||
})
|
||||
.error(function (data, status) {
|
||||
scope[iterator + 'HoldInput'] = false;
|
||||
ProcessErrors(scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to retrieve ' + set + '. GET returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
var id, restUrl, pageSize;
|
||||
|
||||
// if you're editing an object, make sure you're on the right
|
||||
// page to display the element you are editing
|
||||
if (scope.addedItem) {
|
||||
id = scope.addedItem + "";
|
||||
delete scope.addedItem;
|
||||
$rootScope.rowBeingEdited = id;
|
||||
$rootScope.listBeingEdited = set;
|
||||
$rootScope.addedAnItem = true;
|
||||
restUrl = params.url.split("?")[0];
|
||||
pageSize = scope[iterator + '_page_size'];
|
||||
pagination.getInitialPageForList(id, restUrl, pageSize)
|
||||
.then(function (currentPage) {
|
||||
scope.getPage(currentPage, set, iterator);
|
||||
});
|
||||
} else if ($location.$$url.split("/")[1] === params.set && $location.$$url.split("/")[2] && $location.$$url.split("/")[2] !== "add" && !scope.getNewPage) {
|
||||
id = $location.$$url.split("/")[2];
|
||||
restUrl = params.url.split("?")[0];
|
||||
pageSize = scope[iterator + '_page_size'];
|
||||
pagination.getInitialPageForList(id, restUrl, pageSize)
|
||||
.then(function (currentPage) {
|
||||
scope[iterator + '_page'] = currentPage;
|
||||
params.url = params.url + "&page=" + currentPage;
|
||||
getPage(params.url);
|
||||
|
||||
});
|
||||
} else {
|
||||
getPage(params.url);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
}
|
||||
]);
|
||||
@ -1,295 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:related-search
|
||||
* @description
|
||||
* RelatedSearchHelper
|
||||
*
|
||||
* All the parts for controlling the search widget on
|
||||
* related collections.
|
||||
*
|
||||
* SearchInit({
|
||||
* scope: <scope>,
|
||||
* relatedSets: <array of related collections {model_name, url, iterator}>,
|
||||
* form: <form object used by FormGenerator>
|
||||
* });
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
export default
|
||||
angular.module('RelatedSearchHelper', ['RestServices', 'Utilities', 'RefreshRelatedHelper'])
|
||||
.factory('RelatedSearchInit', ['$timeout', 'Alert', 'Rest', 'RefreshRelated', 'Wait', 'Empty',
|
||||
function ($timeout, Alert, Rest, RefreshRelated, Wait, Empty) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
relatedSets = params.relatedSets,
|
||||
form = params.form, f;
|
||||
|
||||
|
||||
|
||||
// add 'selected' class to the selected li element
|
||||
function setSelectedItem(iterator, label) {
|
||||
$('#' + iterator + 'SearchDropdown' + ' li').each(function() {
|
||||
$(this).removeClass('selected');
|
||||
var link = $(this).find('a');
|
||||
if (label === link.text()) {
|
||||
$(this).addClass('selected');
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// Set default values
|
||||
function setDefaults(inIterator) {
|
||||
var iterator, f, fld, set;
|
||||
for (set in form.related) {
|
||||
if (form.related[set].type !== 'tree' && (inIterator === undefined || inIterator === form.related[set].iterator)) {
|
||||
iterator = form.related[set].iterator;
|
||||
for (fld in form.related[set].fields) {
|
||||
if (form.related[set].fields[fld].key) {
|
||||
if (form.related[set].fields[fld].searchable === undefined || form.related[set].fields[fld].searchable === true) {
|
||||
scope[iterator + 'SearchField'] = fld;
|
||||
scope[iterator + 'SearchFieldLabel'] = form.related[set].fields[fld].label;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (Empty(scope[iterator + 'SearchField'])) {
|
||||
// A field marked as key may not be 'searchable'. Find the first searchable field.
|
||||
for (fld in form.related[set].fields) {
|
||||
if (form.related[set].fields[fld].searchable === undefined || form.related[set].fields[fld].searchable === true) {
|
||||
scope[iterator + 'SearchField'] = fld;
|
||||
scope[iterator + 'SearchFieldLabel'] = form.related[set].fields[fld].label;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
scope[iterator + 'SortOrder'] = null;
|
||||
scope[iterator + 'SearchType'] = 'icontains';
|
||||
scope[iterator + 'SearchTypeLabel'] = 'Contains';
|
||||
scope[iterator + 'SearchValue'] = null;
|
||||
scope[iterator + 'SelectShow'] = false;
|
||||
//scope[iterator + 'HideSearchType'] = false;
|
||||
scope[iterator + 'ShowStartBtn'] = true;
|
||||
scope[iterator + 'HideAllStartBtn'] = false;
|
||||
|
||||
f = scope[iterator + 'SearchField'];
|
||||
if (form.related[set].fields[f].searchType &&
|
||||
(form.related[set].fields[f].searchType === 'boolean' || form.related[set].fields[f].searchType === 'select')) {
|
||||
scope[iterator + 'SelectShow'] = true;
|
||||
scope[iterator + 'SearchSelectOpts'] = form.related[set].fields[f].searchOptions;
|
||||
}
|
||||
if (form.related[set].fields[f].searchType && form.related[set].fields[f].searchType === 'gtzero') {
|
||||
scope[iterator + "InputHide"] = true;
|
||||
}
|
||||
|
||||
setSelectedItem(iterator, scope[iterator + 'SearchFieldLabel']);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setDefaults();
|
||||
|
||||
scope.resetSearch = function (iterator) {
|
||||
setDefaults(iterator);
|
||||
scope.search(iterator);
|
||||
};
|
||||
|
||||
// Functions to handle search widget changes
|
||||
scope.setSearchField = function (iterator, fld, label) {
|
||||
|
||||
var f, related;
|
||||
|
||||
for (related in form.related) {
|
||||
if (form.related[related].iterator === iterator) {
|
||||
f = form.related[related].fields[fld];
|
||||
}
|
||||
}
|
||||
|
||||
scope[iterator + 'SearchFieldLabel'] = label;
|
||||
scope[iterator + 'SearchField'] = fld;
|
||||
scope[iterator + 'SearchValue'] = '';
|
||||
scope[iterator + 'SelectShow'] = false;
|
||||
//scope[iterator + 'HideSearchType'] = false;
|
||||
scope[iterator + 'InputHide'] = false;
|
||||
scope[iterator + 'ShowStartBtn'] = true;
|
||||
|
||||
if (f.searchType !== undefined && f.searchType === 'gtzero') {
|
||||
scope[iterator + "InputHide"] = true;
|
||||
scope[iterator + 'ShowStartBtn'] = false;
|
||||
}
|
||||
if (f.searchType !== undefined && (f.searchType === 'boolean' || f.searchType === 'select')) {
|
||||
scope[iterator + 'SelectShow'] = true;
|
||||
scope[iterator + 'SearchSelectOpts'] = f.searchOptions;
|
||||
}
|
||||
|
||||
if (f.searchType !== undefined && f.searchType === 'int') {
|
||||
//scope[iterator + 'HideSearchType'] = true;
|
||||
scope[iterator + 'SearchType'] = 'int';
|
||||
}
|
||||
|
||||
setSelectedItem(iterator, label);
|
||||
|
||||
scope.search(iterator);
|
||||
|
||||
};
|
||||
|
||||
scope.setSearchType = function (model, type, label) {
|
||||
scope[model + 'SearchTypeLabel'] = label;
|
||||
scope[model + 'SearchType'] = type;
|
||||
scope.search(model);
|
||||
};
|
||||
|
||||
scope.startSearch = function (e, iterator) {
|
||||
// If use clicks enter while on input field, start the search
|
||||
if (e.keyCode === 13) {
|
||||
scope.search(iterator);
|
||||
}
|
||||
};
|
||||
|
||||
scope.search = function (iterator) {
|
||||
//scope[iterator + 'SearchSpin'] = true;
|
||||
Wait('start');
|
||||
scope[iterator + 'Loading'] = false;
|
||||
scope[iterator + 'HoldInput'] = true;
|
||||
|
||||
if (scope[iterator + 'SearchValue']) {
|
||||
// User typed a value in input field
|
||||
scope[iterator + 'ShowStartBtn'] = false;
|
||||
}
|
||||
|
||||
if(scope[iterator + 'SearchValue'] && scope[iterator + 'SearchValue'] !== '') {
|
||||
scope[iterator + '_active_search'] = true;
|
||||
}
|
||||
else {
|
||||
scope[iterator + '_active_search'] = false;
|
||||
}
|
||||
|
||||
if (iterator === 'host') {
|
||||
if (scope.hostSearchField === 'has_active_failures') {
|
||||
if (scope.hostSearchSelectValue && scope.hostSearchSelectValue.value === 1) {
|
||||
scope.hostFailureFilter = true;
|
||||
} else {
|
||||
scope.hostFailureFilter = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var fld, key, set, url, sort_order;
|
||||
for (key in relatedSets) {
|
||||
if (relatedSets[key].iterator === iterator) {
|
||||
set = key;
|
||||
url = relatedSets[key].url;
|
||||
for (fld in form.related[key].fields) {
|
||||
if (form.related[key].fields[fld].key) {
|
||||
if (form.related[key].fields[fld].desc) {
|
||||
sort_order = '-' + fld;
|
||||
} else {
|
||||
sort_order = fld;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
sort_order = (scope[iterator + 'SortOrder'] === null) ? sort_order : scope[iterator + 'SortOrder'];
|
||||
f = form.related[set].fields[scope[iterator + 'SearchField']];
|
||||
if ((scope[iterator + 'SelectShow'] === false && !Empty(scope[iterator + 'SearchValue'])) ||
|
||||
(scope[iterator + 'SelectShow'] && scope[iterator + 'SearchSelectValue']) ||
|
||||
(f.searchType && f.searchType === 'gtzero')) {
|
||||
if (f.sourceModel) {
|
||||
// handle fields whose source is a related model e.g. inventories.organization
|
||||
scope[iterator + 'SearchParams'] = f.sourceModel + '__' + f.sourceField + '__';
|
||||
} else if (f.searchField) {
|
||||
scope[iterator + 'SearchParams'] = f.searchField + '__';
|
||||
} else {
|
||||
scope[iterator + 'SearchParams'] = scope[iterator + 'SearchField'] + '__';
|
||||
}
|
||||
|
||||
if (f.searchType && (f.searchType === 'int' || f.searchType === 'boolean')) {
|
||||
scope[iterator + 'SearchParams'] += 'int=';
|
||||
} else if (f.searchType && f.searchType === 'gtzero') {
|
||||
scope[iterator + 'SearchParams'] += 'gt=0';
|
||||
} else {
|
||||
scope[iterator + 'SearchParams'] += scope[iterator + 'SearchType'] + '=';
|
||||
}
|
||||
|
||||
if (f.searchType && (f.searchType === 'boolean' || f.searchType === 'select')) {
|
||||
scope[iterator + 'SearchParams'] += scope[iterator + 'SearchSelectValue'].value;
|
||||
} else if (f.searchType === undefined || f.searchType === 'gtzero') {
|
||||
scope[iterator + 'SearchParams'] += encodeURI(scope[iterator + 'SearchValue']);
|
||||
}
|
||||
scope[iterator + 'SearchParams'] += (sort_order) ? '&order_by=' + encodeURI(sort_order) : '';
|
||||
} else {
|
||||
scope[iterator + 'SearchParams'] = (sort_order) ? 'order_by=' + encodeURI(sort_order) : '';
|
||||
}
|
||||
scope[iterator + '_page'] = 1;
|
||||
url += (url.match(/\/$/)) ? '?' : '&';
|
||||
url += scope[iterator + 'SearchParams'];
|
||||
url += (scope[iterator + '_page_size']) ? '&page_size=' + scope[iterator + '_page_size'] : "";
|
||||
if (scope[iterator + 'SearchFilters']){
|
||||
url += _.reduce(scope[iterator+'SearchFilters'], (result, filter) => result + '&' + filter.url, '');
|
||||
}
|
||||
RefreshRelated({ scope: scope, set: set, iterator: iterator, url: url });
|
||||
};
|
||||
|
||||
|
||||
scope.$on("refreshList", function(e, iterator) {
|
||||
scope.search(iterator);
|
||||
});
|
||||
|
||||
scope.sort = function (iterator, fld) {
|
||||
var sort_order, icon, direction, set;
|
||||
|
||||
// reset sort icons back to 'icon-sort' on all columns
|
||||
// except the one clicked
|
||||
$('.' + iterator + ' .list-header').each(function () {
|
||||
if ($(this).attr('id') !== iterator + '-' + fld + '-header') {
|
||||
var icon = $(this).find('i');
|
||||
icon.attr('class', 'fa fa-sort');
|
||||
}
|
||||
});
|
||||
|
||||
// Toggle the icon for the clicked column
|
||||
// and set the sort direction
|
||||
icon = $('#' + iterator + '-' + fld + '-header i');
|
||||
direction = '';
|
||||
if (icon.hasClass('fa-sort')) {
|
||||
icon.removeClass('fa-sort');
|
||||
icon.addClass('fa-sort-up');
|
||||
} else if (icon.hasClass('fa-sort-up')) {
|
||||
icon.removeClass('fa-sort-up');
|
||||
icon.addClass('fa-sort-down');
|
||||
direction = '-';
|
||||
} else if (icon.hasClass('fa-sort-down')) {
|
||||
icon.removeClass('fa-sort-down');
|
||||
icon.addClass('fa-sort-up');
|
||||
}
|
||||
|
||||
// Set the sorder order value and call the API to refresh the list with the new order
|
||||
for (set in form.related) {
|
||||
if (form.related[set].iterator === iterator) {
|
||||
if (form.related[set].fields[fld].sourceModel) {
|
||||
sort_order = direction + form.related[set].fields[fld].sourceModel + '__' +
|
||||
form.related[set].fields[fld].sourceField;
|
||||
} else {
|
||||
sort_order = direction + fld;
|
||||
}
|
||||
}
|
||||
}
|
||||
scope[iterator + 'SortOrder'] = sort_order;
|
||||
scope.search(iterator);
|
||||
};
|
||||
};
|
||||
}
|
||||
]);
|
||||
@ -1,536 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:search
|
||||
* @description
|
||||
* SearchHelper
|
||||
*
|
||||
* All the parts for controlling the search widget on
|
||||
* related collections.
|
||||
*
|
||||
* SearchInit({
|
||||
* scope: <scope>,
|
||||
* set: <model name (i.e. organizations) used in ng-repeat>
|
||||
* url: <default api url used to load data>
|
||||
* list: <list object used by ListGenerator>
|
||||
* });
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
export default
|
||||
angular.module('SearchHelper', ['RestServices', 'Utilities', 'RefreshHelper'])
|
||||
|
||||
.factory('SearchInit', ['Alert', 'Rest', 'Refresh', '$location', 'GetBasePath', 'Empty', '$timeout', 'Wait', 'Store',
|
||||
function (Alert, Rest, Refresh, $location, GetBasePath, Empty, $timeout, Wait, Store) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope,
|
||||
set = params.set,
|
||||
defaultUrl = params.url,
|
||||
list = params.list,
|
||||
iterator = (params.iterator) ? params.iterator : list.iterator,
|
||||
setWidgets = (params.setWidgets === false) ? false : true,
|
||||
sort_order = params.sort_order || '',
|
||||
widgets, i, modifier;
|
||||
|
||||
|
||||
// add 'selected' class to the selected li element
|
||||
function setSelectedItem(iterator, label, modifier) {
|
||||
// add 'selected' class to the selected li element
|
||||
$('#' + iterator + 'SearchDropdown' + modifier + ' li').each(function() {
|
||||
$(this).removeClass('selected');
|
||||
var link = $(this).find('a');
|
||||
if (label === link.text()) {
|
||||
$(this).addClass('selected');
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function setDefaults(widget) {
|
||||
// Set default values
|
||||
var f, fld, fka, modifier;
|
||||
modifier = (widget === undefined || widget === 1) ? '' : widget;
|
||||
scope[iterator + 'SearchField' + modifier] = '';
|
||||
scope[iterator + 'SearchFieldLabel' + modifier] = '';
|
||||
for (fld in list.fields) {
|
||||
if (list.fields[fld].searchWidget === undefined && widget === 1 ||
|
||||
list.fields[fld].searchWidget === widget) {
|
||||
if (list.fields[fld].key) {
|
||||
if (list.fields[fld].sourceModel) {
|
||||
fka = list.fields[fld].sourceModel + '__' + list.fields[fld].sourceField;
|
||||
sort_order = (list.fields[fld].desc) ? '-' + fka : fka;
|
||||
} else {
|
||||
sort_order = (list.fields[fld].desc) ? '-' + fld : fld;
|
||||
}
|
||||
if (list.fields[fld].searchable === undefined || list.fields[fld].searchable === true) {
|
||||
scope[iterator + 'SearchField' + modifier] = fld;
|
||||
scope[iterator + 'SearchFieldLabel' + modifier] = list.fields[fld].label;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Default the search field to 'defaultSearchField', if one exists
|
||||
for (fld in list.fields) {
|
||||
if (list.fields[fld].searchWidget === undefined && widget === 1 ||
|
||||
list.fields[fld].searchWidget === widget) {
|
||||
if (list.fields[fld].defaultSearchField) {
|
||||
scope[iterator + 'SearchField' + modifier] = fld;
|
||||
scope[iterator + 'SearchFieldLabel' + modifier] = list.fields[fld].label;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// A field marked as key may not be 'searchable', and there might not be a 'defaultSearchField',
|
||||
// so find the first searchable field.
|
||||
if (Empty(scope[iterator + 'SearchField' + modifier])) {
|
||||
for (fld in list.fields) {
|
||||
if (list.fields[fld].searchWidget === undefined && widget === 1 ||
|
||||
list.fields[fld].searchWidget === widget) {
|
||||
if (list.fields[fld].searchable === undefined || list.fields[fld].searchable === true) {
|
||||
scope[iterator + 'SearchField' + modifier] = fld;
|
||||
scope[iterator + 'SearchFieldLabel' + modifier] = list.fields[fld].label;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
scope[iterator + 'SearchType' + modifier] = 'icontains';
|
||||
scope[iterator + 'SearchTypeLabel' + modifier] = 'Contains';
|
||||
scope[iterator + 'SearchParams' + modifier] = '';
|
||||
scope[iterator + 'SearchValue' + modifier] = '';
|
||||
scope[iterator + 'SelectShow' + modifier] = false; // show/hide the Select
|
||||
scope[iterator + 'HideSearchType' + modifier] = false;
|
||||
scope[iterator + 'InputDisable' + modifier] = false;
|
||||
scope[iterator + 'ExtraParms' + modifier] = '';
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = true;
|
||||
scope[iterator + 'HideAllStartBtn' + modifier] = false;
|
||||
|
||||
if (list.fields[scope[iterator + 'SearchField' + modifier]] &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder) {
|
||||
if (scope[list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder]) {
|
||||
// if set to a scope variable
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = scope[list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder];
|
||||
} else {
|
||||
// Set to a string value in the list definition
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder;
|
||||
}
|
||||
} else {
|
||||
// Default value
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = 'Search';
|
||||
}
|
||||
|
||||
scope[iterator + 'InputDisable' + modifier] =
|
||||
(list.fields[scope[iterator + 'SearchField' + modifier]] &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchObject === 'all') ? true : false;
|
||||
|
||||
f = scope[iterator + 'SearchField' + modifier];
|
||||
if (list.fields[f]) {
|
||||
if (list.fields[f].searchType && (list.fields[f].searchType === 'boolean' ||
|
||||
list.fields[f].searchType === 'select')) {
|
||||
scope[iterator + 'SelectShow' + modifier] = true;
|
||||
scope[iterator + 'SearchSelectOpts' + modifier] = list.fields[f].searchOptions;
|
||||
}
|
||||
if (list.fields[f].searchType && list.fields[f].searchType === 'int') {
|
||||
scope[iterator + 'HideSearchType' + modifier] = true;
|
||||
}
|
||||
if (list.fields[f].searchType && list.fields[f].searchType === 'gtzero') {
|
||||
scope[iterator + 'InputHide' + modifier] = true;
|
||||
}
|
||||
}
|
||||
|
||||
setSelectedItem(iterator, scope[iterator + 'SearchFieldLabel' + modifier], modifier);
|
||||
}
|
||||
|
||||
if (setWidgets) {
|
||||
// Set default values for each search widget on the page
|
||||
widgets = (list.searchWidgets) ? list.searchWidgets : 1;
|
||||
for (i = 1; i <= widgets; i++) {
|
||||
modifier = (i === 1) ? '' : i;
|
||||
if ($('#search-widget-container' + modifier)) {
|
||||
setDefaults(i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
scope[iterator + '_current_search_params'] = {
|
||||
set: set,
|
||||
defaultUrl: defaultUrl,
|
||||
list: list,
|
||||
iterator: iterator,
|
||||
sort_order: sort_order
|
||||
};
|
||||
|
||||
Store(iterator + '_current_search_params', scope[iterator + '_current_search_params']);
|
||||
Store('CurrentSearchParams', scope[iterator + '_current_search_params']); // Keeping this around for activity stream
|
||||
|
||||
|
||||
// Functions to handle search widget changes
|
||||
scope.setSearchField = function (iterator, fld, label, widget) {
|
||||
|
||||
var modifier = (widget === undefined || widget === 1) ? '' : widget;
|
||||
scope[iterator + 'SearchFieldLabel' + modifier] = label;
|
||||
scope[iterator + 'SearchField' + modifier] = fld;
|
||||
scope[iterator + 'SearchValue' + modifier] = '';
|
||||
scope[iterator + 'SelectShow' + modifier] = false;
|
||||
scope[iterator + 'HideSearchType' + modifier] = false;
|
||||
scope[iterator + 'InputHide' + modifier] = false;
|
||||
scope[iterator + 'SearchType' + modifier] = 'icontains';
|
||||
scope[iterator + 'InputDisable' + modifier] = (list.fields[fld].searchObject === 'all') ? true : false;
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = true;
|
||||
|
||||
if (list.fields[scope[iterator + 'SearchField' + modifier]] &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder) {
|
||||
if (scope[list.fields[scope[iterator + 'SearchField' + modifier]].searchPlaceholder]) {
|
||||
// if set to a scope variable
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = scope[list.fields[scope[iterator + 'SearchField' +
|
||||
modifier]].searchPlaceholder];
|
||||
} else {
|
||||
// Set to a string value in the list definition
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = list.fields[scope[iterator + 'SearchField' +
|
||||
modifier]].searchPlaceholder;
|
||||
}
|
||||
} else {
|
||||
// Default value
|
||||
scope[iterator + 'SearchPlaceholder' + modifier] = 'Search';
|
||||
}
|
||||
|
||||
if (list.fields[fld].searchType && list.fields[fld].searchType === 'gtzero') {
|
||||
scope[iterator + "InputDisable" + modifier] = true;
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = false;
|
||||
scope.search(iterator);
|
||||
} else if (list.fields[fld].searchSingleValue) {
|
||||
// Query a specific attribute for one specific value
|
||||
// searchSingleValue: true
|
||||
// searchType: 'boolean|int|etc.'
|
||||
// searchValue: < value to match for boolean use 'true'|'false' >
|
||||
scope[iterator + 'InputDisable' + modifier] = true;
|
||||
scope[iterator + "SearchValue" + modifier] = list.fields[fld].searchValue;
|
||||
// For boolean type, SearchValue must be an object
|
||||
if (list.fields[fld].searchType === 'boolean' && list.fields[fld].searchValue === 'true') {
|
||||
scope[iterator + "SearchSelectValue" + modifier] = {
|
||||
value: 1
|
||||
};
|
||||
} else if (list.fields[fld].searchType === 'boolean' && list.fields[fld].searchValue === 'false') {
|
||||
scope[iterator + "SearchSelectValue" + modifier] = {
|
||||
value: 0
|
||||
};
|
||||
} else {
|
||||
scope[iterator + "SearchSelectValue" + modifier] = {
|
||||
value: list.fields[fld].searchValue
|
||||
};
|
||||
}
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = false;
|
||||
} else if (list.fields[fld].searchType === 'in') {
|
||||
scope[iterator + "SearchType" + modifier] = 'in';
|
||||
scope[iterator + "SearchValue" + modifier] = list.fields[fld].searchValue;
|
||||
scope[iterator + "InputDisable" + modifier] = true;
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = false;
|
||||
} else if (list.fields[fld].searchType && (list.fields[fld].searchType === 'boolean' ||
|
||||
list.fields[fld].searchType === 'select' || list.fields[fld].searchType === 'select_or')) {
|
||||
scope[iterator + 'SelectShow' + modifier] = true;
|
||||
scope[iterator + 'SearchSelectOpts' + modifier] = list.fields[fld].searchOptions;
|
||||
scope[iterator + 'SearchType' + modifier] = '';
|
||||
} else if (list.fields[fld].searchType && list.fields[fld].searchType === 'int') {
|
||||
//scope[iterator + 'HideSearchType' + modifier] = true;
|
||||
scope[iterator + 'SearchType' + modifier] = 'int';
|
||||
} else if (list.fields[fld].searchType && list.fields[fld].searchType === 'isnull') {
|
||||
scope[iterator + 'SearchType' + modifier] = 'isnull';
|
||||
scope[iterator + 'InputDisable' + modifier] = true;
|
||||
scope[iterator + 'SearchValue' + modifier] = 'true';
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = false;
|
||||
}
|
||||
|
||||
setSelectedItem(iterator, label, modifier);
|
||||
|
||||
scope.search(iterator);
|
||||
};
|
||||
|
||||
scope.resetSearch = function (iterator) {
|
||||
// Respdond to click of reset button
|
||||
var i,
|
||||
widgets = (list.searchWidgets) ? list.searchWidgets : 1;
|
||||
|
||||
for (i = 1; i <= widgets; i++) {
|
||||
// Clear each search widget
|
||||
setDefaults(i);
|
||||
}
|
||||
// Force removal of search keys from the URL
|
||||
window.location = '/#' + $location.path();
|
||||
scope.search(iterator);
|
||||
};
|
||||
|
||||
if (scope.removeDoSearch) {
|
||||
scope.removeDoSearch();
|
||||
}
|
||||
scope.removeDoSearch = scope.$on('doSearch', function (e, iterator, page, load, calcOnly, deferWaitStop) {
|
||||
//
|
||||
// Execute the search
|
||||
//
|
||||
var url = (calcOnly) ? '' : defaultUrl,
|
||||
connect;
|
||||
|
||||
if (!calcOnly) {
|
||||
scope[iterator + 'Loading'] = (load === undefined || load === true) ? true : false;
|
||||
scope[iterator + 'Page'] = (page) ? parseInt(page) - 1 : 0;
|
||||
}
|
||||
|
||||
//finalize and execute the query
|
||||
if (scope[iterator + 'SearchParams']) {
|
||||
if (/\/$/.test(url)) {
|
||||
url += '?' + scope[iterator + 'SearchParams'];
|
||||
} else {
|
||||
url += '&' + scope[iterator + 'SearchParams'];
|
||||
}
|
||||
}
|
||||
connect = (/\/$/.test(url)) ? '?' : '&';
|
||||
url += (scope[iterator + '_page_size']) ? connect + 'page_size=' + scope[iterator + '_page_size'] : "";
|
||||
if (page) {
|
||||
connect = (/\/$/.test(url)) ? '?' : '&';
|
||||
url += connect + 'page=' + page;
|
||||
}
|
||||
if (scope[iterator + 'ExtraParms']) {
|
||||
connect = (/\/$/.test(url)) ? '?' : '&';
|
||||
url += connect + scope[iterator + 'ExtraParms'];
|
||||
}
|
||||
url = url.replace(/\&\&/g, '&').replace(/\?\&/,'?');
|
||||
if (scope[iterator + 'SearchFilters']){
|
||||
url += _.reduce(scope[iterator+'SearchFilters'], (result, filter) => result + '&' + filter.url, '');
|
||||
}
|
||||
if (calcOnly) {
|
||||
scope.$emit('searchParamsReady', url);
|
||||
}
|
||||
else if (defaultUrl && !/undefined/.test(url)) {
|
||||
Refresh({
|
||||
scope: scope,
|
||||
set: set,
|
||||
iterator: iterator,
|
||||
url: url,
|
||||
deferWaitStop: deferWaitStop
|
||||
});
|
||||
}
|
||||
e.stopPropagation();
|
||||
});
|
||||
|
||||
|
||||
if (scope.removePrepareSearch) {
|
||||
scope.removePrepareSearch();
|
||||
}
|
||||
scope.removePrepareSearch = scope.$on('prepareSearch', function (e, iterator, page, load, calcOnly, deferWaitStop, spinner) {
|
||||
// Start the search spinner
|
||||
if (spinner) {
|
||||
Wait('start');
|
||||
}
|
||||
e.stopPropagation();
|
||||
scope.$emit('prepareSearch2', iterator, page, load, calcOnly, deferWaitStop);
|
||||
|
||||
});
|
||||
|
||||
if (scope.removePrepareSearch2) {
|
||||
scope.removePrepareSearch2();
|
||||
}
|
||||
scope.removePrepareSearch2 = scope.$on('prepareSearch2', function (e, iterator, page, load, calcOnly, deferWaitStop) {
|
||||
// Continue building the search by examining the remaining search widgets. If we're looking at activity_stream,
|
||||
// there's more than one.
|
||||
var i, modifier,
|
||||
widgets = (list.searchWidgets) ? list.searchWidgets : 1;
|
||||
|
||||
// Initialize SearchParams as an empty string if it's not defined. If we don't do this and SearchParams === undefined
|
||||
// then 'undefined' will sneak into the string as we are concatenating and the request will never get sent since we
|
||||
// regex search for 'undefined' in the doSearch section of this process.
|
||||
scope[iterator + 'SearchParams'] = (!scope[iterator + 'SearchParams'] || scope[iterator + 'SearchParams'] === undefined) ? '' : scope[iterator + 'SearchParams'];
|
||||
|
||||
for (i = 1; i <= widgets; i++) {
|
||||
modifier = (i === 1) ? '' : i;
|
||||
scope[iterator + 'HoldInput' + modifier] = true;
|
||||
if ($('#search-widget-container' + modifier) &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]] && !list.fields[scope[iterator + 'SearchField' + modifier]].searchObject) {
|
||||
if (scope[iterator + 'SearchValue' + modifier]) {
|
||||
// if user typed a value in the input box, show the reset link
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = false;
|
||||
} else {
|
||||
scope[iterator + 'ShowStartBtn' + modifier] = true;
|
||||
}
|
||||
if ((!scope[iterator + 'SelectShow' + modifier] && !Empty(scope[iterator + 'SearchValue' + modifier])) ||
|
||||
(scope[iterator + 'SelectShow' + modifier] && scope[iterator + 'SearchSelectValue' + modifier]) ||
|
||||
(list.fields[scope[iterator + 'SearchField' + modifier]] &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'gtzero')) {
|
||||
scope[iterator + '_active_search'] = true;
|
||||
if (list.fields[scope[iterator + 'SearchField' + modifier]].searchField) {
|
||||
scope[iterator + 'SearchParams'] += '&' + list.fields[scope[iterator + 'SearchField' + modifier]].searchField + '__';
|
||||
} else if (list.fields[scope[iterator + 'SearchField' + modifier]].sourceModel) {
|
||||
// handle fields whose source is a related model e.g. inventories.organization
|
||||
scope[iterator + 'SearchParams'] += '&' + list.fields[scope[iterator + 'SearchField' + modifier]].sourceModel + '__' +
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].sourceField + '__';
|
||||
} else if ( list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'select' &&
|
||||
Empty(scope[iterator + 'SearchSelectValue' + modifier].value) ) {
|
||||
scope[iterator + 'SearchParams'] += '&' + scope[iterator + 'SearchField' + modifier] + '__';
|
||||
} else if ( list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'select' &&
|
||||
!Empty(scope[iterator + 'SearchSelectValue' + modifier].value) ) {
|
||||
scope[iterator + 'SearchParams'] += '&' + scope[iterator + 'SearchField' + modifier];
|
||||
} else {
|
||||
scope[iterator + 'SearchParams'] += '&' + scope[iterator + 'SearchField' + modifier] + '__';
|
||||
}
|
||||
|
||||
if (list.fields[scope[iterator + 'SearchField' + modifier]].searchType &&
|
||||
(list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'int' ||
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'boolean')) {
|
||||
scope[iterator + 'SearchParams'] += 'int=';
|
||||
} else if (list.fields[scope[iterator + 'SearchField' + modifier]].searchType &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'gtzero') {
|
||||
scope[iterator + 'SearchParams'] += 'gt=0';
|
||||
} else if (list.fields[scope[iterator + 'SearchField' + modifier]].searchType &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'isnull') {
|
||||
scope[iterator + 'SearchParams'] += 'isnull=';
|
||||
} else if ( (list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'select') &&
|
||||
Empty(scope[iterator + 'SearchSelectValue' + modifier].value) && !/\_\_$/.test(scope[iterator + 'SearchParams']) ) {
|
||||
scope[iterator + 'SearchParams'] += '=iexact=';
|
||||
} else if (list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'in') {
|
||||
if (!/\_\_$/.test(scope[iterator + 'SearchParams'])) {
|
||||
scope[iterator + 'SearchParams'] += '__';
|
||||
}
|
||||
scope[iterator + 'SearchParams'] += 'in=';
|
||||
} else if (/\_\_$/.test(scope[iterator + 'SearchParams'])) {
|
||||
scope[iterator + 'SearchParams'] += 'icontains=';
|
||||
} else {
|
||||
scope[iterator + 'SearchParams'] += scope[iterator + 'SearchType' + modifier] + '=';
|
||||
}
|
||||
|
||||
if (list.fields[scope[iterator + 'SearchField' + modifier]].searchType &&
|
||||
(list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'boolean' ||
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType === 'select')) {
|
||||
scope[iterator + 'SearchParams'] += scope[iterator + 'SearchSelectValue' + modifier].value;
|
||||
} else {
|
||||
if ((!list.fields[scope[iterator + 'SearchField' + modifier]].searchType) ||
|
||||
(list.fields[scope[iterator + 'SearchField' + modifier]].searchType &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType !== 'or' &&
|
||||
list.fields[scope[iterator + 'SearchField' + modifier]].searchType !== 'gtzero')) {
|
||||
scope[iterator + 'SearchParams'] += encodeURI(scope[iterator + 'SearchValue' + modifier]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ((iterator === 'inventory' && scope.inventoryFailureFilter) ||
|
||||
(iterator === 'host' && scope.hostFailureFilter)) {
|
||||
//Things that bypass the search widget. Should go back and add a second widget possibly on
|
||||
//inventory pages and eliminate this
|
||||
scope[iterator + 'SearchParams'] += '&has_active_failures=true';
|
||||
}
|
||||
|
||||
if (sort_order) {
|
||||
scope[iterator + 'SearchParams'] = 'order_by=' + encodeURI(sort_order);
|
||||
}
|
||||
e.stopPropagation();
|
||||
scope.$emit('doSearch', iterator, page, load, calcOnly, deferWaitStop);
|
||||
});
|
||||
|
||||
scope.startSearch = function (e, iterator) {
|
||||
// If use clicks enter while on input field, start the search
|
||||
if (e.keyCode === 13) {
|
||||
scope.search(iterator);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Initiate a searh.
|
||||
*
|
||||
* @iterator: required, list.iterator value
|
||||
* @Page: optional. Added to accomodate back function on Job Events detail.
|
||||
* @Load: optional, set to false if 'Loading' message not desired
|
||||
* @calcOnly: optional, set to true when you want to calc or figure out search params without executing the search
|
||||
* @deferWaitStop: optional, when true refresh.js will NOT issue Wait('stop'), thus leaving the spinner. Caller is then
|
||||
* responsible for stopping the spinner post refresh.
|
||||
* @spinner: optional, if false, don't show the spinner.
|
||||
*/
|
||||
scope.search = function (iterator, page, load, calcOnly, deferWaitStop, spinner) {
|
||||
page = page || null;
|
||||
load = (load || !scope[set] || scope[set].length === 0) ? true : false;
|
||||
calcOnly = (calcOnly) ? true : false;
|
||||
deferWaitStop = (deferWaitStop) ? true : false;
|
||||
spinner = (spinner === undefined) ? true : spinner;
|
||||
if (load) {
|
||||
scope[set] = []; //clear the list array to make sure 'Loading' is the only thing visible on the list
|
||||
}
|
||||
|
||||
if(scope[iterator + 'SearchFilters'] && scope[iterator + 'SearchFilters'].length > 0) {
|
||||
scope[iterator + '_active_search'] = true;
|
||||
}
|
||||
else {
|
||||
scope[iterator + '_active_search'] = false;
|
||||
}
|
||||
|
||||
scope.$emit('prepareSearch', iterator, page, load, calcOnly, deferWaitStop, spinner);
|
||||
};
|
||||
|
||||
|
||||
scope.sort = function (iterator, fld) {
|
||||
// resets any existing order_by parameters in $scope.current_url;
|
||||
var resetOrderBy = function(){
|
||||
var url = _.filter(scope.current_url.split('&'), (o) => !o.includes('order_by'));
|
||||
scope.current_url = url.join('&');
|
||||
};
|
||||
resetOrderBy();
|
||||
// Reset sort icons back to 'icon-sort' on all columns
|
||||
// except the one clicked.
|
||||
$('.list-header').each(function () {
|
||||
if ($(this).attr('id') !== iterator + '-' + fld + '-header') {
|
||||
var icon = $(this).find('i');
|
||||
icon.attr('class', 'fa fa-sort');
|
||||
}
|
||||
});
|
||||
|
||||
// Toggle the icon for the clicked column
|
||||
// and set the sort direction
|
||||
var icon = $('#' + iterator + '-' + fld + '-header i'),
|
||||
direction = '';
|
||||
if (icon.hasClass('fa-sort')) {
|
||||
icon.removeClass('fa-sort');
|
||||
icon.addClass('fa-sort-up');
|
||||
} else if (icon.hasClass('fa-sort-up')) {
|
||||
icon.removeClass('fa-sort-up');
|
||||
icon.addClass('fa-sort-down');
|
||||
direction = '-';
|
||||
} else if (icon.hasClass('fa-sort-down')) {
|
||||
icon.removeClass('fa-sort-down');
|
||||
icon.addClass('fa-sort-up');
|
||||
}
|
||||
|
||||
// Set the sorder order value and call the API to refresh the list with the new order
|
||||
if (list.fields[fld].searchField) {
|
||||
sort_order = direction + list.fields[fld].searchField;
|
||||
} else if (list.fields[fld].sortField) {
|
||||
sort_order = direction + list.fields[fld].sortField;
|
||||
} else {
|
||||
if (list.fields[fld].sourceModel) {
|
||||
sort_order = direction + list.fields[fld].sourceModel + '__' + list.fields[fld].sourceField;
|
||||
} else {
|
||||
sort_order = direction + fld;
|
||||
}
|
||||
}
|
||||
|
||||
scope[list.iterator + '_current_search_params'].sort_order = sort_order;
|
||||
Store(iterator + '_current_search_params', scope[iterator + '_current_search_params']);
|
||||
scope.search(list.iterator);
|
||||
};
|
||||
|
||||
// Call after modal dialogs to remove any lingering callbacks
|
||||
scope.searchCleanup = function () {
|
||||
scope.removeDoSearch();
|
||||
scope.removePrepareSearch();
|
||||
scope.removePrepareSearch2();
|
||||
};
|
||||
|
||||
};
|
||||
}
|
||||
]);
|
||||
@ -3,7 +3,7 @@
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
|
||||
/**
|
||||
* @ngdoc function
|
||||
* @name helpers.function:teams
|
||||
@ -15,8 +15,7 @@
|
||||
import listGenerator from '../shared/list-generator/main';
|
||||
|
||||
export default
|
||||
angular.module('TeamHelper', ['RestServices', 'Utilities', 'OrganizationListDefinition', 'SearchHelper',
|
||||
'PaginationHelpers', listGenerator.name
|
||||
angular.module('TeamHelper', ['RestServices', 'Utilities', 'OrganizationListDefinition', listGenerator.name
|
||||
])
|
||||
.factory('SetTeamListeners', ['Alert', 'Rest',
|
||||
function (Alert, Rest) {
|
||||
@ -40,7 +39,10 @@ export default
|
||||
}
|
||||
}
|
||||
}
|
||||
scope[iterator + 'SearchSpin'] = false;
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// scope[iterator + 'SearchSpin'] = false;
|
||||
|
||||
scope[set] = results;
|
||||
}
|
||||
});
|
||||
@ -74,8 +76,8 @@ export default
|
||||
}
|
||||
])
|
||||
|
||||
.factory('TeamLookUpOrganizationInit', ['Alert', 'Rest', 'OrganizationList', 'generateList', 'SearchInit', 'PaginateInit',
|
||||
function (Alert, Rest, OrganizationList, GenerateList, SearchInit, PaginateInit) {
|
||||
.factory('TeamLookUpOrganizationInit', ['Alert', 'Rest', 'OrganizationList', 'generateList',
|
||||
function (Alert, Rest, OrganizationList, GenerateList) {
|
||||
return function (params) {
|
||||
|
||||
var scope = params.scope;
|
||||
@ -115,19 +117,21 @@ export default
|
||||
}
|
||||
};
|
||||
|
||||
SearchInit({
|
||||
scope: listScope,
|
||||
set: list.name,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
PaginateInit({
|
||||
scope: listScope,
|
||||
list: list,
|
||||
url: defaultUrl,
|
||||
mode: 'lookup'
|
||||
});
|
||||
scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: listScope,
|
||||
// set: list.name,
|
||||
// list: list,
|
||||
// url: defaultUrl
|
||||
// });
|
||||
// PaginateInit({
|
||||
// scope: listScope,
|
||||
// list: list,
|
||||
// url: defaultUrl,
|
||||
// mode: 'lookup'
|
||||
// });
|
||||
// scope.search(list.iterator);
|
||||
|
||||
listScope.toggle_organization(scope.organization);
|
||||
};
|
||||
};
|
||||
|
||||
@ -11,9 +11,8 @@
|
||||
*/
|
||||
|
||||
function InventoriesAdd($scope, $rootScope, $compile, $location, $log,
|
||||
$stateParams, InventoryForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ReturnToCaller, ClearScope, generateList, OrganizationList, SearchInit,
|
||||
PaginateInit, LookUpInit, GetBasePath, ParseTypeChange, Wait, ToJSON,
|
||||
$stateParams, GenerateForm, InventoryForm, Rest, Alert, ProcessErrors,
|
||||
ClearScope, GetBasePath, ParseTypeChange, Wait, ToJSON,
|
||||
$state) {
|
||||
|
||||
Rest.setUrl(GetBasePath('inventory'));
|
||||
@ -29,36 +28,28 @@ function InventoriesAdd($scope, $rootScope, $compile, $location, $log,
|
||||
|
||||
// Inject dynamic view
|
||||
var defaultUrl = GetBasePath('inventory'),
|
||||
form = InventoryForm(),
|
||||
generator = GenerateForm;
|
||||
form = InventoryForm();
|
||||
|
||||
form.formLabelSize = null;
|
||||
form.formFieldSize = null;
|
||||
init();
|
||||
|
||||
generator.inject(form, { mode: 'add', related: false, scope: $scope });
|
||||
function init() {
|
||||
form.formLabelSize = null;
|
||||
form.formFieldSize = null;
|
||||
|
||||
generator.reset();
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
$scope.parseType = 'yaml';
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
variable: 'variables',
|
||||
parse_variable: 'parseType',
|
||||
field_id: 'inventory_variables'
|
||||
});
|
||||
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: ($stateParams.organization_id) ? $stateParams.organization_id : null,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
$scope.parseType = 'yaml';
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
variable: 'variables',
|
||||
parse_variable: 'parseType',
|
||||
field_id: 'inventory_variables'
|
||||
});
|
||||
}
|
||||
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
generator.clearApiErrors();
|
||||
$scope.formSave = function() {
|
||||
Wait('start');
|
||||
try {
|
||||
var fld, json_data, data;
|
||||
@ -68,22 +59,24 @@ function InventoriesAdd($scope, $rootScope, $compile, $location, $log,
|
||||
data = {};
|
||||
for (fld in form.fields) {
|
||||
if (form.fields[fld].realName) {
|
||||
data[form.fields[fld].realName] = $scope[fld];
|
||||
data[form.fields[fld].realName] = $scope[fld];
|
||||
} else {
|
||||
data[fld] = $scope[fld];
|
||||
data[fld] = $scope[fld];
|
||||
}
|
||||
}
|
||||
|
||||
Rest.setUrl(defaultUrl);
|
||||
Rest.post(data)
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
var inventory_id = data.id;
|
||||
Wait('stop');
|
||||
$location.path('/inventories/' + inventory_id + '/manage');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors( $scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory. Post returned status: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory. Post returned status: ' + status
|
||||
});
|
||||
});
|
||||
} catch (err) {
|
||||
Wait('stop');
|
||||
@ -92,13 +85,13 @@ function InventoriesAdd($scope, $rootScope, $compile, $location, $log,
|
||||
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('inventories');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('inventories');
|
||||
};
|
||||
}
|
||||
|
||||
export default['$scope', '$rootScope', '$compile', '$location',
|
||||
'$log', '$stateParams', 'InventoryForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'generateList',
|
||||
'OrganizationList', 'SearchInit', 'PaginateInit', 'LookUpInit',
|
||||
'GetBasePath', 'ParseTypeChange', 'Wait', 'ToJSON', '$state', InventoriesAdd];
|
||||
export default ['$scope', '$rootScope', '$compile', '$location',
|
||||
'$log', '$stateParams', 'GenerateForm', 'InventoryForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ClearScope', 'GetBasePath', 'ParseTypeChange',
|
||||
'Wait', 'ToJSON', '$state', InventoriesAdd
|
||||
];
|
||||
|
||||
@ -1,19 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
import InventoriesAdd from './inventory-add.controller';
|
||||
|
||||
export default {
|
||||
name: 'inventories.add',
|
||||
route: '/add',
|
||||
templateUrl: templateUrl('inventories/inventories'),
|
||||
controller: InventoriesAdd,
|
||||
ncyBreadcrumb: {
|
||||
parent: "inventories",
|
||||
label: "CREATE INVENTORY"
|
||||
}
|
||||
};
|
||||
@ -4,10 +4,8 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import route from './inventory-add.route';
|
||||
import controller from './inventory-add.controller';
|
||||
|
||||
export default
|
||||
angular.module('inventoryAdd', [])
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}]);
|
||||
angular.module('inventoryAdd', [])
|
||||
.controller('InventoryAddController', controller);
|
||||
|
||||
@ -11,88 +11,62 @@
|
||||
*/
|
||||
|
||||
function InventoriesEdit($scope, $rootScope, $compile, $location,
|
||||
$log, $stateParams, InventoryForm, GenerateForm, Rest, Alert, ProcessErrors,
|
||||
ReturnToCaller, ClearScope, generateList, OrganizationList, SearchInit,
|
||||
PaginateInit, LookUpInit, GetBasePath, ParseTypeChange, Wait, ToJSON,
|
||||
ParseVariableString, RelatedSearchInit, RelatedPaginateInit,
|
||||
Prompt, InitiatePlaybookRun, CreateDialog, deleteJobTemplate, $state,
|
||||
$filter) {
|
||||
ClearScope();
|
||||
$log, $stateParams, InventoryForm, Rest, Alert, ProcessErrors,
|
||||
ClearScope, GetBasePath, ParseTypeChange, Wait, ToJSON,
|
||||
ParseVariableString, Prompt, InitiatePlaybookRun,
|
||||
deleteJobTemplate, $state, $filter) {
|
||||
|
||||
// Inject dynamic view
|
||||
var defaultUrl = GetBasePath('inventory'),
|
||||
form = InventoryForm(),
|
||||
generator = GenerateForm,
|
||||
inventory_id = $stateParams.inventory_id,
|
||||
master = {},
|
||||
fld, json_data, data,
|
||||
relatedSets = {};
|
||||
fld, json_data, data;
|
||||
|
||||
form.formLabelSize = null;
|
||||
form.formFieldSize = null;
|
||||
$scope.inventory_id = inventory_id;
|
||||
ClearScope();
|
||||
init();
|
||||
|
||||
$scope.$watch('invnentory_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
function init() {
|
||||
ClearScope();
|
||||
form.formLabelSize = null;
|
||||
form.formFieldSize = null;
|
||||
$scope.inventory_id = inventory_id;
|
||||
|
||||
generator.inject(form, { mode: 'edit', related: true, scope: $scope });
|
||||
|
||||
generator.reset();
|
||||
|
||||
|
||||
// After the project is loaded, retrieve each related set
|
||||
if ($scope.inventoryLoadedRemove) {
|
||||
$scope.inventoryLoadedRemove();
|
||||
$scope.$watch('invnentory_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
}
|
||||
$scope.projectLoadedRemove = $scope.$on('inventoryLoaded', function () {
|
||||
var set;
|
||||
for (set in relatedSets) {
|
||||
$scope.search(relatedSets[set].iterator);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
Wait('start');
|
||||
Rest.setUrl(GetBasePath('inventory') + inventory_id + '/');
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
.success(function(data) {
|
||||
var fld;
|
||||
for (fld in form.fields) {
|
||||
if (fld === 'variables') {
|
||||
$scope.variables = ParseVariableString(data.variables);
|
||||
master.variables = $scope.variables;
|
||||
} else if (fld === 'inventory_name') {
|
||||
$scope[fld] = data.name;
|
||||
$scope[fld] = data.name;
|
||||
master[fld] = $scope[fld];
|
||||
} else if (fld === 'inventory_description') {
|
||||
$scope[fld] = data.description;
|
||||
$scope[fld] = data.description;
|
||||
master[fld] = $scope[fld];
|
||||
} else if (data[fld]) {
|
||||
$scope[fld] = data[fld];
|
||||
$scope[fld] = data[fld];
|
||||
master[fld] = $scope[fld];
|
||||
}
|
||||
if (form.fields[fld].sourceModel && data.summary_fields &&
|
||||
data.summary_fields[form.fields[fld].sourceModel]) {
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
master[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
}
|
||||
}
|
||||
relatedSets = form.relatedSets(data.related);
|
||||
|
||||
// Initialize related search functions. Doing it here to make sure relatedSets object is populated.
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
|
||||
Wait('stop');
|
||||
$scope.parseType = 'yaml';
|
||||
@ -102,224 +76,94 @@ function InventoriesEdit($scope, $rootScope, $compile, $location,
|
||||
parse_variable: 'parseType',
|
||||
field_id: 'inventory_variables'
|
||||
});
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
current_item: $scope.organization,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
$scope.inventory_obj = data;
|
||||
|
||||
$scope.$emit('inventoryLoaded');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Failed to get inventory: ' + inventory_id + '. GET returned: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to get inventory: ' + inventory_id + '. GET returned: ' + status
|
||||
});
|
||||
});
|
||||
// Save
|
||||
$scope.formSave = function () {
|
||||
Wait('start');
|
||||
$scope.formSave = function() {
|
||||
Wait('start');
|
||||
|
||||
// Make sure we have valid variable data
|
||||
json_data = ToJSON($scope.parseType, $scope.variables);
|
||||
// Make sure we have valid variable data
|
||||
json_data = ToJSON($scope.parseType, $scope.variables);
|
||||
|
||||
data = {};
|
||||
for (fld in form.fields) {
|
||||
if (form.fields[fld].realName) {
|
||||
data[form.fields[fld].realName] = $scope[fld];
|
||||
} else {
|
||||
data[fld] = $scope[fld];
|
||||
}
|
||||
}
|
||||
data = {};
|
||||
for (fld in form.fields) {
|
||||
if (form.fields[fld].realName) {
|
||||
data[form.fields[fld].realName] = $scope[fld];
|
||||
} else {
|
||||
data[fld] = $scope[fld];
|
||||
}
|
||||
}
|
||||
|
||||
Rest.setUrl(defaultUrl + inventory_id + '/');
|
||||
Rest.put(data)
|
||||
.success(function () {
|
||||
Wait('stop');
|
||||
$state.go($state.current, {}, {reload: true});
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to update inventory. PUT returned status: ' + status });
|
||||
});
|
||||
Rest.setUrl(defaultUrl + inventory_id + '/');
|
||||
Rest.put(data)
|
||||
.success(function() {
|
||||
Wait('stop');
|
||||
$state.go($state.current, {}, { reload: true });
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to update inventory. PUT returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
$scope.manageInventory = function(){
|
||||
$location.path($location.path() + '/manage');
|
||||
$scope.manageInventory = function() {
|
||||
$location.path($location.path() + '/manage');
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('inventories');
|
||||
$scope.formCancel = function() {
|
||||
$state.go('inventories');
|
||||
};
|
||||
|
||||
$scope.addScanJob = function(){
|
||||
$location.path($location.path()+'/job_templates/add');
|
||||
$scope.addScanJob = function() {
|
||||
$location.path($location.path() + '/job_templates/add');
|
||||
};
|
||||
|
||||
$scope.launchScanJob = function(){
|
||||
$scope.launchScanJob = function() {
|
||||
InitiatePlaybookRun({ scope: $scope, id: this.scan_job_template.id });
|
||||
};
|
||||
|
||||
$scope.scheduleScanJob = function(){
|
||||
$location.path('/job_templates/'+this.scan_job_template.id+'/schedules');
|
||||
$scope.scheduleScanJob = function() {
|
||||
$location.path('/job_templates/' + this.scan_job_template.id + '/schedules');
|
||||
};
|
||||
|
||||
$scope.editScanJob = function(){
|
||||
$location.path($location.path()+'/job_templates/'+this.scan_job_template.id);
|
||||
$scope.editScanJob = function() {
|
||||
$location.path($location.path() + '/job_templates/' + this.scan_job_template.id);
|
||||
};
|
||||
|
||||
$scope.copyScanJobTemplate = function(){
|
||||
var id = this.scan_job_template.id,
|
||||
name = this.scan_job_template.name,
|
||||
element,
|
||||
buttons = [{
|
||||
"label": "Cancel",
|
||||
"onClick": function() {
|
||||
$(this).dialog('close');
|
||||
},
|
||||
"icon": "fa-times",
|
||||
"class": "btn btn-default",
|
||||
"id": "copy-close-button"
|
||||
},{
|
||||
"label": "Copy",
|
||||
"onClick": function() {
|
||||
copyAction();
|
||||
},
|
||||
"icon": "fa-copy",
|
||||
"class": "btn btn-primary",
|
||||
"id": "job-copy-button"
|
||||
}],
|
||||
copyAction = function () {
|
||||
// retrieve the copy of the job template object from the api, then overwrite the name and throw away the id
|
||||
Wait('start');
|
||||
var url = GetBasePath('job_templates')+id;
|
||||
Rest.setUrl(url);
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
data.name = $scope.new_copy_name;
|
||||
delete data.id;
|
||||
$scope.$emit('GoToCopy', data);
|
||||
})
|
||||
.error(function (data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status });
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
CreateDialog({
|
||||
id: 'copy-job-modal' ,
|
||||
title: "Copy",
|
||||
scope: $scope,
|
||||
buttons: buttons,
|
||||
width: 500,
|
||||
height: 300,
|
||||
minWidth: 200,
|
||||
callback: 'CopyDialogReady'
|
||||
});
|
||||
|
||||
$('#job_name').text(name);
|
||||
$('#copy-job-modal').show();
|
||||
|
||||
|
||||
if ($scope.removeCopyDialogReady) {
|
||||
$scope.removeCopyDialogReady();
|
||||
}
|
||||
$scope.removeCopyDialogReady = $scope.$on('CopyDialogReady', function() {
|
||||
//clear any old remaining text
|
||||
$scope.new_copy_name = "" ;
|
||||
$scope.copy_form.$setPristine();
|
||||
$('#copy-job-modal').dialog('open');
|
||||
$('#job-copy-button').attr('ng-disabled', "!copy_form.$valid");
|
||||
element = angular.element(document.getElementById('job-copy-button'));
|
||||
$compile(element)($scope);
|
||||
|
||||
});
|
||||
|
||||
if ($scope.removeGoToCopy) {
|
||||
$scope.removeGoToCopy();
|
||||
}
|
||||
$scope.removeGoToCopy = $scope.$on('GoToCopy', function(e, data) {
|
||||
var url = GetBasePath('job_templates'),
|
||||
old_survey_url = (data.related.survey_spec) ? data.related.survey_spec : "" ;
|
||||
Rest.setUrl(url);
|
||||
Rest.post(data)
|
||||
.success(function (data) {
|
||||
if(data.survey_enabled===true){
|
||||
$scope.$emit("CopySurvey", data, old_survey_url);
|
||||
}
|
||||
else {
|
||||
$('#copy-job-modal').dialog('close');
|
||||
Wait('stop');
|
||||
$location.path($location.path() + '/job_templates/' + data.id);
|
||||
}
|
||||
|
||||
})
|
||||
.error(function (data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + url + ' failed. DELETE returned status: ' + status });
|
||||
});
|
||||
});
|
||||
|
||||
if ($scope.removeCopySurvey) {
|
||||
$scope.removeCopySurvey();
|
||||
}
|
||||
$scope.removeCopySurvey = $scope.$on('CopySurvey', function(e, new_data, old_url) {
|
||||
// var url = data.related.survey_spec;
|
||||
Rest.setUrl(old_url);
|
||||
Rest.get()
|
||||
.success(function (survey_data) {
|
||||
|
||||
Rest.setUrl(new_data.related.survey_spec);
|
||||
Rest.post(survey_data)
|
||||
.success(function () {
|
||||
$('#copy-job-modal').dialog('close');
|
||||
Wait('stop');
|
||||
$location.path($location.path() + '/job_templates/' + new_data.id);
|
||||
})
|
||||
.error(function (data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + new_data.related.survey_spec + ' failed. DELETE returned status: ' + status });
|
||||
});
|
||||
|
||||
|
||||
})
|
||||
.error(function (data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'Call to ' + old_url + ' failed. DELETE returned status: ' + status });
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
};
|
||||
|
||||
$scope.deleteScanJob = function () {
|
||||
var id = this.scan_job_template.id ,
|
||||
action = function () {
|
||||
$('#prompt-modal').modal('hide');
|
||||
Wait('start');
|
||||
deleteJobTemplate(id)
|
||||
.success(function () {
|
||||
$('#prompt-modal').modal('hide');
|
||||
$scope.search(form.related.scan_job_templates.iterator);
|
||||
})
|
||||
.error(function (data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, { hdr: 'Error!',
|
||||
msg: 'DELETE returned status: ' + status });
|
||||
});
|
||||
};
|
||||
$scope.deleteScanJob = function() {
|
||||
var id = this.scan_job_template.id,
|
||||
action = function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
Wait('start');
|
||||
deleteJobTemplate(id)
|
||||
.success(function() {
|
||||
$('#prompt-modal').modal('hide');
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(form.related.scan_job_templates.iterator);
|
||||
})
|
||||
.error(function(data) {
|
||||
Wait('stop');
|
||||
ProcessErrors($scope, data, status, null, {
|
||||
hdr: 'Error!',
|
||||
msg: 'DELETE returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
Prompt({
|
||||
hdr: 'Delete',
|
||||
body: '<div class="Prompt-bodyQuery">Are you sure you want to delete the job template below?</div><div class="Prompt-bodyTarget">' + $filter('sanitize')(this.scan_job_template.name) + '</div>',
|
||||
body: '<div class="Prompt-bodyQuery">Are you sure you want to delete the job template below?</div><div class="Prompt-bodyTarget">' + $filter('sanitize')(this.scan_job_template.name) + '</div>',
|
||||
action: action,
|
||||
actionText: 'DELETE'
|
||||
});
|
||||
@ -329,11 +173,8 @@ function InventoriesEdit($scope, $rootScope, $compile, $location,
|
||||
}
|
||||
|
||||
export default ['$scope', '$rootScope', '$compile', '$location',
|
||||
'$log', '$stateParams', 'InventoryForm', 'GenerateForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ReturnToCaller', 'ClearScope', 'generateList',
|
||||
'OrganizationList', 'SearchInit', 'PaginateInit', 'LookUpInit',
|
||||
'GetBasePath', 'ParseTypeChange', 'Wait', 'ToJSON', 'ParseVariableString',
|
||||
'RelatedSearchInit', 'RelatedPaginateInit', 'Prompt',
|
||||
'InitiatePlaybookRun', 'CreateDialog', 'deleteJobTemplate', '$state',
|
||||
'$filter', InventoriesEdit,
|
||||
'$log', '$stateParams', 'InventoryForm', 'Rest', 'Alert',
|
||||
'ProcessErrors', 'ClearScope', 'GetBasePath', 'ParseTypeChange', 'Wait',
|
||||
'ToJSON', 'ParseVariableString', 'Prompt', 'InitiatePlaybookRun',
|
||||
'deleteJobTemplate', '$state', '$filter', InventoriesEdit,
|
||||
];
|
||||
|
||||
@ -1,22 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
import InventoriesEdit from './inventory-edit.controller';
|
||||
|
||||
export default {
|
||||
name: 'inventories.edit',
|
||||
route: '/:inventory_id',
|
||||
templateUrl: templateUrl('inventories/inventories'),
|
||||
controller: InventoriesEdit,
|
||||
data: {
|
||||
activityStreamId: 'inventory_id'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
parent: 'inventories',
|
||||
label: "{{inventory_obj.name}}"
|
||||
}
|
||||
};
|
||||
@ -4,10 +4,8 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import route from './inventory-edit.route';
|
||||
import controller from './inventory-edit.controller';
|
||||
|
||||
export default
|
||||
angular.module('inventoryEdit', [])
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}]);
|
||||
.controller('InventoryEditController', controller);
|
||||
|
||||
@ -1,5 +0,0 @@
|
||||
<div class="tab-pane" id="inventories">
|
||||
<div ui-view=""></div>
|
||||
<div ng-cloak id="htmlTemplate" class="Panel"></div>
|
||||
<div ng-include="'/static/partials/logviewer.html'"></div>
|
||||
</div>
|
||||
@ -11,11 +11,15 @@
|
||||
*/
|
||||
|
||||
function InventoriesList($scope, $rootScope, $location, $log,
|
||||
$stateParams, $compile, $filter, sanitizeFilter, Rest, Alert, InventoryList,
|
||||
generateList, Prompt, SearchInit, PaginateInit, ReturnToCaller,
|
||||
ClearScope, ProcessErrors, GetBasePath, Wait,
|
||||
Find, Empty, $state, rbacUiControlService) {
|
||||
$stateParams, $compile, $filter, sanitizeFilter, Rest, Alert, InventoryList, Prompt,
|
||||
ClearScope, ProcessErrors, GetBasePath, Wait, Find, Empty, $state, rbacUiControlService, Dataset) {
|
||||
|
||||
let list = InventoryList,
|
||||
defaultUrl = GetBasePath('inventory');
|
||||
|
||||
init();
|
||||
|
||||
function init(){
|
||||
$scope.canAdd = false;
|
||||
|
||||
rbacUiControlService.canAdd('inventory')
|
||||
@ -23,11 +27,49 @@ function InventoriesList($scope, $rootScope, $location, $log,
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
var list = InventoryList,
|
||||
defaultUrl = GetBasePath('inventory') + ($stateParams.status === 'sync-failed' ? '?not__inventory_sources_with_failures=0' : ''),
|
||||
view = generateList,
|
||||
paths = $location.path().replace(/^\//, '').split('/'),
|
||||
mode = (paths[0] === 'inventories') ? 'edit' : 'select';
|
||||
$scope.$watchCollection(list.name, function(){
|
||||
_.forEach($scope[list.name], buildStatusIndicators);
|
||||
});
|
||||
|
||||
// Search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = Dataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
$rootScope.flashMessage = null;
|
||||
|
||||
}
|
||||
|
||||
function buildStatusIndicators(inventory){
|
||||
inventory.launch_class = "";
|
||||
if (inventory.has_inventory_sources) {
|
||||
if (inventory.inventory_sources_with_failures > 0) {
|
||||
inventory.syncStatus = 'error';
|
||||
inventory.syncTip = inventory.inventory_sources_with_failures + ' groups with sync failures. Click for details';
|
||||
}
|
||||
else {
|
||||
inventory.syncStatus = 'successful';
|
||||
inventory.syncTip = 'No inventory sync failures. Click for details.';
|
||||
}
|
||||
}
|
||||
else {
|
||||
inventory.syncStatus = 'na';
|
||||
inventory.syncTip = 'Not configured for inventory sync.';
|
||||
inventory.launch_class = "btn-disabled";
|
||||
}
|
||||
if (inventory.has_active_failures) {
|
||||
inventory.hostsStatus = 'error';
|
||||
inventory.hostsTip = inventory.hosts_with_active_failures + ' hosts with failures. Click for details.';
|
||||
}
|
||||
else if (inventory.total_hosts) {
|
||||
inventory.hostsStatus = 'successful';
|
||||
inventory.hostsTip = 'No hosts with failures. Click for details.';
|
||||
}
|
||||
else {
|
||||
inventory.hostsStatus = 'none';
|
||||
inventory.hostsTip = 'Inventory contains 0 hosts.';
|
||||
}
|
||||
}
|
||||
|
||||
function ellipsis(a) {
|
||||
if (a.length > 20) {
|
||||
@ -62,117 +104,6 @@ function InventoriesList($scope, $rootScope, $location, $log,
|
||||
$scope.triggerPopover(event);
|
||||
}
|
||||
|
||||
view.inject(InventoryList, { mode: mode, scope: $scope });
|
||||
$rootScope.flashMessage = null;
|
||||
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: 'inventories',
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: defaultUrl
|
||||
});
|
||||
|
||||
if ($stateParams.name) {
|
||||
$scope[InventoryList.iterator + 'InputDisable'] = false;
|
||||
$scope[InventoryList.iterator + 'SearchValue'] = $stateParams.name;
|
||||
$scope[InventoryList.iterator + 'SearchField'] = 'name';
|
||||
$scope[InventoryList.iterator + 'SearchFieldLabel'] = InventoryList.fields.name.label;
|
||||
$scope[InventoryList.iterator + 'SearchSelectValue'] = null;
|
||||
}
|
||||
|
||||
if ($stateParams.has_active_failures) {
|
||||
$scope[InventoryList.iterator + 'InputDisable'] = true;
|
||||
$scope[InventoryList.iterator + 'SearchValue'] = $stateParams.has_active_failures;
|
||||
$scope[InventoryList.iterator + 'SearchField'] = 'has_active_failures';
|
||||
$scope[InventoryList.iterator + 'SearchFieldLabel'] = InventoryList.fields.has_active_failures.label;
|
||||
$scope[InventoryList.iterator + 'SearchSelectValue'] = ($stateParams.has_active_failures === 'true') ? {
|
||||
value: 1
|
||||
} : {
|
||||
value: 0
|
||||
};
|
||||
}
|
||||
|
||||
if ($stateParams.has_inventory_sources) {
|
||||
$scope[InventoryList.iterator + 'InputDisable'] = true;
|
||||
$scope[InventoryList.iterator + 'SearchValue'] = $stateParams.has_inventory_sources;
|
||||
$scope[InventoryList.iterator + 'SearchField'] = 'has_inventory_sources';
|
||||
$scope[InventoryList.iterator + 'SearchFieldLabel'] = InventoryList.fields.has_inventory_sources.label;
|
||||
$scope[InventoryList.iterator + 'SearchSelectValue'] = ($stateParams.has_inventory_sources === 'true') ? {
|
||||
value: 1
|
||||
} : {
|
||||
value: 0
|
||||
};
|
||||
}
|
||||
|
||||
if ($stateParams.inventory_sources_with_failures) {
|
||||
// pass a value of true, however this field actually contains an integer value
|
||||
$scope[InventoryList.iterator + 'InputDisable'] = true;
|
||||
$scope[InventoryList.iterator + 'SearchValue'] = $stateParams.inventory_sources_with_failures;
|
||||
$scope[InventoryList.iterator + 'SearchField'] = 'inventory_sources_with_failures';
|
||||
$scope[InventoryList.iterator + 'SearchFieldLabel'] = InventoryList.fields.inventory_sources_with_failures.label;
|
||||
$scope[InventoryList.iterator + 'SearchType'] = 'gtzero';
|
||||
}
|
||||
|
||||
$scope.search(list.iterator);
|
||||
|
||||
if ($scope.removePostRefresh) {
|
||||
$scope.removePostRefresh();
|
||||
}
|
||||
$scope.removePostRefresh = $scope.$on('PostRefresh', function () {
|
||||
//If we got here by deleting an inventory, stop the spinner and cleanup events
|
||||
Wait('stop');
|
||||
try {
|
||||
$('#prompt-modal').modal('hide');
|
||||
}
|
||||
catch(e) {
|
||||
// ignore
|
||||
}
|
||||
$scope.inventories.forEach(function(inventory, idx) {
|
||||
$scope.inventories[idx].launch_class = "";
|
||||
if (inventory.has_inventory_sources) {
|
||||
if (inventory.inventory_sources_with_failures > 0) {
|
||||
$scope.inventories[idx].syncStatus = 'error';
|
||||
$scope.inventories[idx].syncTip = inventory.inventory_sources_with_failures + ' groups with sync failures. Click for details';
|
||||
}
|
||||
else {
|
||||
$scope.inventories[idx].syncStatus = 'successful';
|
||||
$scope.inventories[idx].syncTip = 'No inventory sync failures. Click for details.';
|
||||
}
|
||||
}
|
||||
else {
|
||||
$scope.inventories[idx].syncStatus = 'na';
|
||||
$scope.inventories[idx].syncTip = 'Not configured for inventory sync.';
|
||||
$scope.inventories[idx].launch_class = "btn-disabled";
|
||||
}
|
||||
if (inventory.has_active_failures) {
|
||||
$scope.inventories[idx].hostsStatus = 'error';
|
||||
$scope.inventories[idx].hostsTip = inventory.hosts_with_active_failures + ' hosts with failures. Click for details.';
|
||||
}
|
||||
else if (inventory.total_hosts) {
|
||||
$scope.inventories[idx].hostsStatus = 'successful';
|
||||
$scope.inventories[idx].hostsTip = 'No hosts with failures. Click for details.';
|
||||
}
|
||||
else {
|
||||
$scope.inventories[idx].hostsStatus = 'none';
|
||||
$scope.inventories[idx].hostsTip = 'Inventory contains 0 hosts.';
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
if ($scope.removeRefreshInventories) {
|
||||
$scope.removeRefreshInventories();
|
||||
}
|
||||
$scope.removeRefreshInventories = $scope.$on('RefreshInventories', function () {
|
||||
// Reflect changes after inventory properties edit completes
|
||||
$scope.search(list.iterator);
|
||||
});
|
||||
|
||||
if ($scope.removeHostSummaryReady) {
|
||||
$scope.removeHostSummaryReady();
|
||||
}
|
||||
@ -343,7 +274,8 @@ function InventoriesList($scope, $rootScope, $location, $log,
|
||||
if (parseInt($state.params.inventory_id) === id) {
|
||||
$state.go("^", null, {reload: true});
|
||||
} else {
|
||||
$scope.search(list.iterator);
|
||||
// @issue: OLD SEARCH
|
||||
// $scope.search(list.iterator);
|
||||
}
|
||||
})
|
||||
.error(function (data, status) {
|
||||
@ -361,15 +293,6 @@ function InventoriesList($scope, $rootScope, $location, $log,
|
||||
});
|
||||
};
|
||||
|
||||
$scope.lookupOrganization = function (organization_id) {
|
||||
Rest.setUrl(GetBasePath('organizations') + organization_id + '/');
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
return data.name;
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
// Failed jobs link. Go to the jobs tabs, find all jobs for the inventory and sort by status
|
||||
$scope.viewJobs = function (id) {
|
||||
$location.url('/jobs/?inventory__int=' + id);
|
||||
@ -382,5 +305,5 @@ function InventoriesList($scope, $rootScope, $location, $log,
|
||||
|
||||
export default ['$scope', '$rootScope', '$location', '$log',
|
||||
'$stateParams', '$compile', '$filter', 'sanitizeFilter', 'Rest', 'Alert', 'InventoryList',
|
||||
'generateList', 'Prompt', 'SearchInit', 'PaginateInit', 'ReturnToCaller',
|
||||
'ClearScope', 'ProcessErrors', 'GetBasePath', 'Wait', 'Find', 'Empty', '$state', 'rbacUiControlService', InventoriesList];
|
||||
'Prompt', 'ClearScope', 'ProcessErrors', 'GetBasePath', 'Wait', 'Find', 'Empty', '$state', 'rbacUiControlService', 'Dataset', InventoriesList
|
||||
];
|
||||
|
||||
@ -1,22 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
import InventoriesList from './inventory-list.controller';
|
||||
|
||||
export default {
|
||||
name: 'inventories',
|
||||
route: '/inventories?{status}',
|
||||
templateUrl: templateUrl('inventories/inventories'),
|
||||
controller: InventoriesList,
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'inventory'
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: "INVENTORIES"
|
||||
}
|
||||
};
|
||||
@ -4,10 +4,8 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import route from './inventory-list.route';
|
||||
import controller from './inventory-list.controller';
|
||||
|
||||
export default
|
||||
angular.module('inventoryList', [])
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}]);
|
||||
angular.module('inventoryList', [])
|
||||
.controller('InventoryListController', controller);
|
||||
|
||||
@ -8,11 +8,218 @@ import inventoryAdd from './add/main';
|
||||
import inventoryEdit from './edit/main';
|
||||
import inventoryList from './list/main';
|
||||
import inventoryManage from './manage/main';
|
||||
|
||||
import inventoryManageListRoute from './manage/inventory-manage.route';
|
||||
import { copyMoveGroupRoute, copyMoveHostRoute } from './manage/copy-move/copy-move.route';
|
||||
import adHocRoute from './manage/adhoc/adhoc.route';
|
||||
import { templateUrl } from '../shared/template-url/template-url.factory';
|
||||
export default
|
||||
angular.module('inventory', [
|
||||
inventoryAdd.name,
|
||||
inventoryEdit.name,
|
||||
inventoryList.name,
|
||||
inventoryManage.name,
|
||||
]);
|
||||
inventoryAdd.name,
|
||||
inventoryEdit.name,
|
||||
inventoryList.name,
|
||||
inventoryManage.name,
|
||||
])
|
||||
.config(['$stateProvider', '$stateExtenderProvider', 'stateDefinitionsProvider',
|
||||
function($stateProvider, $stateExtenderProvider, stateDefinitionsProvider) {
|
||||
// When stateDefinition.lazyLoad() resolves, states matching name.** or /url** will be de-registered and replaced with resolved states
|
||||
// This means inventoryManage states will not be registered correctly on page refresh, unless they're registered at the same time as the inventories state tree
|
||||
let stateTree, inventories,
|
||||
addGroup, editGroup, addHost, editHost,
|
||||
listSchedules, addSchedule, editSchedule,
|
||||
stateDefinitions = stateDefinitionsProvider.$get(),
|
||||
stateExtender = $stateExtenderProvider.$get();
|
||||
|
||||
function generateStateTree() {
|
||||
|
||||
// inventories state node
|
||||
inventories = stateDefinitions.generateTree({
|
||||
parent: 'inventories', // top-most node in the generated tree (will replace this state definition)
|
||||
modes: ['add', 'edit'],
|
||||
list: 'InventoryList',
|
||||
form: 'InventoryForm',
|
||||
controllers: {
|
||||
list: 'InventoryListController',
|
||||
add: 'InventoryAddController',
|
||||
edit: 'InventoryEditController'
|
||||
},
|
||||
data: {
|
||||
activityStream: true,
|
||||
activityStreamTarget: 'inventory'
|
||||
}
|
||||
});
|
||||
|
||||
// scheduler state nodes
|
||||
listSchedules = {
|
||||
name: 'inventoryManage.editGroup.schedules',
|
||||
url: '/schedules',
|
||||
searchPrefix: 'schedule',
|
||||
ncyBreadcrumb: {
|
||||
parent: 'inventoryManage.editGroup({group_id: parentObject.id})',
|
||||
label: 'SCHEDULES'
|
||||
},
|
||||
resolve: {
|
||||
Dataset: ['SchedulesList', 'QuerySet', '$stateParams', 'GetBasePath', 'groupData',
|
||||
function(list, qs, $stateParams, GetBasePath, groupData) {
|
||||
let path = `${groupData.related.inventory_source}schedules`;
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}
|
||||
],
|
||||
ParentObject: ['groupData', function(groupData) {
|
||||
return groupData;
|
||||
}]
|
||||
},
|
||||
views: {
|
||||
// clear form template when views render in this substate
|
||||
'form@': {
|
||||
templateProvider: () => ''
|
||||
},
|
||||
'list@': {
|
||||
templateProvider: function(SchedulesList, generateList, ParentObject) {
|
||||
// include name of parent resource in listTitle
|
||||
SchedulesList.listTitle = `${ParentObject.name}<div class='List-titleLockup'></div>Schedules`;
|
||||
let html = generateList.build({
|
||||
list: SchedulesList,
|
||||
mode: 'edit'
|
||||
});
|
||||
html = generateList.wrapPanel(html);
|
||||
return html;
|
||||
},
|
||||
controller: 'schedulerListController'
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
addSchedule = {
|
||||
name: 'inventoryManage.editGroup.schedules.add',
|
||||
url: '/add',
|
||||
ncyBreadcrumb: {
|
||||
label: "CREATE SCHEDULE"
|
||||
},
|
||||
views: {
|
||||
'form@': {
|
||||
controller: 'schedulerAddController',
|
||||
templateUrl: templateUrl("scheduler/schedulerForm")
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
editSchedule = {
|
||||
name: 'inventoryManage.editGroup.schedules.edit',
|
||||
url: '/:schedule_id',
|
||||
ncyBreadcrumb: {
|
||||
label: "{{schedule_obj.name}}"
|
||||
},
|
||||
views: {
|
||||
'form@': {
|
||||
templateUrl: templateUrl("scheduler/schedulerForm"),
|
||||
controller: 'schedulerEditController',
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// group state nodes
|
||||
addGroup = stateDefinitions.generateTree({
|
||||
url: '/add-group',
|
||||
name: 'inventoryManage.addGroup',
|
||||
modes: ['add'],
|
||||
form: 'GroupForm',
|
||||
controllers: {
|
||||
add: 'GroupAddController'
|
||||
}
|
||||
});
|
||||
|
||||
editGroup = stateDefinitions.generateTree({
|
||||
//parent: 'inventoryManage', // top-most node in the generated tree (tree will replace this node)
|
||||
url: '/edit-group/:group_id',
|
||||
name: 'inventoryManage.editGroup',
|
||||
modes: ['edit'],
|
||||
form: 'GroupForm',
|
||||
controllers: {
|
||||
edit: 'GroupEditController'
|
||||
},
|
||||
resolve: {
|
||||
edit: {
|
||||
groupData: ['$stateParams', 'GroupManageService', function($stateParams, GroupManageService) {
|
||||
return GroupManageService.get({ id: $stateParams.group_id }).then(res => res.data.results[0]);
|
||||
}],
|
||||
inventorySourceData: ['$stateParams', 'GroupManageService', function($stateParams, GroupManageService) {
|
||||
return GroupManageService.getInventorySource({ group: $stateParams.group_id }).then(res => res.data.results[0]);
|
||||
}]
|
||||
}
|
||||
},
|
||||
// concat boilerplate schedule state definitions with generated editGroup state definitions
|
||||
}).then((generated) => {
|
||||
let schedulerDefinitions = _.map([
|
||||
stateExtender.buildDefinition(listSchedules),
|
||||
stateExtender.buildDefinition(addSchedule),
|
||||
stateExtender.buildDefinition(editSchedule)
|
||||
],
|
||||
(state) => stateExtender.buildDefinition(state));
|
||||
return {
|
||||
states: _(generated.states)
|
||||
.concat(schedulerDefinitions)
|
||||
.value()
|
||||
};
|
||||
});
|
||||
|
||||
// host state nodes
|
||||
addHost = stateDefinitions.generateTree({
|
||||
url: '/add-host',
|
||||
name: 'inventoryManage.addHost',
|
||||
modes: ['add'],
|
||||
form: 'HostForm',
|
||||
controllers: {
|
||||
add: 'HostsAddController'
|
||||
}
|
||||
});
|
||||
|
||||
editHost = stateDefinitions.generateTree({
|
||||
url: '/edit-host/:host_id',
|
||||
name: 'inventoryManage.editHost',
|
||||
modes: ['edit'],
|
||||
form: 'HostForm',
|
||||
controllers: {
|
||||
edit: 'HostEditController'
|
||||
},
|
||||
resolve: {
|
||||
host: ['$stateParams', 'HostManageService', function($stateParams, HostManageService) {
|
||||
return HostManageService.get({ id: $stateParams.host_id }).then(function(res) {
|
||||
return res.data.results[0];
|
||||
});
|
||||
}]
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: "{{host.name}}",
|
||||
},
|
||||
});
|
||||
|
||||
return Promise.all([
|
||||
inventories,
|
||||
addGroup,
|
||||
editGroup,
|
||||
addHost,
|
||||
editHost,
|
||||
]).then((generated) => {
|
||||
return {
|
||||
states: _.reduce(generated, (result, definition) => {
|
||||
return result.concat(definition.states);
|
||||
}, [
|
||||
stateExtender.buildDefinition(inventoryManageListRoute),
|
||||
stateExtender.buildDefinition(copyMoveGroupRoute),
|
||||
stateExtender.buildDefinition(copyMoveHostRoute),
|
||||
stateExtender.buildDefinition(adHocRoute),
|
||||
|
||||
])
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
stateTree = {
|
||||
name: 'inventories',
|
||||
url: '/inventories',
|
||||
lazyLoad: () => generateStateTree()
|
||||
};
|
||||
|
||||
$stateProvider.state(stateTree);
|
||||
}
|
||||
]);
|
||||
|
||||
@ -12,7 +12,7 @@
|
||||
function adhocController($q, $scope, $location, $stateParams,
|
||||
$state, CheckPasswords, PromptForPasswords, CreateLaunchDialog, CreateSelect2, adhocForm,
|
||||
GenerateForm, Rest, ProcessErrors, ClearScope, GetBasePath, GetChoices,
|
||||
KindChange, LookUpInit, CredentialList, Empty, Wait) {
|
||||
KindChange, CredentialList, Empty, Wait) {
|
||||
|
||||
ClearScope();
|
||||
|
||||
@ -118,17 +118,6 @@ function adhocController($q, $scope, $location, $stateParams,
|
||||
// call helpers to initialize lookup and select fields through get
|
||||
// requests
|
||||
privateFn.initializeFields = function(machineCredentialUrl, adhocUrl) {
|
||||
// setup machine credential lookup
|
||||
LookUpInit({
|
||||
url: machineCredentialUrl,
|
||||
scope: $scope,
|
||||
form: adhocForm,
|
||||
current_item: (!Empty($scope.credential_id)) ?
|
||||
$scope.credential_id : null,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
// setup module name select
|
||||
GetChoices({
|
||||
@ -308,5 +297,5 @@ function adhocController($q, $scope, $location, $stateParams,
|
||||
export default ['$q', '$scope', '$location', '$stateParams',
|
||||
'$state', 'CheckPasswords', 'PromptForPasswords', 'CreateLaunchDialog', 'CreateSelect2',
|
||||
'adhocForm', 'GenerateForm', 'Rest', 'ProcessErrors', 'ClearScope', 'GetBasePath',
|
||||
'GetChoices', 'KindChange', 'LookUpInit', 'CredentialList', 'Empty', 'Wait',
|
||||
'GetChoices', 'KindChange', 'CredentialList', 'Empty', 'Wait',
|
||||
adhocController];
|
||||
|
||||
@ -25,7 +25,7 @@ export default function() {
|
||||
ngOptions: 'module.label for module in adhoc_module_options' +
|
||||
' track by module.value',
|
||||
ngChange: 'moduleChange()',
|
||||
addRequired: true,
|
||||
required: true,
|
||||
awPopOver:'<p>These are the modules that Tower supports ' +
|
||||
'running commands against.',
|
||||
dataTitle: 'Module',
|
||||
@ -40,13 +40,12 @@ export default function() {
|
||||
dataTitle: 'Arguments',
|
||||
dataPlacement: 'right',
|
||||
dataContainer: 'body',
|
||||
addRequired: false,
|
||||
autocomplete: false
|
||||
},
|
||||
limit: {
|
||||
label: 'Limit',
|
||||
type: 'text',
|
||||
addRequired: false,
|
||||
|
||||
awPopOver: '<p>The pattern used to target hosts in the ' +
|
||||
'inventory. Leaving the field blank, all, and * will ' +
|
||||
'all target all hosts in the inventory. You can find ' +
|
||||
@ -61,6 +60,8 @@ export default function() {
|
||||
credential: {
|
||||
label: 'Machine Credential',
|
||||
type: 'lookup',
|
||||
list: 'CredentialList',
|
||||
basePath: 'credentials',
|
||||
sourceModel: 'credential',
|
||||
sourceField: 'name',
|
||||
ngClick: 'lookUpCredential()',
|
||||
@ -81,7 +82,7 @@ export default function() {
|
||||
become_enabled: {
|
||||
label: 'Enable Privilege Escalation',
|
||||
type: 'checkbox',
|
||||
addRequired: false,
|
||||
|
||||
column: 2,
|
||||
awPopOver: "<p>If enabled, run this playbook as an administrator. This is the equivalent of passing the<code> --become</code> option to the <code> ansible</code> command. </p>",
|
||||
dataPlacement: 'right',
|
||||
@ -95,7 +96,7 @@ export default function() {
|
||||
ngOptions: 'verbosity.label for verbosity in ' +
|
||||
'adhoc_verbosity_options ' +
|
||||
'track by verbosity.value',
|
||||
addRequired: true,
|
||||
required: true,
|
||||
awPopOver:'<p>These are the verbosity levels for standard ' +
|
||||
'out of the command run that are supported.',
|
||||
dataTitle: 'Verbosity',
|
||||
@ -111,7 +112,7 @@ export default function() {
|
||||
min: 0,
|
||||
spinner: true,
|
||||
"default": 0,
|
||||
addRequired: true,
|
||||
required: true,
|
||||
'class': "input-small",
|
||||
column: 1,
|
||||
awPopOver: '<p>The number of parallel or simultaneous processes to use while executing the command. 0 signifies ' +
|
||||
|
||||
@ -7,7 +7,7 @@
|
||||
import {templateUrl} from '../../../shared/template-url/template-url.factory';
|
||||
|
||||
export default {
|
||||
route: '/adhoc',
|
||||
url: '/adhoc',
|
||||
params:{
|
||||
pattern: {
|
||||
value: 'all',
|
||||
@ -23,10 +23,5 @@ export default {
|
||||
},
|
||||
ncyBreadcrumb: {
|
||||
label: "RUN COMMAND"
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@ -1,11 +1,7 @@
|
||||
import route from './adhoc.route';
|
||||
import adhocController from './adhoc.controller';
|
||||
import form from './adhoc.form';
|
||||
|
||||
export default
|
||||
export default
|
||||
angular.module('adhoc', [])
|
||||
.controller('adhocController', adhocController)
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}])
|
||||
.factory('adhocForm', form);
|
||||
|
||||
@ -5,8 +5,8 @@
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$scope', '$state', '$stateParams', 'generateList', 'SearchInit', 'PaginateInit', 'GroupManageService', 'GetBasePath', 'CopyMoveGroupList', 'group',
|
||||
function($scope, $state, $stateParams, GenerateList, SearchInit, PaginateInit, GroupManageService, GetBasePath, CopyMoveGroupList, group){
|
||||
['$scope', '$state', '$stateParams', 'generateList', 'GroupManageService', 'GetBasePath', 'CopyMoveGroupList', 'group',
|
||||
function($scope, $state, $stateParams, GenerateList, GroupManageService, GetBasePath, CopyMoveGroupList, group){
|
||||
var list = CopyMoveGroupList,
|
||||
view = GenerateList;
|
||||
$scope.item = group;
|
||||
@ -69,19 +69,21 @@
|
||||
scope: $scope,
|
||||
input_type: 'radio'
|
||||
});
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: list.name,
|
||||
list: list,
|
||||
url: url
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url : url,
|
||||
mode: 'lookup'
|
||||
});
|
||||
$scope.search(list.iterator, null, true, false);
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: $scope,
|
||||
// set: list.name,
|
||||
// list: list,
|
||||
// url: url
|
||||
// });
|
||||
// PaginateInit({
|
||||
// scope: $scope,
|
||||
// list: list,
|
||||
// url : url,
|
||||
// mode: 'lookup'
|
||||
// });
|
||||
// $scope.search(list.iterator, null, true, false);
|
||||
// remove the current group from list
|
||||
};
|
||||
init();
|
||||
|
||||
@ -5,8 +5,8 @@
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$scope', '$state', '$stateParams', 'generateList', 'SearchInit', 'PaginateInit', 'HostManageService', 'GetBasePath', 'CopyMoveGroupList', 'host',
|
||||
function($scope, $state, $stateParams, GenerateList, SearchInit, PaginateInit, HostManageService, GetBasePath, CopyMoveGroupList, host){
|
||||
['$scope', '$state', '$stateParams', 'generateList', 'HostManageService', 'GetBasePath', 'CopyMoveGroupList', 'host',
|
||||
function($scope, $state, $stateParams, GenerateList, HostManageService, GetBasePath, CopyMoveGroupList, host){
|
||||
var list = CopyMoveGroupList,
|
||||
view = GenerateList;
|
||||
$scope.item = host;
|
||||
@ -48,19 +48,21 @@
|
||||
scope: $scope,
|
||||
input_type: 'radio'
|
||||
});
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
set: list.name,
|
||||
list: list,
|
||||
url: url
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url : url,
|
||||
mode: 'lookup'
|
||||
});
|
||||
$scope.search(list.iterator, null, true, false);
|
||||
|
||||
// @issue: OLD SEARCH
|
||||
// SearchInit({
|
||||
// scope: $scope,
|
||||
// set: list.name,
|
||||
// list: list,
|
||||
// url: url
|
||||
// });
|
||||
// PaginateInit({
|
||||
// scope: $scope,
|
||||
// list: list,
|
||||
// url : url,
|
||||
// mode: 'lookup'
|
||||
// });
|
||||
// $scope.search(list.iterator, null, true, false);
|
||||
};
|
||||
init();
|
||||
}];
|
||||
|
||||
@ -8,9 +8,9 @@ import {templateUrl} from '../../../shared/template-url/template-url.factory';
|
||||
import CopyMoveGroupsController from './copy-move-groups.controller';
|
||||
import CopyMoveHostsController from './copy-move-hosts.controller';
|
||||
|
||||
var copyMoveGroup = {
|
||||
var copyMoveGroupRoute = {
|
||||
name: 'inventoryManage.copyMoveGroup',
|
||||
route: '/copy-move-group/{group_id}',
|
||||
url: '/copy-move-group/{group_id}',
|
||||
data: {
|
||||
group_id: 'group_id',
|
||||
},
|
||||
@ -22,11 +22,6 @@ var copyMoveGroup = {
|
||||
return GroupManageService.get({id: $stateParams.group_id}).then(res => res.data.results[0]);
|
||||
}]
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage' : {
|
||||
controller: CopyMoveGroupsController,
|
||||
@ -34,9 +29,9 @@ var copyMoveGroup = {
|
||||
}
|
||||
}
|
||||
};
|
||||
var copyMoveHost = {
|
||||
var copyMoveHostRoute = {
|
||||
name: 'inventoryManage.copyMoveHost',
|
||||
route: '/copy-move-host/{host_id}',
|
||||
url: '/copy-move-host/{host_id}',
|
||||
ncyBreadcrumb: {
|
||||
label: "COPY OR MOVE {{item.name}}"
|
||||
},
|
||||
@ -45,11 +40,6 @@ var copyMoveHost = {
|
||||
return HostManageService.get({id: $stateParams.host_id}).then(res => res.data.results[0]);
|
||||
}]
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage': {
|
||||
templateUrl: templateUrl('inventories/manage/copy-move/copy-move'),
|
||||
@ -58,4 +48,4 @@ var copyMoveHost = {
|
||||
}
|
||||
};
|
||||
|
||||
export {copyMoveGroup, copyMoveHost};
|
||||
export {copyMoveGroupRoute, copyMoveHostRoute};
|
||||
|
||||
@ -4,11 +4,10 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {copyMoveGroup, copyMoveHost} from './copy-move.route';
|
||||
import CopyMoveGroupsController from './copy-move-groups.controller';
|
||||
import CopyMoveHostsController from './copy-move-hosts.controller';
|
||||
|
||||
export default
|
||||
angular.module('manageCopyMove', [])
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(copyMoveGroup);
|
||||
$stateExtender.addState(copyMoveHost);
|
||||
}]);
|
||||
.controller('CopyMoveGroupsController', CopyMoveGroupsController)
|
||||
.controller('CopyMoveHostsController', CopyMoveHostsController);
|
||||
|
||||
@ -4,27 +4,47 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$state', '$stateParams', '$scope', 'GroupForm', 'CredentialList', 'inventoryScriptsListObject', 'ParseTypeChange', 'GenerateForm', 'inventoryData', 'LookUpInit',
|
||||
export default ['$state', '$stateParams', '$scope', 'GroupForm', 'CredentialList', 'ParseTypeChange', 'GenerateForm', 'inventoryData',
|
||||
'GroupManageService', 'GetChoices', 'GetBasePath', 'CreateSelect2', 'GetSourceTypeOptions', 'rbacUiControlService',
|
||||
function($state, $stateParams, $scope, GroupForm, CredentialList, InventoryScriptsList, ParseTypeChange, GenerateForm, inventoryData, LookUpInit,
|
||||
GroupManageService, GetChoices, GetBasePath, CreateSelect2, GetSourceTypeOptions, rbacUiControlService){
|
||||
var generator = GenerateForm,
|
||||
form = GroupForm();
|
||||
function($state, $stateParams, $scope, GroupForm, CredentialList, ParseTypeChange, GenerateForm, inventoryData,
|
||||
GroupManageService, GetChoices, GetBasePath, CreateSelect2, GetSourceTypeOptions, rbacUiControlService) {
|
||||
var form = GroupForm();
|
||||
|
||||
// remove "type" field from search options
|
||||
CredentialList = _.cloneDeep(CredentialList);
|
||||
CredentialList.fields.kind.noSearch = true;
|
||||
init();
|
||||
|
||||
function init() {
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
rbacUiControlService.canAdd(GetBasePath('inventory') + $stateParams.inventory_id + "/groups")
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.envParseType = 'yaml';
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'group_variables',
|
||||
variable: 'variables',
|
||||
});
|
||||
initSources();
|
||||
}
|
||||
|
||||
$scope.formCancel = function(){
|
||||
$scope.lookupCredential = function(){
|
||||
$state.go('.lookup.credential', {
|
||||
credential_search: {
|
||||
kind: $scope.source.value,
|
||||
page_size: '5',
|
||||
page: '1'
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
$scope.formCancel = function() {
|
||||
$state.go('^');
|
||||
};
|
||||
$scope.formSave = function(){
|
||||
|
||||
$scope.formSave = function() {
|
||||
var params, source;
|
||||
// group fields
|
||||
var group = {
|
||||
@ -33,11 +53,11 @@
|
||||
description: $scope.description,
|
||||
inventory: inventoryData.id
|
||||
};
|
||||
if ($scope.source){
|
||||
if ($scope.source) {
|
||||
// inventory_source fields
|
||||
params = {
|
||||
instance_filters: $scope.instance_filters,
|
||||
source_vars: $scope[$scope.source.value + '_variables'] === '---' || $scope[$scope.source.value + '_variables'] === '{}' ? null : $scope[$scope.source.value + '_variables'],
|
||||
source_vars: $scope[$scope.source.value + '_variables'] === '---' || $scope[$scope.source.value + '_variables'] === '{}' ? null : $scope[$scope.source.value + '_variables'],
|
||||
source_script: $scope.inventory_script,
|
||||
source: $scope.source.value,
|
||||
credential: $scope.credential,
|
||||
@ -50,73 +70,47 @@
|
||||
source_regions: _.map($scope.source_regions, 'value').join(',')
|
||||
};
|
||||
source = $scope.source.value;
|
||||
}
|
||||
else{
|
||||
} else {
|
||||
source = null;
|
||||
}
|
||||
switch(source){
|
||||
switch (source) {
|
||||
// no inventory source set, just create a new group
|
||||
// '' is the value supplied for Manual source type
|
||||
case null || '':
|
||||
GroupManageService.post(group).then(res => {
|
||||
// associate
|
||||
if ($stateParams.group){
|
||||
if ($stateParams.group) {
|
||||
return GroupManageService.associateGroup(res.data, _.last($stateParams.group))
|
||||
.then(() => $state.go('^', null, {reload: true}));
|
||||
}
|
||||
else{
|
||||
$state.go('^', null, {reload: true});
|
||||
.then(() => $state.go('^', null, { reload: true }));
|
||||
} else {
|
||||
$state.go('^', null, { reload: true });
|
||||
}
|
||||
});
|
||||
break;
|
||||
// create a new group and create/associate an inventory source
|
||||
// equal to case 'rax' || 'ec2' || 'azure' || 'azure_rm' || 'vmware' || 'satellite6' || 'cloudforms' || 'openstack' || 'custom'
|
||||
// create a new group and create/associate an inventory source
|
||||
// equal to case 'rax' || 'ec2' || 'azure' || 'azure_rm' || 'vmware' || 'satellite6' || 'cloudforms' || 'openstack' || 'custom'
|
||||
default:
|
||||
GroupManageService.post(group)
|
||||
// associate to group
|
||||
.then(res => {
|
||||
if ($stateParams.group){
|
||||
if ($stateParams.group) {
|
||||
GroupManageService.associateGroup(res.data, _.last($stateParams.group));
|
||||
return res;
|
||||
}
|
||||
else {return res;}
|
||||
} else {
|
||||
return res; }
|
||||
// pass the original POST response and not the association response
|
||||
})
|
||||
.then(res => GroupManageService.putInventorySource(
|
||||
// put the received group ID into inventory source payload
|
||||
// and pass the related endpoint
|
||||
_.assign(params, {group: res.data.id}), res.data.related.inventory_source))
|
||||
.then(res => $state.go('inventoryManage.editGroup', {group_id: res.data.group}, {reload: true}));
|
||||
_.assign(params, { group: res.data.id }), res.data.related.inventory_source))
|
||||
.then(res => $state.go('inventoryManage.editGroup', { group_id: res.data.group }, { reload: true }));
|
||||
break;
|
||||
}
|
||||
};
|
||||
$scope.sourceChange = function(source){
|
||||
$scope.sourceChange = function(source) {
|
||||
source = source.value;
|
||||
if (source === 'custom'){
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_script'),
|
||||
form: form,
|
||||
list: InventoryScriptsList,
|
||||
field: 'inventory_script',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
// equal to case 'ec2' || 'rax' || 'azure' || 'azure_rm' || 'vmware' || 'satellite6' || 'cloudforms' || 'openstack'
|
||||
else{
|
||||
var credentialBasePath = (source === 'ec2') ? GetBasePath('credentials') + '?kind=aws' : GetBasePath('credentials') + (source === '' ? '' : '?kind=' + (source));
|
||||
$scope.cloudCredentialRequired = source !== '' && source !== 'custom' && source !== 'ec2' ? true : false;
|
||||
CredentialList.basePath = credentialBasePath;
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: credentialBasePath,
|
||||
form: form,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
if (source === 'ec2' || source === 'custom' || source === 'vmware' || source === 'openstack'){
|
||||
if (source === 'ec2' || source === 'custom' || source === 'vmware' || source === 'openstack') {
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: source + '_variables',
|
||||
@ -135,7 +129,16 @@
|
||||
$scope.credential_name = null;
|
||||
initRegionSelect();
|
||||
};
|
||||
var initRegionSelect = function(){
|
||||
// region / source options callback
|
||||
$scope.$on('choicesReadyGroup', function() {
|
||||
initRegionSelect();
|
||||
});
|
||||
|
||||
$scope.$on('sourceTypeOptionsReady', function() {
|
||||
initSourceSelect();
|
||||
});
|
||||
|
||||
function initRegionSelect(){
|
||||
CreateSelect2({
|
||||
element: '#group_source_regions',
|
||||
multiple: true
|
||||
@ -144,14 +147,15 @@
|
||||
element: '#group_group_by',
|
||||
multiple: true
|
||||
});
|
||||
};
|
||||
var initSourceSelect = function(){
|
||||
}
|
||||
function initSourceSelect(){
|
||||
CreateSelect2({
|
||||
element: '#group_source',
|
||||
multiple: false
|
||||
});
|
||||
};
|
||||
var initSources = function(){
|
||||
}
|
||||
|
||||
function initSources(){
|
||||
GetChoices({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_sources'),
|
||||
@ -202,25 +206,6 @@
|
||||
variable: 'source_type_options',
|
||||
//callback: 'sourceTypeOptionsReady' this callback is hard-coded into GetSourceTypeOptions(), included for ref
|
||||
});
|
||||
};
|
||||
// region / source options callback
|
||||
$scope.$on('choicesReadyGroup', function(){
|
||||
initRegionSelect();
|
||||
});
|
||||
|
||||
$scope.$on('sourceTypeOptionsReady', function(){
|
||||
initSourceSelect();
|
||||
});
|
||||
var init = function(){
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.envParseType = 'yaml';
|
||||
generator.inject(form, {mode: 'add', related: false, id: 'Inventory-groupManage--panel', scope: $scope});
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'group_variables',
|
||||
variable: 'variables',
|
||||
});
|
||||
initSources();
|
||||
};
|
||||
init();
|
||||
}];
|
||||
}
|
||||
}
|
||||
];
|
||||
|
||||
@ -4,30 +4,59 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$state', '$stateParams', '$scope', 'GroupForm', 'CredentialList', 'inventoryScriptsListObject', 'ToggleNotification', 'ParseVariableString',
|
||||
'ParseTypeChange', 'GenerateForm', 'LookUpInit', 'RelatedSearchInit', 'RelatedPaginateInit', 'NotificationsListInit',
|
||||
'GroupManageService','GetChoices', 'GetBasePath', 'CreateSelect2', 'GetSourceTypeOptions', 'groupData', 'inventorySourceData',
|
||||
function($state, $stateParams, $scope, GroupForm, CredentialList, InventoryScriptsList, ToggleNotification, ParseVariableString,
|
||||
ParseTypeChange, GenerateForm, LookUpInit, RelatedSearchInit, RelatedPaginateInit, NotificationsListInit,
|
||||
GroupManageService, GetChoices, GetBasePath, CreateSelect2, GetSourceTypeOptions, groupData, inventorySourceData){
|
||||
var generator = GenerateForm,
|
||||
form = GroupForm();
|
||||
export default ['$state', '$stateParams', '$scope', 'ToggleNotification', 'ParseVariableString',
|
||||
'ParseTypeChange', 'GroupManageService', 'GetChoices', 'GetBasePath', 'CreateSelect2', 'GetSourceTypeOptions', 'groupData', 'inventorySourceData',
|
||||
function($state, $stateParams, $scope, ToggleNotification, ParseVariableString,
|
||||
ParseTypeChange, GroupManageService, GetChoices, GetBasePath, CreateSelect2, GetSourceTypeOptions, groupData, inventorySourceData) {
|
||||
|
||||
// remove "type" field from search options
|
||||
CredentialList = _.cloneDeep(CredentialList);
|
||||
CredentialList.fields.kind.noSearch = true;
|
||||
init();
|
||||
|
||||
$scope.$watch('group_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
function init() {
|
||||
// instantiate expected $scope values from inventorySourceData & groupData
|
||||
_.assign($scope, { credential: inventorySourceData.credential }, { overwrite: inventorySourceData.overwrite }, { overwrite_vars: inventorySourceData.overwrite_vars }, { update_on_launch: inventorySourceData.update_on_launch }, { update_cache_timeout: inventorySourceData.update_cache_timeout }, { instance_filters: inventorySourceData.instance_filters }, { inventory_script: inventorySourceData.source_script });
|
||||
if (inventorySourceData.credential) {
|
||||
$scope.credential_name = inventorySourceData.summary_fields.credential.name;
|
||||
}
|
||||
});
|
||||
$scope = angular.extend($scope, groupData);
|
||||
|
||||
$scope.formCancel = function(){
|
||||
// display custom inventory_script name
|
||||
if (inventorySourceData.source === 'custom') {
|
||||
$scope.inventory_script_name = inventorySourceData.summary_fields.source_script.name;
|
||||
}
|
||||
|
||||
$scope.$watch('summary_fields.user_capabilities.edit', function(val) {
|
||||
$scope.canAdd = val;
|
||||
});
|
||||
|
||||
// init codemirror(s)
|
||||
$scope.variables = $scope.variables === null || $scope.variables === '' ? '---' : ParseVariableString($scope.variables);
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.envParseType = 'yaml';
|
||||
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'group_variables',
|
||||
variable: 'variables',
|
||||
});
|
||||
|
||||
initSources();
|
||||
}
|
||||
|
||||
var initRegionSelect = function() {
|
||||
CreateSelect2({
|
||||
element: '#group_source_regions',
|
||||
multiple: true
|
||||
});
|
||||
CreateSelect2({
|
||||
element: '#group_group_by',
|
||||
multiple: true
|
||||
});
|
||||
};
|
||||
|
||||
$scope.formCancel = function() {
|
||||
$state.go('^');
|
||||
};
|
||||
$scope.formSave = function(){
|
||||
$scope.formSave = function() {
|
||||
var params, source;
|
||||
// group fields
|
||||
var group = {
|
||||
@ -37,7 +66,7 @@
|
||||
inventory: $scope.inventory,
|
||||
id: groupData.id
|
||||
};
|
||||
if ($scope.source){
|
||||
if ($scope.source) {
|
||||
// inventory_source fields
|
||||
params = {
|
||||
group: groupData.id,
|
||||
@ -55,69 +84,29 @@
|
||||
source_vars: $scope[$scope.source.value + '_variables'] === '---' || $scope[$scope.source.value + '_variables'] === '{}' ? null : $scope[$scope.source.value + '_variables']
|
||||
};
|
||||
source = $scope.source.value;
|
||||
}
|
||||
else{
|
||||
} else {
|
||||
source = null;
|
||||
}
|
||||
switch(source){
|
||||
switch (source) {
|
||||
// no inventory source set, just create a new group
|
||||
// '' is the value supplied for Manual source type
|
||||
case null || '':
|
||||
GroupManageService.put(group).then(() => $state.go($state.current, null, {reload: true}));
|
||||
GroupManageService.put(group).then(() => $state.go($state.current, null, { reload: true }));
|
||||
break;
|
||||
// create a new group and create/associate an inventory source
|
||||
// equal to case 'rax' || 'ec2' || 'azure' || 'azure_rm' || 'vmware' || 'satellite6' || 'cloudforms' || 'openstack' || 'custom'
|
||||
// create a new group and create/associate an inventory source
|
||||
// equal to case 'rax' || 'ec2' || 'azure' || 'azure_rm' || 'vmware' || 'satellite6' || 'cloudforms' || 'openstack' || 'custom'
|
||||
default:
|
||||
GroupManageService.put(group)
|
||||
.then(() => GroupManageService.putInventorySource(params, groupData.related.inventory_source))
|
||||
.then(() => $state.go($state.current, null, {reload: true}));
|
||||
.then(() => $state.go($state.current, null, { reload: true }));
|
||||
break;
|
||||
}
|
||||
};
|
||||
$scope.toggleNotification = function(event, notifier_id, column) {
|
||||
var notifier = this.notification;
|
||||
try {
|
||||
$(event.target).tooltip('hide');
|
||||
}
|
||||
catch(e) {
|
||||
// ignore
|
||||
}
|
||||
ToggleNotification({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_sources'),
|
||||
id: inventorySourceData.id,
|
||||
notifier: notifier,
|
||||
column: column,
|
||||
callback: 'NotificationRefresh'
|
||||
});
|
||||
};
|
||||
$scope.sourceChange = function(source){
|
||||
|
||||
$scope.sourceChange = function(source) {
|
||||
$scope.source = source;
|
||||
if (source.value === 'custom'){
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_script'),
|
||||
form: form,
|
||||
list: InventoryScriptsList,
|
||||
field: 'inventory_script',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
else{
|
||||
var credentialBasePath = (source.value === 'ec2') ? GetBasePath('credentials') + '?kind=aws' : GetBasePath('credentials') + (source.value === '' ? '' : '?kind=' + (source.value));
|
||||
CredentialList.basePath = credentialBasePath;
|
||||
$scope.cloudCredentialRequired = source.value !== '' && source.value !== 'custom' && source.value !== 'ec2' ? true : false;
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: credentialBasePath,
|
||||
form: form,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
if (source.value === 'ec2' || source.value === 'custom' ||
|
||||
source.value === 'vmware' || source.value === 'openstack'){
|
||||
source.value === 'vmware' || source.value === 'openstack') {
|
||||
$scope[source.value + '_variables'] = $scope[source.value + '_variables'] === null ? '---' : $scope[source.value + '_variables'];
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
@ -137,18 +126,8 @@
|
||||
initRegionSelect();
|
||||
};
|
||||
|
||||
var initRegionSelect = function(){
|
||||
CreateSelect2({
|
||||
element: '#group_source_regions',
|
||||
multiple: true
|
||||
});
|
||||
CreateSelect2({
|
||||
element: '#group_group_by',
|
||||
multiple: true
|
||||
});
|
||||
};
|
||||
var initSourceSelect = function(){
|
||||
$scope.source = _.find($scope.source_type_options, {value: inventorySourceData.source});
|
||||
function initSourceSelect() {
|
||||
$scope.source = _.find($scope.source_type_options, { value: inventorySourceData.source });
|
||||
CreateSelect2({
|
||||
element: '#group_source',
|
||||
multiple: false
|
||||
@ -156,8 +135,8 @@
|
||||
// After the source is set, conditional fields will be visible
|
||||
// CodeMirror is buggy if you instantiate it in a not-visible element
|
||||
// So we initialize it here instead of the init() routine
|
||||
if(inventorySourceData.source === 'ec2' || inventorySourceData.source === 'openstack' ||
|
||||
inventorySourceData.source === 'custom' || inventorySourceData.source === 'vmware'){
|
||||
if (inventorySourceData.source === 'ec2' || inventorySourceData.source === 'openstack' ||
|
||||
inventorySourceData.source === 'custom' || inventorySourceData.source === 'vmware') {
|
||||
$scope[inventorySourceData.source + '_variables'] = inventorySourceData.source_vars === null || inventorySourceData.source_vars === '' ? '---' : ParseVariableString(inventorySourceData.source_vars);
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
@ -166,29 +145,31 @@
|
||||
parse_variable: 'envParseType',
|
||||
});
|
||||
}
|
||||
};
|
||||
var initRegionData = function(){
|
||||
}
|
||||
|
||||
function initRegionData() {
|
||||
var source = $scope.source.value === 'azure_rm' ? 'azure' : $scope.source.value;
|
||||
var regions = inventorySourceData.source_regions.split(',');
|
||||
// azure_rm regions choices are keyed as "azure" in an OPTIONS request to the inventory_sources endpoint
|
||||
$scope.source_region_choices = $scope[source + '_regions'];
|
||||
|
||||
// the API stores azure regions as all-lowercase strings - but the azure regions received from OPTIONS are Snake_Cased
|
||||
if (source === 'azure'){
|
||||
$scope.source_regions = _.map(regions, (region) => _.find($scope[source+'_regions'], (o) => o.value.toLowerCase() === region));
|
||||
if (source === 'azure') {
|
||||
$scope.source_regions = _.map(regions, (region) => _.find($scope[source + '_regions'], (o) => o.value.toLowerCase() === region));
|
||||
}
|
||||
// all other regions are 1-1
|
||||
else{
|
||||
$scope.source_regions = _.map(regions, (region) => _.find($scope[source+'_regions'], (o) => o.value === region));
|
||||
else {
|
||||
$scope.source_regions = _.map(regions, (region) => _.find($scope[source + '_regions'], (o) => o.value === region));
|
||||
}
|
||||
$scope.group_by_choices = source === 'ec2' ? $scope.ec2_group_by : null;
|
||||
if (source ==='ec2'){
|
||||
if (source === 'ec2') {
|
||||
var group_by = inventorySourceData.group_by.split(',');
|
||||
$scope.group_by = _.map(group_by, (item) => _.find($scope.ec2_group_by, {value: item}));
|
||||
$scope.group_by = _.map(group_by, (item) => _.find($scope.ec2_group_by, { value: item }));
|
||||
}
|
||||
initRegionSelect();
|
||||
};
|
||||
var initSources = function(){
|
||||
}
|
||||
|
||||
function initSources() {
|
||||
GetSourceTypeOptions({
|
||||
scope: $scope,
|
||||
variable: 'source_type_options',
|
||||
@ -234,88 +215,17 @@
|
||||
choice_name: 'ec2_group_by_choices',
|
||||
callback: 'choicesReadyGroup'
|
||||
});
|
||||
};
|
||||
}
|
||||
|
||||
// region / source options callback
|
||||
$scope.$on('choicesReadyGroup', function(){
|
||||
if (angular.isObject($scope.source)){
|
||||
$scope.$on('choicesReadyGroup', function() {
|
||||
if (angular.isObject($scope.source)) {
|
||||
initRegionData();
|
||||
}
|
||||
});
|
||||
|
||||
$scope.$on('sourceTypeOptionsReady', function(){
|
||||
$scope.$on('sourceTypeOptionsReady', function() {
|
||||
initSourceSelect();
|
||||
});
|
||||
var init = function(){
|
||||
// instantiate expected $scope values from inventorySourceData & groupData
|
||||
var relatedSets = form.relatedSets(groupData.related);
|
||||
generator.inject(form, {mode: 'edit', related: false, id: 'Inventory-groupManage--panel', scope: $scope});
|
||||
_.assign($scope,
|
||||
{credential: inventorySourceData.credential},
|
||||
{overwrite: inventorySourceData.overwrite},
|
||||
{overwrite_vars: inventorySourceData.overwrite_vars},
|
||||
{update_on_launch: inventorySourceData.update_on_launch},
|
||||
{update_cache_timeout: inventorySourceData.update_cache_timeout},
|
||||
{instance_filters: inventorySourceData.instance_filters},
|
||||
{inventory_script: inventorySourceData.source_script}
|
||||
);
|
||||
if (inventorySourceData.credential){
|
||||
$scope.credential_name = inventorySourceData.summary_fields.credential.name;
|
||||
}
|
||||
$scope = angular.extend($scope, groupData);
|
||||
$scope.group_obj = groupData;
|
||||
|
||||
// instantiate lookup fields
|
||||
if (inventorySourceData.source !== 'custom'){
|
||||
var credentialBasePath = (inventorySourceData.source === 'ec2') ? GetBasePath('credentials') + '?kind=aws' : GetBasePath('credentials') + (inventorySourceData.source === '' ? '' : '?kind=' + (inventorySourceData.source));
|
||||
CredentialList.basePath = credentialBasePath;
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: credentialBasePath,
|
||||
form: form,
|
||||
list: CredentialList,
|
||||
field: 'credential',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
// equal to case 'custom'
|
||||
else{
|
||||
$scope.inventory_script_name = inventorySourceData.summary_fields.source_script.name;
|
||||
LookUpInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_script'),
|
||||
form: form,
|
||||
list: InventoryScriptsList,
|
||||
field: 'inventory_script',
|
||||
input_type: "radio"
|
||||
});
|
||||
}
|
||||
// init codemirror(s)
|
||||
$scope.variables = $scope.variables === null || $scope.variables === '' ? '---' : ParseVariableString($scope.variables);
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.envParseType = 'yaml';
|
||||
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'group_variables',
|
||||
variable: 'variables',
|
||||
});
|
||||
|
||||
NotificationsListInit({
|
||||
scope: $scope,
|
||||
url: GetBasePath('inventory_sources'),
|
||||
id: inventorySourceData.id
|
||||
});
|
||||
RelatedSearchInit({
|
||||
scope: $scope,
|
||||
form: form,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
RelatedPaginateInit({
|
||||
scope: $scope,
|
||||
relatedSets: relatedSets
|
||||
});
|
||||
initSources();
|
||||
_.forEach(relatedSets, (value, key) => $scope.search(relatedSets[key].iterator));
|
||||
};
|
||||
init();
|
||||
}];
|
||||
}
|
||||
];
|
||||
|
||||
@ -1,4 +0,0 @@
|
||||
<div class="tab-pane" id="Inventory-groupManage">
|
||||
<div ng-cloak id="Inventory-groupManage--panel" class="Panel">
|
||||
</div>
|
||||
</div>
|
||||
@ -4,15 +4,18 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
export default
|
||||
['$scope', '$rootScope', '$state', '$stateParams', 'InventoryGroups', 'generateList', 'InventoryUpdate', 'GroupManageService', 'GroupsCancelUpdate', 'ViewUpdateStatus',
|
||||
'InventoryManageService', 'groupsUrl', 'SearchInit', 'PaginateInit', 'GetSyncStatusMsg', 'GetHostsStatusMsg', 'Find', 'Rest', 'GetBasePath', 'rbacUiControlService',
|
||||
function($scope, $rootScope, $state, $stateParams, InventoryGroups, generateList, InventoryUpdate, GroupManageService, GroupsCancelUpdate, ViewUpdateStatus,
|
||||
InventoryManageService, groupsUrl, SearchInit, PaginateInit, GetSyncStatusMsg, GetHostsStatusMsg, Find, Rest, GetBasePath, rbacUiControlService){
|
||||
var list = InventoryGroups,
|
||||
view = generateList,
|
||||
pageSize = 20;
|
||||
['$scope', '$rootScope', '$state', '$stateParams', 'InventoryGroups', 'generateList', 'InventoryUpdate',
|
||||
'GroupManageService', 'GroupsCancelUpdate', 'ViewUpdateStatus', 'rbacUiControlService', 'GetBasePath',
|
||||
'InventoryManageService', 'groupsUrl', 'GetSyncStatusMsg', 'GetHostsStatusMsg', 'groupsDataset',
|
||||
function($scope, $rootScope, $state, $stateParams, InventoryGroups, generateList, InventoryUpdate,
|
||||
GroupManageService, GroupsCancelUpdate, ViewUpdateStatus, rbacUiControlService, GetBasePath,
|
||||
InventoryManageService, groupsUrl, GetSyncStatusMsg, GetHostsStatusMsg, groupsDataset){
|
||||
|
||||
let list = InventoryGroups;
|
||||
|
||||
init();
|
||||
|
||||
function init(){
|
||||
$scope.inventory_id = $stateParams.inventory_id;
|
||||
|
||||
$scope.canAdd = false;
|
||||
@ -22,16 +25,52 @@
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
// Search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = groupsDataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
// The ncy breadcrumb directive will look at this attribute when attempting to bind to the correct scope.
|
||||
// In this case, we don't want to incidentally bind to this scope when editing a host or a group. See:
|
||||
// https://github.com/ncuillery/angular-breadcrumb/issues/42 for a little more information on the
|
||||
// problem that this solves.
|
||||
$scope.ncyBreadcrumbIgnore = true;
|
||||
if($state.current.name === "inventoryManage.editGroup") {
|
||||
$scope.rowBeingEdited = $state.params.group_id;
|
||||
$scope.listBeingEdited = "groups";
|
||||
}
|
||||
|
||||
$scope.inventory_id = $stateParams.inventory_id;
|
||||
_.forEach($scope[list.name], buildStatusIndicators);
|
||||
|
||||
// The ncy breadcrumb directive will look at this attribute when attempting to bind to the correct scope.
|
||||
// In this case, we don't want to incidentally bind to this scope when editing a host or a group. See:
|
||||
// https://github.com/ncuillery/angular-breadcrumb/issues/42 for a little more information on the
|
||||
// problem that this solves.
|
||||
$scope.ncyBreadcrumbIgnore = true;
|
||||
if($state.current.name === "inventoryManage.editGroup") {
|
||||
$scope.rowBeingEdited = $state.params.group_id;
|
||||
$scope.listBeingEdited = "groups";
|
||||
}
|
||||
|
||||
function buildStatusIndicators(group){
|
||||
let group_status, hosts_status;
|
||||
|
||||
group_status = GetSyncStatusMsg({
|
||||
status: group.summary_fields.inventory_source.status,
|
||||
has_inventory_sources: group.has_inventory_sources,
|
||||
source: ( (group.summary_fields.inventory_source) ? group.summary_fields.inventory_source.source : null )
|
||||
});
|
||||
hosts_status = GetHostsStatusMsg({
|
||||
active_failures: group.hosts_with_active_failures,
|
||||
total_hosts: group.total_hosts,
|
||||
inventory_id: $scope.inventory_id,
|
||||
group_id: group.id
|
||||
});
|
||||
_.assign(group,
|
||||
{status_class: group_status.class},
|
||||
{status_tooltip: group_status.tooltip},
|
||||
{launch_tooltip: group_status.launch_tip},
|
||||
{launch_class: group_status.launch_class},
|
||||
{group_schedule_tooltip: group_status.schedule_tip},
|
||||
{hosts_status_tip: hosts_status.tooltip},
|
||||
{hosts_status_class: hosts_status.class},
|
||||
{source: group.summary_fields.inventory_source ? group.summary_fields.inventory_source.source : null},
|
||||
{status: group.summary_fields.inventory_source ? group.summary_fields.inventory_source.status : null});
|
||||
}
|
||||
|
||||
$scope.groupSelect = function(id){
|
||||
var group = $stateParams.group === undefined ? [id] : _($stateParams.group).concat(id).value();
|
||||
$state.go('inventoryManage', {inventory_id: $stateParams.inventory_id, group: group}, {reload: true});
|
||||
@ -137,39 +176,14 @@
|
||||
// added to the breadcrumb trail
|
||||
var groupsArr = $stateParams.group ? $stateParams.group : [];
|
||||
groupsArr.push(id);
|
||||
$state.go('inventoryManage.schedules', {id: id, group: groupsArr}, {reload: true});
|
||||
$state.go('inventoryManage.editGroup.schedules', {group_id: id, group: groupsArr}, {reload: true});
|
||||
};
|
||||
// $scope.$parent governed by InventoryManageController, for unified multiSelect options
|
||||
$scope.$on('multiSelectList.selectionChanged', (event, selection) => {
|
||||
$scope.$parent.groupsSelected = selection.length > 0 ? true : false;
|
||||
$scope.$parent.groupsSelectedItems = selection.selectedItems;
|
||||
});
|
||||
$scope.$on('PostRefresh', () => {
|
||||
$scope.groups.forEach( (group, index) => {
|
||||
var group_status, hosts_status;
|
||||
group_status = GetSyncStatusMsg({
|
||||
status: group.summary_fields.inventory_source.status,
|
||||
has_inventory_sources: group.has_inventory_sources,
|
||||
source: ( (group.summary_fields.inventory_source) ? group.summary_fields.inventory_source.source : null )
|
||||
});
|
||||
hosts_status = GetHostsStatusMsg({
|
||||
active_failures: group.hosts_with_active_failures,
|
||||
total_hosts: group.total_hosts,
|
||||
inventory_id: $scope.inventory_id,
|
||||
group_id: group.id
|
||||
});
|
||||
_.assign($scope.groups[index],
|
||||
{status_class: group_status.class},
|
||||
{status_tooltip: group_status.tooltip},
|
||||
{launch_tooltip: group_status.launch_tip},
|
||||
{launch_class: group_status.launch_class},
|
||||
{group_schedule_tooltip: group_status.schedule_tip},
|
||||
{hosts_status_tip: hosts_status.tooltip},
|
||||
{hosts_status_class: hosts_status.class},
|
||||
{source: group.summary_fields.inventory_source ? group.summary_fields.inventory_source.source : null},
|
||||
{status: group.summary_fields.inventory_source ? group.summary_fields.inventory_source.status : null});
|
||||
});
|
||||
});
|
||||
|
||||
$scope.copyMoveGroup = function(id){
|
||||
$state.go('inventoryManage.copyMoveGroup', {group_id: id, groups: $stateParams.groups});
|
||||
};
|
||||
@ -190,26 +204,4 @@
|
||||
cleanUpStateChangeListener();
|
||||
});
|
||||
|
||||
var init = function(){
|
||||
list.basePath = groupsUrl;
|
||||
view.inject(list,{
|
||||
id: 'groups-list',
|
||||
$scope: $scope,
|
||||
mode: 'edit'
|
||||
});
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: groupsUrl,
|
||||
set: 'groups'
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: groupsUrl,
|
||||
pageSize: pageSize
|
||||
});
|
||||
$scope.search(list.iterator);
|
||||
};
|
||||
init();
|
||||
}];
|
||||
|
||||
@ -1,4 +1,3 @@
|
||||
<div id="groups-list" class="Panel"></div>
|
||||
<div class="modal fade GroupDelete" id="group-delete-modal" role="dialog">
|
||||
<div class="modal-dialog">
|
||||
<div class="modal-content Modal-content">
|
||||
|
||||
@ -1,61 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
import {templateUrl} from '../../../shared/template-url/template-url.factory';
|
||||
import addController from './groups-add.controller';
|
||||
import editController from './groups-edit.controller';
|
||||
|
||||
var ManageGroupsEdit = {
|
||||
name: 'inventoryManage.editGroup',
|
||||
route: '/edit-group?group_id',
|
||||
ncyBreadcrumb: {
|
||||
label: "{{name}}"
|
||||
},
|
||||
data: {
|
||||
mode: 'edit'
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
resolve: {
|
||||
groupData: ['$stateParams', 'GroupManageService', function($stateParams, GroupManageService){
|
||||
return GroupManageService.get({id: $stateParams.group_id}).then(res => res.data.results[0]);
|
||||
}],
|
||||
inventorySourceData: ['$stateParams', 'GroupManageService', function($stateParams, GroupManageService){
|
||||
return GroupManageService.getInventorySource({group: $stateParams.group_id}).then(res => res.data.results[0]);
|
||||
}]
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage': {
|
||||
controller: editController,
|
||||
templateUrl: templateUrl('inventories/manage/groups/groups-form'),
|
||||
}
|
||||
}
|
||||
};
|
||||
var ManageGroupsAdd = {
|
||||
name: 'inventoryManage.addGroup',
|
||||
route: '/add-group',
|
||||
// use a query string to break regex search
|
||||
ncyBreadcrumb: {
|
||||
label: "CREATE GROUP"
|
||||
},
|
||||
data: {
|
||||
mode: 'add'
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage': {
|
||||
controller: addController,
|
||||
templateUrl: templateUrl('inventories/manage/groups/groups-form'),
|
||||
}
|
||||
}
|
||||
};
|
||||
export {ManageGroupsAdd, ManageGroupsEdit};
|
||||
@ -4,11 +4,10 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {ManageGroupsAdd, ManageGroupsEdit} from './groups.route';
|
||||
import GroupAddController from './groups-add.controller';
|
||||
import GroupEditController from './groups-edit.controller';
|
||||
|
||||
export default
|
||||
angular.module('manageGroups', [])
|
||||
.run(['$stateExtender', function($stateExtender){
|
||||
$stateExtender.addState(ManageGroupsAdd);
|
||||
$stateExtender.addState(ManageGroupsEdit);
|
||||
}]);
|
||||
angular.module('manageGroups', [])
|
||||
.controller('GroupAddController', GroupAddController)
|
||||
.controller('GroupEditController', GroupEditController);
|
||||
|
||||
@ -4,27 +4,39 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$state', '$stateParams', '$scope', 'HostForm', 'ParseTypeChange', 'GenerateForm', 'HostManageService', 'rbacUiControlService', 'GetBasePath',
|
||||
function($state, $stateParams, $scope, HostForm, ParseTypeChange, GenerateForm, HostManageService, rbacUiControlService, GetBasePath){
|
||||
var generator = GenerateForm,
|
||||
form = HostForm;
|
||||
export default ['$state', '$stateParams', '$scope', 'HostForm', 'ParseTypeChange',
|
||||
'GenerateForm', 'HostManageService', 'rbacUiControlService', 'GetBasePath',
|
||||
function($state, $stateParams, $scope, HostForm, ParseTypeChange,
|
||||
GenerateForm, HostManageService, rbacUiControlService, GetBasePath) {
|
||||
|
||||
$scope.canAdd = false;
|
||||
init();
|
||||
|
||||
rbacUiControlService.canAdd(GetBasePath('inventory') + $stateParams.inventory_id + "/hosts")
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
function init() {
|
||||
$scope.canAdd = false;
|
||||
|
||||
rbacUiControlService.canAdd(GetBasePath('inventory') + $stateParams.inventory_id + "/hosts")
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.host = { enabled: true };
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(HostForm, $scope);
|
||||
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'host_variables',
|
||||
variable: 'variables',
|
||||
parse_variable: 'parseType'
|
||||
});
|
||||
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.formCancel = function(){
|
||||
}
|
||||
$scope.formCancel = function() {
|
||||
$state.go('^');
|
||||
};
|
||||
$scope.toggleHostEnabled = function(){
|
||||
$scope.toggleHostEnabled = function() {
|
||||
$scope.host.enabled = !$scope.host.enabled;
|
||||
};
|
||||
$scope.formSave = function(){
|
||||
$scope.formSave = function() {
|
||||
var params = {
|
||||
variables: $scope.variables === '---' || $scope.variables === '{}' ? null : $scope.variables,
|
||||
name: $scope.name,
|
||||
@ -32,25 +44,16 @@
|
||||
enabled: $scope.host.enabled,
|
||||
inventory: $stateParams.inventory_id
|
||||
};
|
||||
HostManageService.post(params).then(function(res){
|
||||
HostManageService.post(params).then(function(res) {
|
||||
// assign the host to current group if not at the root level
|
||||
if ($stateParams.group){
|
||||
HostManageService.associateGroup(res.data, _.last($stateParams.group)).then(function(){
|
||||
$state.go('inventoryManage.editHost', {host_id: res.data.id}, {reload: true});
|
||||
if ($stateParams.group) {
|
||||
HostManageService.associateGroup(res.data, _.last($stateParams.group)).then(function() {
|
||||
$state.go('inventoryManage.editHost', { host_id: res.data.id }, { reload: true });
|
||||
});
|
||||
}
|
||||
else{
|
||||
$state.go('inventoryManage.editHost', {host_id: res.data.id}, {reload: true});
|
||||
} else {
|
||||
$state.go('inventoryManage.editHost', { host_id: res.data.id }, { reload: true });
|
||||
}
|
||||
});
|
||||
};
|
||||
var init = function(){
|
||||
$scope.host = {enabled: true};
|
||||
generator.inject(form, {mode: 'add', related: false, id: 'Inventory-hostManage--panel', scope: $scope});
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'host_variables',
|
||||
});
|
||||
};
|
||||
init();
|
||||
}];
|
||||
}
|
||||
];
|
||||
|
||||
@ -5,18 +5,28 @@
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
['$state', '$stateParams', '$scope', 'HostForm', 'ParseTypeChange', 'GenerateForm', 'HostManageService', 'host',
|
||||
function($state, $stateParams, $scope, HostForm, ParseTypeChange, GenerateForm, HostManageService, host){
|
||||
var generator = GenerateForm,
|
||||
form = HostForm;
|
||||
['$state', '$stateParams', '$scope', 'HostForm', 'ParseTypeChange', 'HostManageService', 'host',
|
||||
function($state, $stateParams, $scope, HostForm, ParseTypeChange, HostManageService, host){
|
||||
|
||||
$scope.$watch('host.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
init();
|
||||
|
||||
$scope.parseType = 'yaml';
|
||||
function init(){
|
||||
$scope.$watch('host.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
$scope.canAdd = false;
|
||||
}
|
||||
});
|
||||
|
||||
$scope.parseType = 'yaml';
|
||||
$scope.host = host;
|
||||
$scope.variables = host.variables === '' ? '---' : host.variables;
|
||||
$scope.name = host.name;
|
||||
$scope.description = host.description;
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'host_variables',
|
||||
});
|
||||
}
|
||||
$scope.formCancel = function(){
|
||||
$state.go('^');
|
||||
};
|
||||
@ -35,16 +45,4 @@
|
||||
$state.go($state.current, null, {reload: true});
|
||||
});
|
||||
};
|
||||
var init = function(){
|
||||
$scope.host = host;
|
||||
generator.inject(form, {mode: 'edit', related: false, id: 'Inventory-hostManage--panel', scope: $scope});
|
||||
$scope.variables = host.variables === '' ? '---' : host.variables;
|
||||
$scope.name = host.name;
|
||||
$scope.description = host.description;
|
||||
ParseTypeChange({
|
||||
scope: $scope,
|
||||
field_id: 'host_variables',
|
||||
});
|
||||
};
|
||||
init();
|
||||
}];
|
||||
|
||||
@ -1,4 +0,0 @@
|
||||
<div class="tab-pane" id="Inventory-hostManage">
|
||||
<div ng-cloak id="Inventory-hostManage--panel" class="Panel">
|
||||
</div>
|
||||
</div>
|
||||
@ -5,32 +5,38 @@
|
||||
*************************************************/
|
||||
export default
|
||||
['$scope', '$rootScope', '$state', '$stateParams', 'InventoryHosts', 'generateList', 'InventoryManageService', 'HostManageService',
|
||||
'hostsUrl', 'SearchInit', 'PaginateInit', 'SetStatus', 'Prompt', 'Wait', 'inventoryData', '$filter', 'Rest', 'GetBasePath', 'rbacUiControlService',
|
||||
'hostsUrl', 'SetStatus', 'Prompt', 'Wait', 'inventoryData', '$filter', 'hostsDataset', 'GetBasePath', 'rbacUiControlService',
|
||||
function($scope, $rootScope, $state, $stateParams, InventoryHosts, generateList, InventoryManageService, HostManageService,
|
||||
hostsUrl, SearchInit, PaginateInit, SetStatus, Prompt, Wait, inventoryData, $filter, Rest, GetBasePath, rbacUiControlService){
|
||||
hostsUrl, SetStatus, Prompt, Wait, inventoryData, $filter, hostsDataset, GetBasePath, rbacUiControlService){
|
||||
var list = InventoryHosts;
|
||||
|
||||
var list = InventoryHosts,
|
||||
view = generateList,
|
||||
pageSize = 20;
|
||||
init();
|
||||
function init(){
|
||||
$scope.inventory_id = $stateParams.inventory_id;
|
||||
|
||||
$scope.inventory_id = $stateParams.inventory_id;
|
||||
$scope.canAdd = false;
|
||||
|
||||
$scope.canAdd = false;
|
||||
rbacUiControlService.canAdd(GetBasePath('inventory') + $scope.inventory_id + "/hosts")
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
|
||||
rbacUiControlService.canAdd(GetBasePath('inventory') + $scope.inventory_id + "/hosts")
|
||||
.then(function(canAdd) {
|
||||
$scope.canAdd = canAdd;
|
||||
});
|
||||
// Search init
|
||||
$scope.list = list;
|
||||
$scope[`${list.iterator}_dataset`] = hostsDataset.data;
|
||||
$scope[list.name] = $scope[`${list.iterator}_dataset`].results;
|
||||
|
||||
// The ncy breadcrumb directive will look at this attribute when attempting to bind to the correct scope.
|
||||
// In this case, we don't want to incidentally bind to this scope when editing a host or a group. See:
|
||||
// https://github.com/ncuillery/angular-breadcrumb/issues/42 for a little more information on the
|
||||
// problem that this solves.
|
||||
$scope.ncyBreadcrumbIgnore = true;
|
||||
if($state.current.name === "inventoryManage.editHost") {
|
||||
$scope.rowBeingEdited = $state.params.host_id;
|
||||
$scope.listBeingEdited = "hosts";
|
||||
// The ncy breadcrumb directive will look at this attribute when attempting to bind to the correct scope.
|
||||
// In this case, we don't want to incidentally bind to this scope when editing a host or a group. See:
|
||||
// https://github.com/ncuillery/angular-breadcrumb/issues/42 for a little more information on the
|
||||
// problem that this solves.
|
||||
$scope.ncyBreadcrumbIgnore = true;
|
||||
if($state.current.name === "inventoryManage.editHost") {
|
||||
$scope.rowBeingEdited = $state.params.host_id;
|
||||
$scope.listBeingEdited = "hosts";
|
||||
}
|
||||
}
|
||||
|
||||
$scope.createHost = function(){
|
||||
$state.go('inventoryManage.addHost');
|
||||
};
|
||||
@ -80,9 +86,6 @@
|
||||
$scope.$parent.systemTrackingDisabled = selection.length > 0 && selection.length < 3 ? false : true;
|
||||
$scope.$parent.systemTrackingTooltip = selection.length > 0 && selection.length < 3 ? "Compare host facts over time" : "Select one or two hosts by clicking the checkbox beside the host. System tracking offers the ability to compare the results of two scan runs from different dates on one host or the same date on two hosts.";
|
||||
});
|
||||
$scope.$on('PostRefresh', ()=>{
|
||||
_.forEach($scope.hosts, (host) => SetStatus({scope: $scope, host: host}));
|
||||
});
|
||||
var cleanUpStateChangeListener = $rootScope.$on('$stateChangeSuccess', function(event, toState, toParams) {
|
||||
if (toState.name === "inventoryManage.editHost") {
|
||||
$scope.rowBeingEdited = toParams.host_id;
|
||||
@ -97,26 +100,4 @@
|
||||
$scope.$on('$destroy', function() {
|
||||
cleanUpStateChangeListener();
|
||||
});
|
||||
var init = function(){
|
||||
list.basePath = hostsUrl;
|
||||
view.inject(list,{
|
||||
id: 'hosts-list',
|
||||
scope: $scope,
|
||||
mode: 'edit'
|
||||
});
|
||||
SearchInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: hostsUrl,
|
||||
set: 'hosts'
|
||||
});
|
||||
PaginateInit({
|
||||
scope: $scope,
|
||||
list: list,
|
||||
url: hostsUrl,
|
||||
pageSize: pageSize
|
||||
});
|
||||
$scope.search(list.iterator);
|
||||
};
|
||||
init();
|
||||
}];
|
||||
|
||||
@ -1,60 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2016 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
import {templateUrl} from '../../../shared/template-url/template-url.factory';
|
||||
import addController from './hosts-add.controller';
|
||||
import editController from './hosts-edit.controller';
|
||||
|
||||
var ManageHostsEdit = {
|
||||
name: 'inventoryManage.editHost',
|
||||
route: '/edit-host?host_id',
|
||||
ncyBreadcrumb: {
|
||||
label: "{{host.name}}",
|
||||
},
|
||||
data: {
|
||||
mode: 'edit'
|
||||
},
|
||||
resolve: {
|
||||
host: ['$stateParams', 'HostManageService', function($stateParams, HostManageService){
|
||||
return HostManageService.get({id: $stateParams.host_id}).then(function(res){
|
||||
return res.data.results[0];
|
||||
});
|
||||
}]
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage': {
|
||||
controller: editController,
|
||||
templateUrl: templateUrl('inventories/manage/hosts/hosts-form'),
|
||||
}
|
||||
}
|
||||
};
|
||||
var ManageHostsAdd = {
|
||||
name: 'inventoryManage.addHost',
|
||||
route: '/add-host',
|
||||
// use a query string to break regex search
|
||||
ncyBreadcrumb: {
|
||||
label: "CREATE HOST"
|
||||
},
|
||||
data: {
|
||||
mode: 'add'
|
||||
},
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
},
|
||||
views: {
|
||||
'form@inventoryManage': {
|
||||
controller: addController,
|
||||
templateUrl: templateUrl('inventories/manage/hosts/hosts-form'),
|
||||
}
|
||||
}
|
||||
};
|
||||
export {ManageHostsAdd, ManageHostsEdit};
|
||||
@ -4,11 +4,56 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {ManageHostsAdd, ManageHostsEdit} from './hosts.route';
|
||||
import HostsAddController from './hosts-add.controller';
|
||||
import HostsEditController from './hosts-edit.controller';
|
||||
|
||||
export default
|
||||
angular.module('manageHosts', [])
|
||||
.run(['$stateExtender', function($stateExtender){
|
||||
$stateExtender.addState(ManageHostsAdd);
|
||||
$stateExtender.addState(ManageHostsEdit);
|
||||
}]);
|
||||
angular.module('manageHosts', [])
|
||||
.controller('HostsAddController', HostsAddController)
|
||||
.controller('HostEditController', HostsEditController)
|
||||
.config(['$stateProvider', 'stateDefinitionsProvider',
|
||||
function($stateProvider, stateDefinitionsProvider) {
|
||||
let addHost, editHost,
|
||||
stateDefinitions = stateDefinitionsProvider.$get();
|
||||
addHost = {
|
||||
name: 'inventoryManage.addHost',
|
||||
url: '/add-host',
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
url: '/add-host',
|
||||
name: 'inventoryManage.addHost',
|
||||
modes: ['add'],
|
||||
form: 'HostForm',
|
||||
controllers: {
|
||||
add: 'HostsAddController'
|
||||
}
|
||||
})
|
||||
};
|
||||
|
||||
editHost = {
|
||||
name: 'inventoryManage.editHost',
|
||||
url: '/edit-host/:host_id',
|
||||
ncyBreadcrumb: {
|
||||
label: '{{host.name}}',
|
||||
},
|
||||
lazyLoad: () => stateDefinitions.generateTree({
|
||||
url: '/edit-host/:host_id',
|
||||
name: 'inventoryManage.editHost',
|
||||
modes: ['edit'],
|
||||
form: 'HostForm',
|
||||
controllers: {
|
||||
edit: 'HostEditController'
|
||||
},
|
||||
resolve: {
|
||||
host: ['$stateParams', 'HostManageService', function($stateParams, HostManageService) {
|
||||
return HostManageService.get({ id: $stateParams.host_id }).then(function(res) {
|
||||
return res.data.results[0];
|
||||
});
|
||||
}]
|
||||
}
|
||||
})
|
||||
};
|
||||
|
||||
$stateProvider.state(addHost);
|
||||
$stateProvider.state(editHost);
|
||||
}
|
||||
]);
|
||||
|
||||
@ -1,10 +1,7 @@
|
||||
<div class="tab-pane InventoryManage-container" id="inventory_edit">
|
||||
<div ui-view="form"></div>
|
||||
<div ng-cloak id="htmlTemplate">
|
||||
<div class="row">
|
||||
<div ui-view="groupsList" class="col-lg-6"></div>
|
||||
<div ui-view="hostsList" class="col-lg-6"></div>
|
||||
</div>
|
||||
<div ng-include="'/static/partials/logviewer.html'"></div>
|
||||
<div class="row">
|
||||
<div ui-view="groupsList" class="col-lg-6"></div>
|
||||
<div ui-view="hostsList" class="col-lg-6"></div>
|
||||
</div>
|
||||
<div ng-include="'/static/partials/logviewer.html'"></div>
|
||||
</div>
|
||||
|
||||
@ -4,7 +4,7 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
import { templateUrl } from '../../shared/template-url/template-url.factory';
|
||||
import InventoriesManage from './inventory-manage.controller';
|
||||
import BreadcrumbsController from './breadcrumbs/breadcrumbs.controller';
|
||||
import HostsListController from './hosts/hosts-list.controller';
|
||||
@ -12,18 +12,33 @@ import GroupsListController from './groups/groups-list.controller';
|
||||
|
||||
export default {
|
||||
name: 'inventoryManage',
|
||||
url: '/inventories/:inventory_id/manage?{group:int}{failed}',
|
||||
socket: {
|
||||
"groups":{
|
||||
"jobs": ["status_changed"]
|
||||
data: {
|
||||
socket: {
|
||||
"groups": {
|
||||
"jobs": ["status_changed"]
|
||||
}
|
||||
}
|
||||
},
|
||||
params:{
|
||||
group:{
|
||||
// instead of a single 'searchPrefix' attribute, provide hard-coded search params
|
||||
url: '/inventories/:inventory_id/manage?{group:int}{group_search:queryset}{host_search:queryset}',
|
||||
params: {
|
||||
group: {
|
||||
array: true
|
||||
},
|
||||
failed:{
|
||||
value: 'false',
|
||||
group_search: {
|
||||
value: {
|
||||
page_size: '20',
|
||||
page: '1',
|
||||
order_by: 'name',
|
||||
},
|
||||
squash: true
|
||||
},
|
||||
host_search: {
|
||||
value: {
|
||||
page_size: '20',
|
||||
page: '1',
|
||||
order_by: 'name',
|
||||
},
|
||||
squash: true
|
||||
}
|
||||
},
|
||||
@ -31,45 +46,78 @@ export default {
|
||||
skip: true // Never display this state in ncy-breadcrumb.
|
||||
},
|
||||
// enforce uniqueness in group param
|
||||
onEnter: function($stateParams){
|
||||
onEnter: function($stateParams) {
|
||||
$stateParams.group = _.uniq($stateParams.group);
|
||||
},
|
||||
resolve: {
|
||||
groupsUrl: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams){
|
||||
return !$stateParams.group ?
|
||||
InventoryManageService.rootGroupsUrl($stateParams.inventory_id) :
|
||||
InventoryManageService.childGroupsUrl(_.last($stateParams.group));
|
||||
groupsUrl: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams) {
|
||||
return $stateParams.group && $stateParams.group.length > 0 ?
|
||||
// nested context - provide this node's children
|
||||
InventoryManageService.childGroupsUrl(_.last($stateParams.group)) :
|
||||
// root context - provide root nodes
|
||||
InventoryManageService.rootGroupsUrl($stateParams.inventory_id);
|
||||
}],
|
||||
hostsUrl: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams){
|
||||
// at the root group level
|
||||
return !$stateParams.group ?
|
||||
InventoryManageService.rootHostsUrl($stateParams.inventory_id, $stateParams.failed) :
|
||||
InventoryManageService.childHostsUrl(_.last($stateParams.group, $stateParams.failed));
|
||||
hostsUrl: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams) {
|
||||
return $stateParams.group && $stateParams.group.length > 0 ?
|
||||
// nested context - provide all hosts managed by nodes
|
||||
InventoryManageService.childHostsUrl(_.last($stateParams.group)) :
|
||||
// root context - provide all hosts in an inventory
|
||||
InventoryManageService.rootHostsUrl($stateParams.inventory_id);
|
||||
}],
|
||||
inventoryData: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams){
|
||||
inventoryData: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams) {
|
||||
return InventoryManageService.getInventory($stateParams.inventory_id).then(res => res.data);
|
||||
}],
|
||||
breadCrumbData: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams){
|
||||
return ( (!$stateParams.group) ? false : InventoryManageService.getBreadcrumbs($stateParams.group).then(res => res.data.results));
|
||||
breadCrumbData: ['InventoryManageService', '$stateParams', function(InventoryManageService, $stateParams) {
|
||||
return $stateParams.group && $stateParams.group.length > 0 ?
|
||||
// nested context - provide breadcrumb data
|
||||
InventoryManageService.getBreadcrumbs($stateParams.group).then(res => res.data.results) :
|
||||
// root context
|
||||
false;
|
||||
}],
|
||||
groupsDataset: ['InventoryGroups', 'QuerySet', '$stateParams', 'groupsUrl', (list, qs, $stateParams, groupsUrl) => {
|
||||
let path = groupsUrl;
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}],
|
||||
hostsDataset: ['InventoryHosts', 'QuerySet', '$stateParams', 'hostsUrl', (list, qs, $stateParams, hostsUrl) => {
|
||||
let path = hostsUrl;
|
||||
return qs.search(path, $stateParams[`${list.iterator}_search`]);
|
||||
}]
|
||||
},
|
||||
views:{
|
||||
// target the ui-view with name "groupBreadcrumbs" at the root template level
|
||||
views: {
|
||||
// target the ui-view with name "groupBreadcrumbs" at the root view
|
||||
'groupBreadcrumbs@': {
|
||||
controller: BreadcrumbsController,
|
||||
templateUrl: templateUrl('inventories/manage/breadcrumbs/breadcrumbs')
|
||||
},
|
||||
'': {
|
||||
// target the ui-view with name "list" at the root view
|
||||
'list@': {
|
||||
templateUrl: templateUrl('inventories/manage/inventory-manage'),
|
||||
controller: InventoriesManage
|
||||
},
|
||||
// target ui-views with name@inventoryManage template level
|
||||
// target ui-views with name@inventoryManage state
|
||||
'groupsList@inventoryManage': {
|
||||
templateUrl: templateUrl('inventories/manage/groups/groups-list'),
|
||||
templateProvider: function(InventoryGroups, generateList, $templateRequest) {
|
||||
let html = generateList.build({
|
||||
list: InventoryGroups,
|
||||
mode: 'edit'
|
||||
});
|
||||
html = generateList.wrapPanel(html);
|
||||
// I'm so sorry
|
||||
// group delete modal
|
||||
return $templateRequest(templateUrl('inventories/manage/groups/groups-list')).then((template) => {
|
||||
return html.concat(template);
|
||||
});
|
||||
},
|
||||
controller: GroupsListController
|
||||
},
|
||||
'hostsList@inventoryManage': {
|
||||
template: '<div id="hosts-list" class="Panel"></div>',
|
||||
templateProvider: function(InventoryHosts, generateList) {
|
||||
let html = generateList.build({
|
||||
list: InventoryHosts,
|
||||
mode: 'edit'
|
||||
});
|
||||
return generateList.wrapPanel(html);
|
||||
},
|
||||
controller: HostsListController
|
||||
}
|
||||
}
|
||||
|
||||
@ -40,24 +40,20 @@
|
||||
.error(this.error.bind(this))
|
||||
.finally(Wait('stop'));
|
||||
},
|
||||
// these methods generate a query string to pass to PaginateInit(), SearchInit()
|
||||
// always supply trailing slashes and ? prefix
|
||||
rootHostsUrl: function(id, failed){
|
||||
var url = GetBasePath('inventory') + id + '/hosts' +
|
||||
(failed === 'true' ? '?has_active_failures=true' : '?');
|
||||
rootHostsUrl: function(id){
|
||||
var url = GetBasePath('inventory') + id + '/hosts';
|
||||
return url;
|
||||
},
|
||||
childHostsUrl: function(id, failed){
|
||||
var url = GetBasePath('groups') + id + '/all_hosts' +
|
||||
(failed === 'true' ? '?has_active_failures=true' : '?');
|
||||
childHostsUrl: function(id){
|
||||
var url = GetBasePath('groups') + id + '/all_hosts';
|
||||
return url;
|
||||
},
|
||||
childGroupsUrl: function(id){
|
||||
var url = GetBasePath('groups') + id + '/children?';
|
||||
var url = GetBasePath('groups') + id + '/children';
|
||||
return url;
|
||||
},
|
||||
rootGroupsUrl: function(id){
|
||||
var url = GetBasePath('inventory') + id+ '/root_groups/';
|
||||
var url = GetBasePath('inventory') + id+ '/root_groups';
|
||||
return url;
|
||||
}
|
||||
};
|
||||
|
||||
@ -4,7 +4,6 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import route from './inventory-manage.route';
|
||||
import InventoryManageService from './inventory-manage.service';
|
||||
import HostManageService from './hosts/hosts.service';
|
||||
import GroupManageService from './groups/groups.service';
|
||||
@ -20,9 +19,6 @@ angular.module('inventoryManage', [
|
||||
copyMove.name,
|
||||
adhoc.name
|
||||
])
|
||||
.service('InventoryManageService', InventoryManageService)
|
||||
.service('InventoryManageService', InventoryManageService)
|
||||
.service('HostManageService', HostManageService)
|
||||
.service('GroupManageService', GroupManageService)
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}]);
|
||||
.service('GroupManageService', GroupManageService);
|
||||
|
||||
@ -4,18 +4,20 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
[ '$rootScope', 'pagination', '$compile','SchedulerInit', 'Rest', 'Wait',
|
||||
'inventoryScriptsFormObject', 'ProcessErrors', 'GetBasePath', 'Empty',
|
||||
'GenerateForm', 'SearchInit' , 'PaginateInit',
|
||||
'LookUpInit', 'OrganizationList', '$scope', '$state', 'Alert',
|
||||
function(
|
||||
$rootScope, pagination, $compile, SchedulerInit, Rest, Wait,
|
||||
inventoryScriptsFormObject, ProcessErrors, GetBasePath, Empty,
|
||||
GenerateForm, SearchInit, PaginateInit,
|
||||
LookUpInit, OrganizationList, $scope, $state, Alert
|
||||
) {
|
||||
Rest.setUrl(GetBasePath('inventory_scripts'));
|
||||
export default ['$rootScope', 'Rest', 'Wait',
|
||||
'InventoryScriptsForm', 'ProcessErrors', 'GetBasePath', 'Empty',
|
||||
'GenerateForm', '$scope', '$state', 'Alert',
|
||||
function($rootScope, Rest, Wait,
|
||||
InventoryScriptsForm, ProcessErrors, GetBasePath, Empty,
|
||||
GenerateForm, $scope, $state, Alert
|
||||
) {
|
||||
var form = InventoryScriptsForm,
|
||||
url = GetBasePath('inventory_scripts');
|
||||
|
||||
init();
|
||||
|
||||
function init() {
|
||||
Rest.setUrl(url);
|
||||
Rest.options()
|
||||
.success(function(data) {
|
||||
if (!data.actions.POST) {
|
||||
@ -24,51 +26,37 @@ export default
|
||||
}
|
||||
});
|
||||
|
||||
var scope = $scope,
|
||||
generator = GenerateForm,
|
||||
form = inventoryScriptsFormObject,
|
||||
url = GetBasePath('inventory_scripts');
|
||||
// apply form definition's default field values
|
||||
GenerateForm.applyDefaults(form, $scope);
|
||||
|
||||
generator.inject(form, {
|
||||
mode: 'add' ,
|
||||
scope:scope,
|
||||
related: false
|
||||
});
|
||||
generator.reset();
|
||||
// @issue @jmitchell - this setting probably collides with new RBAC can* implementation?
|
||||
$scope.canEdit = true;
|
||||
}
|
||||
|
||||
LookUpInit({
|
||||
url: GetBasePath('organization'),
|
||||
scope: scope,
|
||||
form: form,
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
|
||||
// Save
|
||||
scope.formSave = function () {
|
||||
generator.clearApiErrors();
|
||||
Wait('start');
|
||||
Rest.setUrl(url);
|
||||
Rest.post({
|
||||
name: scope.name,
|
||||
description: scope.description,
|
||||
organization: scope.organization,
|
||||
script: scope.script
|
||||
// Save
|
||||
$scope.formSave = function() {
|
||||
Wait('start');
|
||||
Rest.setUrl(url);
|
||||
Rest.post({
|
||||
name: $scope.name,
|
||||
description: $scope.description,
|
||||
organization: $scope.organization,
|
||||
script: $scope.script
|
||||
})
|
||||
.success(function (data) {
|
||||
$state.go('inventoryScripts.edit', {inventory_script_id: data.id}, {reload: true});
|
||||
.success(function(data) {
|
||||
$state.go('inventoryScripts.edit', { inventory_script_id: data.id }, { reload: true });
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors(scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory script. POST returned status: ' + status });
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory script. POST returned status: ' + status
|
||||
});
|
||||
});
|
||||
};
|
||||
};
|
||||
|
||||
scope.formCancel = function () {
|
||||
$state.transitionTo('inventoryScripts');
|
||||
};
|
||||
|
||||
}
|
||||
];
|
||||
$scope.formCancel = function() {
|
||||
$state.go('^');
|
||||
};
|
||||
}
|
||||
];
|
||||
|
||||
@ -1,3 +0,0 @@
|
||||
<div class="tab-pane" id="inventory_scripts_add">
|
||||
<div ng-cloak id="htmlTemplate" class="Panel"></div>
|
||||
</div>
|
||||
@ -1,18 +0,0 @@
|
||||
/*************************************************
|
||||
* Copyright (c) 2015 Ansible, Inc.
|
||||
*
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import {templateUrl} from '../../shared/template-url/template-url.factory';
|
||||
|
||||
export default {
|
||||
name: 'inventoryScripts.add',
|
||||
route: '/add',
|
||||
templateUrl: templateUrl('inventory-scripts/add/add'),
|
||||
controller: 'inventoryScriptsAddController',
|
||||
ncyBreadcrumb: {
|
||||
parent: 'inventoryScripts',
|
||||
label: 'CREATE INVENTORY SCRIPT'
|
||||
}
|
||||
};
|
||||
@ -4,12 +4,8 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
import route from './add.route';
|
||||
import controller from './add.controller';
|
||||
|
||||
export default
|
||||
angular.module('inventoryScriptsAdd', [])
|
||||
.controller('inventoryScriptsAddController', controller)
|
||||
.run(['$stateExtender', function($stateExtender) {
|
||||
$stateExtender.addState(route);
|
||||
}]);
|
||||
.controller('InventoryScriptsAddController', controller);
|
||||
|
||||
@ -4,27 +4,26 @@
|
||||
* All Rights Reserved
|
||||
*************************************************/
|
||||
|
||||
export default
|
||||
[ 'Rest', 'Wait',
|
||||
'inventoryScriptsFormObject', 'ProcessErrors', 'GetBasePath',
|
||||
'GenerateForm', 'SearchInit' , 'PaginateInit',
|
||||
'LookUpInit', 'OrganizationList', 'inventory_script',
|
||||
'$scope', '$state',
|
||||
function(
|
||||
Rest, Wait,
|
||||
inventoryScriptsFormObject, ProcessErrors, GetBasePath,
|
||||
GenerateForm, SearchInit, PaginateInit,
|
||||
LookUpInit, OrganizationList, inventory_script,
|
||||
$scope, $state
|
||||
) {
|
||||
export default ['Rest', 'Wait',
|
||||
'InventoryScriptsForm', 'ProcessErrors', 'GetBasePath',
|
||||
'GenerateForm', 'OrganizationList', 'inventory_scriptData',
|
||||
'$scope', '$state',
|
||||
function(
|
||||
Rest, Wait, InventoryScriptsForm, ProcessErrors, GetBasePath,
|
||||
GenerateForm, OrganizationList, inventory_scriptData,
|
||||
$scope, $state
|
||||
) {
|
||||
var generator = GenerateForm,
|
||||
data = inventory_scriptData,
|
||||
id = inventory_scriptData.id,
|
||||
form = InventoryScriptsForm,
|
||||
master = {},
|
||||
url = GetBasePath('inventory_scripts');
|
||||
|
||||
var generator = GenerateForm,
|
||||
id = inventory_script.id,
|
||||
form = inventoryScriptsFormObject,
|
||||
master = {},
|
||||
url = GetBasePath('inventory_scripts');
|
||||
init();
|
||||
|
||||
$scope.inventory_script = inventory_script;
|
||||
function init() {
|
||||
$scope.inventory_script = inventory_scriptData;
|
||||
|
||||
$scope.$watch('inventory_script_obj.summary_fields.user_capabilities.edit', function(val) {
|
||||
if (val === false) {
|
||||
@ -32,78 +31,49 @@ export default
|
||||
}
|
||||
});
|
||||
|
||||
generator.inject(form, {
|
||||
mode: 'edit' ,
|
||||
scope:$scope,
|
||||
related: false,
|
||||
activityStream: false
|
||||
});
|
||||
generator.reset();
|
||||
LookUpInit({
|
||||
url: GetBasePath('organization'),
|
||||
scope: $scope,
|
||||
form: form,
|
||||
// hdr: "Select Custom Inventory",
|
||||
list: OrganizationList,
|
||||
field: 'organization',
|
||||
input_type: 'radio'
|
||||
});
|
||||
var fld;
|
||||
for (fld in form.fields) {
|
||||
if (data[fld]) {
|
||||
$scope[fld] = data[fld];
|
||||
master[fld] = data[fld];
|
||||
}
|
||||
|
||||
// Retrieve detail record and prepopulate the form
|
||||
if (form.fields[fld].sourceModel && data.summary_fields &&
|
||||
data.summary_fields[form.fields[fld].sourceModel]) {
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
master[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
$scope.formSave = function() {
|
||||
generator.clearApiErrors();
|
||||
Wait('start');
|
||||
Rest.setUrl(url + id+'/');
|
||||
Rest.get()
|
||||
.success(function (data) {
|
||||
var fld;
|
||||
for (fld in form.fields) {
|
||||
if (data[fld]) {
|
||||
$scope[fld] = data[fld];
|
||||
master[fld] = data[fld];
|
||||
}
|
||||
|
||||
if (form.fields[fld].sourceModel && data.summary_fields &&
|
||||
data.summary_fields[form.fields[fld].sourceModel]) {
|
||||
$scope[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
master[form.fields[fld].sourceModel + '_' + form.fields[fld].sourceField] =
|
||||
data.summary_fields[form.fields[fld].sourceModel][form.fields[fld].sourceField];
|
||||
}
|
||||
}
|
||||
$scope.canEdit = data.script !== null;
|
||||
if (!$scope.canEdit) {
|
||||
$scope.script = "Script contents hidden";
|
||||
}
|
||||
$scope.inventory_script_obj = data;
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to retrieve inventory script: ' + id + '. GET status: ' + status });
|
||||
});
|
||||
|
||||
$scope.formSave = function () {
|
||||
generator.clearApiErrors();
|
||||
Wait('start');
|
||||
Rest.setUrl(url+ id+'/');
|
||||
Rest.put({
|
||||
Rest.setUrl(url + id + '/');
|
||||
Rest.put({
|
||||
name: $scope.name,
|
||||
description: $scope.description,
|
||||
organization: $scope.organization,
|
||||
script: $scope.script
|
||||
})
|
||||
.success(function () {
|
||||
$state.go($state.current, null, {reload: true});
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function (data, status) {
|
||||
ProcessErrors($scope, data, status, form, { hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory script. PUT returned status: ' + status });
|
||||
.success(function() {
|
||||
$state.go($state.current, null, { reload: true });
|
||||
Wait('stop');
|
||||
})
|
||||
.error(function(data, status) {
|
||||
ProcessErrors($scope, data, status, form, {
|
||||
hdr: 'Error!',
|
||||
msg: 'Failed to add new inventory script. PUT returned status: ' + status
|
||||
});
|
||||
};
|
||||
});
|
||||
};
|
||||
|
||||
$scope.formCancel = function () {
|
||||
$state.transitionTo('inventoryScripts');
|
||||
};
|
||||
$scope.formCancel = function() {
|
||||
$state.go('inventoryScripts');
|
||||
};
|
||||
|
||||
}
|
||||
];
|
||||
}
|
||||
];
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user