PHPackages                             from-developers-for-developers/relmon-php-sdk - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [API Development](/categories/api)
4. /
5. from-developers-for-developers/relmon-php-sdk

ActiveSdk[API Development](/categories/api)

from-developers-for-developers/relmon-php-sdk
=============================================

Official PHP SDK for RelMon protocol

v1.0.1-beta(1mo ago)02[2 issues](https://github.com/from-developers-for-developers/relmon-php-sdk/issues)MITPHPPHP &gt;=8.0CI passing

Since May 31Pushed 1mo agoCompare

[ Source](https://github.com/from-developers-for-developers/relmon-php-sdk)[ Packagist](https://packagist.org/packages/from-developers-for-developers/relmon-php-sdk)[ RSS](/packages/from-developers-for-developers-relmon-php-sdk/feed)WikiDiscussions main Synced 1w ago

READMEChangelogDependencies (5)Versions (3)Used By (0)

RelMon PHP SDK
==============

[](#relmon-php-sdk)

Official PHP SDK for [RelMon protocol](https://github.com/from-developers-for-developers/relmon-protocol).

[![Tests](https://github.com/from-developers-for-developers/relmon-php-sdk/actions/workflows/tests.yml/badge.svg)](https://github.com/from-developers-for-developers/relmon-php-sdk/actions/workflows/tests.yml/badge.svg)[![codecov](https://camo.githubusercontent.com/6638bbb08032dbcf7ba15178baf702146b820640b3a213549db314fc6aefbef9/68747470733a2f2f636f6465636f762e696f2f67682f66726f6d2d646576656c6f706572732d666f722d646576656c6f706572732f72656c6d6f6e2d7068702d73646b2f6272616e63682f6d61696e2f67726170682f62616467652e737667)](https://codecov.io/gh/from-developers-for-developers/relmon-php-sdk)

Requirements
------------

[](#requirements)

- PHP &gt;= 8.0
- `xml`, `mbstring` extensions

Installation
------------

[](#installation)

```
composer require from-developers-for-developers/relmon-php-sdk
```

Usage
-----

[](#usage)

### Facade

[](#facade)

Use `RelMonFacade` when you want the SDK to wire the default parser and service stack.

```
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$relmon = RelMonFacade::build([
    'protocol' => 'relmon@1.0.0/3',
    'net' => '100.00',
    'gross' => '121.00',
    'tax' => '21.00',
    'taxRate' => '21.00',
    'unit' => 'EUR',
    'precision' => 2,
]);

echo $relmon->getGross();          // 12100
echo $relmon->getGrossFormatted(); // 121.00
```

The second argument can be used to force a parser instead of auto-detection:

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$relmon = RelMonFacade::build($jsonString, Format::JSON_STRING);
```

Custom format parsers can be passed as the third argument:

```
$relmon = RelMonFacade::build($input, CsvRelMonParser::class, [
    new CsvRelMonParser(),
]);
```

Default values for optional fields can be passed with the `defaults` named argument:

```
use FromDevelopersForDevelopers\RelMon\Enum\RoundingApplication;
use FromDevelopersForDevelopers\RelMon\Enum\RoundingMode;
use FromDevelopersForDevelopers\RelMon\Enum\Scope;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$relmon = RelMonFacade::build(
    [
        'protocol' => 'relmon@1.0.0/1',
        'net' => '100.00',
    ],
    defaults: [
        'unit' => 'EUR',
        'scope' => Scope::ROOT,
        'roundingMode' => RoundingMode::HALF_EVEN,
        'roundingApplication' => RoundingApplication::TAX,
        'taxRate' => '21.00',
    ],
);
```

### Services

[](#services)

Use `RelMonService` directly when your application manages dependencies itself.

```
use FromDevelopersForDevelopers\RelMon\FormatParser\FormatParserFactory;
use FromDevelopersForDevelopers\RelMon\FormatParser\FormatParserLocator;
use FromDevelopersForDevelopers\RelMon\FormatParser\JsonArrayParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\JsonStringParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\UriJsonParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\UriMinimalisticParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\UriXmlParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\XmlDomDocumentParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\XmlSimpleXmlParser;
use FromDevelopersForDevelopers\RelMon\FormatParser\XmlStringParser;
use FromDevelopersForDevelopers\RelMon\Service\DerivationService;
use FromDevelopersForDevelopers\RelMon\Service\MinorsService;
use FromDevelopersForDevelopers\RelMon\Service\RelMonService;
use FromDevelopersForDevelopers\RelMon\Service\ValidationService;

$parserLocator = new FormatParserLocator([
    new JsonArrayParser(),
    new JsonStringParser(),
    new XmlSimpleXmlParser(),
    new XmlDomDocumentParser(),
    new XmlStringParser(),
    new UriJsonParser(),
    new UriXmlParser(),
    new UriMinimalisticParser(),
]);

$service = new RelMonService(
    new FormatParserFactory($parserLocator),
    new ValidationService(),
    new MinorsService(),
    new DerivationService(),
);

$relmon = $service->build($input);
```

`RelMonService::build()` also accepts defaults as its third argument:

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;

$relmon = $service->build($input, Format::AUTO, [
    'unit' => 'EUR',
    'taxRate' => '21.00',
]);
```

Supported Formats
-----------------

[](#supported-formats)

`Format::AUTO` detects:

- PHP array: `Format::JSON_ARRAY`
- JSON string: `Format::JSON_STRING`
- XML string: `Format::XML_STRING`
- `SimpleXMLElement`: `Format::XML_SIMPLE_XML`
- `DOMDocument`: `Format::XML_DOM_DOCUMENT`
- `relmon-json://...`: `Format::URI_JSON`
- `relmon-xml://...`: `Format::URI_XML`
- `relmon-min://...`: `Format::URI_MINIMALISTIC`

JSON and XML inputs support normal field names and compact aliases. URI JSON and URI XML contain a base64-encoded JSON/XML payload. URI XML also accepts URL-safe base64 without padding.

### JSON Array, Normal

[](#json-array-normal)

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$input = [
    'protocol' => 'relmon@1.0.0/3',
    'net' => '100.00',
    'gross' => '121.00',
    'tax' => '21.00',
    'taxRate' => '21.00',
    'unit' => 'EUR',
    'precision' => 2,
    'scope' => 'r',
    'rounding' => [
        'mode' => 'heven',
        'application' => 'tax',
    ],
    'components' => [
        [
            'net' => '100.00',
            'gross' => '121.00',
            'tax' => '21.00',
            'taxRate' => '21.00',
            'comment' => 'Test component',
        ],
    ],
];

$relmon = RelMonFacade::build($input, Format::JSON_ARRAY);
```

The same normal or compact JSON payload can be passed as a string with `Format::JSON_STRING`.

### JSON String, Compact

[](#json-string-compact)

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$input = json_encode([
    'p' => 'relmon@1.0.0/3:c',
    'n' => '100.00',
    'g' => '121.00',
    't' => '21.00',
    'tr' => '21.00',
    'u' => 'EUR',
    'pr' => 2,
    's' => 'c',
    'r' => [
        'm' => 'heven',
        'a' => 'tax',
    ],
    'cs' => [
        [
            'n' => '100.00',
            'g' => '121.00',
            't' => '21.00',
            'tr' => '21.00',
            'c' => 'Test component',
        ],
    ],
]);

$relmon = RelMonFacade::build($input, Format::JSON_STRING);
```

### XML String, Normal

[](#xml-string-normal)

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$input =  'relmon@1.0.0/3:c',
    'n' => '100.00',
    'g' => '121.00',
    't' => '21.00',
    'tr' => '21.00',
]));

$input = 'relmon-json://' . $payload;
$relmon = RelMonFacade::build($input, Format::URI_JSON);
```

### URI XML

[](#uri-xml)

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$payload = base64_encode('relmon@1.0.0/3:c100.00121.0021.00');

$input = 'relmon-xml://' . $payload;
$relmon = RelMonFacade::build($input, Format::URI_XML);
```

### Minimalistic URI

[](#minimalistic-uri)

Minimalistic URI format has exactly four semicolon-separated values:

```
use FromDevelopersForDevelopers\RelMon\Enum\Format;
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$input = 'relmon-min://1.0.0/3;100.00;121.00;21.00';
$relmon = RelMonFacade::build($input, Format::URI_MINIMALISTIC);
```

This maps to:

- protocol identifier: `relmon@1.0.0/3`
- net: `100.00`
- gross: `121.00`
- tax: `21.00`

Field Aliases
-------------

[](#field-aliases)

NormalCompact`protocol``p``net``n``gross``g``tax``t``taxRate``tr``unit``u``precision``pr``scope``s``rounding``r``rounding.mode``r.m``rounding.application``r.a``components``cs``components[].comment``cs[].c`Supported values:

- scope: `r` for root, `c` for component
- rounding mode: `haway`, `hzero`, `heven`, `up`, `down`
- rounding application: `tax`, `total`
- protocol modes: `c` for compact, `m` for minors, for example `relmon@1.0.0/3:c.m`

In normal mode, `net`, `gross`, and `tax` values must be decimal strings such as `"100.00"`. In minors mode (`:m`), they must be integers such as `10000`.

Default Values
--------------

[](#default-values)

Defaults are applied after parsing and before validation. They reduce repeated payload data without changing validation behavior: if a default value is invalid, validation still fails; if a determinism level requires `taxRate`, a configured default `taxRate` is validated as part of the parsed data.

Supported default keys:

KeyApplies to`unit`Root object when omitted.`scope`Root object when omitted.`roundingMode`Root object when omitted.`roundingApplication`Root object when omitted.`taxRate`Root object and components when omitted.Explicit input values always take precedence over defaults.

Custom Formats
--------------

[](#custom-formats)

Custom formats can be supported by implementing `FormatParserInterface` and passing the parser to `RelMonFacade::build()`. The parser converts your input into a `RelMonDto`; the SDK then handles validation, minors conversion, and derivation normally.

```
use FromDevelopersForDevelopers\RelMon\Dto\RelMonDto;
use FromDevelopersForDevelopers\RelMon\FormatParser\FormatParserInterface;

final class CsvRelMonParser implements FormatParserInterface
{
    public function parse(mixed $input): RelMonDto
    {
        [$protocol, $net, $gross, $tax, $taxRate] = str_getcsv($input);

        return new RelMonDto(
            protocolIdentifier: $protocol,
            net: $net,
            gross: $gross,
            tax: $tax,
            taxRate: $taxRate,
        );
    }
}
```

Pass the parser instance as the third argument and its class name as the explicit format:

```
use FromDevelopersForDevelopers\RelMon\RelMonFacade;

$relmon = RelMonFacade::build(
    'relmon@1.0.0/3,100.00,121.00,21.00,21.00',
    CsvRelMonParser::class,
    [new CsvRelMonParser()],
);
```

RelMonObject Public Methods
---------------------------

[](#relmonobject-public-methods)

`RelMonObject` stores monetary values as integer minors and exposes formatted helpers for display.

MethodReturnDescription`getNet()``int`Net amount in minors.`getGross()``int`Gross amount in minors.`getTax()``int`Tax amount in minors.`getTaxRate()``?int`Tax rate converted using tax rate precision.`getUnit()``?string`Unit/currency, for example `EUR`.`getPrecision()``?int`Monetary precision used for net/gross/tax values.`getTaxRatePrecision()``?int`Precision used for tax rate values.`getScope()``string``r` or `c`.`getRoundingMode()``string`Rounding mode code.`getRoundingApplication()``string`Rounding application code.`getComponents()``MonetaryComponent[]`Parsed and derived component values.`getNetFormatted(string $decimalSeparator = '.', string $thousandsSeparator = '')``string`Net formatted using object precision.`getGrossFormatted(string $decimalSeparator = '.', string $thousandsSeparator = '')``string`Gross formatted using object precision.`getTaxFormatted(string $decimalSeparator = '.', string $thousandsSeparator = '')``string`Tax formatted using object precision.`getTaxRateFormatted(string $decimalSeparator = '.', string $thousandsSeparator = '')``?string`Tax rate formatted using tax rate precision.Example:

```
$relmon = RelMonFacade::build([
    'protocol' => 'relmon@1.0.0/3',
    'net' => '1234.56',
    'gross' => '1493.81',
    'tax' => '259.25',
    'taxRate' => '21.00',
]);

echo $relmon->getNet();                 // 123456
echo $relmon->getNetFormatted();        // 1234.56
echo $relmon->getNetFormatted(',', ' '); // 1 234,56
echo $relmon->getTaxRateFormatted();    // 21.00
```

Features
--------

[](#features)

- Support for PHP 8.0, 8.1, 8.2, 8.3, 8.4.
- Determinism Levels 1, 2, and 3 (DL1, DL2, DL3).
- Multiple input formats: JSON, XML, URI.
- Precise rounding and tax derivation.

License
-------

[](#license)

MIT

###  Health Score

32

—

LowBetter than 69% of packages

Maintenance89

Actively maintained with recent releases

Popularity2

Limited adoption so far

Community6

Small or concentrated contributor base

Maturity26

Early-stage or recently created project

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~0 days

Total

2

Last Release

54d ago

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/959271?v=4)[Dmitry Abrosimov](/maintainers/dmitrya2e)[@dmitrya2e](https://github.com/dmitrya2e)

---

Top Contributors

[![dmitrya2e](https://avatars.githubusercontent.com/u/959271?v=4)](https://github.com/dmitrya2e "dmitrya2e (35 commits)")

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/from-developers-for-developers-relmon-php-sdk/health.svg)

```
[![Health](https://phpackages.com/badges/from-developers-for-developers-relmon-php-sdk/health.svg)](https://phpackages.com/packages/from-developers-for-developers-relmon-php-sdk)
```

###  Alternatives

[symfony/symfony

The Symfony PHP framework

31.4k87.2M2.2k](/packages/symfony-symfony)[statamic/cms

The Statamic CMS Core Package

4.8k3.6M1.0k](/packages/statamic-cms)[matomo/matomo

Matomo is the leading Free/Libre open analytics platform

21.7k38.9k](/packages/matomo-matomo)[craftcms/cms

Craft CMS

3.6k3.6M3.2k](/packages/craftcms-cms)[api-platform/core

Build a fully-featured hypermedia or GraphQL API in minutes!

2.6k51.2M353](/packages/api-platform-core)[drupal/core

Drupal is an open source content management platform powering millions of websites and applications.

19566.0M1.8k](/packages/drupal-core)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
