From 4d18a46ee3ada751517f9bf767d5057a3bf5eb9e Mon Sep 17 00:00:00 2001
From: rsanchez <rsanchez@curisit.net>
Date: Thu, 16 Oct 2014 18:16:33 +0000
Subject: [PATCH] #2021 feature - Added Pack management (in Beta)
---
securis/src/main/resources/static/admin.html | 2
securis/src/main/resources/static/licenses.html | 139 +++++++++++++++++++++------
securis/src/main/resources/static/js/licenses.js | 63 +++++++++++-
securis/src/main/resources/static/js/login.js | 10 +
securis/src/main/resources/static/js/admin.js | 6
securis/src/main/resources/static/js/main.js | 12 +
securis/src/main/java/net/curisit/securis/db/Pack.java | 36 +++++++
securis/src/main/resources/db/schema.sql | 3
8 files changed, 221 insertions(+), 50 deletions(-)
diff --git a/securis/src/main/java/net/curisit/securis/db/Pack.java b/securis/src/main/java/net/curisit/securis/db/Pack.java
index 6e89e47..c6f3274 100644
--- a/securis/src/main/java/net/curisit/securis/db/Pack.java
+++ b/securis/src/main/java/net/curisit/securis/db/Pack.java
@@ -73,6 +73,16 @@
@Column(name = "num_licenses")
@JsonProperty("num_licenses")
private int numLicenses;
+
+ @Column(name = "init_valid_date")
+ @JsonProperty("init_valid_date")
+ private Date initValidDate;
+
+ @Column(name = "end_valid_date")
+ @JsonProperty("end_valid_date")
+ private Date endValidDate;
+
+ private String status;
@Column(name = "license_preactivation")
@JsonProperty("license_preactivation")
@@ -239,7 +249,7 @@
@JsonProperty("created_by_name")
public String getCreatedByname() {
- return createdBy == null ? null : String.format("%s %s (%s)", createdBy.getFirstName(), createdBy.getLastName(), createdBy.getUsername());
+ return createdBy == null ? null : String.format("%s %s (%s)", createdBy.getFirstName(), createdBy.getLastName() != null ? createdBy.getLastName() : "", createdBy.getUsername());
}
@JsonProperty("licensetype_code")
@@ -271,6 +281,30 @@
this.metadata = metadata;
}
+ public String getStatus() {
+ return status;
+ }
+
+ public void setStatus(String status) {
+ this.status = status;
+ }
+
+ public Date getInitValidDate() {
+ return initValidDate;
+ }
+
+ public void setInitValidDate(Date initValidDate) {
+ this.initValidDate = initValidDate;
+ }
+
+ public Date getEndValidDate() {
+ return endValidDate;
+ }
+
+ public void setEndValidDate(Date endValidDate) {
+ this.endValidDate = endValidDate;
+ }
+
@Override
public boolean equals(Object obj) {
if (!(obj instanceof Pack))
diff --git a/securis/src/main/resources/db/schema.sql b/securis/src/main/resources/db/schema.sql
index b6337b0..b249a28 100644
--- a/securis/src/main/resources/db/schema.sql
+++ b/securis/src/main/resources/db/schema.sql
@@ -75,6 +75,9 @@
id INT NOT NULL auto_increment,
code VARCHAR(50) NOT NULL ,
num_licenses INT NOT NULL ,
+ init_valid_date DATE NOT NULL default today(),
+ end_valid_date DATE NOT NULL default today(),
+ status VARCHAR(2) NOT NULL default 'PE',
comments VARCHAR(1024) NULL ,
license_type_id INT NOT NULL,
organization_id INT NOT NULL,
diff --git a/securis/src/main/resources/static/admin.html b/securis/src/main/resources/static/admin.html
index 789ecde..8ef388b 100644
--- a/securis/src/main/resources/static/admin.html
+++ b/securis/src/main/resources/static/admin.html
@@ -77,7 +77,7 @@
</td>
<td>
<input type="text" id="md_value" name="md_value" placeholder=""
- class="form-control" ng-model="row_md['value']" ng-required="row_md['mandatory']" ng-maxlength="150" />
+ class="form-control" ng-model="row_md['value']" ng-required="false" ng-maxlength="150" />
</td>
<td>
<input type="checkbox" id="md_mandatory" name="md_mandatory" ng-disabled="!field.allow_creation"
diff --git a/securis/src/main/resources/static/js/admin.js b/securis/src/main/resources/static/js/admin.js
index d3f015b..566f992 100644
--- a/securis/src/main/resources/static/js/admin.js
+++ b/securis/src/main/resources/static/js/admin.js
@@ -38,7 +38,9 @@
'$store',
'$L',
function($scope, $http, toaster, Catalogs, $store, $L) {
- $scope.showForm = false;
+ $store.set('location', '/admin');
+
+ $scope.showForm = false;
$scope.isNew = false;
$scope.formu = {};
$scope.catalogIndex = 0;
@@ -145,8 +147,6 @@
$('select').val(null);
$scope.$parent.formu = {};
- console.log("Refs for new form:");
- console.log($scope.refs);
var fields = Catalogs.getMetadata().fields;
fields.forEach(function(field) {
if (!field.listingOnly) $scope.$parent.formu[field.name] = null;
diff --git a/securis/src/main/resources/static/js/licenses.js b/securis/src/main/resources/static/js/licenses.js
index 15a7306..a2e3a20 100644
--- a/securis/src/main/resources/static/js/licenses.js
+++ b/securis/src/main/resources/static/js/licenses.js
@@ -74,7 +74,8 @@
'$store',
'$L',
function($scope, $http, toaster, $store, $L) {
-
+ $store.set('location', '/licenses');
+
$scope.maxLengthErrorMsg = function(displayname, fieldMaxlength) {
return $L.get("{0} length is too long (max: {1}).", $L.get(displayname), fieldMaxlength);
}
@@ -101,6 +102,13 @@
var packResource = $resource('/pack/:packId', {
packId : '@id'
});
+ var PACK_STATUS = [
+ {id: 'PE', label: $L.get('Pending')},
+ {id: 'AC', label: $L.get('Active')},
+ {id: 'OH', label: $L.get('On Hold')},
+ {id: 'EX', label: $L.get('Expired')},
+ {id: 'CA', label: $L.get('Cancelled')}
+ ];
$scope.mandatory = {
code: true,
num_licenses: true,
@@ -116,6 +124,7 @@
var refFields = [{resource: 'organization', name: 'organization_id'},{resource: 'licensetype', name: 'license_type_id'}];
Catalogs.loadRefs(function(refs) {
$scope.refs = refs;
+ $scope.refs['pack_status'] = PACK_STATUS;
}, refFields);
});
@@ -128,12 +137,28 @@
$scope.packs = packResource.query();
- $scope.save = function() {
+ var _savePackData = function() {
var _success = function() {
if (!$scope.isNew) $scope.showForm = false;
$scope.packs = packResource.query();
+ toaster.pop('success', Catalogs.getName(), $L.get("Pack '{0}' {1} successfully", $scope.pack.code, $scope.isNew ? $L.get("created") : $L.get("updated")));
}
- packResource.save($scope.pack, _success)
+ var _error = function(error) {
+ console.log(error);
+ toaster.pop('error', Catalogs.getName(), $L.get("Error {0} pack '{1}'. Reason: {2}", $scope.isNew ? $L.get("creating") : $L.get("updating"), $scope.pack.code, $L.get(error.headers('X-SECURIS-ERROR'))));
+ }
+ packResource.save($scope.pack, _success, _error);
+ }
+ $scope.save = function() {
+ if ($scope.pack.num_activations > 0) {
+ BootstrapDialog.confirm($L.get("The pack '{0}' has active licenses, Do you want to modify it ?", $scope.pack.code), function(answer){
+ if (answer) {
+ _savePackData();
+ }
+ });
+ } else {
+ _savePackData();
+ }
}
$scope.newPack = function() {
@@ -141,9 +166,10 @@
$scope.showForm = true;
$scope.pack = {
license_preactivation: true,
+ status: 'PE',
num_licenses: 1,
- license_type_id: !$scope.refs.license_type_id || !$scope.refs.license_type_id.length ? null : $scope.refs.license_type_id[0].id,
- organization_id: !$scope.refs.organization_id || !$scope.refs.organization_id.length ? null : $scope.refs.organization_id[0].id
+ license_type_id: null,
+ organization_id: null //!$scope.refs.organization_id || !$scope.refs.organization_id.length ? null : $scope.refs.organization_id[0].id
}
setTimeout(function() {
$('#code').focus();
@@ -188,6 +214,33 @@
$scope.$parent.$broadcast('pack_changed', pack);
}
+ $scope.createMetadataRow = function() {
+ if (!$scope.formu.metadata) {
+ $scope.formu.metadata = [];
+ }
+ $scope.formu.metadata.push({key: '', value: '', mandatory: true});
+ }
+ $scope.removeMetadataKey = function(row_md) {
+ $scope.formu.metadata.splice( $scope.formu.metadata.indexOf(row_md), 1 );
+ }
+ $scope.updateMetadata = function() {
+ // Called when Application ID change in current field
+ var newLTId = $scope.pack['license_type_id'];
+ if (newLTId) {
+ // Only if there is a "valid" value selected we should update the metadata
+ Catalogs.getResource('licensetype').get({licenseTypeId: newLTId}).$promise.then(function(lt) {
+ $scope.pack.metadata = [];
+ lt.metadata.forEach(function(md) {
+ $scope.pack.metadata.push({
+ key: md.key,
+ value: md.value,
+ readonly: !!md.value,
+ mandatory: md.mandatory
+ });
+ });
+ });
+ }
+ }
} ]);
app.controller('LicensesCtrl', [
diff --git a/securis/src/main/resources/static/js/login.js b/securis/src/main/resources/static/js/login.js
index 704bdc3..8051120 100644
--- a/securis/src/main/resources/static/js/login.js
+++ b/securis/src/main/resources/static/js/login.js
@@ -23,14 +23,18 @@
}).
success(function(data, status, headers, config) {
toaster.pop('success', $L.get('Login successful'), $L.get('User {0} has logged in application', $scope.username), 1500);
- $location.path('/licenses');
+ var location = $store.get('location') || '/licenses';
+
+ $location.path(location);
$store.put('username', $scope.username);
$store.put('token', data.token);
$http.defaults.headers.common['X-SECURIS-TOKEN'] = data.token;
}).
error(function(data, status, headers, config) {
- if (status === 403 /* forbidden */) {
- toaster.pop('error', $L.get('Login error'), $L.get('Invalid credentials'), 3000);
+ if (status === 403 /* forbidden */ || status === 401 /* unauthorized */) {
+ toaster.pop('error', $L.get('Login error'), $L.get('Invalid credentials'), 2000);
+ } else if (status === 418 /* Teapot */) {
+ toaster.pop('error', $L.get('Login error'), $L.get(headers['X-SECURIS-ERROR-MSG']), 2000);
} else {
console.error(data + " status: "+ status);
toaster.pop('error', $L.get('Unexpected Login error'), $L.get('Unexpected error HTTP ({0}) accessing to server. Contact with the administrator.', status), 5000);
diff --git a/securis/src/main/resources/static/js/main.js b/securis/src/main/resources/static/js/main.js
index 1406d54..1c7c442 100644
--- a/securis/src/main/resources/static/js/main.js
+++ b/securis/src/main/resources/static/js/main.js
@@ -78,10 +78,14 @@
// configure html5 to get links working on jsfiddle
$locationProvider.html5Mode(true);
$httpProvider.interceptors.push('securisHttpInterceptor');
- });
+ });
+
m.controller('MainCtrl', ['$scope', '$http', '$location', '$L', '$store',
function($scope, $http, $location, $L, $store) {
+ $scope.currentRoute = null;
+ console.log('Current location: ' + $location);
+ console.log($location);
$location.path('/login');
if ($store.get('token') != null) {
@@ -91,8 +95,10 @@
}
}).success(function(data) {
if (data.valid) {
- $http.defaults.headers.common['X-SECURIS-TOKEN'] = $store.get('token');
- $location.path('/licenses');
+ $http.defaults.headers.common['X-SECURIS-TOKEN'] = $store.get('token');
+ var location = $store.get('location') || '/licenses';
+
+ $location.path(location);
$store.set('user', data.user);
}
});
diff --git a/securis/src/main/resources/static/licenses.html b/securis/src/main/resources/static/licenses.html
index 9f290c9..7d40fa9 100644
--- a/securis/src/main/resources/static/licenses.html
+++ b/securis/src/main/resources/static/licenses.html
@@ -21,15 +21,16 @@
</a></li>
</ul>
<div class="navbar-form navbar-right form-group">
- <span class="input-group input-group-sm">
- <div class="input-group-addon" style="width: 28px;" >
+ <span class="input-group input-group-sm">
+ <div class="input-group-addon" style="width: 28px;">
<span class=" glyphicon glyphicon-search"></span>
+ </div> <input type="text" class="form-control" placeholder="Search"
+ ng-model="$searchPacksText">
+ <div class="input-group-addon" style="width: 20px;">
+ <span class=" glyphicon glyphicon-remove"
+ ng-click="$searchPacksText = '';"></span>
</div>
- <input type="text" class="form-control" placeholder="Search" ng-model="$searchPacksText">
- <div class="input-group-addon" style="width: 20px;" >
- <span class=" glyphicon glyphicon-remove" ng-click="$searchPacksText = '';"></span>
- </div>
- </span>
+ </span>
</div>
</div>
</div>
@@ -63,6 +64,32 @@
</div>
<div class="form-group">
+ <label class="col-md-3 control-label" for="code" i18n>Validity (from - to)</label>
+ <div class="col-md-4">
+ <input type="date" id="init_valid_date" name="init_valid_date" placeholder=""
+ class="form-control" ng-model="pack.init_valid_date"
+ ng-required="mandatory.init_valid_date" />
+ <div class="alert inline-alert alert-warning"
+ ng-show="packForm.initValidDate.$invalid">
+ <span class="glyphicon glyphicon-warning-sign"></span>
+ <span ng-show="packForm.init_valid_date.$error.required"
+ ng-bind="mandatoryFieldErrorMsg('Init valid date')"></span>
+ </div>
+ </div>
+ <div class="col-md-4">
+ <input type="date" id="end_valid_date" name="end_valid_date" placeholder=""
+ class="form-control" ng-model="pack.end_valid_date"
+ ng-required="mandatory.end_valid_date" />
+ <div class="alert inline-alert alert-warning"
+ ng-show="packForm.initValidDate.$invalid">
+ <span class="glyphicon glyphicon-warning-sign"></span>
+ <span ng-show="packForm.end_valid_date.$error.required"
+ ng-bind="mandatoryFieldErrorMsg('End valid date')"></span>
+ </div>
+ </div>
+ </div>
+
+ <div class="form-group">
<label class="col-md-3 control-label" for="num_licenses" i18n>Num.
Licenses</label>
<div class="col-md-8">
@@ -80,15 +107,33 @@
</div>
</div>
+ <div class="form-group" ng-if="!isNew">
+ <label class="col-md-3 control-label" for="status" i18n>Status</label>
+ <div class="col-md-8">
+ <select class="form-control" id="status"
+ ng-required="mandatory.status"
+ ng-model="pack.status"
+ ng-options="o.id as o.label for o in refs.pack_status">
+ </select>
+ <div class="alert inline-alert alert-warning"
+ ng-show="packForm.status.$invalid">
+ <span class="glyphicon glyphicon-warning-sign"></span> <span
+ ng-show="packForm.status.$error.required"
+ ng-bind="mandatoryFieldErrorMsg('Status')"></span>
+ </div>
+ </div>
+ </div>
+
<div class="form-group">
<label class="col-md-3 control-label" for="license_type_id" i18n>License
type</label>
<div class="col-md-8">
- <select class="form-control"
+ <select class="form-control" id="license_type_id"
+ ng-change="updateMetadata()"
ng-required="mandatory.license_type_id"
ng-model="pack.license_type_id"
ng-options="o.id as o.label for o in refs.license_type_id">
-
+
</select>
<div class="alert inline-alert alert-warning"
ng-show="packForm.license_type_id.$invalid">
@@ -143,17 +188,42 @@
</div>
<div class="form-group" ng-if="!isNew">
- <label class="col-md-3 control-label">Created by</label>
+ <label i18n class="col-md-3 control-label">Created by</label>
<div class="col-md-8">
<p class="form-control-static" ng-bind="pack.created_by_name"></p>
</div>
</div>
<div class="form-group" ng-if="!isNew">
- <label class="col-md-3 control-label">Creation date</label>
+ <label i18n class="col-md-3 control-label">Creation date</label>
<div class="col-md-8">
<p class="form-control-static"
ng-bind="pack.creationTimestamp | date:'medium'"></p>
+ </div>
+ </div>
+
+ <div class="form-group">
+ <label class="col-md-3 control-label" i18n>Metadata</label>
+ <div class="col-md-8">
+ <table class="table table-hover table-condensed">
+ <thead>
+ <tr>
+ <th i18n>Key</th>
+ <th i18n>Value</th>
+ </tr>
+ </thead>
+ <tbody>
+ <tr ng-repeat="row_md in pack.metadata">
+ <td><input type="text" id="md_key" name="md_key"
+ placeholder="" ng-readonly="true"
+ class="form-control" ng-model="row_md['key']"
+ ng-required="true" /></td>
+ <td><input type="text" id="md_value" name="md_value" ng-readonly="row_md['readonly']"
+ placeholder="" class="form-control" ng-model="row_md['value']"
+ ng-required="row_md['mandatory']" ng-maxlength="150" /></td>
+ </tr>
+ </tbody>
+ </table>
</div>
</div>
@@ -213,33 +283,34 @@
<nav class="navbar navbar-default navbar-static-top"
ng-disabled="!currentPack">
<div class="container-fluid">
- <!-- Brand and toggle get grouped for better mobile display -->
- <div class="navbar-header success">
- <a class="navbar-brand" i18n>Licenses</a>
- </div>
+ <!-- Brand and toggle get grouped for better mobile display -->
+ <div class="navbar-header success">
+ <a class="navbar-brand" i18n>Licenses</a>
+ </div>
- <!-- Collect the nav links, forms, and other content for toggling -->
- <div class="collapse navbar-collapse"
- id="bs-example-navbar-collapse-1">
- <ul class="nav navbar-nav">
- <li><a i18n ng-click="newLicense()"><span
- class="glyphicon glyphicon-plus"></span> New</a></li>
- <li><a i18n ng-click="cancel()"> <span
- class="glyphicon glyphicon-ban-circle"></span> Cancel
- </a></li>
- </ul>
- <div class="navbar-form navbar-right form-group">
- <span class="input-group input-group-sm">
- <div class="input-group-addon" style="width: 28px;" >
+ <!-- Collect the nav links, forms, and other content for toggling -->
+ <div class="collapse navbar-collapse"
+ id="bs-example-navbar-collapse-1">
+ <ul class="nav navbar-nav">
+ <li><a i18n ng-click="newLicense()"><span
+ class="glyphicon glyphicon-plus"></span> New</a></li>
+ <li><a i18n ng-click="cancel()"> <span
+ class="glyphicon glyphicon-ban-circle"></span> Cancel
+ </a></li>
+ </ul>
+ <div class="navbar-form navbar-right form-group">
+ <span class="input-group input-group-sm">
+ <div class="input-group-addon" style="width: 28px;">
<span class=" glyphicon glyphicon-search"></span>
+ </div> <input type="text" class="form-control" placeholder="Search"
+ ng-model="$searchLicensesText">
+ <div class="input-group-addon" style="width: 20px;">
+ <span class=" glyphicon glyphicon-remove"
+ ng-click="$searchLicensesText = '';"></span>
</div>
- <input type="text" class="form-control" placeholder="Search" ng-model="$searchLicensesText">
- <div class="input-group-addon" style="width: 20px;" >
- <span class=" glyphicon glyphicon-remove" ng-click="$searchLicensesText = '';"></span>
- </div>
- </span>
+ </span>
</div>
- </div>
+ </div>
</div>
</nav>
--
Gitblit v1.3.2