Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/kubinyete/edi-php
A standard library for declaring EDI parsers
https://github.com/kubinyete/edi-php
edi library parsing php php8
Last synced: 3 days ago
JSON representation
A standard library for declaring EDI parsers
- Host: GitHub
- URL: https://github.com/kubinyete/edi-php
- Owner: Kubinyete
- Created: 2023-10-05T13:53:30.000Z (about 1 year ago)
- Default Branch: master
- Last Pushed: 2024-05-03T13:01:11.000Z (7 months ago)
- Last Synced: 2024-05-04T05:09:46.550Z (7 months ago)
- Topics: edi, library, parsing, php, php8
- Language: PHP
- Homepage:
- Size: 34.2 KB
- Stars: 0
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
Awesome Lists containing this project
README
# EDI PHP
A standard library for declaring EDI parsers, because that's not a fun thing to do.
### Why should I use it?
This is a very common use-case for many services that output data using a defined text-file layout, for example,
many services (Ex: Payment providers) output some sort of layout file that follows a simplified column separated values
that has a fixed size set.For example, the following line (25 bytes):
`120240503Hello World `
Can be interpreted as
| Range | Size | Column | Value
| ------ | ---- | ---------- | -----
| 0 - 0 | 1 | Reg. type | 1
| 1 - 8 | 8 | Date | 2024-05-03
| 9 - 25 | 16 | Message | Hello World### How it works
To provide a better developer experience while creating these parsers, this library provides some useful property
attributes and a base class for declaring these types of data.For example, to declare the previous line, we can declare it in code as the following:
```php
final class ExampleLayoutType extends Registry {
#[Number(1)]
public int $type;#[Date(8, format: '!Ymd')]
public DateTimeInterface $type;#[Text(16)]
public string $message;
}// We can parse the data directly
$example = ExampleLayoutType::from('120240503Hello World ')// Or we can hydrate it
$example = new ExampleLayoutType();
$example->hydrate('120240503Hello World ');```
### Declaring dynamic parsers
Using our built in line parser, we can create dynamically parsed (by line) types, with the power of generators, these types are parsed on demand:
```php
// Using a standard line parser, iterates over each line
class EDIParser extends LineParser
{
// Ran on each line iteration
protected function parse(LineContext $ctx): ?Registry
{
[$contents, $number] = $ctx->unwrap();
// For this EDI file, we can deduce which type it is based on
// the first 2 letters provided each line.
$code = substr($contents, 0, 2);try {
return match ($code) {
EDIRegistry::TYPE_HEADER_START => EDIHeader::from($contents),
EDIRegistry::TYPE_TRANSACTION_BATCH_START => EDITransactionBatch::from($contents),
EDIRegistry::TYPE_SALE_RECEIPT => EDISaleReceipt::from($contents),
// Our LineContext can provide a more verbose message to inform
// where in our data the error ocurred.
default => $ctx->raise("Cannot parse EDI of type '$code'", 0),
};
} catch (FieldException $e) {
$ctx->raise($e->getMessage(), $e->getCursor());
}
}
}// Using our parser directly
// Reading directly from stdin
$buffer = Stream::file('php://stdin', 'rb');
$parser = EDIParser::loadFromStream($buffer);foreach ($parser as $registry) {
/** @var Registry $registry */
// We have direct access to our parsed objects on demand
dump($registry);
}
```### Understanding parsing errors
> This feature is work-in-progress, there are a some things we can do to make it better
We enable out-of-the-box support for friendly contextual messages on any errors that ocurred.
```js
PHP Fatal error: Uncaught Kubinyete\Edi\Parser\Exception\ParseException: Line 1: Failed to parse field '202d1001025840' as a date with format 'YmdHis'
Contents: "A00003.1202d1001025840000442ADIQ SOLUCOES PAGAMENTOS S.A 0040002783189N000001"
--------^
in /home/vitorkubinyete/code/edi-php/src/Parser/LineContext.php:38