PRRO.cloud

Контакти

Відповідаємо в робочі дні.

Кабінет

SDK для Go і PHP

Офіційні клієнтські бібліотеки PRRO.cloud. Обидві звірені з контрактом OpenAPI тестами, не тягнуть сторонніх залежностей і беруть на себе те, що в кожній інтеграції пишуть заново: ключі ідемпотентності, повтори при збоях мережі, очікування відповіді ДПС і перевірку підпису вебхуків.

GoPHP

Що вміють обидві бібліотеки

  • Безпечні повтори.

    Ключ ідемпотентності генерується автоматично, мережеві збої та відповіді 5xx повторюються з експоненційною затримкою — той самий чек двічі не пробʼється.

  • Синхронно або асинхронно.

    Фіскальний номер зазвичай приходить одразу у відповіді; якщо ДПС не відповіла за 30 секунд, wait дочекається результату завдання.

  • Типізовані помилки.

    Відмову ДПС видно як структуру з кодом і поясненням, яку можна обробити в коді, а не як рядок у журналі.

  • Вебхуки.

    Перевірка підпису HMAC-SHA256 на сирому тілі запиту, типізовані події, зокрема receipt.registered з повним вмістом чека, і готовий приймач.

Go

Лише стандартна бібліотека Go, потрібен Go 1.27 або новіший. Підпакет webhook — перевірка підпису, типізовані події й готовий http.Handler.

GitHub · pkg.go.dev · повний приклад

Встановлення

go get github.com/prro-cloud/prro-go

Перший чек

c := prro.NewClient(os.Getenv("PRRO_TOKEN"))

task, err := c.Receipts.Create(ctx, &prro.SettlementReceipt{
	CashRegisterID: registerID, // з c.CashRegisters.List
	Type:           prro.ReceiptSale,
	Items: []prro.ReceiptItem{
		{Name: "Кава американо", Quantity: "1", Price: "65.00", TaxLetters: "А"},
	},
	Payments: []prro.Payment{{Type: prro.PaymentCard, Sum: "65.00"}},
}, prro.WithIdempotencyKey("order-10412"))
if err != nil {
	return err
}
if !task.Done() { // ДПС не відповіла за 30 секунд
	if task, err = c.Tasks.Wait(ctx, task.ID); err != nil {
		return err
	}
}

r := task.Result.Receipt
fmt.Println(r.FiscalNumber) // фіскальний номер від ДПС
fmt.Println(r.ReceiptURL)   // чек для покупця: https://r.prro.cloud/…

Приймач вебхуків

import "github.com/prro-cloud/prro-go/webhook"

secret := os.Getenv("PRRO_WEBHOOK_SECRET")

http.Handle("POST /prro-hook", webhook.Handler(secret, func(ctx context.Context, e *webhook.Event) error {
	if e.Type == prro.EventTaskCompleted {
		d, err := e.Task()
		if err != nil {
			return err
		}
		return markOrder(ctx, d.TaskID, d.Status)
	}
	return nil
}))

PHP

PHP 8.2 або новіший, лише ext-curl і ext-json — тож вбудовується у WordPress-плагін без конфліктів із чужими версіями Guzzle. Готові приймачі вебхуків для чистого PHP, PSR-7, Laravel, Symfony і WordPress.

GitHub · Packagist · повний приклад

Встановлення

composer require prro-cloud/prro-php

Перший чек

use PrroCloud\Prro\Client;
use PrroCloud\Prro\Enum\{PaymentType, ReceiptType};
use PrroCloud\Prro\Input\{Payment, ReceiptItem, SettlementReceipt};

$client = new Client(token: getenv('PRRO_TOKEN'));

$task = $client->receipts->create(new SettlementReceipt(
    cashRegisterId: $registerId, // з $client->cashRegisters->list()
    type: ReceiptType::Sale,
    items: [new ReceiptItem(name: 'Кава американо', quantity: '1', price: '65.00', taxLetters: 'А')],
    payments: [new Payment(type: PaymentType::Card, sum: '65.00')],
), idempotencyKey: "order-{$order->id}");

if (!$task->isDone()) { // ДПС не відповіла за 30 секунд
    $task = $client->tasks->wait($task->id);
}

$r = $task->result->receipt;
echo $r->fiscalNumber; // фіскальний номер від ДПС
echo $r->receiptUrl;   // чек для покупця: https://r.prro.cloud/…

Приймач вебхуків

use PrroCloud\Prro\Enum\WebhookEvent;
use PrroCloud\Prro\Webhook\{Event, Webhook};

Webhook::handle(getenv('PRRO_WEBHOOK_SECRET'), function (Event $e): void {
    if ($e->eventType() === WebhookEvent::TaskCompleted) {
        $d = $e->task();
        markOrder($d->taskId, $d->status);
    }
});