All files / projects-dev/libs/patterns/src/money money.ts

100% Statements 103/103
100% Branches 19/19
100% Functions 14/14
100% Lines 103/103

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 1041x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 43x 38x 38x 43x 43x 52x 52x 43x 43x 3x 3x 3x 3x 3x 3x 43x 43x 4x 4x 4x 1x 1x 2x 2x 2x 2x 4x 43x 43x 2x 2x 2x 2x 43x 43x 3x 1x 1x 2x 2x 2x 2x 3x 43x 43x 1x 1x 43x 43x 1x 1x 43x 43x 2x 2x 43x 43x 1x 1x 43x 43x 2x 2x 43x 43x 7x 2x 2x 7x 43x  
import { CurrencyInterface } from "./currency";
 
export interface MoneyInterface {
    getAmount(): number;
    getCurrency(): CurrencyInterface;
    add(money: MoneyInterface): number;
    substract(money: MoneyInterface): number;
    multiply(multiplier: number): number;
    divide(divider: number): number;
    isEqualTo(money: MoneyInterface): boolean;
    greaterThan(money: MoneyInterface): boolean;
    greaterOrEqualThan(money: MoneyInterface): boolean;
    lowerThan(money: MoneyInterface): boolean;
    lowerOrEqualThan(money: MoneyInterface): boolean;
}
 
export class Money implements MoneyInterface {
    protected amount: number;
 
    protected currency: CurrencyInterface;
 
    private readonly sameCurrencyError: string = "Operation is only permitted on same currency";
 
    private readonly amountTooLowError: string = "Operation not possible, amount is not enough";
 
    private readonly dividerShouldBeGreatherThanZero: string =
        "Operation not possible, divider should be greater than 0";
 
    public constructor(amount: number, currency: CurrencyInterface) {
        this.amount = amount;
        this.currency = currency;
    }
 
    public getAmount(): number {
        return this.amount;
    }
 
    public getCurrency(): CurrencyInterface {
        return this.currency;
    }
 
    public add(money: MoneyInterface): number {
        this.checkCurrencies(this.currency, money.getCurrency());
 
        this.amount += money.getAmount();
 
        return this.amount;
    }
 
    public substract(money: MoneyInterface): number {
        this.checkCurrencies(this.currency, money.getCurrency());
 
        if (money.getAmount() > this.amount) {
            throw new Error(this.amountTooLowError);
        }
 
        this.amount -= money.getAmount();
 
        return this.amount;
    }
 
    public multiply(multiplier: number): number {
        this.amount *= multiplier;
 
        return this.amount;
    }
 
    public divide(divider: number): number {
        if (divider <= 0) {
            throw new Error(this.dividerShouldBeGreatherThanZero);
        }
 
        this.amount /= divider;
 
        return this.amount;
    }
 
    public isEqualTo(money: MoneyInterface): boolean {
        return this.amount === money.getAmount() && this.currency === money.getCurrency();
    }
 
    public greaterThan(money: MoneyInterface): boolean {
        return this.amount > money.getAmount();
    }
 
    public greaterOrEqualThan(money: MoneyInterface): boolean {
        return this.amount >= money.getAmount();
    }
 
    public lowerThan(money: MoneyInterface): boolean {
        return this.amount < money.getAmount();
    }
 
    public lowerOrEqualThan(money: MoneyInterface): boolean {
        return this.amount <= money.getAmount();
    }
 
    private checkCurrencies(currency1: CurrencyInterface, currency2: CurrencyInterface): void {
        if (currency1 !== currency2) {
            throw new TypeError(this.sameCurrencyError);
        }
    }
}