Валидация данных в C++: библиотеки и методы (libvalidate, nlohmann/json, Boost)

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

Валидация данных в C++: обзор библиотек и практических подходов

Валидация данных — один из ключевых аспектов разработки надёжного программного обеспечения на C++. Корректная проверка входных данных позволяет предотвратить ошибки выполнения, уязвимости и неопределённое поведение. В отличие от языков с динамической типизацией, C++ требует от разработчика явного контроля типов и форматов. В этой статье мы рассмотрим как ручные методы, так и специализированные библиотеки, упрощающие валидацию.

1. Ручная валидация: базовые приёмы

Простейший способ — проверить данные с помощью условных операторов. Этот подход хорош для небольших проектов, но быстро становится громоздким.

#include <iostream>
#include <string>
#include <cctype>

bool validateEmail(const std::string& email) {
    if (email.empty()) return false;
    size_t atPos = email.find('@');
    if (atPos == std::string::npos || atPos == 0) return false;
    size_t dotPos = email.rfind('.');
    if (dotPos == std::string::npos || dotPos <= atPos + 1) return false;
    if (dotPos == email.length() - 1) return false;
    return true;
}

int main() {
    std::string testEmail = "user@example.com";
    std::cout << (validateEmail(testEmail) ? "Valid" : "Invalid") << std::endl;
    return 0;
}

Недостатки: сложность поддержки, дублирование кода, отсутствие единого интерфейса.

2. Библиотека libvalidate

libvalidate — легковесная библиотека для декларативной валидации данных в C++17 и выше. Она позволяет описывать правила проверки в цепочном стиле, напоминающем валидаторы в PHP или Python.

Установка

Библиотека распространяется как header-only. Достаточно скопировать validate.hpp в проект или подключить через CMake:

# Пример FetchContent
include(FetchContent)
FetchContent_Declare(libvalidate
    GIT_REPOSITORY https://github.com/username/libvalidate.git
    GIT_TAG v1.0.0)
FetchContent_MakeAvailable(libvalidate)

Пример использования

#include "validate.hpp"
#include <iostream>
#include <string>

int main() {
    using namespace validate;

    // Валидация числа (возраст)
    int age = 25;
    auto ageResult = check(age)
        .min(18, "Возраст должен быть не менее 18 лет")
        .max(120, "Возраст должен быть не более 120 лет");

    if (!ageResult.valid()) {
        std::cerr << ageResult.error() << std::endl;
    }

    // Валидация строки (пароль)
    std::string password = "P@ssw0rd";
    auto passResult = check(password)
        .minLength(8, "Пароль должен содержать минимум 8 символов")
        .matches(R"((?=.*[A-Z])(?=.*[a-z])(?=.*\d).*)", "Пароль должен содержать заглавные, строчные буквы и цифры");

    if (!passResult.valid()) {
        std::cerr << passResult.error() << std::endl;
    }

    // Комбинированная валидация объекта
    struct User {
        std::string name;
        int age;
        std::string email;
    };

    User user{"Alice", 30, "alice@example.com"};
    auto userResult = check(user)
        .field(&User::name, "name")
            .minLength(2)
            .maxLength(50)
        .field(&User::age, "age")
            .range(18, 100)
        .field(&User::email, "email")
            .email(); // встроенная проверка email

    if (!userResult.valid()) {
        for (const auto& err : userResult.errors()) {
            std::cerr << err.field << ": " << err.message << std::endl;
        }
    }

    return 0;
}

Особенности:

  • Поддержка встроенных правил: min, max, range, email, regex, notEmpty.
  • Возможность создания пользовательских валидаторов через лямбда-функции.
  • Сбор всех ошибок валидации в контейнер.
  • Лёгкая интеграция с JSON и структурами.

3. Валидация JSON через nlohmann/json + JSON Schema

Для веб-сервисов и конфигурационных файлов часто используется JSON. Библиотека nlohmann/json в паре с JSON Schema Validator позволяет проверять структуру данных по схеме.

Пример

Рекомендаций