vaened/php-price-engine

A powerful pricing calculator for products and services, with comprehensive tax and discount calculations.

v0.6.1 2023-08-16 18:29 UTC

This package is auto-updated.

Last update: 2024-04-16 19:54:34 UTC


README

Build Status Software License

The Price Calculation Library is a tool that allows you to perform complex calculations for prices, taxes, discounts, and charges in your applications. This library is based on the Brick\Money library to ensure precise monetary calculations.

Installation

You can install the library using composer.

composer require vaened/php-price-engine

Usage

Initializing the Cashier

To start using the Price Engine, create an instance of the any Cashier and provide an Amount.

$cashier = new SimpleCashier(
    Amount::taxable(
        Money::of(100, 'USD'),
        TaxCodes::any()
    ),
    quantity : 1,
    taxes    : Taxes::from([
        Tax\Inclusive::proporcional(21, TaxCode::IVA),
    ])
);

Updating Quantity

You can update the quantity using the update() method, that will calculate the totals in the next summary.

$cashier->update(10);

Applying Discounts

To apply discounts, use the apply() method, that will calculate the totals in the next summary, and receive as parameter N amount of Discount.

$cashier->apply(
    Discount::proporcional(2)->named('NEW_USERS'),
    Discount::fixed(5)->named('PROMOTIONAL'),
);

Adding Charges

To add charges, use the add() method, it will calculate the totals in the next summary, and received as parameter N amount of Charge.

$cashier->add(
    Charge::proporcional(5)->named('POS'),
    Charge::fixed(10)->named('DELIVERY')
);

Obtaining Individual Totals

To obtain individual values of any price adjuster, you can use the tax() charge(), or discount() functions, all of which receive the code established during creation and return an instance of Adjustment

$cashier->taxes()->locate('IVA');
$cashier->charges()->locate('DELIVERY');
$cashier->discounts()->locate('NEW_USERS');

Obtaining Totals

To obtain the total, you can use individual functions, each of which returns an instance of Brick\Money.

$cashier->quantity();
$cashier->unitPrice();
$cashier->subtotal();
$cashier->taxes()->total();
$cashier->charges()->total();
$cashier->discounts()->total();
$cashier->total();

Configuration

Currently there are 2 built-in ways to handle calculations

Cashiers

  • SimpleCashier: This cashier operates based on the gross price concept. It means that the price provided will be cleaned to get the final price without tax. Adjustments are applied directly to the gross price and taxes are calculated separately after adjustments are applied

  • RegularCashier: This cashier operates based on the concept of unit price + taxes. It means that the configured taxes will be maintained or added to the indicated price, and discounts and charges will be applied to this price with taxes included.

Choose the cashier that best suits your specific business needs and requirements. You can create your own cashier to fit any specific logic or rule related to your business. If you need to create additional cashiers or implement custom logic, you can do so by extending Cashier. This library provides a flexible foundation to handle various pricing scenarios effectively.

Amounts

There are 2 ways to create the amount.

  • Amount with applicable taxes: these amounts are subject to taxes, whether they are inclusive taxes or exclusive taxes and can be defined as follows.

    Amount::taxable(
        Money::of(100, 'PEN'),
        TaxCodes::only(['IGV'])
    );

    The tax codes establish what taxes are applicable for the amount

    Allow All Only Allowed Allow Nothing
    TaxCodes::any() TaxCodes::only(['IGV', ...]) TaxCodes::none()
  • Amounts without applicable taxes: These amounts are not subject to any tax and will not have taxes applied.

    Amount::taxexempt(
        Money::of(10, 'PEN')
    );

    These would be the same as creating a taxable amount but passing TaxCodes::none() as the allowed codes.

Taxes

Taxes can be established in two ways.

  • Inclusive: Taxes included in the unit price, and will be cleared during calculations
    use Vaened\PriceEngine\Adjustments\Tax;
    
    $amount->impose([
      Tax\Inclusive::proporcional(18, 'IGV'); // 18%
      Tax\Inclusive::fixed(2, 'ISC'); // 2 PEN
    ]);
    // or
    $cashier = new RegularCashier(
      ...
      taxes : Taxes::from([
        Tax\Inclusive::proporcional(18, 'IGV'); // 18%
        Tax\Inclusive::fixed(2, 'ISC'); // 2 PEN
      ])
    );
  • Exclusive: Taxes not included in the unit price, and will be added for the final calculations.
    use Vaened\PriceEngine\Adjustments\Tax;
    
    $amount->impose([
      Tax\Exclusive::proporcional(18, 'IGV'); // 18%
      Tax\Exclusive::fixed(2, 'ISC'); // 2 PEN
    ]);
    // or
    $cashier = new RegularCashier(
      ...
      taxes : Taxes::from([
        Tax\Exclusive::proporcional(18, 'IGV'); // 18%
        Tax\Exclusive::fixed(2, 'ISC'); // 2 PEN
      ])
    );

License

This library is licensed under the MIT License. For more information, please see the license file.