mirror of
https://github.com/bigcapitalhq/bigcapital.git
synced 2026-02-17 13:20:31 +00:00
add server to monorepo.
This commit is contained in:
@@ -0,0 +1,211 @@
|
||||
import { Inject, Service } from 'typedi';
|
||||
import TenancyService from '@/services/Tenancy/TenancyService';
|
||||
import { ServiceError } from '@/exceptions';
|
||||
import { IAccountDTO, IAccount, IAccountCreateDTO } from '@/interfaces';
|
||||
import AccountTypesUtils from '@/lib/AccountTypes';
|
||||
import { ERRORS } from './constants';
|
||||
|
||||
@Service()
|
||||
export class CommandAccountValidators {
|
||||
@Inject()
|
||||
private tenancy: TenancyService;
|
||||
|
||||
/**
|
||||
* Throws error if the account was prefined.
|
||||
* @param {IAccount} account
|
||||
*/
|
||||
public throwErrorIfAccountPredefined(account: IAccount) {
|
||||
if (account.predefined) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_PREDEFINED);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Diff account type between new and old account, throw service error
|
||||
* if they have different account type.
|
||||
*
|
||||
* @param {IAccount|IAccountDTO} oldAccount
|
||||
* @param {IAccount|IAccountDTO} newAccount
|
||||
*/
|
||||
public async isAccountTypeChangedOrThrowError(
|
||||
oldAccount: IAccount | IAccountDTO,
|
||||
newAccount: IAccount | IAccountDTO
|
||||
) {
|
||||
if (oldAccount.accountType !== newAccount.accountType) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_TYPE_NOT_ALLOWED_TO_CHANGE);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve account type or throws service error.
|
||||
* @param {number} tenantId -
|
||||
* @param {number} accountTypeId -
|
||||
* @return {IAccountType}
|
||||
*/
|
||||
public getAccountTypeOrThrowError(accountTypeKey: string) {
|
||||
const accountType = AccountTypesUtils.getType(accountTypeKey);
|
||||
|
||||
if (!accountType) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_TYPE_NOT_FOUND);
|
||||
}
|
||||
return accountType;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve parent account or throw service error.
|
||||
* @param {number} tenantId
|
||||
* @param {number} accountId
|
||||
* @param {number} notAccountId
|
||||
*/
|
||||
public async getParentAccountOrThrowError(
|
||||
tenantId: number,
|
||||
accountId: number,
|
||||
notAccountId?: number
|
||||
) {
|
||||
const { Account } = this.tenancy.models(tenantId);
|
||||
|
||||
const parentAccount = await Account.query()
|
||||
.findById(accountId)
|
||||
.onBuild((query) => {
|
||||
if (notAccountId) {
|
||||
query.whereNot('id', notAccountId);
|
||||
}
|
||||
});
|
||||
if (!parentAccount) {
|
||||
throw new ServiceError(ERRORS.PARENT_ACCOUNT_NOT_FOUND);
|
||||
}
|
||||
return parentAccount;
|
||||
}
|
||||
|
||||
/**
|
||||
* Throws error if the account type was not unique on the storage.
|
||||
* @param {number} tenantId
|
||||
* @param {string} accountCode
|
||||
* @param {number} notAccountId
|
||||
*/
|
||||
public async isAccountCodeUniqueOrThrowError(
|
||||
tenantId: number,
|
||||
accountCode: string,
|
||||
notAccountId?: number
|
||||
) {
|
||||
const { Account } = this.tenancy.models(tenantId);
|
||||
|
||||
const account = await Account.query()
|
||||
.where('code', accountCode)
|
||||
.onBuild((query) => {
|
||||
if (notAccountId) {
|
||||
query.whereNot('id', notAccountId);
|
||||
}
|
||||
});
|
||||
|
||||
if (account.length > 0) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_CODE_NOT_UNIQUE);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates the account name uniquiness.
|
||||
* @param {number} tenantId
|
||||
* @param {string} accountName
|
||||
* @param {number} notAccountId - Ignore the account id.
|
||||
*/
|
||||
public async validateAccountNameUniquiness(
|
||||
tenantId: number,
|
||||
accountName: string,
|
||||
notAccountId?: number
|
||||
) {
|
||||
const { Account } = this.tenancy.models(tenantId);
|
||||
|
||||
const foundAccount = await Account.query()
|
||||
.findOne('name', accountName)
|
||||
.onBuild((query) => {
|
||||
if (notAccountId) {
|
||||
query.whereNot('id', notAccountId);
|
||||
}
|
||||
});
|
||||
if (foundAccount) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_NAME_NOT_UNIQUE);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates the given account type supports multi-currency.
|
||||
* @param {IAccountDTO} accountDTO -
|
||||
*/
|
||||
public validateAccountTypeSupportCurrency = (
|
||||
accountDTO: IAccountCreateDTO,
|
||||
baseCurrency: string
|
||||
) => {
|
||||
// Can't continue to validate the type has multi-currency feature
|
||||
// if the given currency equals the base currency or not assigned.
|
||||
if (accountDTO.currencyCode === baseCurrency || !accountDTO.currencyCode) {
|
||||
return;
|
||||
}
|
||||
const meta = AccountTypesUtils.getType(accountDTO.accountType);
|
||||
|
||||
// Throw error if the account type does not support multi-currency.
|
||||
if (!meta?.multiCurrency) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_TYPE_NOT_SUPPORTS_MULTI_CURRENCY);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Validates the account DTO currency code whether equals the currency code of
|
||||
* parent account.
|
||||
* @param {IAccountCreateDTO} accountDTO
|
||||
* @param {IAccount} parentAccount
|
||||
* @param {string} baseCurrency -
|
||||
* @throws {ServiceError(ERRORS.ACCOUNT_CURRENCY_NOT_SAME_PARENT_ACCOUNT)}
|
||||
*/
|
||||
public validateCurrentSameParentAccount = (
|
||||
accountDTO: IAccountCreateDTO,
|
||||
parentAccount: IAccount,
|
||||
baseCurrency: string,
|
||||
) => {
|
||||
// If the account DTO currency not assigned and the parent account has no base currency.
|
||||
if (
|
||||
!accountDTO.currencyCode &&
|
||||
parentAccount.currencyCode !== baseCurrency
|
||||
) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_CURRENCY_NOT_SAME_PARENT_ACCOUNT);
|
||||
}
|
||||
// If the account DTO is assigned and not equals the currency code of parent account.
|
||||
if (
|
||||
accountDTO.currencyCode &&
|
||||
parentAccount.currencyCode !== accountDTO.currencyCode
|
||||
) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_CURRENCY_NOT_SAME_PARENT_ACCOUNT);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Throws service error if parent account has different type.
|
||||
* @param {IAccountDTO} accountDTO
|
||||
* @param {IAccount} parentAccount
|
||||
*/
|
||||
public throwErrorIfParentHasDiffType(
|
||||
accountDTO: IAccountDTO,
|
||||
parentAccount: IAccount
|
||||
) {
|
||||
if (accountDTO.accountType !== parentAccount.accountType) {
|
||||
throw new ServiceError(ERRORS.PARENT_ACCOUNT_HAS_DIFFERENT_TYPE);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve account of throw service error in case account not found.
|
||||
* @param {number} tenantId
|
||||
* @param {number} accountId
|
||||
* @return {IAccount}
|
||||
*/
|
||||
public async getAccountOrThrowError(tenantId: number, accountId: number) {
|
||||
const { accountRepository } = this.tenancy.repositories(tenantId);
|
||||
|
||||
const account = await accountRepository.findOneById(accountId);
|
||||
|
||||
if (!account) {
|
||||
throw new ServiceError(ERRORS.ACCOUNT_NOT_FOUND);
|
||||
}
|
||||
return account;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user