mirror of
https://github.com/frappe/books.git
synced 2025-01-02 22:50:14 +00:00
fix: remove valuation selection
- book COGS according to FIFO valuation on Shipment
This commit is contained in:
parent
18be2b5106
commit
034d612d29
@ -1,12 +1,10 @@
|
||||
import { Doc } from 'fyo/model/doc';
|
||||
import { FiltersMap, ReadOnlyMap } from 'fyo/model/types';
|
||||
import { AccountTypeEnum } from 'models/baseModels/Account/types';
|
||||
import { ValuationMethod } from './types';
|
||||
|
||||
export class InventorySettings extends Doc {
|
||||
defaultLocation?: string;
|
||||
stockInHand?: string;
|
||||
valuationMethod?: ValuationMethod;
|
||||
stockReceivedButNotBilled?: string;
|
||||
costOfGoodsSold?: string;
|
||||
enableBarcodes?: boolean;
|
||||
|
@ -27,6 +27,7 @@ import {
|
||||
validateSerialNumber,
|
||||
} from './helpers';
|
||||
import { ReturnDocItem } from './types';
|
||||
import { getShipmentCOGSAmountFromSLEs } from 'reports/inventory/helpers';
|
||||
|
||||
export abstract class StockTransfer extends Transfer {
|
||||
name?: string;
|
||||
@ -128,7 +129,7 @@ export abstract class StockTransfer extends Transfer {
|
||||
'stockInHand'
|
||||
)) as string;
|
||||
|
||||
const amount = this.grandTotal ?? this.fyo.pesa(0);
|
||||
const amount = await this.getPostingAmount();
|
||||
const posting = new LedgerPosting(this, this.fyo);
|
||||
|
||||
if (this.isSales) {
|
||||
@ -163,6 +164,14 @@ export abstract class StockTransfer extends Transfer {
|
||||
return posting;
|
||||
}
|
||||
|
||||
async getPostingAmount(): Promise<Money> {
|
||||
if (!this.isSales) {
|
||||
return this.grandTotal ?? this.fyo.pesa(0);
|
||||
}
|
||||
|
||||
return await getShipmentCOGSAmountFromSLEs(this);
|
||||
}
|
||||
|
||||
async validateAccounts() {
|
||||
const settings: string[] = ['stockInHand'];
|
||||
if (this.isSales) {
|
||||
|
@ -90,9 +90,7 @@ export class StockLedger extends Report {
|
||||
}
|
||||
|
||||
async _setRawData() {
|
||||
const valuationMethod =
|
||||
this.fyo.singles.InventorySettings?.valuationMethod ??
|
||||
ValuationMethod.FIFO;
|
||||
const valuationMethod = ValuationMethod.FIFO;
|
||||
|
||||
const rawSLEs = await getRawStockLedgerEntries(this.fyo);
|
||||
this._rawData = getStockLedgerEntries(rawSLEs, valuationMethod);
|
||||
|
@ -3,17 +3,22 @@ import { StockQueue } from 'models/inventory/stockQueue';
|
||||
import { ValuationMethod } from 'models/inventory/types';
|
||||
import { ModelNameEnum } from 'models/types';
|
||||
import { safeParseFloat, safeParseInt } from 'utils/index';
|
||||
import {
|
||||
import type {
|
||||
ComputedStockLedgerEntry,
|
||||
RawStockLedgerEntry,
|
||||
StockBalanceEntry,
|
||||
} from './types';
|
||||
import type { QueryFilter } from 'utils/db/types';
|
||||
import type { StockTransfer } from 'models/inventory/StockTransfer';
|
||||
|
||||
type Item = string;
|
||||
type Location = string;
|
||||
type Batch = string;
|
||||
|
||||
export async function getRawStockLedgerEntries(fyo: Fyo) {
|
||||
export async function getRawStockLedgerEntries(
|
||||
fyo: Fyo,
|
||||
filters: QueryFilter = {}
|
||||
) {
|
||||
const fieldnames = [
|
||||
'name',
|
||||
'date',
|
||||
@ -29,11 +34,73 @@ export async function getRawStockLedgerEntries(fyo: Fyo) {
|
||||
|
||||
return (await fyo.db.getAllRaw(ModelNameEnum.StockLedgerEntry, {
|
||||
fields: fieldnames,
|
||||
filters,
|
||||
orderBy: ['date', 'created', 'name'],
|
||||
order: 'asc',
|
||||
})) as RawStockLedgerEntry[];
|
||||
}
|
||||
|
||||
export async function getShipmentCOGSAmountFromSLEs(
|
||||
stockTransfer: StockTransfer
|
||||
) {
|
||||
const fyo = stockTransfer.fyo;
|
||||
const date = stockTransfer.date ?? new Date();
|
||||
const items = (stockTransfer.items ?? []).filter((i) => i.item);
|
||||
const itemNames = Array.from(new Set(items.map((i) => i.item))) as string[];
|
||||
|
||||
type Item = string;
|
||||
type Batch = string;
|
||||
type Location = string;
|
||||
type Queues = Record<Item, Record<Location, Record<Batch, StockQueue>>>;
|
||||
|
||||
const rawSles = await getRawStockLedgerEntries(fyo, {
|
||||
item: ['in', itemNames],
|
||||
date: ['<=', date.toISOString()],
|
||||
});
|
||||
|
||||
const q: Queues = {};
|
||||
for (const sle of rawSles) {
|
||||
const i = sle.item;
|
||||
const l = sle.location;
|
||||
const b = sle.batch ?? '-';
|
||||
|
||||
q[i] ??= {};
|
||||
q[i][l] ??= {};
|
||||
q[i][l][b] ??= new StockQueue();
|
||||
|
||||
const sq = q[i][l][b];
|
||||
if (sle.quantity > 0) {
|
||||
const rate = fyo.pesa(sle.rate);
|
||||
sq.inward(rate.float, sle.quantity);
|
||||
} else {
|
||||
sq.outward(-sle.quantity);
|
||||
}
|
||||
}
|
||||
|
||||
let total = fyo.pesa(0);
|
||||
for (const item of items) {
|
||||
const i = item.item ?? '-';
|
||||
const l = item.location ?? '-';
|
||||
const b = item.batch ?? '-';
|
||||
|
||||
const sq = q[i][l][b];
|
||||
const stAmount = item.amount ?? 0;
|
||||
if (!sq) {
|
||||
total = total.add(stAmount);
|
||||
}
|
||||
|
||||
const stRate = item.rate?.float ?? 0;
|
||||
const stQuantity = item.quantity ?? 0;
|
||||
|
||||
const rate = sq.outward(stQuantity) ?? stRate;
|
||||
const amount = rate * stQuantity;
|
||||
|
||||
total = total.add(amount);
|
||||
}
|
||||
|
||||
return total;
|
||||
}
|
||||
|
||||
export function getStockLedgerEntries(
|
||||
rawSLEs: RawStockLedgerEntry[],
|
||||
valuationMethod: ValuationMethod
|
||||
|
@ -4,24 +4,6 @@
|
||||
"isSingle": true,
|
||||
"isChild": false,
|
||||
"fields": [
|
||||
{
|
||||
"fieldname": "valuationMethod",
|
||||
"label": "Valuation Method",
|
||||
"fieldtype": "Select",
|
||||
"options": [
|
||||
{
|
||||
"value": "FIFO",
|
||||
"label": "FIFO"
|
||||
},
|
||||
{
|
||||
"value": "MovingAverage",
|
||||
"label": "Moving Average"
|
||||
}
|
||||
],
|
||||
"default": "FIFO",
|
||||
"required": true,
|
||||
"section": "Default"
|
||||
},
|
||||
{
|
||||
"fieldname": "defaultLocation",
|
||||
"label": "Default Location",
|
||||
|
Loading…
Reference in New Issue
Block a user