@hlf-core/coin-chaincode
Это исполняющая половина системы токенов — то, что происходит в ledger, когда приходит команда
из @hlf-core/coin. Пакет берёт модели и команды из coin и превращает их в реальные
изменения состояния, с валидацией, событиями и осмысленными ошибками.
Центральный класс — CoinManager, наследник EntityManagerImpl. Он отвечает и
за сами монеты (создание, чтение, сохранение, удаление), и за операции над балансами: emit и
emitHeld, burn и burnHeld, hold и unhold, nullify, и целое семейство переводов —
transfer, transferToHeld, transferFromHeld, transferFromToHeld. Доступ к счетам идёт через
accountGet, accountSet и accountList. Удаление монеты, к слову, снимает заодно и все её счета
по префиксу — за этим стоит обход, о стоимости которого скажу ниже.
Отдельно стоит CoinAccountManager — менеджер счетов, и у него есть одна характерная повадка:
save удаляет счёт, как только тот оказывается пуст. То есть нулевые счета в состоянии не хранятся
вовсе, а accountGet для адреса без средств возвращает не null, а новый пустой счёт. Это снимает
с вызывающего кода лишние проверки на существование.
Поверх менеджеров лежит CoinService — фасад бизнес-логики. Его методы принимают holder, DTO и
флаг рассылки события, валидируют вход, выполняют операцию и диспетчеризуют событие. Обычно именно
с ним и работает обработчик команды.
const manager = new CoinManager(logger, stub);
const coin = manager.create('MYCOIN', 18, 'owner-uid');
await manager.emit(coin, {ownerUid: 'user-uid', id: 'OWNER'}, '1000');
await service.transfer(holder, {coinUid: coin.uid, object: {...}, target: {...}, value: '100'}, true);
:::warning О стоимости и ответственности
Здесь стоит быть внимательным. Один transfer выполняет несколько операций со state, а
accountList и удаление монеты обходят все счета в одной транзакции — стоимость растёт линейно и
рано или поздно упирается в лимиты Fabric. И ещё одно, о чём нельзя забывать: права доступа пакет
не проверяет, это сознательно оставлено на вызывающий код. hlf-core даёт механику токенов, а
решение «кому можно» остаётся за прикладной логикой.
:::