fixes #4945 Dejar de buscar por tag 'Nombre temporal' #1258
|
@ -14,6 +14,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
||||||
- [Artículo](Datos Básicos) Añadido campo Unidades/Caja
|
- [Artículo](Datos Básicos) Añadido campo Unidades/Caja
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
|
- [Reclamaciones](Descriptor) Cambiado el campo Agencia por Zona
|
||||||
- [Tickets](Líneas preparadas) Actualizada sección para que sea más visual
|
- [Tickets](Líneas preparadas) Actualizada sección para que sea más visual
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
|
|
|
@ -0,0 +1,49 @@
|
||||||
|
const {Report} = require('vn-print');
|
||||||
|
|
||||||
|
module.exports = Self => {
|
||||||
|
Self.remoteMethodCtx('previousLabel', {
|
||||||
|
description: 'Returns the previa label pdf',
|
||||||
|
accessType: 'READ',
|
||||||
|
accepts: [
|
||||||
|
{
|
||||||
|
arg: 'id',
|
||||||
|
type: 'number',
|
||||||
|
required: true,
|
||||||
|
description: 'The item id',
|
||||||
|
http: {source: 'path'}
|
||||||
|
}],
|
||||||
|
returns: [
|
||||||
|
{
|
||||||
|
arg: 'body',
|
||||||
|
type: 'file',
|
||||||
|
root: true
|
||||||
|
}, {
|
||||||
|
arg: 'Content-Type',
|
||||||
|
type: 'String',
|
||||||
|
http: {target: 'header'}
|
||||||
|
}, {
|
||||||
|
arg: 'Content-Disposition',
|
||||||
|
type: 'String',
|
||||||
|
http: {target: 'header'}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
http: {
|
||||||
|
path: '/:id/previousLabel',
|
||||||
|
verb: 'GET'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
Self.previousLabel = async(ctx, id) => {
|
||||||
|
const args = Object.assign({}, ctx.args);
|
||||||
|
const params = {lang: ctx.req.getLocale()};
|
||||||
|
|
||||||
|
delete args.ctx;
|
||||||
|
for (const param in args)
|
||||||
|
params[param] = args[param];
|
||||||
|
|
||||||
|
const report = new Report('previa-label', params);
|
||||||
|
const stream = await report.toPdfStream();
|
||||||
|
|
||||||
|
return [stream, 'application/pdf', `filename="previa-${id}.pdf"`];
|
||||||
|
};
|
||||||
|
};
|
|
@ -3,4 +3,5 @@ module.exports = Self => {
|
||||||
require('../methods/collection/newCollection')(Self);
|
require('../methods/collection/newCollection')(Self);
|
||||||
require('../methods/collection/getSectors')(Self);
|
require('../methods/collection/getSectors')(Self);
|
||||||
require('../methods/collection/setSaleQuantity')(Self);
|
require('../methods/collection/setSaleQuantity')(Self);
|
||||||
|
require('../methods/collection/previousLabel')(Self);
|
||||||
};
|
};
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
UPDATE `vn`.`collection`
|
||||||
|
SET sectorFk=1
|
||||||
|
WHERE id=1;
|
|
@ -0,0 +1,3 @@
|
||||||
|
ALTER TABLE `vn`.`itemPackingType` ADD isActive BOOLEAN NOT NULL;
|
||||||
|
UPDATE `vn`.`itemPackingType` SET isActive = 0 WHERE code IN ('P', 'F');
|
||||||
|
UPDATE `vn`.`itemPackingType` SET isActive = 1 WHERE code IN ('V', 'H');
|
|
@ -0,0 +1,23 @@
|
||||||
|
DROP FUNCTION IF EXISTS `vn`.`priceFixed_getRate2`;
|
||||||
|
|
||||||
|
DELIMITER $$
|
||||||
|
$$
|
||||||
|
CREATE FUNCTION `vn`.`priceFixed_getRate2`(vFixedPriceFk INT, vRate3 DOUBLE)
|
||||||
|
RETURNS DOUBLE
|
||||||
|
BEGIN
|
||||||
|
|
||||||
|
DECLARE vWarehouse INT;
|
||||||
|
DECLARE vRate2 DOUBLE;
|
||||||
|
|
||||||
|
SELECT round(vRate3 * (1 + ((r.rate2 - r.rate3)/100)), 2) INTO vRate2
|
||||||
|
FROM vn.rate r
|
||||||
|
JOIN vn.priceFixed p ON p.id = vFixedPriceFk
|
||||||
|
WHERE r.dated <= p.started
|
||||||
|
AND r.warehouseFk = p.warehouseFk
|
||||||
|
ORDER BY r.dated DESC
|
||||||
|
LIMIT 1;
|
||||||
|
|
||||||
|
RETURN vRate2;
|
||||||
|
|
||||||
|
END$$
|
||||||
|
DELIMITER ;
|
|
@ -1215,7 +1215,7 @@ INSERT INTO `vn`.`tag`(`id`, `code`, `name`, `isFree`, `isQuantitatif`, `sourceT
|
||||||
(7, NULL, 'Ancho de la base', 1, 1, NULL, 'mm',NULL, NULL),
|
(7, NULL, 'Ancho de la base', 1, 1, NULL, 'mm',NULL, NULL),
|
||||||
(23, 'stems', 'Tallos', 1, 1, NULL, NULL, NULL, 'stems'),
|
(23, 'stems', 'Tallos', 1, 1, NULL, NULL, NULL, 'stems'),
|
||||||
(27, NULL, 'Longitud(cm)', 1, 1, NULL, 'cm', NULL, NULL),
|
(27, NULL, 'Longitud(cm)', 1, 1, NULL, 'cm', NULL, NULL),
|
||||||
(36, NULL, 'Proveedor', 1, 0, NULL, NULL, NULL, NULL),
|
(36, 'producer', 'Proveedor', 1, 0, NULL, NULL, NULL, 'producer'),
|
||||||
(56, NULL, 'Genero', 1, 0, NULL, NULL, NULL, NULL),
|
(56, NULL, 'Genero', 1, 0, NULL, NULL, NULL, NULL),
|
||||||
(58, NULL, 'Variedad', 1, 0, NULL, NULL, NULL, NULL),
|
(58, NULL, 'Variedad', 1, 0, NULL, NULL, NULL, NULL),
|
||||||
(67, 'category', 'Categoria', 1, 0, NULL, NULL, NULL, NULL),
|
(67, 'category', 'Categoria', 1, 0, NULL, NULL, NULL, NULL),
|
||||||
|
|
|
@ -80203,3 +80203,4 @@ USE `vncontrol`;
|
||||||
-- Dump completed on 2022-11-21 7:57:28
|
-- Dump completed on 2022-11-21 7:57:28
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -417,8 +417,8 @@ export default {
|
||||||
fourthFixedPrice: 'vn-fixed-price tr:nth-child(5)',
|
fourthFixedPrice: 'vn-fixed-price tr:nth-child(5)',
|
||||||
fourthItemID: 'vn-fixed-price tr:nth-child(5) vn-autocomplete[ng-model="price.itemFk"]',
|
fourthItemID: 'vn-fixed-price tr:nth-child(5) vn-autocomplete[ng-model="price.itemFk"]',
|
||||||
fourthWarehouse: 'vn-fixed-price tr:nth-child(5) vn-autocomplete[ng-model="price.warehouseFk"]',
|
fourthWarehouse: 'vn-fixed-price tr:nth-child(5) vn-autocomplete[ng-model="price.warehouseFk"]',
|
||||||
fourthPPU: 'vn-fixed-price tr:nth-child(5) > td:nth-child(4)',
|
fourthGroupingPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(4)',
|
||||||
fourthPPP: 'vn-fixed-price tr:nth-child(5) > td:nth-child(5)',
|
fourthPackingPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(5)',
|
||||||
fourthHasMinPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(6) > vn-check[ng-model="price.hasMinPrice"]',
|
fourthHasMinPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(6) > vn-check[ng-model="price.hasMinPrice"]',
|
||||||
fourthMinPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(6) > vn-input-number[ng-model="price.minPrice"]',
|
fourthMinPrice: 'vn-fixed-price tr:nth-child(5) > td:nth-child(6) > vn-input-number[ng-model="price.minPrice"]',
|
||||||
fourthStarted: 'vn-fixed-price tr:nth-child(5) vn-date-picker[ng-model="price.started"]',
|
fourthStarted: 'vn-fixed-price tr:nth-child(5) vn-date-picker[ng-model="price.started"]',
|
||||||
|
|
|
@ -24,8 +24,8 @@ describe('Item fixed prices path', () => {
|
||||||
it('should fill the fixed price data', async() => {
|
it('should fill the fixed price data', async() => {
|
||||||
const now = new Date();
|
const now = new Date();
|
||||||
await page.autocompleteSearch(selectors.itemFixedPrice.fourthWarehouse, 'Warehouse one');
|
await page.autocompleteSearch(selectors.itemFixedPrice.fourthWarehouse, 'Warehouse one');
|
||||||
await page.write(selectors.itemFixedPrice.fourthPPU, '1');
|
await page.writeOnEditableTD(selectors.itemFixedPrice.fourthGroupingPrice, '1');
|
||||||
await page.write(selectors.itemFixedPrice.fourthPPP, '1');
|
await page.writeOnEditableTD(selectors.itemFixedPrice.fourthPackingPrice, '1');
|
||||||
await page.write(selectors.itemFixedPrice.fourthMinPrice, '1');
|
await page.write(selectors.itemFixedPrice.fourthMinPrice, '1');
|
||||||
await page.pickDate(selectors.itemFixedPrice.fourthStarted, now);
|
await page.pickDate(selectors.itemFixedPrice.fourthStarted, now);
|
||||||
await page.pickDate(selectors.itemFixedPrice.fourthEnded, now);
|
await page.pickDate(selectors.itemFixedPrice.fourthEnded, now);
|
||||||
|
|
|
@ -19,9 +19,9 @@ class Controller extends ModuleCard {
|
||||||
}, {
|
}, {
|
||||||
relation: 'ticket',
|
relation: 'ticket',
|
||||||
scope: {
|
scope: {
|
||||||
fields: ['agencyModeFk'],
|
fields: ['zoneFk'],
|
||||||
include: {
|
include: {
|
||||||
relation: 'agencyMode'
|
relation: 'zone'
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}, {
|
}, {
|
||||||
|
|
|
@ -27,16 +27,16 @@
|
||||||
<slot-body>
|
<slot-body>
|
||||||
<div class="attributes">
|
<div class="attributes">
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="State"
|
label="State"
|
||||||
value="{{$ctrl.claim.claimState.description}}">
|
value="{{$ctrl.claim.claimState.description}}">
|
||||||
</vn-label-value>
|
</vn-label-value>
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="Created"
|
label="Created"
|
||||||
value="{{$ctrl.claim.created | date: 'dd/MM/yyyy HH:mm'}}">
|
value="{{$ctrl.claim.created | date: 'dd/MM/yyyy HH:mm'}}">
|
||||||
</vn-label-value>
|
</vn-label-value>
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="Salesperson">
|
label="Salesperson">
|
||||||
<span
|
<span
|
||||||
ng-click="workerDescriptor.show($event, $ctrl.claim.client.salesPersonFk)"
|
ng-click="workerDescriptor.show($event, $ctrl.claim.client.salesPersonFk)"
|
||||||
class="link">
|
class="link">
|
||||||
{{$ctrl.claim.client.salesPersonUser.name}}
|
{{$ctrl.claim.client.salesPersonUser.name}}
|
||||||
|
@ -44,19 +44,23 @@
|
||||||
</vn-label-value>
|
</vn-label-value>
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="Attended by">
|
label="Attended by">
|
||||||
<span
|
<span
|
||||||
ng-click="workerDescriptor.show($event, $ctrl.claim.worker.userFk)"
|
ng-click="workerDescriptor.show($event, $ctrl.claim.worker.userFk)"
|
||||||
class="link">
|
class="link">
|
||||||
{{$ctrl.claim.worker.user.name}}
|
{{$ctrl.claim.worker.user.name}}
|
||||||
</span>
|
</span>
|
||||||
</vn-label-value>
|
</vn-label-value>
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="Agency"
|
label="Zone">
|
||||||
value="{{$ctrl.claim.ticket.agencyMode.name}}">
|
<span
|
||||||
|
ng-click="zoneDescriptor.show($event, $ctrl.claim.ticket.zoneFk)"
|
||||||
|
class="link">
|
||||||
|
{{$ctrl.claim.ticket.zoneFk}}
|
||||||
|
</span>
|
||||||
</vn-label-value>
|
</vn-label-value>
|
||||||
<vn-label-value
|
<vn-label-value
|
||||||
label="Ticket">
|
label="Ticket">
|
||||||
<span
|
<span
|
||||||
ng-click="ticketDescriptor.show($event, $ctrl.claim.ticketFk)"
|
ng-click="ticketDescriptor.show($event, $ctrl.claim.ticketFk)"
|
||||||
class="link">
|
class="link">
|
||||||
{{$ctrl.claim.ticketFk}}
|
{{$ctrl.claim.ticketFk}}
|
||||||
|
@ -94,12 +98,15 @@
|
||||||
question="Delete claim"
|
question="Delete claim"
|
||||||
message="Are you sure you want to delete this claim?">
|
message="Are you sure you want to delete this claim?">
|
||||||
</vn-confirm>
|
</vn-confirm>
|
||||||
<vn-worker-descriptor-popover
|
<vn-worker-descriptor-popover
|
||||||
vn-id="workerDescriptor">
|
vn-id="workerDescriptor">
|
||||||
</vn-worker-descriptor-popover>
|
</vn-worker-descriptor-popover>
|
||||||
<vn-ticket-descriptor-popover
|
<vn-ticket-descriptor-popover
|
||||||
vn-id="ticketDescriptor">
|
vn-id="ticketDescriptor">
|
||||||
</vn-ticket-descriptor-popover>
|
</vn-ticket-descriptor-popover>
|
||||||
<vn-popup vn-id="summary">
|
<vn-popup vn-id="summary">
|
||||||
<vn-claim-summary claim="$ctrl.claim"></vn-claim-summary>
|
<vn-claim-summary claim="$ctrl.claim"></vn-claim-summary>
|
||||||
</vn-popup>
|
</vn-popup>
|
||||||
|
<vn-zone-descriptor-popover
|
||||||
|
vn-id="zoneDescriptor">
|
||||||
|
</vn-zone-descriptor-popover>
|
||||||
|
|
|
@ -0,0 +1,39 @@
|
||||||
|
module.exports = Self => {
|
||||||
|
Self.remoteMethod('getRate2', {
|
||||||
|
description: 'Return the rate2',
|
||||||
|
accessType: 'READ',
|
||||||
|
accepts: [
|
||||||
|
{
|
||||||
|
arg: 'fixedPriceId',
|
||||||
|
type: 'integer',
|
||||||
|
description: 'The fixedPrice Id',
|
||||||
|
required: true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
arg: 'rate3',
|
||||||
|
type: 'number',
|
||||||
|
description: `The price rate 3`,
|
||||||
|
required: true
|
||||||
|
}
|
||||||
|
],
|
||||||
|
returns: {
|
||||||
|
type: 'object',
|
||||||
|
root: true
|
||||||
|
},
|
||||||
|
http: {
|
||||||
|
path: `/getRate2`,
|
||||||
|
verb: 'GET'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
Self.getRate2 = async(fixedPriceId, rate3, options) => {
|
||||||
|
const myOptions = {};
|
||||||
|
|
||||||
|
if (typeof options == 'object')
|
||||||
|
Object.assign(myOptions, options);
|
||||||
|
|
||||||
|
const [result] = await Self.rawSql(`SELECT vn.priceFixed_getRate2(?, ?) as rate2`,
|
||||||
|
[fixedPriceId, rate3], myOptions);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
};
|
|
@ -0,0 +1,39 @@
|
||||||
|
const models = require('vn-loopback/server/server').models;
|
||||||
|
|
||||||
|
describe('getRate2()', () => {
|
||||||
|
it(`should return new rate2 if exists rate`, async() => {
|
||||||
|
const tx = await models.FixedPrice.beginTransaction({});
|
||||||
|
|
||||||
|
try {
|
||||||
|
const options = {transaction: tx};
|
||||||
|
const fixedPriceId = 1;
|
||||||
|
const rate3 = 2;
|
||||||
|
const result = await models.FixedPrice.getRate2(fixedPriceId, rate3, options);
|
||||||
|
|
||||||
|
expect(result.rate2).toEqual(1.9);
|
||||||
|
|
||||||
|
await tx.rollback();
|
||||||
|
} catch (e) {
|
||||||
|
await tx.rollback();
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`should return null if not exists rate`, async() => {
|
||||||
|
const tx = await models.FixedPrice.beginTransaction({});
|
||||||
|
|
||||||
|
try {
|
||||||
|
const options = {transaction: tx};
|
||||||
|
const fixedPriceId = 13;
|
||||||
|
const rate3 = 2;
|
||||||
|
const result = await models.FixedPrice.getRate2(fixedPriceId, rate3, options);
|
||||||
|
|
||||||
|
expect(result.rate2).toEqual(null);
|
||||||
|
|
||||||
|
await tx.rollback();
|
||||||
|
} catch (e) {
|
||||||
|
await tx.rollback();
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
|
@ -1,4 +1,5 @@
|
||||||
module.exports = Self => {
|
module.exports = Self => {
|
||||||
require('../methods/fixed-price/filter')(Self);
|
require('../methods/fixed-price/filter')(Self);
|
||||||
require('../methods/fixed-price/upsertFixedPrice')(Self);
|
require('../methods/fixed-price/upsertFixedPrice')(Self);
|
||||||
|
require('../methods/fixed-price/getRate2')(Self);
|
||||||
};
|
};
|
||||||
|
|
|
@ -13,6 +13,9 @@
|
||||||
},
|
},
|
||||||
"description": {
|
"description": {
|
||||||
"type": "string"
|
"type": "string"
|
||||||
|
},
|
||||||
|
"isActive":{
|
||||||
|
"type": "boolean"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"acls": [
|
"acls": [
|
||||||
|
@ -23,4 +26,4 @@
|
||||||
"permission": "ALLOW"
|
"permission": "ALLOW"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
|
@ -41,14 +41,12 @@
|
||||||
<span translate>Warehouse</span>
|
<span translate>Warehouse</span>
|
||||||
</th>
|
</th>
|
||||||
<th
|
<th
|
||||||
field="rate2"
|
field="rate2">
|
||||||
vn-tooltip="Price By Unit">
|
<span translate>Grouping price</span>
|
||||||
<span translate>P.P.U.</span>
|
|
||||||
</th>
|
</th>
|
||||||
<th
|
<th
|
||||||
field="rate3"
|
field="rate3">
|
||||||
vn-tooltip="Price By Package">
|
<span translate>Packing price</span>
|
||||||
<span translate>P.P.P.</span>
|
|
||||||
</th>
|
</th>
|
||||||
<th field="minPrice">
|
<th field="minPrice">
|
||||||
<span translate>Min price</span>
|
<span translate>Min price</span>
|
||||||
|
@ -72,7 +70,7 @@
|
||||||
show-field="name"
|
show-field="name"
|
||||||
value-field="id"
|
value-field="id"
|
||||||
search-function="$ctrl.itemSearchFunc($search)"
|
search-function="$ctrl.itemSearchFunc($search)"
|
||||||
on-change="$ctrl.upsertPrice(price)"
|
on-change="$ctrl.upsertPrice(price, true)"
|
||||||
order="id DESC"
|
order="id DESC"
|
||||||
tabindex="1">
|
tabindex="1">
|
||||||
<tpl-item>
|
<tpl-item>
|
||||||
|
@ -112,18 +110,32 @@
|
||||||
</vn-autocomplete>
|
</vn-autocomplete>
|
||||||
</td>
|
</td>
|
||||||
<td shrink-field>
|
<td shrink-field>
|
||||||
<vn-input-number
|
<vn-td-editable number>
|
||||||
ng-model="price.rate2"
|
<text>{{price.rate2 | currency: 'EUR':2}}</text>
|
||||||
on-change="$ctrl.upsertPrice(price)"
|
<field>
|
||||||
step="0.01">
|
<vn-input-number
|
||||||
</vn-input-number>
|
class="dense"
|
||||||
|
vn-focus
|
||||||
|
ng-model="price.rate2"
|
||||||
|
on-change="$ctrl.upsertPrice(price)"
|
||||||
|
step="0.01">
|
||||||
|
</vn-input-number>
|
||||||
|
</field>
|
||||||
|
</vn-td-editable>
|
||||||
</td>
|
</td>
|
||||||
<td shrink-field>
|
<td shrink-field>
|
||||||
<vn-input-number
|
<vn-td-editable number>
|
||||||
ng-model="price.rate3"
|
<text>{{price.rate3 | currency: 'EUR':2}}</text>
|
||||||
on-change="$ctrl.upsertPrice(price)"
|
<field>
|
||||||
step="0.01">
|
<vn-input-number
|
||||||
</vn-input-number>
|
class="dense"
|
||||||
|
vn-focus
|
||||||
|
ng-model="price.rate3"
|
||||||
|
on-change="$ctrl.upsertPrice(price); $ctrl.recalculateRate2(price)"
|
||||||
|
step="0.01"s>
|
||||||
|
</vn-input-number>
|
||||||
|
</field>
|
||||||
|
</vn-td-editable>
|
||||||
</td>
|
</td>
|
||||||
<td shrink-field-expand class="minPrice">
|
<td shrink-field-expand class="minPrice">
|
||||||
<vn-check
|
<vn-check
|
||||||
|
|
|
@ -62,7 +62,10 @@ export default class Controller extends Section {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
upsertPrice(price) {
|
upsertPrice(price, resetMinPrice) {
|
||||||
|
if (resetMinPrice)
|
||||||
|
delete price['minPrice'];
|
||||||
|
|
||||||
price.hasMinPrice = price.minPrice ? true : false;
|
price.hasMinPrice = price.minPrice ? true : false;
|
||||||
|
|
||||||
let requiredFields = ['itemFk', 'started', 'ended', 'rate2', 'rate3'];
|
let requiredFields = ['itemFk', 'started', 'ended', 'rate2', 'rate3'];
|
||||||
|
@ -110,6 +113,24 @@ export default class Controller extends Section {
|
||||||
return {[param]: value};
|
return {[param]: value};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
recalculateRate2(price) {
|
||||||
|
if (!price.id || !price.rate3) return;
|
||||||
|
|
||||||
|
const query = 'FixedPrices/getRate2';
|
||||||
|
const params = {
|
||||||
|
fixedPriceId: price.id,
|
||||||
|
rate3: price.rate3
|
||||||
|
};
|
||||||
|
this.$http.get(query, {params})
|
||||||
|
.then(res => {
|
||||||
|
const rate2 = res.data.rate2;
|
||||||
|
if (rate2) {
|
||||||
|
price.rate2 = rate2;
|
||||||
|
this.upsertPrice(price);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ngModule.vnComponent('vnFixedPrice', {
|
ngModule.vnComponent('vnFixedPrice', {
|
||||||
|
|
|
@ -85,5 +85,25 @@ describe('fixed price', () => {
|
||||||
expect(controller.$.model.remove).toHaveBeenCalled();
|
expect(controller.$.model.remove).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('recalculateRate2()', () => {
|
||||||
|
it(`should rate2 recalculate`, () => {
|
||||||
|
jest.spyOn(controller.vnApp, 'showSuccess');
|
||||||
|
const price = {
|
||||||
|
id: 1,
|
||||||
|
itemFk: 1,
|
||||||
|
rate2: 2,
|
||||||
|
rate3: 2
|
||||||
|
};
|
||||||
|
const response = {rate2: 1};
|
||||||
|
controller.recalculateRate2(price);
|
||||||
|
|
||||||
|
const query = `FixedPrices/getRate2?fixedPriceId=${price.id}&rate3=${price.rate3}`;
|
||||||
|
$httpBackend.expectGET(query).respond(response);
|
||||||
|
$httpBackend.flush();
|
||||||
|
|
||||||
|
expect(price.rate2).toEqual(response.rate2);
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -3,5 +3,3 @@ Search prices by item ID or code: Buscar por ID de artículo o código
|
||||||
Search fixed prices: Buscar precios fijados
|
Search fixed prices: Buscar precios fijados
|
||||||
Add fixed price: Añadir precio fijado
|
Add fixed price: Añadir precio fijado
|
||||||
This row will be removed: Esta linea se eliminará
|
This row will be removed: Esta linea se eliminará
|
||||||
Price By Unit: Precio Por Unidad
|
|
||||||
Price By Package: Precio Por Paquete
|
|
|
@ -25,7 +25,10 @@ class Controller extends SearchPanel {
|
||||||
|
|
||||||
getItemPackingTypes() {
|
getItemPackingTypes() {
|
||||||
let itemPackingTypes = [];
|
let itemPackingTypes = [];
|
||||||
this.$http.get('ItemPackingTypes').then(res => {
|
const filter = {
|
||||||
|
where: {isActive: true}
|
||||||
|
};
|
||||||
|
this.$http.get('ItemPackingTypes', {filter}).then(res => {
|
||||||
for (let ipt of res.data) {
|
for (let ipt of res.data) {
|
||||||
itemPackingTypes.push({
|
itemPackingTypes.push({
|
||||||
code: ipt.code,
|
code: ipt.code,
|
||||||
|
|
|
@ -39,6 +39,7 @@ export default class Controller extends Section {
|
||||||
field: 'ipt',
|
field: 'ipt',
|
||||||
autocomplete: {
|
autocomplete: {
|
||||||
url: 'ItemPackingTypes',
|
url: 'ItemPackingTypes',
|
||||||
|
where: `{isActive: true}`,
|
||||||
showField: 'description',
|
showField: 'description',
|
||||||
valueField: 'code'
|
valueField: 'code'
|
||||||
}
|
}
|
||||||
|
@ -47,6 +48,7 @@ export default class Controller extends Section {
|
||||||
field: 'futureIpt',
|
field: 'futureIpt',
|
||||||
autocomplete: {
|
autocomplete: {
|
||||||
url: 'ItemPackingTypes',
|
url: 'ItemPackingTypes',
|
||||||
|
where: `{isActive: true}`,
|
||||||
showField: 'description',
|
showField: 'description',
|
||||||
valueField: 'code'
|
valueField: 'code'
|
||||||
}
|
}
|
||||||
|
|
|
@ -25,7 +25,10 @@ class Controller extends SearchPanel {
|
||||||
|
|
||||||
getItemPackingTypes() {
|
getItemPackingTypes() {
|
||||||
let itemPackingTypes = [];
|
let itemPackingTypes = [];
|
||||||
this.$http.get('ItemPackingTypes').then(res => {
|
const filter = {
|
||||||
|
where: {isActive: true}
|
||||||
|
};
|
||||||
|
this.$http.get('ItemPackingTypes', {filter}).then(res => {
|
||||||
for (let ipt of res.data) {
|
for (let ipt of res.data) {
|
||||||
itemPackingTypes.push({
|
itemPackingTypes.push({
|
||||||
description: this.$t(ipt.description),
|
description: this.$t(ipt.description),
|
||||||
|
|
|
@ -134,7 +134,7 @@
|
||||||
{{::ticket.shipped | date: 'dd/MM/yyyy HH:mm'}}
|
{{::ticket.shipped | date: 'dd/MM/yyyy HH:mm'}}
|
||||||
</span>
|
</span>
|
||||||
</td>
|
</td>
|
||||||
<td>{{::ticket.ipt}}</td>
|
<td>{{::ticket.ipt | dashIfEmpty}}</td>
|
||||||
<td>
|
<td>
|
||||||
<span
|
<span
|
||||||
class="chip {{$ctrl.stateColor(ticket.state)}}">
|
class="chip {{$ctrl.stateColor(ticket.state)}}">
|
||||||
|
@ -155,7 +155,7 @@
|
||||||
{{::ticket.futureShipped | date: 'dd/MM/yyyy HH:mm'}}
|
{{::ticket.futureShipped | date: 'dd/MM/yyyy HH:mm'}}
|
||||||
</span>
|
</span>
|
||||||
</td>
|
</td>
|
||||||
<td>{{::ticket.futureIpt}}</td>
|
<td>{{::ticket.futureIpt | dashIfEmpty}}</td>
|
||||||
<td>
|
<td>
|
||||||
<span
|
<span
|
||||||
class="chip {{$ctrl.stateColor(ticket.futureState)}}">
|
class="chip {{$ctrl.stateColor(ticket.futureState)}}">
|
||||||
|
|
|
@ -34,6 +34,7 @@ export default class Controller extends Section {
|
||||||
field: 'ipt',
|
field: 'ipt',
|
||||||
autocomplete: {
|
autocomplete: {
|
||||||
url: 'ItemPackingTypes',
|
url: 'ItemPackingTypes',
|
||||||
|
where: `{isActive: true}`,
|
||||||
showField: 'description',
|
showField: 'description',
|
||||||
valueField: 'code'
|
valueField: 'code'
|
||||||
}
|
}
|
||||||
|
@ -42,6 +43,7 @@ export default class Controller extends Section {
|
||||||
field: 'futureIpt',
|
field: 'futureIpt',
|
||||||
autocomplete: {
|
autocomplete: {
|
||||||
url: 'ItemPackingTypes',
|
url: 'ItemPackingTypes',
|
||||||
|
where: `{isActive: true}`,
|
||||||
showField: 'description',
|
showField: 'description',
|
||||||
valueField: 'code'
|
valueField: 'code'
|
||||||
}
|
}
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -3,9 +3,12 @@ SELECT
|
||||||
i.name,
|
i.name,
|
||||||
i.stems,
|
i.stems,
|
||||||
i.size,
|
i.size,
|
||||||
b.packing
|
b.packing,
|
||||||
|
p.name as 'producer'
|
||||||
FROM vn.item i
|
FROM vn.item i
|
||||||
JOIN cache.last_buy clb ON clb.item_id = i.id
|
JOIN cache.last_buy clb ON clb.item_id = i.id
|
||||||
JOIN vn.buy b ON b.id = clb.buy_id
|
JOIN vn.buy b ON b.id = clb.buy_id
|
||||||
JOIN vn.entry e ON e.id = b.entryFk
|
JOIN vn.entry e ON e.id = b.entryFk
|
||||||
|
JOIN vn.producer p ON p.id = i.producerFk
|
||||||
|
|
||||||
WHERE i.id = ? AND clb.warehouse_id = ?
|
WHERE i.id = ? AND clb.warehouse_id = ?
|
|
@ -0,0 +1,12 @@
|
||||||
|
const Stylesheet = require(`vn-print/core/stylesheet`);
|
||||||
|
|
||||||
|
const path = require('path');
|
||||||
|
const vnPrintPath = path.resolve('print');
|
||||||
|
|
||||||
|
module.exports = new Stylesheet([
|
||||||
|
`${vnPrintPath}/common/css/spacing.css`,
|
||||||
|
`${vnPrintPath}/common/css/misc.css`,
|
||||||
|
`${vnPrintPath}/common/css/layout.css`,
|
||||||
|
`${vnPrintPath}/common/css/report.css`,
|
||||||
|
`${__dirname}/style.css`])
|
||||||
|
.mergeStyles();
|
|
@ -0,0 +1,85 @@
|
||||||
|
* {
|
||||||
|
box-sizing: border-box;
|
||||||
|
padding-right: 1%;
|
||||||
|
}
|
||||||
|
.label {
|
||||||
|
font-size: 1.2em;
|
||||||
|
font-family: Arial, Helvetica, sans-serif;
|
||||||
|
}
|
||||||
|
.barcode {
|
||||||
|
float: left;
|
||||||
|
width: 40%;
|
||||||
|
}
|
||||||
|
.barcode h1 {
|
||||||
|
text-align: center;
|
||||||
|
font-size: 1.8em;
|
||||||
|
margin: 0 0 10px 0
|
||||||
|
}
|
||||||
|
.barcode .image {
|
||||||
|
text-align: center
|
||||||
|
}
|
||||||
|
.barcode .image img {
|
||||||
|
width: 170px
|
||||||
|
}
|
||||||
|
.data {
|
||||||
|
float: left;
|
||||||
|
width: 60%;
|
||||||
|
}
|
||||||
|
.data .header {
|
||||||
|
background-color: #000;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
overflow: hidden;
|
||||||
|
margin-bottom: 25px;
|
||||||
|
text-align: right;
|
||||||
|
font-size: 1.2em;
|
||||||
|
padding: 0.2em;
|
||||||
|
color: #FFF
|
||||||
|
}
|
||||||
|
.data .sector,
|
||||||
|
.data .producer {
|
||||||
|
text-transform: uppercase;
|
||||||
|
text-align: right;
|
||||||
|
font-size: 1.5em;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.data .sector-sm {
|
||||||
|
text-transform: uppercase;
|
||||||
|
text-align: right;
|
||||||
|
font-size: 1.2em;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.data .producer {
|
||||||
|
text-justify: inter-character;
|
||||||
|
}
|
||||||
|
.data .details {
|
||||||
|
border-top: 4px solid #000;
|
||||||
|
padding-top: 2px;
|
||||||
|
}
|
||||||
|
.data .details .package {
|
||||||
|
padding-right: 5px;
|
||||||
|
float: left;
|
||||||
|
width: 50%;
|
||||||
|
}
|
||||||
|
.package .packing,
|
||||||
|
.package .dated,
|
||||||
|
.package .labelNumber {
|
||||||
|
text-align: right
|
||||||
|
}
|
||||||
|
.package .packing {
|
||||||
|
font-size: 1.8em;
|
||||||
|
font-weight: 400
|
||||||
|
}
|
||||||
|
.data .details .size {
|
||||||
|
background-color: #000;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 3em;
|
||||||
|
padding: 0.2em 0;
|
||||||
|
float: left;
|
||||||
|
width: 50%;
|
||||||
|
color: #FFF
|
||||||
|
}
|
|
@ -0,0 +1,2 @@
|
||||||
|
previous: PREVIOUS
|
||||||
|
report: Report
|
|
@ -0,0 +1,2 @@
|
||||||
|
previous: PREVIA
|
||||||
|
report: Ticket
|
|
@ -0,0 +1,11 @@
|
||||||
|
{
|
||||||
|
"width": "10.4cm",
|
||||||
|
"height": "4.8cm",
|
||||||
|
"margin": {
|
||||||
|
"top": "0cm",
|
||||||
|
"right": "0cm",
|
||||||
|
"bottom": "0cm",
|
||||||
|
"left": "0cm"
|
||||||
|
},
|
||||||
|
"printBackground": true
|
||||||
|
}
|
|
@ -0,0 +1,26 @@
|
||||||
|
<DOCTYPE html>
|
||||||
|
<body>
|
||||||
|
<div class="label">
|
||||||
|
<div class="barcode">
|
||||||
|
<h1>{{previa.saleGroupFk}}</h1>
|
||||||
|
<div class="image">
|
||||||
|
<img v-bind:src="barcode" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="data">
|
||||||
|
<div class="header">{{ $t('previous') }}</div>
|
||||||
|
<div v-if="sector.description.length > 16" class="sector-sm">
|
||||||
|
{{sector.description}}
|
||||||
|
</div>
|
||||||
|
<div v-else class="sector">{{sector.description}}</div>
|
||||||
|
<div class="producer">{{ $t('report') }}#{{previa.ticketFk}}</div>
|
||||||
|
<div class="details">
|
||||||
|
<div class="package">
|
||||||
|
<div class="packing">{{previa.itemPackingTypeFk}}</div>
|
||||||
|
<div class="dated">{{previa.shippingHour}}:{{previa.shippingMinute}}</div>
|
||||||
|
</div>
|
||||||
|
<div class="size">{{previa.items}}</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</body>
|
|
@ -0,0 +1,42 @@
|
||||||
|
const Component = require(`vn-print/core/component`);
|
||||||
|
const reportBody = new Component('report-body');
|
||||||
|
const qrcode = require('qrcode');
|
||||||
|
const UserError = require('vn-loopback/util/user-error');
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
name: 'previa-label',
|
||||||
|
async serverPrefetch() {
|
||||||
|
this.previa = await this.fetchPrevia(this.id);
|
||||||
|
this.sector = await this.fetchSector(this.id);
|
||||||
|
this.barcode = await this.getBarcodeBase64(this.id);
|
||||||
|
|
||||||
|
if (this.previa)
|
||||||
|
this.previa = this.previa[0];
|
||||||
|
|
||||||
|
if (!this.sector)
|
||||||
|
throw new UserError('Something went wrong - no sector found');
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
fetchPrevia(id) {
|
||||||
|
return this.findOneFromDef('previa', [id]);
|
||||||
|
},
|
||||||
|
getBarcodeBase64(id) {
|
||||||
|
const data = String(id);
|
||||||
|
|
||||||
|
return qrcode.toDataURL(data, {margin: 0});
|
||||||
|
},
|
||||||
|
fetchSector(id) {
|
||||||
|
return this.findOneFromDef('sector', [id]);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
components: {
|
||||||
|
'report-body': reportBody.build()
|
||||||
|
},
|
||||||
|
props: {
|
||||||
|
id: {
|
||||||
|
type: Number,
|
||||||
|
required: true,
|
||||||
|
description: 'The saleGroupFk id'
|
||||||
|
},
|
||||||
|
}
|
||||||
|
};
|
|
@ -0,0 +1 @@
|
||||||
|
CALL vn.previousSticker_get(?)
|
|
@ -0,0 +1,4 @@
|
||||||
|
SELECT s.description
|
||||||
|
FROM vn.saleGroup sg
|
||||||
|
JOIN vn.sector s ON sg.sectorFk = s.id
|
||||||
|
WHERE sg.id = ?
|
Loading…
Reference in New Issue