Merge pull request 'feat: 汇总后端计算' (#395) from feat_group_backend into @hera/dev

Reviewed-on: daoyoucloud/tachycode#395
Reviewed-by: sealday <zhanglin@daoyoucloud.com>
This commit is contained in:
sealday 2024-03-15 20:29:02 +08:00
commit edac378ae9
2 changed files with 64 additions and 30 deletions

View File

@ -47,6 +47,7 @@ export const GroupBlock = (props) => {
url: requeatItem.fieldFormat.requestUrl,
params: {
filter: { ...filter },
collection: params.collection,
},
}),
requeatItem,

View File

@ -3,10 +3,9 @@ import { QueryTypes } from 'sequelize';
import { RecordPdfService } from '../services/record-pdf-service';
import { SystemSettingService, SqlLoader } from '@hera/plugin-core';
import { Action, Controller, Inject } from '@nocobase/utils';
import { Record } from '../../interfaces/record';
import { Movement } from '../../utils/constants';
import _ from 'lodash';
import { FilterParser } from '@nocobase/database';
@Controller('records')
export class RecordPreviewController {
@Inject(() => SqlLoader)
@ -20,33 +19,66 @@ export class RecordPreviewController {
@Action('group')
async group(ctx: Context) {
const filter = ctx.action.params.filter;
const records = (await ctx.db
.getRepository('records')
.find({ filter, appends: ['items', 'items.product', 'items.product.category'], limit: 10 })) as Record[];
// 模拟计算
const { collection: collectionName, filter } = ctx.action.params;
const collection = ctx.db.getCollection(collectionName);
const fields = collection.fields;
const filterParser = new FilterParser(filter, {
collection,
});
const { sequelize } = ctx.db;
const { where, include } = filterParser.toSequelizeParams();
const parsedFilterInclude =
include?.map((item) => {
if (fields.get(item.association)?.type === 'belongsToMany') {
item.through = { attributes: [] };
}
return item;
}) || [];
const query = {
where: where || {},
attributes: [
[sequelize.fn('sum', sequelize.col('items.count')), 'count'],
[sequelize.col('items.product_id'), 'product_id'],
[sequelize.col('records.movement'), 'movement'],
],
include: [
{
association: 'items',
attributes: [],
},
...parsedFilterInclude,
],
group: [sequelize.col('items.product_id'), sequelize.col('records.movement')],
order: [],
subQuery: false,
raw: true,
} as any;
const records = await ctx.db.getModel('records').findAll(query);
if (records) {
const allProducts = await ctx.db.getRepository('product').find({ appends: ['category'] });
if (!allProducts) return;
const items = {} as { [key: string]: { name: string; sort: number; out: number; in: number; total: number } };
records.forEach((record) => {
record.items.forEach((item) => {
if (!items[item.product.name]) {
items[item.product.name] = {
name: item.product.name,
sort: item.product.category.sort,
records.forEach((item) => {
const product = allProducts.find((p) => p.id === item?.product_id);
if (!product) return;
if (!items[product.name]) {
items[product.name] = {
name: product.name,
sort: product.category.sort,
out: 0,
in: 0,
total: 0,
};
}
const count = item.product.category.convertible ? item.count * item.product.ratio : item.count;
if (record.movement === Movement.in) {
items[item.product.name].in += count;
items[item.product.name].total += count;
const count = product.category.convertible ? item.count * product.ratio : item.count;
if (item.movement === Movement.in) {
items[product.name].in += count;
items[product.name].total += count;
} else {
items[item.product.name].out += count;
items[item.product.name].total -= count;
items[product.name].out += count;
items[product.name].total -= count;
}
});
});
ctx.body = _.toArray(items)
.sort((a, b) => a.sort - b.sort)
.map((item) => ({
@ -57,6 +89,7 @@ export class RecordPreviewController {
},
}));
}
}
@Action('pdf')
async printPreview(ctx: Context) {