Taxes
Summary
Taxes are an optional extension of PriceSpecification that allows automatic calculation and display of price breakdowns with tax information. This feature enables businesses to show transparent pricing to their customers, complying with local tax regulations.
When taxes are configured, the system calculates and returns a detailed breakdown including base price, individual tax amounts, and total price.
Tax Specification
A tax is defined with the following attributes:
| Name | Type | Description |
|---|---|---|
| name | String | A user-friendly name for the tax (e.g., "IVA", "Municipal fee") |
| type | PERCENTAGE | FIXED | The type of tax calculation |
| value | String | The tax value: percentage (e.g., "21") or fixed amount ("1.00") |
| inclusion | INCLUDED_IN_PRICE | NOT_INCLUDED_IN_PRICE | Whether the tax is included in the base price or added on top |
Tax Types
Percentage
A percentage-based tax is calculated as a proportion of the base price. This is the most common type for taxes like VAT/IVA.
{
name: "IVA",
type: "PERCENTAGE",
value: "21", // 21%
inclusion: "INCLUDED_IN_PRICE" // Tax is included in the displayed price
}
Fixed
A fixed tax adds a constant amount regardless of the base price. This is useful for municipal fees, service charges, or other flat-rate taxes.
{
name: "Municipal fee",
type: "FIXED",
value: "1.00", // 1.00 EUR
inclusion: "NOT_INCLUDED_IN_PRICE" // Tax is added on top of the base price
}
Tax Inclusion Mode
The inclusion field determines how the tax relates to the base price:
INCLUDED_IN_PRICE- The tax is already included in the displayed price. The system will calculate and show the breakdown (base price without tax + tax amount = total).NOT_INCLUDED_IN_PRICE- The tax is added on top of the base price. The total will be higher than the displayed base price.
Configuration in PriceSpecification
Taxes are configured at the PriceSpecification level through an optional taxes array. This applies to both FixedPriceSpecification and TieredPriceSpecification.
Fixed Price with Taxes
{
type: "FIXED",
amount: "40.00",
taxes: [
{
name: "IVA",
type: "PERCENTAGE",
value: "21",
inclusion: "INCLUDED_IN_PRICE"
}
]
}
Tiered Price with Taxes
For tiered pricing, taxes are shared across all tiers. The tax configuration applies to whichever tier is selected based on the booking duration.
{
type: "TIERED",
tiers: [
{ duration: "PT1H", amount: "30.00" },
{ duration: "PT2H", amount: "50.00" }
],
taxes: [
{
name: "IVA",
type: "PERCENTAGE",
value: "21",
inclusion: "INCLUDED_IN_PRICE"
}
]
}
Multiple Taxes
A price can have multiple taxes configured. They are calculated independently and then summed.
{
type: "FIXED",
amount: "100.00",
taxes: [
{
name: "IVA",
type: "PERCENTAGE",
value: "21",
inclusion: "NOT_INCLUDED_IN_PRICE"
},
{
name: "Municipal fee",
type: "FIXED",
value: "1.00",
inclusion: "NOT_INCLUDED_IN_PRICE"
}
]
}
Usage Examples
Example 1: Padel Class with VAT Included
A padel class costs 40€/hour with 21% VAT included in the price.
Configuration:
{
type: "TIERED",
tiers: [
{ duration: "PT1H", amount: "40.00" }
],
taxes: [
{
name: "IVA",
type: "PERCENTAGE",
value: "21",
inclusion: "INCLUDED_IN_PRICE"
}
]
}
Resulting breakdown for a 1-hour booking:
| Concept | Amount |
|---|---|
| Base price | 33.06 € |
| IVA (21%) | 6.94 € |
| Total | 40.00 € |
Example 2: Waste Collection with Municipal Fee
A waste collection service costs 100€ fixed price, plus a 1€ municipal fee per service.
Configuration:
{
type: "FIXED",
amount: "100.00",
taxes: [
{
name: "Municipal fee",
type: "FIXED",
value: "1.00",
inclusion: "NOT_INCLUDED_IN_PRICE"
}
]
}
Resulting breakdown:
| Concept | Amount |
|---|---|
| Base price | 100.00 € |
| Municipal fee | 1.00 € |
| Total | 101.00 € |
Example 3: Service with VAT Excluded and Fixed Fee
A consultation service at 80€ plus 21% VAT (excluded) and a 2€ booking fee.
Configuration:
{
type: "FIXED",
amount: "80.00",
taxes: [
{
name: "IVA",
type: "PERCENTAGE",
value: "21",
inclusion: "NOT_INCLUDED_IN_PRICE"
},
{
name: "Booking fee",
type: "FIXED",
value: "2.00",
inclusion: "NOT_INCLUDED_IN_PRICE"
}
]
}
Resulting breakdown:
| Concept | Amount |
|---|---|
| Base price | 80.00 € |
| IVA (21%) | 16.80 € |
| Booking fee | 2.00 € |
| Total | 98.80 € |
Price Calculation
Formulas
Percentage Tax (NOT_INCLUDED_IN_PRICE)
When the tax is not included in the base price:
taxAmount = basePrice × (rate / 100)
total = basePrice + taxAmount
Percentage Tax (INCLUDED_IN_PRICE)
When the tax is already included in the displayed price:
basePrice = displayedPrice / (1 + rate / 100)
taxAmount = displayedPrice - basePrice
total = displayedPrice
Fixed Tax (NOT_INCLUDED_IN_PRICE)
total = basePrice + fixedAmount
Fixed Tax (INCLUDED_IN_PRICE)
basePrice = displayedPrice - fixedAmount
total = displayedPrice
Multiple Taxes
When multiple taxes are configured:
- Calculate each tax independently based on the base price
- Round each tax amount individually to 2 decimal places
- Sum all tax amounts to get total taxes
- Add total taxes to base price to get final total
Rounding Rules
Following standard Spanish accounting practices:
- All monetary amounts are rounded to 2 decimal places
- Rounding is applied per tax line (each tax is rounded individually before summing)
- Standard mathematical rounding (0.5 rounds up)
API Response: Price Breakdown
When taxes are configured, the API returns a detailed price breakdown instead of a simple amount.
PriceBreakdown Structure
| Name | Type | Description |
|---|---|---|
| basePrice | MonetaryAmount | The price before taxes |
| taxes | Array<TaxLineItem> | Individual tax calculations |
| totalPrice | MonetaryAmount | The final price including all taxes |
TaxLineItem Structure
| Name | Type | Description |
|---|---|---|
| name | String | Name of the tax |
| type | String | "PERCENTAGE" or "FIXED" |
| rate | String | The configured rate/amount |
| amount | MonetaryAmount | The calculated tax amount |
| inclusion | String | "INCLUDED_IN_PRICE" or "NOT_INCLUDED_IN_PRICE" |
Example API Response
{
"price": {
"basePrice": {
"amount": "33.06",
"currency": "EUR"
},
"taxes": [
{
"name": "IVA",
"type": "PERCENTAGE",
"rate": "21",
"amount": {
"amount": "6.94",
"currency": "EUR"
},
"inclusion": "INCLUDED_IN_PRICE"
}
],
"totalPrice": {
"amount": "40.00",
"currency": "EUR"
}
}
}
Backward Compatibility
When no taxes are configured, the response maintains the existing simple format:
{
"price": {
"amount": "40.00",
"currency": "EUR"
}
}
Taxes in Overrides
Each override in a pricing policy can define its own taxes, independent of the default price specification taxes.
This allows for scenarios like:
- Different tax rates for different time periods (e.g., reduced VAT on weekends)
- Special fees that only apply during certain schedules
- Tax-exempt periods
Example: Weekend with Different Tax
{
"priceSpecification": {
"type": "FIXED",
"amount": "40.00",
"taxes": [
{ "name": "IVA", "type": "PERCENTAGE", "value": "21", "inclusion": "INCLUDED_IN_PRICE" }
]
},
"overrides": [
{
"name": "Weekend rate",
"rules": {
"schedule": "RRULE:FREQ=WEEKLY;BYDAY=SA,SU"
},
"priceSpecification": {
"type": "FIXED",
"amount": "50.00",
"taxes": [
{ "name": "IVA", "type": "PERCENTAGE", "value": "10", "inclusion": "INCLUDED_IN_PRICE" }
]
}
}
]
}
Default Behavior
- If no
taxesarray is provided, the price is treated as having no taxes - The
taxesarray can be empty ([]), which is equivalent to no taxes - When taxes are not configured, the API response uses the simple price format for backward compatibility