Fix/save through table data (#1714)
* fix: save through table data * chore: variable name * fix: format
This commit is contained in:
parent
1654b42037
commit
9fc8f5389b
@ -181,6 +181,80 @@ describe('repository.find', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('repository create with belongs to many', () => {
|
||||||
|
let db: Database;
|
||||||
|
|
||||||
|
beforeEach(async () => {
|
||||||
|
db = mockDatabase({
|
||||||
|
tablePrefix: '',
|
||||||
|
});
|
||||||
|
await db.clean({ drop: true });
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(async () => [await db.close()]);
|
||||||
|
|
||||||
|
it('should save value at through table', async () => {
|
||||||
|
const Product = db.collection({
|
||||||
|
name: 'products',
|
||||||
|
fields: [
|
||||||
|
{ type: 'string', name: 'name' },
|
||||||
|
{ type: 'integer', name: 'price' },
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
const OrderProduct = db.collection({
|
||||||
|
name: 'orders_products',
|
||||||
|
fields: [{ type: 'integer', name: 'quantity' }],
|
||||||
|
});
|
||||||
|
|
||||||
|
const Order = db.collection({
|
||||||
|
name: 'orders',
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
type: 'belongsToMany',
|
||||||
|
name: 'products',
|
||||||
|
through: 'orders_products',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
await db.sync();
|
||||||
|
|
||||||
|
await Product.repository.create({
|
||||||
|
values: [
|
||||||
|
{
|
||||||
|
name: 'product1',
|
||||||
|
price: 100,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'product2',
|
||||||
|
price: 200,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
const p1 = await Product.repository.findOne({
|
||||||
|
filter: { name: 'product1' },
|
||||||
|
});
|
||||||
|
|
||||||
|
await Order.repository.create({
|
||||||
|
values: {
|
||||||
|
products: [
|
||||||
|
{
|
||||||
|
id: p1.get('id'),
|
||||||
|
orders_products: {
|
||||||
|
quantity: 20,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
const through = await OrderProduct.repository.findOne();
|
||||||
|
expect(through.get('quantity')).toBe(20);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('repository.create', () => {
|
describe('repository.create', () => {
|
||||||
let db: Database;
|
let db: Database;
|
||||||
let User: Collection;
|
let User: Collection;
|
||||||
|
@ -6,10 +6,11 @@ import {
|
|||||||
HasOne,
|
HasOne,
|
||||||
Hookable,
|
Hookable,
|
||||||
ModelStatic,
|
ModelStatic,
|
||||||
Transactionable
|
Transactionable,
|
||||||
} from 'sequelize';
|
} from 'sequelize';
|
||||||
import { Model } from './model';
|
import { Model } from './model';
|
||||||
import { UpdateGuard } from './update-guard';
|
import { UpdateGuard } from './update-guard';
|
||||||
|
import lodash from 'lodash';
|
||||||
|
|
||||||
function isUndefinedOrNull(value: any) {
|
function isUndefinedOrNull(value: any) {
|
||||||
return typeof value === 'undefined' || value === null;
|
return typeof value === 'undefined' || value === null;
|
||||||
@ -396,38 +397,40 @@ export async function updateMultipleAssociation(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!Array.isArray(value)) {
|
value = lodash.castArray(value);
|
||||||
value = [value];
|
|
||||||
}
|
|
||||||
|
|
||||||
const list1 = []; // to be setted
|
const setItems = []; // to be setted
|
||||||
const list2 = []; // to be added
|
const objectItems = []; // to be added
|
||||||
const created = [];
|
|
||||||
|
// iterate item in value
|
||||||
for (const item of value) {
|
for (const item of value) {
|
||||||
if (isUndefinedOrNull(item)) {
|
if (isUndefinedOrNull(item)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isStringOrNumber(item)) {
|
if (isStringOrNumber(item)) {
|
||||||
list1.push(item);
|
setItems.push(item);
|
||||||
} else if (item instanceof Model) {
|
} else if (item instanceof Model) {
|
||||||
list1.push(item);
|
setItems.push(item);
|
||||||
} else if (item.sequelize) {
|
} else if (item.sequelize) {
|
||||||
list1.push(item);
|
setItems.push(item);
|
||||||
} else if (typeof item === 'object') {
|
} else if (typeof item === 'object') {
|
||||||
const targetKey = (association as any).targetKey || 'id';
|
const targetKey = (association as any).targetKey || 'id';
|
||||||
|
|
||||||
if (item[targetKey]) {
|
if (item[targetKey]) {
|
||||||
created.push(item[targetKey]);
|
setItems.push(item[targetKey]);
|
||||||
list1.push(item[targetKey]);
|
|
||||||
}
|
}
|
||||||
list2.push(item);
|
|
||||||
|
objectItems.push(item);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// associate targets in lists1
|
// associate targets in lists1
|
||||||
await model[setAccessor](list1, { transaction, context, individualHooks: true });
|
await model[setAccessor](setItems, { transaction, context, individualHooks: true });
|
||||||
|
|
||||||
const list3 = [];
|
const newItems = [];
|
||||||
for (const item of list2) {
|
|
||||||
|
for (const item of objectItems) {
|
||||||
const pk = association.target.primaryKeyAttribute;
|
const pk = association.target.primaryKeyAttribute;
|
||||||
|
|
||||||
const through = (<any>association).through ? (<any>association).through.model.name : null;
|
const through = (<any>association).through ? (<any>association).through.model.name : null;
|
||||||
@ -446,13 +449,14 @@ export async function updateMultipleAssociation(
|
|||||||
if (isUndefinedOrNull(item[pk])) {
|
if (isUndefinedOrNull(item[pk])) {
|
||||||
// create new record
|
// create new record
|
||||||
const instance = await model[createAccessor](item, accessorOptions);
|
const instance = await model[createAccessor](item, accessorOptions);
|
||||||
|
|
||||||
await updateAssociations(instance, item, {
|
await updateAssociations(instance, item, {
|
||||||
...options,
|
...options,
|
||||||
transaction,
|
transaction,
|
||||||
associationContext: association,
|
associationContext: association,
|
||||||
updateAssociationValues: keys,
|
updateAssociationValues: keys,
|
||||||
});
|
});
|
||||||
list3.push(instance);
|
newItems.push(instance);
|
||||||
} else {
|
} else {
|
||||||
// set & update record
|
// set & update record
|
||||||
const instance = await association.target.findByPk<any>(item[pk], {
|
const instance = await association.target.findByPk<any>(item[pk], {
|
||||||
@ -462,9 +466,9 @@ export async function updateMultipleAssociation(
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
const addAccessor = association.accessors.add;
|
const addAccessor = association.accessors.add;
|
||||||
if (!created.includes(item[pk])) {
|
|
||||||
await model[addAccessor](item[pk], accessorOptions);
|
await model[addAccessor](item[pk], accessorOptions);
|
||||||
}
|
|
||||||
if (!recursive) {
|
if (!recursive) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
@ -477,11 +481,11 @@ export async function updateMultipleAssociation(
|
|||||||
associationContext: association,
|
associationContext: association,
|
||||||
updateAssociationValues: keys,
|
updateAssociationValues: keys,
|
||||||
});
|
});
|
||||||
list3.push(instance);
|
newItems.push(instance);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
model.setDataValue(key, list1.concat(list3));
|
model.setDataValue(key, setItems.concat(newItems));
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
throw error;
|
throw error;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user