2
0
mirror of https://github.com/frappe/books.git synced 2025-04-02 00:01:51 +00:00

incr: add default location

This commit is contained in:
18alantom 2022-11-21 12:45:57 +05:30
parent 5d732844fb
commit 8ae6ae0cca
9 changed files with 139 additions and 67 deletions

View File

@ -1,8 +1,34 @@
import { ModelNameEnum } from '../../models/types'; import { ModelNameEnum } from '../../models/types';
import { defaultUOMs } from '../../utils/defaults';
import { DatabaseManager } from '../database/manager'; import { DatabaseManager } from '../database/manager';
import { getDefaultMetaFieldValueMap } from '../helpers'; import { getDefaultMetaFieldValueMap } from '../helpers';
const defaultUOMs = [
{
name: `Unit`,
isWhole: true,
},
{
name: `Kg`,
isWhole: false,
},
{
name: `Gram`,
isWhole: false,
},
{
name: `Meter`,
isWhole: false,
},
{
name: `Hour`,
isWhole: false,
},
{
name: `Day`,
isWhole: false,
},
];
async function execute(dm: DatabaseManager) { async function execute(dm: DatabaseManager) {
for (const uom of defaultUOMs) { for (const uom of defaultUOMs) {
const defaults = getDefaultMetaFieldValueMap(); const defaults = getDefaultMetaFieldValueMap();

View File

@ -4,6 +4,7 @@ import { AccountTypeEnum } from 'models/baseModels/Account/types';
import { ValuationMethod } from './types'; import { ValuationMethod } from './types';
export class InventorySettings extends Doc { export class InventorySettings extends Doc {
defaultLocation?: string;
stockInHand?: string; stockInHand?: string;
valuationMethod?: ValuationMethod; valuationMethod?: ValuationMethod;
stockReceivedButNotBilled?: string; stockReceivedButNotBilled?: string;

View File

@ -3,11 +3,10 @@ import {
FiltersMap, FiltersMap,
FormulaMap, FormulaMap,
ReadOnlyMap, ReadOnlyMap,
RequiredMap RequiredMap,
} from 'fyo/model/types'; } from 'fyo/model/types';
import { ModelNameEnum } from 'models/types'; import { ModelNameEnum } from 'models/types';
import { Money } from 'pesa'; import { Money } from 'pesa';
import { locationFilter } from './helpers';
import { StockMovement } from './StockMovement'; import { StockMovement } from './StockMovement';
import { MovementType } from './types'; import { MovementType } from './types';
@ -21,10 +20,20 @@ export class StockMovementItem extends Doc {
amount?: Money; amount?: Money;
parentdoc?: StockMovement; parentdoc?: StockMovement;
get isIssue() {
return this.parentdoc?.movementType === MovementType.MaterialIssue;
}
get isReceipt() {
return this.parentdoc?.movementType === MovementType.MaterialReceipt;
}
get isTransfer() {
return this.parentdoc?.movementType === MovementType.MaterialTransfer;
}
static filters: FiltersMap = { static filters: FiltersMap = {
item: () => ({ trackItem: true }), item: () => ({ trackItem: true }),
toLocation: locationFilter,
fromLocation: locationFilter,
}; };
formulas: FormulaMap = { formulas: FormulaMap = {
@ -43,40 +52,50 @@ export class StockMovementItem extends Doc {
dependsOn: ['item', 'rate', 'quantity'], dependsOn: ['item', 'rate', 'quantity'],
}, },
fromLocation: { fromLocation: {
formula: () => { formula: (fn) => {
if (this.parentdoc?.movementType === MovementType.MaterialReceipt) { if (this.isReceipt || this.isTransfer) {
return null; return null;
} }
const defaultLocation = this.fyo.singles.InventorySettings
?.defaultLocation as string | undefined;
if (defaultLocation && !this.location && this.isIssue) {
return defaultLocation;
}
return this.toLocation;
}, },
dependsOn: ['movementType'],
}, },
toLocation: { toLocation: {
formula: () => { formula: (fn) => {
if (this.parentdoc?.movementType === MovementType.MaterialIssue) { if (this.isIssue || this.isTransfer) {
return null; return null;
} }
const defaultLocation = this.fyo.singles.InventorySettings
?.defaultLocation as string | undefined;
if (defaultLocation && !this.location && this.isReceipt) {
return defaultLocation;
}
return this.toLocation;
}, },
dependsOn: ['movementType'],
}, },
}; };
required: RequiredMap = { required: RequiredMap = {
fromLocation: () => fromLocation: () => this.isIssue || this.isTransfer,
this.parentdoc?.movementType === 'MaterialIssue' || toLocation: () => this.isReceipt || this.isTransfer,
this.parentdoc?.movementType === 'MaterialTransfer',
toLocation: () =>
this.parentdoc?.movementType === 'MaterialReceipt' ||
this.parentdoc?.movementType === 'MaterialTransfer',
}; };
readOnly: ReadOnlyMap = { readOnly: ReadOnlyMap = {
fromLocation: () => fromLocation: () => this.isReceipt,
this.parentdoc?.movementType === MovementType.MaterialReceipt, toLocation: () => this.isIssue,
toLocation: () =>
this.parentdoc?.movementType === MovementType.MaterialIssue,
}; };
static createFilters: FiltersMap = { static createFilters: FiltersMap = {
item: () => ({ trackItem: true, itemType: 'Product' }), item: () => ({ trackItem: true, itemType: 'Product' }),
fromLocation: (doc: Doc) => ({ item: (doc.item ?? '') as string }),
toLocation: (doc: Doc) => ({ item: (doc.item ?? '') as string }),
}; };
} }

View File

@ -2,7 +2,6 @@ import { Doc } from 'fyo/model/doc';
import { FiltersMap, FormulaMap } from 'fyo/model/types'; import { FiltersMap, FormulaMap } from 'fyo/model/types';
import { ModelNameEnum } from 'models/types'; import { ModelNameEnum } from 'models/types';
import { Money } from 'pesa'; import { Money } from 'pesa';
import { locationFilter } from './helpers';
export class StockTransferItem extends Doc { export class StockTransferItem extends Doc {
item?: string; item?: string;
@ -94,6 +93,20 @@ export class StockTransferItem extends Doc {
}, },
dependsOn: ['item'], dependsOn: ['item'],
}, },
location: {
formula: () => {
if (this.location) {
return;
}
const defaultLocation = this.fyo.singles.InventorySettings
?.defaultLocation as string | undefined;
if (defaultLocation && !this.location) {
return defaultLocation;
}
},
},
}; };
static filters: FiltersMap = { static filters: FiltersMap = {
@ -105,6 +118,5 @@ export class StockTransferItem extends Doc {
return { for: ['not in', [itemNotFor]], trackItem: true }; return { for: ['not in', [itemNotFor]], trackItem: true };
}, },
location: locationFilter,
}; };
} }

View File

@ -1,12 +1 @@
import { Doc } from "fyo/model/doc";
import { FilterFunction } from "fyo/model/types";
import { QueryFilter } from "utils/db/types";
export const locationFilter: FilterFunction = (doc: Doc) => {
const item = doc.item;
if (!doc.item) {
return { item: null };
}
return { item: ['in', [null, item]] } as QueryFilter;
};

View File

@ -21,6 +21,13 @@
"default": "FIFO", "default": "FIFO",
"required": true "required": true
}, },
{
"fieldname": "defaultLocation",
"label": "Default Location",
"fieldtype": "Link",
"target": "Location",
"create": true
},
{ {
"fieldname": "stockInHand", "fieldname": "stockInHand",
"label": "Stock In Hand Acc.", "label": "Stock In Hand Acc.",

View File

@ -12,11 +12,13 @@
"required": true "required": true
}, },
{ {
"fieldname": "item", "fieldname": "address",
"label": "Item", "label": "Address",
"fieldtype": "Link", "fieldtype": "Link",
"target": "Item" "target": "Address",
"placeholder": "Click to create",
"inline": true
} }
], ],
"quickEditFields": ["item"] "quickEditFields": ["item", "address"]
} }

View File

@ -7,7 +7,6 @@ import {
DEFAULT_LOCALE, DEFAULT_LOCALE,
DEFAULT_SERIES_START, DEFAULT_SERIES_START,
} from 'fyo/utils/consts'; } from 'fyo/utils/consts';
import { ValueError } from 'fyo/utils/errors';
import { import {
AccountRootTypeEnum, AccountRootTypeEnum,
AccountTypeEnum, AccountTypeEnum,
@ -23,7 +22,7 @@ import {
setCurrencySymbols, setCurrencySymbols,
} from 'src/utils/initialization'; } from 'src/utils/initialization';
import { getRandomString } from 'utils'; import { getRandomString } from 'utils';
import { defaultUOMs } from 'utils/defaults'; import { getDefaultLocations, getDefaultUOMs } from 'utils/defaults';
import { getCountryCodeFromCountry, getCountryInfo } from 'utils/misc'; import { getCountryCodeFromCountry, getCountryInfo } from 'utils/misc';
import { CountryInfo } from 'utils/types'; import { CountryInfo } from 'utils/types';
import { CreateCOA } from './createCOA'; import { CreateCOA } from './createCOA';
@ -62,9 +61,13 @@ async function createDefaultEntries(fyo: Fyo) {
/** /**
* Create default UOM entries * Create default UOM entries
*/ */
for (const uom of defaultUOMs) { for (const uom of getDefaultUOMs(fyo)) {
await checkAndCreateDoc(ModelNameEnum.UOM, uom, fyo); await checkAndCreateDoc(ModelNameEnum.UOM, uom, fyo);
} }
for (const loc of getDefaultLocations(fyo)) {
await checkAndCreateDoc(ModelNameEnum.Location, loc, fyo);
}
} }
async function initializeDatabase(dbPath: string, country: string, fyo: Fyo) { async function initializeDatabase(dbPath: string, country: string, fyo: Fyo) {
@ -368,5 +371,10 @@ async function updateInventorySettings(fyo: Fyo) {
inventorySettings.set(settingName, accounts[0].name); inventorySettings.set(settingName, accounts[0].name);
} }
const location = fyo.t`Stores`;
if (await fyo.db.exists(ModelNameEnum.Location, location)) {
inventorySettings.set('defaultLocation', location);
}
await inventorySettings.sync(); await inventorySettings.sync();
} }

View File

@ -1,26 +1,34 @@
export const defaultUOMs = [ import { Fyo } from 'fyo';
{
name: 'Unit', export function getDefaultUOMs(fyo: Fyo) {
isWhole: true, return [
}, {
{ name: fyo.t`Unit`,
name: 'Kg', isWhole: true,
isWhole: false, },
}, {
{ name: fyo.t`Kg`,
name: 'Gram', isWhole: false,
isWhole: false, },
}, {
{ name: fyo.t`Gram`,
name: 'Meter', isWhole: false,
isWhole: false, },
}, {
{ name: fyo.t`Meter`,
name: 'Hour', isWhole: false,
isWhole: false, },
}, {
{ name: fyo.t`Hour`,
name: 'Day', isWhole: false,
isWhole: false, },
}, {
]; name: fyo.t`Day`,
isWhole: false,
},
];
}
export function getDefaultLocations(fyo: Fyo) {
return [{ name: fyo.t`Stores` }];
}