Merge branch 'dev'
This commit is contained in:
commit
70328e6759
|
@ -1,18 +1,18 @@
|
||||||
<div>
|
<div>
|
||||||
<div class="box-wrapper">
|
<div class="box-wrapper">
|
||||||
<div class="box">
|
<div class="box">
|
||||||
<img src="./logo.svg"/>
|
<img src="./logo.svg"/>
|
||||||
<form name="form" ng-submit="$ctrl.submit()">
|
<form name="form" ng-submit="$ctrl.submit()">
|
||||||
<vn-textfield vn-id="userField" label="User" model="$ctrl.user" vn-focus></vn-textfield>
|
<vn-textfield vn-id="userField" label="User" model="$ctrl.user" vn-focus></vn-textfield>
|
||||||
<vn-textfield label="Password" model="$ctrl.password" type="password"></vn-textfield>
|
<vn-textfield label="Password" model="$ctrl.password" type="password"></vn-textfield>
|
||||||
<div class="footer">
|
<div class="footer">
|
||||||
<vn-submit label="Enter"></vn-submit>
|
<vn-submit label="Enter"></vn-submit>
|
||||||
<div class="spinner-wrapper">
|
<div class="spinner-wrapper">
|
||||||
<vn-spinner enable="$ctrl.loading"></vn-spinner>
|
<vn-spinner enable="$ctrl.loading"></vn-spinner>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</form>
|
||||||
</form>
|
</div>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
<vn-snackbar vn-id="snackbar"></vn-snackbar>
|
<vn-snackbar vn-id="snackbar"></vn-snackbar>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -16,6 +16,7 @@ vn-login > div {
|
||||||
margin: auto;
|
margin: auto;
|
||||||
height: inherit;
|
height: inherit;
|
||||||
}
|
}
|
||||||
|
|
||||||
.box {
|
.box {
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
|
@ -27,15 +28,18 @@ vn-login > div {
|
||||||
box-shadow: 0 0 1em 0 rgba(1,1,1,.6);
|
box-shadow: 0 0 1em 0 rgba(1,1,1,.6);
|
||||||
border-radius: .5em;
|
border-radius: .5em;
|
||||||
}
|
}
|
||||||
|
|
||||||
img {
|
img {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
padding-bottom: 1em;
|
padding-bottom: 1em;
|
||||||
}
|
}
|
||||||
|
|
||||||
.footer {
|
.footer {
|
||||||
margin-top: 1em;
|
margin-top: 1em;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
position: relative;
|
position: relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
.spinner-wrapper {
|
.spinner-wrapper {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
width: 0;
|
width: 0;
|
||||||
|
|
|
@ -28,7 +28,9 @@
|
||||||
show-field="name"
|
show-field="name"
|
||||||
value-field="id"
|
value-field="id"
|
||||||
select-fields="surname"
|
select-fields="surname"
|
||||||
label="Salesperson">
|
label="Salesperson"
|
||||||
|
filter-search="{where: {or: [{name: {regexp: 'search'}}, {surname: {regexp: 'search'}}]}}"
|
||||||
|
>
|
||||||
</vn-autocomplete>
|
</vn-autocomplete>
|
||||||
<vn-autocomplete vn-one
|
<vn-autocomplete vn-one
|
||||||
initial-data="$ctrl.client.contactChannel"
|
initial-data="$ctrl.client.contactChannel"
|
||||||
|
|
|
@ -28,11 +28,14 @@
|
||||||
</vn-horizontal>
|
</vn-horizontal>
|
||||||
<vn-horizontal>
|
<vn-horizontal>
|
||||||
<vn-one>
|
<vn-one>
|
||||||
<vn-check label="Recargo de equivalencia" field="$ctrl.client.equalizationTax" vn-acl="administrative"></vn-check>
|
<vn-check label="Equalization tax" field="$ctrl.client.equalizationTax" vn-acl="administrative"></vn-check>
|
||||||
</vn-one>
|
</vn-one>
|
||||||
<vn-one>
|
<vn-one>
|
||||||
<vn-check label="Vies" field="$ctrl.client.vies" vn-acl="administrative"></vn-check>
|
<vn-check label="Vies" field="$ctrl.client.vies" vn-acl="administrative"></vn-check>
|
||||||
</vn-one>
|
</vn-one>
|
||||||
|
<vn-one>
|
||||||
|
<vn-check label="Invoice by address" field="$ctrl.client.hasToInvoiceByAddress" vn-acl="administrative"></vn-check>
|
||||||
|
</vn-one>
|
||||||
</vn-horizontal>
|
</vn-horizontal>
|
||||||
</vn-vertical>
|
</vn-vertical>
|
||||||
</vn-card>
|
</vn-card>
|
||||||
|
@ -72,7 +75,7 @@
|
||||||
</vn-dialog>
|
</vn-dialog>
|
||||||
<vn-dialog
|
<vn-dialog
|
||||||
vn-id="propagate-equalizationTax"
|
vn-id="propagate-equalizationTax"
|
||||||
on-response="$ctrl.returnDialogRE(response)">
|
on-response="$ctrl.returnDialogEt(response)">
|
||||||
<tpl-body>
|
<tpl-body>
|
||||||
<vn-vertical>
|
<vn-vertical>
|
||||||
<vn-one text-center translate>You changes the equivalent tax</vn-one>
|
<vn-one text-center translate>You changes the equivalent tax</vn-one>
|
||||||
|
|
|
@ -9,9 +9,11 @@ export default class Controller {
|
||||||
this.billData = {};
|
this.billData = {};
|
||||||
this.copyData();
|
this.copyData();
|
||||||
}
|
}
|
||||||
|
|
||||||
$onChanges() {
|
$onChanges() {
|
||||||
this.copyData();
|
this.copyData();
|
||||||
}
|
}
|
||||||
|
|
||||||
copyData() {
|
copyData() {
|
||||||
if (this.client) {
|
if (this.client) {
|
||||||
this.billData.payMethodFk = this.client.payMethodFk;
|
this.billData.payMethodFk = this.client.payMethodFk;
|
||||||
|
@ -23,10 +25,12 @@ export default class Controller {
|
||||||
this.equalizationTax = this.client.equalizationTax;
|
this.equalizationTax = this.client.equalizationTax;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
submit() {
|
submit() {
|
||||||
return this.$.watcher.submit().then(
|
return this.$.watcher.submit().then(
|
||||||
() => this.checkPaymentChanges());
|
() => this.checkPaymentChanges());
|
||||||
}
|
}
|
||||||
|
|
||||||
checkPaymentChanges() {
|
checkPaymentChanges() {
|
||||||
let equals = true;
|
let equals = true;
|
||||||
Object.keys(this.billData).forEach(
|
Object.keys(this.billData).forEach(
|
||||||
|
@ -39,25 +43,26 @@ export default class Controller {
|
||||||
);
|
);
|
||||||
|
|
||||||
if (equals) {
|
if (equals) {
|
||||||
this.checkREChanges();
|
this.checkEtChanges();
|
||||||
} else {
|
} else {
|
||||||
this.$.sendMail.show();
|
this.$.sendMail.show();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
returnDialog(response) {
|
returnDialog(response) {
|
||||||
if (response === 'ACCEPT') {
|
if (response === 'ACCEPT') {
|
||||||
this.$http.post(`/mailer/manuscript/payment-update/${this.client.id}`).then(
|
this.$http.post(`/mailer/manuscript/payment-update/${this.client.id}`).then(
|
||||||
() => {
|
() => {
|
||||||
this.vnApp.showMessage(this.translate.instant('Notification sent!'));
|
this.vnApp.showMessage(this.translate.instant('Notification sent!'));
|
||||||
this.checkREChanges();
|
this.checkEtChanges();
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
this.checkREChanges();
|
this.checkEtChanges();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
checkREChanges() {
|
checkEtChanges() {
|
||||||
let equals = this.equalizationTax == this.client.equalizationTax;
|
let equals = this.equalizationTax == this.client.equalizationTax;
|
||||||
this.equalizationTax = this.client.equalizationTax;
|
this.equalizationTax = this.client.equalizationTax;
|
||||||
|
|
||||||
|
@ -65,7 +70,7 @@ export default class Controller {
|
||||||
this.$.propagateEqualizationTax.show();
|
this.$.propagateEqualizationTax.show();
|
||||||
}
|
}
|
||||||
|
|
||||||
returnDialogRE(response) {
|
returnDialogEt(response) {
|
||||||
if (response === 'ACCEPT') {
|
if (response === 'ACCEPT') {
|
||||||
this.$http.patch(`/client/api/Clients/${this.client.id}/addressesPropagateRe`, {isEqualizated: this.client.equalizationTax}).then(
|
this.$http.patch(`/client/api/Clients/${this.client.id}/addressesPropagateRe`, {isEqualizated: this.client.equalizationTax}).then(
|
||||||
res => {
|
res => {
|
||||||
|
|
|
@ -8,5 +8,7 @@
|
||||||
"You changes the equivalent tax": "Has cambiado el recargo de equivalencia",
|
"You changes the equivalent tax": "Has cambiado el recargo de equivalencia",
|
||||||
"Do you want to spread the change to their consignees?" : "¿Deseas propagar el cambio a sus consignatarios?",
|
"Do you want to spread the change to their consignees?" : "¿Deseas propagar el cambio a sus consignatarios?",
|
||||||
"Yes, propagate": "Si, propagar",
|
"Yes, propagate": "Si, propagar",
|
||||||
"Equivalent tax spreaded": "Recargo de equivalencia propagado"
|
"Equivalent tax spreaded": "Recargo de equivalencia propagado",
|
||||||
|
"Invoice by address": "Facturar por consignatario",
|
||||||
|
"Equalization tax": "Recargo de equivalencia"
|
||||||
}
|
}
|
|
@ -1,3 +1,3 @@
|
||||||
vn-descriptor{
|
vn-descriptor {
|
||||||
font-family: raleway-bold;
|
font-family: raleway-bold;
|
||||||
}
|
}
|
|
@ -11,6 +11,6 @@ vn-item-client a:hover {
|
||||||
background-color: #424242;
|
background-color: #424242;
|
||||||
}
|
}
|
||||||
|
|
||||||
.vn-item-client-name{
|
.vn-item-client-name {
|
||||||
font-family: raleway-bold;
|
font-family: raleway-bold;
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,11 +6,13 @@ export default class Controller {
|
||||||
this.$http = $http;
|
this.$http = $http;
|
||||||
this.$state = $state;
|
this.$state = $state;
|
||||||
}
|
}
|
||||||
|
|
||||||
$onChanges() {
|
$onChanges() {
|
||||||
if (this.client) {
|
if (this.client) {
|
||||||
this.getObservation(this.client.id);
|
this.getObservation(this.client.id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getObservation(clientId) {
|
getObservation(clientId) {
|
||||||
let json = JSON.stringify({where: {clientFk: this.client.id}, order: 'created DESC'});
|
let json = JSON.stringify({where: {clientFk: this.client.id}, order: 'created DESC'});
|
||||||
this.$http.get(`/client/api/clientObservations?filter=${json}`).then(
|
this.$http.get(`/client/api/clientObservations?filter=${json}`).then(
|
||||||
|
@ -19,6 +21,7 @@ export default class Controller {
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
newObservation() {
|
newObservation() {
|
||||||
this.$state.go("clientCard.notes.create", {id: this.client.id});
|
this.$state.go("clientCard.notes.create", {id: this.client.id});
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
.notes-date{
|
.notes-date {
|
||||||
font-family: raleway-bold;
|
font-family: raleway-bold;
|
||||||
}
|
}
|
|
@ -6,15 +6,18 @@ export default class Controller {
|
||||||
// onSubmit() is defined by @vnSearchbar
|
// onSubmit() is defined by @vnSearchbar
|
||||||
this.onSubmit = () => {};
|
this.onSubmit = () => {};
|
||||||
}
|
}
|
||||||
|
|
||||||
onSearch() {
|
onSearch() {
|
||||||
this.setStorageValue();
|
this.setStorageValue();
|
||||||
this.onSubmit(this.filter);
|
this.onSubmit(this.filter);
|
||||||
}
|
}
|
||||||
|
|
||||||
$onChanges() {
|
$onChanges() {
|
||||||
var value = JSON.parse(this.$window.sessionStorage.getItem('filter'));
|
var value = JSON.parse(this.$window.sessionStorage.getItem('filter'));
|
||||||
if (value !== undefined)
|
if (value !== undefined)
|
||||||
this.filter = value;
|
this.filter = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
setStorageValue() {
|
setStorageValue() {
|
||||||
this.$window.sessionStorage.setItem('filter', JSON.stringify(this.filter));
|
this.$window.sessionStorage.setItem('filter', JSON.stringify(this.filter));
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,7 +17,7 @@ describe('Client', () => {
|
||||||
}));
|
}));
|
||||||
|
|
||||||
describe('onSearch()', () => {
|
describe('onSearch()', () => {
|
||||||
it(`should call setStorageValue() and onSubmit()`, () => {
|
it('should call setStorageValue() and onSubmit()', () => {
|
||||||
spyOn(controller, 'setStorageValue');
|
spyOn(controller, 'setStorageValue');
|
||||||
spyOn(controller, 'onSubmit');
|
spyOn(controller, 'onSubmit');
|
||||||
controller.setStorageValue();
|
controller.setStorageValue();
|
||||||
|
@ -29,7 +29,7 @@ describe('Client', () => {
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('$onChanges()', () => {
|
describe('$onChanges()', () => {
|
||||||
it(`should set filter properties using the search values`, () => {
|
it('should set filter properties using the search values', () => {
|
||||||
expect(controller.filter).not.toBeDefined();
|
expect(controller.filter).not.toBeDefined();
|
||||||
spyOn(JSON, 'parse').and.returnValue({data: 'data'});
|
spyOn(JSON, 'parse').and.returnValue({data: 'data'});
|
||||||
controller.$onChanges();
|
controller.$onChanges();
|
||||||
|
|
|
@ -29,6 +29,7 @@ export default class Controller {
|
||||||
this.repeatPassword = '';
|
this.repeatPassword = '';
|
||||||
this.$.$apply();
|
this.$.$apply();
|
||||||
}
|
}
|
||||||
|
|
||||||
onPassChange(response) {
|
onPassChange(response) {
|
||||||
if (response == 'ACCEPT' && this.canChangePassword)
|
if (response == 'ACCEPT' && this.canChangePassword)
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -32,6 +32,7 @@ class Autocomplete extends Component {
|
||||||
get showDropDown() {
|
get showDropDown() {
|
||||||
return this._showDropDown;
|
return this._showDropDown;
|
||||||
}
|
}
|
||||||
|
|
||||||
set showDropDown(value) {
|
set showDropDown(value) {
|
||||||
if (value && this.url && !this._preLoad) {
|
if (value && this.url && !this._preLoad) {
|
||||||
this._preLoad = true;
|
this._preLoad = true;
|
||||||
|
@ -77,6 +78,7 @@ class Autocomplete extends Component {
|
||||||
get field() {
|
get field() {
|
||||||
return this.multiple ? this._multiField : this._field;
|
return this.multiple ? this._multiField : this._field;
|
||||||
}
|
}
|
||||||
|
|
||||||
set field(value) {
|
set field(value) {
|
||||||
if (!angular.equals(value, this.field)) {
|
if (!angular.equals(value, this.field)) {
|
||||||
this.finding = true;
|
this.finding = true;
|
||||||
|
@ -103,7 +105,7 @@ class Autocomplete extends Component {
|
||||||
if (value && value.hasOwnProperty(this.valueField)) {
|
if (value && value.hasOwnProperty(this.valueField)) {
|
||||||
this._field = value[this.valueField];
|
this._field = value[this.valueField];
|
||||||
if (this.multiple) {
|
if (this.multiple) {
|
||||||
this._multiField = [value[this.valueField]]
|
this._multiField = [value[this.valueField]];
|
||||||
}
|
}
|
||||||
if (value.hasOwnProperty(this.showField)) {
|
if (value.hasOwnProperty(this.showField)) {
|
||||||
this.displayValue = value[this.showField];
|
this.displayValue = value[this.showField];
|
||||||
|
@ -164,6 +166,7 @@ class Autocomplete extends Component {
|
||||||
json => this.onItemRequest(null)
|
json => this.onItemRequest(null)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
onItemRequest(data) {
|
onItemRequest(data) {
|
||||||
if (data && data.length > 0)
|
if (data && data.length > 0)
|
||||||
this.showItem(data[0]);
|
this.showItem(data[0]);
|
||||||
|
@ -191,10 +194,17 @@ class Autocomplete extends Component {
|
||||||
findItems(search) {
|
findItems(search) {
|
||||||
if (this.url && search && !this.finding) {
|
if (this.url && search && !this.finding) {
|
||||||
this.maxRow = false;
|
this.maxRow = false;
|
||||||
let filter = {where: {name: {regexp: search}}};
|
let filter = {};
|
||||||
if (this.filter && this.filter.where) {
|
if (this.filterSearch) {
|
||||||
Object.assign(filter.where, this.filter.where);
|
let toSearch = this.filterSearch.replace(/search/g, search);
|
||||||
|
filter = this.$scope.$eval(toSearch);
|
||||||
|
} else {
|
||||||
|
filter = {where: {name: {regexp: search}}};
|
||||||
|
if (this.filter && this.filter.where) {
|
||||||
|
Object.assign(filter.where, this.filter.where);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
filter.order = this.order;
|
||||||
let json = JSON.stringify(filter);
|
let json = JSON.stringify(filter);
|
||||||
this.finding = true;
|
this.finding = true;
|
||||||
this.$http.get(`${this.url}?filter=${json}`).then(
|
this.$http.get(`${this.url}?filter=${json}`).then(
|
||||||
|
@ -222,6 +232,7 @@ class Autocomplete extends Component {
|
||||||
this.getItems();
|
this.getItems();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getItems() {
|
getItems() {
|
||||||
if (this.url === undefined) {
|
if (this.url === undefined) {
|
||||||
this.items = copyObject(this.data);
|
this.items = copyObject(this.data);
|
||||||
|
@ -273,6 +284,7 @@ class Autocomplete extends Component {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$onInit() {
|
$onInit() {
|
||||||
this.findMore = this.url && this.maxRow;
|
this.findMore = this.url && this.maxRow;
|
||||||
this.mouseFocus = false;
|
this.mouseFocus = false;
|
||||||
|
@ -321,7 +333,6 @@ class Autocomplete extends Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Autocomplete.$inject = ['$element', '$scope', '$http', '$timeout', '$filter'];
|
Autocomplete.$inject = ['$element', '$scope', '$http', '$timeout', '$filter'];
|
||||||
|
|
||||||
module.component('vnAutocomplete', {
|
module.component('vnAutocomplete', {
|
||||||
|
@ -339,7 +350,8 @@ module.component('vnAutocomplete', {
|
||||||
label: '@',
|
label: '@',
|
||||||
multiple: '@?',
|
multiple: '@?',
|
||||||
order: '@?',
|
order: '@?',
|
||||||
filter: '<?'
|
filter: '<?',
|
||||||
|
filterSearch: '@?'
|
||||||
},
|
},
|
||||||
transclude: {
|
transclude: {
|
||||||
tplItem: '?tplItem'
|
tplItem: '?tplItem'
|
||||||
|
|
|
@ -120,8 +120,8 @@ describe('Component vnAutocomplete', () => {
|
||||||
|
|
||||||
it(`should perform a query if the item id isn't present in the controller.items property`, () => {
|
it(`should perform a query if the item id isn't present in the controller.items property`, () => {
|
||||||
controller.url = 'test.com';
|
controller.url = 'test.com';
|
||||||
$httpBackend.whenGET('test.com?filter={"fields":{"id":true,"name":true},"where":{"id":3}}').respond();
|
$httpBackend.whenGET(`${controller.url}?filter={"fields":{"id":true,"name":true},"where":{"id":3}}`).respond();
|
||||||
$httpBackend.expectGET('test.com?filter={"fields":{"id":true,"name":true},"where":{"id":3}}');
|
$httpBackend.expectGET(`${controller.url}?filter={"fields":{"id":true,"name":true},"where":{"id":3}}`);
|
||||||
controller.items = [{id: 1, name: 'test1'}, {id: 2, name: 'Bruce Wayne'}];
|
controller.items = [{id: 1, name: 'test1'}, {id: 2, name: 'Bruce Wayne'}];
|
||||||
controller.field = 3;
|
controller.field = 3;
|
||||||
$httpBackend.flush();
|
$httpBackend.flush();
|
||||||
|
@ -136,8 +136,8 @@ describe('Component vnAutocomplete', () => {
|
||||||
|
|
||||||
it(`should set field performing a query as the item id isn't present in the controller.items property`, () => {
|
it(`should set field performing a query as the item id isn't present in the controller.items property`, () => {
|
||||||
controller.url = 'test.com';
|
controller.url = 'test.com';
|
||||||
$httpBackend.whenGET('test.com?filter={"fields":{"id":true,"name":true},"where":{"id":3}}').respond();
|
$httpBackend.whenGET(`${controller.url}?filter={"fields":{"id":true,"name":true},"where":{"id":3}}`).respond();
|
||||||
$httpBackend.expectGET('test.com?filter={"fields":{"id":true,"name":true},"where":{"id":3}}');
|
$httpBackend.expectGET(`${controller.url}?filter={"fields":{"id":true,"name":true},"where":{"id":3}}`);
|
||||||
controller.items = [{id: 1, name: 'test1'}, {id: 2, name: 'Bruce Wayne'}];
|
controller.items = [{id: 1, name: 'test1'}, {id: 2, name: 'Bruce Wayne'}];
|
||||||
controller.field = 3;
|
controller.field = 3;
|
||||||
$httpBackend.flush();
|
$httpBackend.flush();
|
||||||
|
@ -150,9 +150,23 @@ describe('Component vnAutocomplete', () => {
|
||||||
let controller = $componentController('vnAutocomplete', {$scope, $element, $httpBackend, $timeout});
|
let controller = $componentController('vnAutocomplete', {$scope, $element, $httpBackend, $timeout});
|
||||||
controller.url = 'test.com';
|
controller.url = 'test.com';
|
||||||
let search = 'The Joker';
|
let search = 'The Joker';
|
||||||
let json = JSON.stringify({where: {name: {regexp: search}}});
|
let json = JSON.stringify({where: {name: {regexp: search}}, order: controller.order});
|
||||||
$httpBackend.whenGET(`test.com?filter=${json}`).respond([{id: 3, name: 'The Joker'}]);
|
$httpBackend.whenGET(`${controller.url}?filter=${json}`).respond([{id: 3, name: 'The Joker'}]);
|
||||||
$httpBackend.expectGET(`test.com?filter=${json}`);
|
$httpBackend.expectGET(`${controller.url}?filter=${json}`);
|
||||||
|
controller.findItems(search);
|
||||||
|
$httpBackend.flush();
|
||||||
|
|
||||||
|
expect(controller.items[0]).toEqual({id: 3, name: 'The Joker'});
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`should perform a search and store the result in controller items with filterSearch`, () => {
|
||||||
|
let controller = $componentController('vnAutocomplete', {$scope, $element, $httpBackend, $timeout});
|
||||||
|
controller.url = 'test.com';
|
||||||
|
let search = 'The Joker';
|
||||||
|
controller.filterSearch = "{where: {surname: {regexp: 'search'}}}";
|
||||||
|
let json = JSON.stringify({where: {surname: {regexp: search}}, order: controller.order});
|
||||||
|
$httpBackend.whenGET(`${controller.url}?filter=${json}`).respond([{id: 3, name: 'The Joker'}]);
|
||||||
|
$httpBackend.expectGET(`${controller.url}?filter=${json}`);
|
||||||
controller.findItems(search);
|
controller.findItems(search);
|
||||||
$httpBackend.flush();
|
$httpBackend.flush();
|
||||||
|
|
||||||
|
@ -163,9 +177,9 @@ describe('Component vnAutocomplete', () => {
|
||||||
controller.url = 'test.com';
|
controller.url = 'test.com';
|
||||||
let search = 'Joker';
|
let search = 'Joker';
|
||||||
controller.multiple = true;
|
controller.multiple = true;
|
||||||
let json = JSON.stringify({where: {name: {regexp: search}}});
|
let json = JSON.stringify({where: {name: {regexp: search}}, order: controller.order});
|
||||||
$httpBackend.whenGET(`test.com?filter=${json}`).respond([{id: 3, name: 'The Joker'}, {id: 4, name: 'Joker'}]);
|
$httpBackend.whenGET(`${controller.url}?filter=${json}`).respond([{id: 3, name: 'The Joker'}, {id: 4, name: 'Joker'}]);
|
||||||
$httpBackend.expectGET(`test.com?filter=${json}`);
|
$httpBackend.expectGET(`${controller.url}?filter=${json}`);
|
||||||
controller.findItems(search);
|
controller.findItems(search);
|
||||||
$httpBackend.flush();
|
$httpBackend.flush();
|
||||||
|
|
||||||
|
@ -184,8 +198,8 @@ describe('Component vnAutocomplete', () => {
|
||||||
describe('getItems()', () => {
|
describe('getItems()', () => {
|
||||||
it(`should perfom a query to fill the items without filter`, () => {
|
it(`should perfom a query to fill the items without filter`, () => {
|
||||||
controller.url = 'test.com';
|
controller.url = 'test.com';
|
||||||
$httpBackend.whenGET(`test.com?filter={"skip":0,"limit":10,"order":"name ASC"}`).respond([{id: 1, name: 'Batman'}, {id: 2, name: 'Bruce Wayne'}]);
|
$httpBackend.whenGET(`${controller.url}?filter={"skip":0,"limit":10,"order":"name ASC"}`).respond([{id: 1, name: 'Batman'}, {id: 2, name: 'Bruce Wayne'}]);
|
||||||
$httpBackend.expectGET(`test.com?filter={"skip":0,"limit":10,"order":"name ASC"}`);
|
$httpBackend.expectGET(`${controller.url}?filter={"skip":0,"limit":10,"order":"name ASC"}`);
|
||||||
controller.getItems();
|
controller.getItems();
|
||||||
$httpBackend.flush();
|
$httpBackend.flush();
|
||||||
|
|
||||||
|
|
|
@ -5,4 +5,4 @@ vn-icon {
|
||||||
vn-icon > i {
|
vn-icon > i {
|
||||||
display: block;
|
display: block;
|
||||||
font-size: inherit !important;
|
font-size: inherit !important;
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,6 +5,7 @@ import './getTemplate';
|
||||||
import './app';
|
import './app';
|
||||||
import './interceptor';
|
import './interceptor';
|
||||||
import './aclService';
|
import './aclService';
|
||||||
|
import './storageServices';
|
||||||
|
|
||||||
export * from './util';
|
export * from './util';
|
||||||
export {default as splitingRegister} from './splitingRegister';
|
export {default as splitingRegister} from './splitingRegister';
|
||||||
|
|
|
@ -0,0 +1,66 @@
|
||||||
|
import {module} from '../module';
|
||||||
|
|
||||||
|
class VnStorage {
|
||||||
|
constructor() {
|
||||||
|
this._type = '';
|
||||||
|
this.prefix = 'vn';
|
||||||
|
}
|
||||||
|
set type(value) {
|
||||||
|
this._type = value;
|
||||||
|
this.checkSupport();
|
||||||
|
}
|
||||||
|
get type() {
|
||||||
|
return this._type;
|
||||||
|
}
|
||||||
|
get webStorage() {
|
||||||
|
return window[this.type];
|
||||||
|
}
|
||||||
|
checkSupport() {
|
||||||
|
try {
|
||||||
|
let supported = (this.type in window && window[this.type] !== null);
|
||||||
|
if (supported) {
|
||||||
|
let key = '__' + Math.round(Math.random() * 1e7);
|
||||||
|
let webStorage = window[this.type];
|
||||||
|
webStorage.setItem(key, '');
|
||||||
|
webStorage.removeItem(key);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.error('VnStorage.notification.error', e.message);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
get(param) {
|
||||||
|
let toRead = this.webStorage.getItem(`${this.prefix}.${param}`);
|
||||||
|
if (toRead && toRead.startsWith('jsonObject:')) {
|
||||||
|
toRead = JSON.parse(toRead.replace('jsonObject:', ''));
|
||||||
|
}
|
||||||
|
return toRead;
|
||||||
|
}
|
||||||
|
set(param, data) {
|
||||||
|
let toStorage = typeof data === 'object' ? `jsonObject:${JSON.stringify(data)}` : data;
|
||||||
|
this.webStorage.setItem(`${this.prefix}.${param}`, toStorage);
|
||||||
|
}
|
||||||
|
remove(param) {
|
||||||
|
this.webStorage.removeItem(`${this.prefix}.${param}`);
|
||||||
|
}
|
||||||
|
clear() {
|
||||||
|
this.webStorage.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class SessionStorage extends VnStorage {
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
this.type = 'sessionStorage';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class LocalStorage extends VnStorage {
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
this.type = 'localStorage';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
module.service('sessionStorage', SessionStorage);
|
||||||
|
module.service('localStorage', LocalStorage);
|
|
@ -32,7 +32,6 @@ export class ProductionTable {
|
||||||
onOrder(field, order) {
|
onOrder(field, order) {
|
||||||
let reverse = order === 'DESC';
|
let reverse = order === 'DESC';
|
||||||
this.tickets = this.$filter('orderBy')(this.tickets, field, reverse);
|
this.tickets = this.$filter('orderBy')(this.tickets, field, reverse);
|
||||||
this.pageTickets();
|
|
||||||
}
|
}
|
||||||
pageTickets() {
|
pageTickets() {
|
||||||
let init = (this.pageTable.filter.page - 1) * this.itemsDisplayedInList;
|
let init = (this.pageTable.filter.page - 1) * this.itemsDisplayedInList;
|
||||||
|
@ -46,9 +45,9 @@ ProductionTable.$inject = ['$filter'];
|
||||||
ngModule.component('vnProductionTable', {
|
ngModule.component('vnProductionTable', {
|
||||||
template: require('./production-table.html'),
|
template: require('./production-table.html'),
|
||||||
bindings: {
|
bindings: {
|
||||||
tickets: '=',
|
tickets: '<',
|
||||||
footer: '<',
|
footer: '<',
|
||||||
checkAll: '='
|
checkAll: '<'
|
||||||
},
|
},
|
||||||
controller: ProductionTable
|
controller: ProductionTable
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,9 +1,13 @@
|
||||||
<div style="position: fixed; top: 0; right: 0; padding: .8em 1.5em; z-index: 10;">
|
<div style="position: fixed; top: 0; right: 0; padding: .8em 1.5em; z-index: 10;">
|
||||||
<vn-icon icon="apps" id="apps" translate-attr="{title: 'Applications'}"></vn-icon>
|
<vn-icon icon="apps" id="apps" translate-attr="{title: 'Applications'}"></vn-icon>
|
||||||
<vn-icon icon="notifications" translate-attr="{title: 'Notifications'}"></vn-icon>
|
|
||||||
<vn-icon icon="language" translate-attr="{title: 'Change language'}" ng-click="$ctrl.onChangeLanguage()"></vn-icon>
|
<vn-icon icon="language" translate-attr="{title: 'Change language'}" ng-click="$ctrl.onChangeLanguage()"></vn-icon>
|
||||||
<vn-icon icon="exit_to_app" translate-attr="{title: 'Logout'}" ng-click="$ctrl.onLogoutClick()"></vn-icon>
|
<vn-icon icon="exit_to_app" translate-attr="{title: 'Logout'}" ng-click="$ctrl.onLogoutClick()"></vn-icon>
|
||||||
<vn-icon icon="account_circle" translate-attr="{title: 'Profile'}" style="font-size: 35px;"></vn-icon>
|
<!--
|
||||||
|
TODO: Keep it commented until they are functional
|
||||||
|
|
||||||
|
<vn-icon icon="notifications" translate-attr="{title: 'Notifications'}"></vn-icon>
|
||||||
|
<vn-icon icon="account_circle" translate-attr="{title: 'Profile'}"></vn-icon>
|
||||||
|
-->
|
||||||
<ul class="mdl-menu mdl-js-menu mdl-menu--bottom-right" pad-small for="apps">
|
<ul class="mdl-menu mdl-js-menu mdl-menu--bottom-right" pad-small for="apps">
|
||||||
<li class="mdl-menu__item" ng-repeat="mod in $ctrl.modules track by $index" ui-sref="{{::mod.route.state}}">
|
<li class="mdl-menu__item" ng-repeat="mod in $ctrl.modules track by $index" ui-sref="{{::mod.route.state}}">
|
||||||
<vn-icon ng-if="mod.icon && !mod.icon.startsWith('/')" icon="{{::mod.icon}}"></vn-icon>
|
<vn-icon ng-if="mod.icon && !mod.icon.startsWith('/')" icon="{{::mod.icon}}"></vn-icon>
|
||||||
|
|
|
@ -1,4 +1,13 @@
|
||||||
vn-main-menu {
|
vn-main-menu {
|
||||||
|
& > div > vn-icon {
|
||||||
|
font-size: 2.5em;
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
color: #FF9300;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
li.mdl-menu__item{
|
li.mdl-menu__item{
|
||||||
background-color: #FF9300;
|
background-color: #FF9300;
|
||||||
margin-bottom: 8px;
|
margin-bottom: 8px;
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
.display-block {
|
.display-block {
|
||||||
display: block;
|
display: block;
|
||||||
}
|
}
|
||||||
|
|
||||||
.well {
|
.well {
|
||||||
min-height: 20px;
|
min-height: 20px;
|
||||||
padding: 19px;
|
padding: 19px;
|
||||||
|
@ -10,6 +11,7 @@
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);
|
box-shadow: inset 0 1px 1px rgba(0, 0, 0, .05);
|
||||||
}
|
}
|
||||||
|
|
||||||
.form-group {
|
.form-group {
|
||||||
margin-bottom: 15px;
|
margin-bottom: 15px;
|
||||||
}
|
}
|
||||||
|
@ -20,6 +22,7 @@
|
||||||
height: auto;
|
height: auto;
|
||||||
min-width: auto;
|
min-width: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
.popover-label {
|
.popover-label {
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
color: black;
|
color: black;
|
||||||
|
@ -32,12 +35,15 @@
|
||||||
height: 46px;
|
height: 46px;
|
||||||
line-height: 0px;
|
line-height: 0px;
|
||||||
}
|
}
|
||||||
|
|
||||||
input:disabled, button:disabled {
|
input:disabled, button:disabled {
|
||||||
cursor: not-allowed !important;
|
cursor: not-allowed !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
input[type="submit"]:disabled, button:disabled {
|
input[type="submit"]:disabled, button:disabled {
|
||||||
opacity: 0.7;
|
opacity: 0.7;
|
||||||
}
|
}
|
||||||
|
|
||||||
.descriptor-icon{
|
.descriptor-icon{
|
||||||
font-size:60px;
|
font-size:60px;
|
||||||
}
|
}
|
||||||
|
|
|
@ -57,6 +57,8 @@ export default {
|
||||||
postcodeInput: `${components.vnTextfield}[name="postcode"]`,
|
postcodeInput: `${components.vnTextfield}[name="postcode"]`,
|
||||||
provinceInput: `${components.vnAutocomplete}[field="$ctrl.client.provinceFk"] > vn-vertical > ${components.vnTextfield}`,
|
provinceInput: `${components.vnAutocomplete}[field="$ctrl.client.provinceFk"] > vn-vertical > ${components.vnTextfield}`,
|
||||||
provinceFifthOption: `${components.vnAutocomplete}[field="$ctrl.client.provinceFk"] > vn-vertical > vn-drop-down > vn-vertical > vn-one:nth-child(2) > ul > li:nth-child(5)`,
|
provinceFifthOption: `${components.vnAutocomplete}[field="$ctrl.client.provinceFk"] > vn-vertical > vn-drop-down > vn-vertical > vn-one:nth-child(2) > ul > li:nth-child(5)`,
|
||||||
saveButton: 'body > vn-app > vn-vertical > vn-vertical > vn-client-card > vn-horizontal > vn-auto > vn-vertical > vn-client-fiscal-data > form > vn-button-bar > vn-submit > input'
|
countryInput: `${components.vnAutocomplete}[field="$ctrl.client.countryFk"] > vn-vertical > ${components.vnTextfield}`,
|
||||||
|
countryThirdOption: `${components.vnAutocomplete}[field="$ctrl.client.countryFk"] > vn-vertical > vn-drop-down > vn-vertical > vn-one:nth-child(3) > ul > li:nth-child(3)`,
|
||||||
|
saveButton: `${components.vnSubmit}`
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -299,7 +299,6 @@ describe('Edit basicData path', () => {
|
||||||
it('should select the channel', done => {
|
it('should select the channel', done => {
|
||||||
nightmare
|
nightmare
|
||||||
.waitToClick(selectors.basicData.channelInput)
|
.waitToClick(selectors.basicData.channelInput)
|
||||||
.waitToClick(selectors.basicData.channelInput)
|
|
||||||
.waitToClick(selectors.basicData.channelMetropolisOption)
|
.waitToClick(selectors.basicData.channelMetropolisOption)
|
||||||
.waitToClick(selectors.basicData.saveButton)
|
.waitToClick(selectors.basicData.saveButton)
|
||||||
.wait(selectors.globalItems.snackbarIsActive)
|
.wait(selectors.globalItems.snackbarIsActive)
|
||||||
|
@ -317,7 +316,7 @@ describe('Edit basicData path', () => {
|
||||||
.click(selectors.fiscalData.fiscalDataButton)
|
.click(selectors.fiscalData.fiscalDataButton)
|
||||||
.wait(selectors.fiscalData.addressInput)
|
.wait(selectors.fiscalData.addressInput)
|
||||||
.click(selectors.basicData.basicDataButton)
|
.click(selectors.basicData.basicDataButton)
|
||||||
.wait(100)
|
.wait(selectors.basicData.basicDataButton)
|
||||||
.getInputValue(selectors.basicData.channelInput)
|
.getInputValue(selectors.basicData.channelInput)
|
||||||
.then(result => {
|
.then(result => {
|
||||||
expect(result).toEqual('Metropolis newspaper');
|
expect(result).toEqual('Metropolis newspaper');
|
||||||
|
|
|
@ -223,33 +223,61 @@ describe('Edit fiscalData path', () => {
|
||||||
.catch(catchErrors(done));
|
.catch(catchErrors(done));
|
||||||
});
|
});
|
||||||
|
|
||||||
// it(`should edit the province`, done => {
|
it(`should edit the province`, done => {
|
||||||
// nightmare
|
nightmare
|
||||||
// .waitToClick(selectors.fiscalData.provinceInput)
|
.waitToClick(selectors.fiscalData.provinceInput)
|
||||||
// .waitToClick(selectors.fiscalData.provinceInput)
|
.waitToClick(selectors.fiscalData.provinceFifthOption)
|
||||||
// .waitToClick(selectors.fiscalData.provinceMetropolisOption)
|
.waitToClick(selectors.fiscalData.saveButton)
|
||||||
// .waitToClick(selectors.fiscalData.saveButton)
|
.wait(selectors.globalItems.snackbarIsActive)
|
||||||
// .wait(selectors.globalItems.snackbarIsActive)
|
.getInnerText(selectors.globalItems.snackbarIsActive)
|
||||||
// .getInnerText(selectors.globalItems.snackbarIsActive)
|
.then(result => {
|
||||||
// .then(result => {
|
expect(result).toEqual(`¡Datos guardados!`);
|
||||||
// expect(result).toEqual(`¡Datos guardados!`);
|
done();
|
||||||
// done();
|
})
|
||||||
// })
|
.catch(catchErrors(done));
|
||||||
// .catch(catchErrors(done));
|
});
|
||||||
// });
|
|
||||||
|
|
||||||
// it(`should confirm the province have been selected`, done => {
|
it(`should confirm the province have been selected`, done => {
|
||||||
// nightmare
|
nightmare
|
||||||
// .waitForSnackbarReset()
|
.waitForSnackbarReset()
|
||||||
// .click(selectors.fiscalData.fiscalDataButton)
|
.click(selectors.basicData.basicDataButton)
|
||||||
// .wait(selectors.fiscalData.addressInput)
|
.wait(selectors.basicData.nameInput)
|
||||||
// .click(selectors.fiscalData.basicDataButton)
|
.click(selectors.fiscalData.fiscalDataButton)
|
||||||
// .wait(100)
|
.wait(100)
|
||||||
// .getInputValue(selectors.fiscalData.provinceInput)
|
.getInputValue(selectors.fiscalData.provinceInput)
|
||||||
// .then(result => {
|
.then(result => {
|
||||||
// expect(result).toEqual('Province two');
|
expect(result).toEqual('Province two');
|
||||||
// done();
|
done();
|
||||||
// })
|
})
|
||||||
// .catch(catchErrors(done));
|
.catch(catchErrors(done));
|
||||||
// });
|
});
|
||||||
|
|
||||||
|
it(`should edit the country`, done => {
|
||||||
|
nightmare
|
||||||
|
.waitToClick(selectors.fiscalData.countryInput)
|
||||||
|
.waitToClick(selectors.fiscalData.countryThirdOption)
|
||||||
|
.waitToClick(selectors.fiscalData.saveButton)
|
||||||
|
.wait(selectors.globalItems.snackbarIsActive)
|
||||||
|
.getInnerText(selectors.globalItems.snackbarIsActive)
|
||||||
|
.then(result => {
|
||||||
|
expect(result).toEqual(`¡Datos guardados!`);
|
||||||
|
done();
|
||||||
|
})
|
||||||
|
.catch(catchErrors(done));
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`should confirm the country have been selected`, done => {
|
||||||
|
nightmare
|
||||||
|
.waitForSnackbarReset()
|
||||||
|
.click(selectors.fiscalData.fiscalDataButton)
|
||||||
|
.wait(selectors.fiscalData.addressInput)
|
||||||
|
.click(selectors.fiscalData.basicDataButton)
|
||||||
|
.wait(100)
|
||||||
|
.getInputValue(selectors.fiscalData.countryInput)
|
||||||
|
.then(result => {
|
||||||
|
expect(result).toEqual('Holanda');
|
||||||
|
done();
|
||||||
|
})
|
||||||
|
.catch(catchErrors(done));
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -64,6 +64,10 @@
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
"description": "The client has equalization tax"
|
"description": "The client has equalization tax"
|
||||||
},
|
},
|
||||||
|
"hasToInvoiceByAddress": {
|
||||||
|
"type": "boolean",
|
||||||
|
"description": "The client has to be invoiced by address"
|
||||||
|
},
|
||||||
"hasToInvoice": {
|
"hasToInvoice": {
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
"description": "Global invoicing enabled for the client"
|
"description": "Global invoicing enabled for the client"
|
||||||
|
|
Binary file not shown.
After Width: | Height: | Size: 9.7 KiB |
|
@ -1,6 +1,8 @@
|
||||||
{
|
{
|
||||||
"initial:before": {
|
"initial:before": {
|
||||||
"loopback#favicon": {}
|
"loopback#favicon": {
|
||||||
|
"params": "$!../favicon.ico"
|
||||||
|
}
|
||||||
},
|
},
|
||||||
"initial": {
|
"initial": {
|
||||||
"compression": {},
|
"compression": {},
|
||||||
|
|
|
@ -68,16 +68,17 @@ module.exports = function(Self) {
|
||||||
}
|
}
|
||||||
|
|
||||||
function sum(tickets) {
|
function sum(tickets) {
|
||||||
var obj = {lines: 0, m3: 0};
|
let obj = {lines: 0, m3: 0};
|
||||||
tickets.forEach(function(t, i) {
|
if (tickets && tickets.length)
|
||||||
obj.lines += t.lines;
|
tickets.forEach(function(t, i) {
|
||||||
obj.m3 += t.m3;
|
obj.lines += t.lines;
|
||||||
if (tickets[i].problem)
|
obj.m3 += t.m3;
|
||||||
tickets[i].problem = tickets[i].problem.trim();
|
if (tickets[i].problem)
|
||||||
}, this);
|
tickets[i].problem = tickets[i].problem.trim();
|
||||||
|
}, this);
|
||||||
obj.m3 = obj.m3.toFixed(2);
|
obj.m3 = obj.m3.toFixed(2);
|
||||||
obj.total = tickets.length;
|
obj.total = tickets ? tickets.length : 0;
|
||||||
obj.tickets = tickets;
|
obj.tickets = tickets || [];
|
||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,24 +1,24 @@
|
||||||
<!doctype html>
|
<!doctype html>
|
||||||
<html ng-app="salix">
|
<html ng-app="salix">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<title>Salix</title>
|
<title>Salix</title>
|
||||||
<script src="/acl"></script>
|
<script src="/acl"></script>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<vn-app></vn-app>
|
<vn-app></vn-app>
|
||||||
<script type="text/javascript"
|
<script type="text/javascript"
|
||||||
src="/static/routes.js">
|
src="/static/routes.js">
|
||||||
</script>
|
</script>
|
||||||
<script type="text/javascript"
|
<script type="text/javascript"
|
||||||
src="/static/bundle.manifest.js">
|
src="/static/bundle.manifest.js">
|
||||||
</script>
|
</script>
|
||||||
<script type="text/javascript"
|
<script type="text/javascript"
|
||||||
src="/static/bundle.vendor.js">
|
src="/static/bundle.vendor.js">
|
||||||
</script>
|
</script>
|
||||||
<script type="text/javascript"
|
<script type="text/javascript"
|
||||||
src="/static/bundle.salix.js">
|
src="/static/bundle.salix.js">
|
||||||
</script>
|
</script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue