Skip to content

skiddgoddamn/MoyNalog

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

5 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

moynalog-client

Java-библиотека для работы с API сервиса «Мой налог» (ФНС России).
Позволяет программно регистрировать доходы, получать чеки и выставлять счета для самозанятых.


Возможности

  • Аутентификация по логину и паролю с автоматическим retry
  • Автоматическое обновление токена (без повторного ввода пароля)
  • Отправка чека: синхронно и асинхронно
  • Выставление счетов с реквизитами банковского счёта
  • Поддержка прокси (HTTP/HTTPS, с аутентификацией и без)
  • Настраиваемый таймаут запросов
  • Потокобезопасная работа (ReadWriteLock на обновление токена)
  • Spring Boot Starter — достаточно двух строк в application.properties
  • Работает и без Spring — как обычная Java-библиотека

Подключение

Установите библиотеку в локальный Maven-репозиторий:

mvn install

Добавьте зависимость в проект-потребитель:

<dependency>
    <groupId>io.github.skiddgoddamn</groupId>
    <artifactId>moynalog-client</artifactId>
    <version>1.1.3</version>
</dependency>

Использование со Spring Boot

Добавьте учётные данные в application.properties:

moy-nalog.username=ваш_логин
moy-nalog.password=ваш_пароль

Библиотека автоматически создаст и зарегистрирует бин MoyNalogClient.
Аутентификация выполняется при старте приложения — если учётные данные неверны, приложение не запустится.

Используйте клиент через инъекцию зависимостей:

@Service
public class TaxService {

    private final MoyNalogClient moyNalogClient;

    public TaxService(MoyNalogClient moyNalogClient) {
        this.moyNalogClient = moyNalogClient;
    }

    public Receipt registerIncome() {
        return moyNalogClient.addIncome(List.of(
            new IncomeItem("Консультация", 1, 5000.0),
            new IncomeItem("Разработка", 3, 10000.0)
        ));
    }
}

Дополнительные настройки

Свойство По умолчанию Описание
moy-nalog.username Логин (обязательно)
moy-nalog.password Пароль (обязательно)
moy-nalog.zone-offset Z (UTC) Часовой пояс чека, например +03:00
moy-nalog.api-path https://lknpd.nalog.ru/api/v1 Базовый URL API
moy-nalog.prefix (пусто) Префикс генерируемого ID устройства
moy-nalog.request-timeout 30 Таймаут ожидания ответа от сервера (секунды)
moy-nalog.proxy.host (не задан) Хост прокси-сервера
moy-nalog.proxy.port 8080 Порт прокси-сервера
moy-nalog.proxy.username (не задан) Логин для аутентификации на прокси
moy-nalog.proxy.password (не задан) Пароль для аутентификации на прокси

Использование без Spring

// С настройками по умолчанию
MoyNalogClient client = new MoyNalogClient();
client.init("ваш_логин", "ваш_пароль");

// Или с кастомной конфигурацией
MoyNalogClientConfig config = new MoyNalogClientConfig();
config.setZoneOffset("+03:00");
config.setRequestTimeout(60); // секунды

MoyNalogClient client = new MoyNalogClient(config);
AuthenticationDTO.Profile profile = client.init("ваш_логин", "ваш_пароль");

System.out.println("Авторизован: " + profile.getInn());

Прокси

Через application.properties (Spring Boot)

moy-nalog.proxy.host=proxy.example.com
moy-nalog.proxy.port=8080
# Если прокси требует аутентификации:
moy-nalog.proxy.username=proxyuser
moy-nalog.proxy.password=proxypass

Без Spring

MoyNalogClientConfig config = new MoyNalogClientConfig();
config.setProxyHost("proxy.example.com");
config.setProxyPort(8080);
// Если прокси требует аутентификации:
config.setProxyUsername("proxyuser");
config.setProxyPassword("proxypass");

MoyNalogClient client = new MoyNalogClient(config);
client.init("ваш_логин", "ваш_пароль");

Отправка чека

Синхронно

List<IncomeItem> services = List.of(
    new IncomeItem("Консультация", 1, 3000.0),   // 1 × 3000 = 3000 руб.
    new IncomeItem("Обучение",     2, 1500.0)    // 2 × 1500 = 3000 руб.
);

Receipt receipt = client.addIncome(services);

System.out.println("UUID:      " + receipt.uuid());
System.out.println("JSON-чек:  " + receipt.jsonUrl());
System.out.println("Для печати:" + receipt.printUrl());

Асинхронно

CompletableFuture<Receipt> future = client.addIncomeAsync(services);

future.thenAccept(receipt -> System.out.println("Чек зарегистрирован: " + receipt.uuid()))
      .exceptionally(ex -> { System.err.println("Ошибка: " + ex.getMessage()); return null; });

Выставление счёта

1. Получить сохранённые реквизиты

// true — только избранные реквизиты, false — все
List<PaymentType> paymentTypes = client.getPaymentTypes(true);
PaymentType account = paymentTypes.get(0);

2. Выставить счёт

List<IncomeItem> services = List.of(
    new IncomeItem("Разработка сайта", 1, 50000.0)
);

Invoice invoice = client.createInvoice(
    account,                          // реквизиты оплаты
    "ИП Иванов Иван Иванович",        // наименование плательщика
    "123456789012",                   // ИНН плательщика
    ClientType.FROM_LEGAL_ENTITY,     // тип плательщика
    services
);

System.out.println("Статус:        " + invoice.getStatus());
System.out.println("Сумма:         " + invoice.getTotalAmount());
System.out.println("Ссылка оплаты: " + invoice.getTransitionPageURL());

Модель данных

IncomeItem — позиция в чеке / счёте

Поле Тип Описание
name String Наименование услуги
quantity int Количество единиц
amount double Цена за одну единицу (не итог)

Итоговая сумма по услуге рассчитывается автоматически: amount × quantity.

Receipt — подтверждение регистрации чека

Поле Тип Описание
uuid String Идентификатор чека в ФНС
jsonUrl String Ссылка на данные чека (JSON)
printUrl String Ссылка на чек для печати

PaymentType — реквизиты оплаты

Поле Тип Описание
id Long Идентификатор в системе ФНС
type String Тип: ACCOUNT, CARD и др.
bankName String Наименование банка
bankBik String БИК банка
currentAccount String Расчётный счёт
corrAccount String Корреспондентский счёт
favorite Boolean Является ли избранным

ClientType — тип плательщика

Значение Описание
ClientType.FROM_LEGAL_ENTITY Юридическое лицо или ИП
ClientType.FROM_INDIVIDUAL Физическое лицо

Invoice — выставленный счёт

Поле Тип Описание
invoiceId Long Числовой идентификатор счёта
uuid String UUID счёта
status String Статус: CREATED, PAID, CANCELLED
transitionPageURL String Ссылка на страницу оплаты
clientType ClientType Тип плательщика
clientName String Наименование плательщика
clientInn String ИНН плательщика
totalAmount BigDecimal Итоговая сумма (руб.)
totalTax BigDecimal Сумма налога (руб.)
services List<ServiceItem> Список позиций
createdAt String Время создания (ISO-8601)
paidAt String Время оплаты (null, если не оплачен)
cancelledAt String Время отмены (null, если не отменён)

Обработка ошибок

Исключение Когда выбрасывается
ApiRequestException Сервер вернул код ответа, отличный от 200. Содержит statusCode и body.
ApiException Сетевая ошибка или прерывание потока.
IllegalStateException Вызов метода до init.
try {
    Receipt receipt = client.addIncome(services);
} catch (ApiRequestException e) {
    System.err.println("Код ответа: " + e.getStatusCode());
    System.err.println("Ответ сервера: " + e.getBody());
} catch (ApiException e) {
    System.err.println("Сетевая ошибка: " + e.getMessage());
}

Как работает обновление токена

Токен доступа имеет ограниченный срок жизни. Перед каждым вызовом addIncome, createInvoice и getPaymentTypes библиотека проверяет, не истёк ли токен, и при необходимости автоматически обновляет его через refresh-токен — без повторного ввода пароля.

Для безопасной работы в многопоточной среде используется ReadWriteLock:

  • Обычные запросы захватывают read-lock — выполняются параллельно.
  • Обновление токена захватывает write-lock — блокирует новые запросы до завершения обновления.

Changelog

1.1.3

  • Убрана принудительная фиксация HTTP/1.1 — клиент теперь автоматически согласует протокол (HTTP/1.1 / HTTP/2) через TLS ALPN
  • Добавлен настраиваемый таймаут ответа (moy-nalog.request-timeout, по умолчанию 30 сек)
  • Добавлен автоматический retry при аутентификации в случае transient сетевой ошибки

1.1.1

  • Добавлен enum ClientType (FROM_LEGAL_ENTITY, FROM_INDIVIDUAL) вместо строки в createInvoice

1.1.0

  • Добавлена поддержка прокси (с аутентификацией и без)
  • Добавлены методы getPaymentTypes() и createInvoice()
  • Новые модели: PaymentType, Invoice

1.0.1

  • Первый публичный релиз

About

Java-библиотека для работы с API сервиса «Мой налог» (ФНС России). Позволяет программно регистрировать доходы и получать чеки для самозанятых.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages