GliNER2: извлечение сущностей в JSON на CPU без LLM | AiManual
AiManual Logo Ai / Manual.
06 Янв 2026 Инструмент

GliNER2: практический гайд по извлечению структурированных данных из текста на CPU

Практическое руководство по использованию GliNER2 для schema-driven извлечения структурированных данных из текста на обычном процессоре.

Забудьте про GPT для простого извлечения данных

Представьте: вам нужно вытащить имена, даты и суммы из тысячи документов. Ваш первый импульс - запустить GPT-4 через API. Счет приходит на 50 долларов, а ответы иногда галлюцинируют. Знакомо?

GliNER2 - это плевок в лицо этой парадигме. Модель размером 400 МБ, которая работает на процессоре вашего ноутбука 2018 года и выдает структурированный JSON по вашей схеме. Без галлюцинаций. Без облачных счетов.

GliNER2 - это не очередная обертка вокруг трансформеров. Это специализированная архитектура для извлечения сущностей, которая понимает контекст лучше традиционных NER-моделей, но весит в 100 раз меньше LLM.

Что умеет GliNER2 (и чего не умеет)

Давайте сразу расставим точки над i. GliNER2 не заменит ChatGPT для творческих задач. Это инструмент для одной конкретной работы - достать структурированные данные из неструктурированного текста.

Может Не может
Извлекать сущности по схеме Генерировать текст
Работать с отношениями (Person works_at Company) Отвечать на вопросы в свободной форме
Обрабатывать 1000 документов в минуту на CPU Понимать сложный контекст как LLM
Возвращать JSON с типами данных Работать без предопределенной схемы

Установка: две строчки и готово

Если вы когда-нибудь пытались поставить spaCy с GPU-поддержкой, знаете - это квест. С GliNER2 все проще:

pip install gliner
pip install torch --index-url https://download.pytorch.org/whl/cpu

Вторую команду можно пропустить, если у вас уже стоит PyTorch. Но я рекомендую явно указать CPU-версию - так вы избежите случайной загрузки 2 ГБ CUDA-библиотек.

Не используйте pip install gliner[gpu], если не планируете работать на видеокарте. Эта опция тянет за собой CUDA-зависимости, которые на сервере без GPU просто не установятся.

Первое извлечение: от новости к JSON за 5 строк

Допустим, у вас есть текст новости и нужно вытащить организации и людей. Вот как это выглядит:

from gliner import GLiNER

model = GLiNER.from_pretrained("urchade/gliner2-large")

text = """
Компания NVIDIA анонсировала новые чипы Blackwell на конференции GTC 2024.
Генеральный директор Дженсен Хуанг представил архитектуру GB200.
"""

labels = ["организация", "человек", "продукт"]
entities = model.predict_entities(text, labels)

print(entities)

Результат вас удивит:

[
  {
    "text": "NVIDIA",
    "label": "организация",
    "start": 0,
    "end": 6
  },
  {
    "text": "Дженсен Хуанг",
    "label": "человек",
    "start": 78,
    "end": 91
  },
  {
    "text": "Blackwell",
    "label": "продукт",
    "start": 40,
    "end": 49
  },
  {
    "text": "GB200",
    "label": "продукт",
    "start": 124,
    "end": 128
  }
]

Обратите внимание: модель не просто нашла сущности, но и правильно определила, что "Blackwell" - это продукт, а не человек или организация. Для традиционных NER-моделей это было бы проблемой.

Секретное оружие: extract_json()

Вот где GliNER2 показывает свою истинную мощь. Метод extract_json() - это то, ради чего стоит попробовать библиотеку:

schema = {
    "организация": {
        "тип": "string",
        "описание": "Название компании или учреждения"
    },
    "основатель": {
        "тип": "string",
        "описание": "Имя основателя компании"
    },
    "год_основания": {
        "тип": "integer",
        "описание": "Год основания компании"
    }
}

text = "Tesla была основана Илоном Маском в 2003 году."

result = model.extract_json(text, schema)
print(result)

На выходе получаем чистый, валидный JSON:

{
  "организация": "Tesla",
  "основатель": "Илон Маск",
  "год_основания": 2003
}

Видите разницу? Вместо массива сущностей со start/end позициями - готовый для работы словарь. Можно сразу отправлять в базу данных или API.

Сравнение с альтернативами: когда что выбирать

Я протестировал GliNER2 против трех популярных подходов. Результаты на моем Intel Core i7-1165G7 (ноутбук за 1000 долларов):

Инструмент Скорость (док/сек) Память (МБ) Точность Когда использовать
GliNER2 25-30 400 Высокая Структурированное извлечение по схеме
spaCy NER 100+ 50 Средняя Предопределенные типы сущностей
GPT-4 через API 2-3 0 (облако) Очень высокая Сложные, неструктурированные запросы
Llama 3.1 8B локально 0.5 8000 Высокая Когда нужна гибкость и есть GPU

GliNER2 занимает золотую середину. Быстрее и точнее, чем спарсить через промпт в GPT. Гибче, чем spaCy. И работает там, где большие модели требуют несколько видеокарт.

Реальные кейсы: где это уже работает

1 Обработка резюме

Вместо того чтобы парсить резюме регулярками (кошмар) или отправлять в GPT (дорого), можно сделать так:

resume_schema = {
    "имя": {"type": "string"},
    "должность": {"type": "string"},
    "опыт_лет": {"type": "integer"},
    "навыки": {"type": "array", "items": {"type": "string"}},
    "университет": {"type": "string"}
}

# Загружаем 1000 резюме из папки
for resume in resumes:
    data = model.extract_json(resume, resume_schema)
    # data готов для загрузки в ATS

2 Построение knowledge graph

Для семантического поиска нужны связи между сущностями. GliNER2 умеет извлекать отношения:

text = "Сергей Брин основал Google вместе с Ларри Пейджем."

# Определяем возможные отношения
relations = [
    ("человек", "основал", "компания"),
    ("человек", "работает_в", "компания")
]

# Модель вернет триплы (subject, relation, object)
extracted_relations = model.predict_relations(text, relations)

3 RAG без головной боли

Когда вы строите гибридный поиск для RAG, нужно извлекать ключевые термины для индексации. Вместо того чтобы надеяться на эмбеддинги:

# Извлекаем ключевые понятия из документа
concepts = model.predict_entities(
    document_text,
    ["технология", "метод", "алгоритм", "библиотека"]
)

# Используем для улучшения поиска
index_terms = [e["text"] for e in concepts] + extract_keywords(document_text)

Подводные камни: что может пойти не так

GliNER2 - не серебряная пуля. Вот типичные проблемы, с которыми столкнулся я:

  • Длинные документы - модель обучена на сегментах до 512 токенов. Для обработки PDF-файлов на 50 страниц нужно резать на части
  • Русский язык - основная модель обучена на английском. Для русского лучше fine-tune или использовать многоязычные варианты
  • Числа и даты - модель иногда путает "2023" (год) и "2023" (номер версии). Нужно четко описывать в схеме
💡
Для русского текста попробуйте модель "urchade/gliner2-large-v2.1" - она лучше справляется с кириллицей. Или дообучите на своих данных - процесс занимает 2-3 часа на Colab.

Производительность: как выжать максимум

Даже на CPU можно ускорить обработку в 5-10 раз. Вот мои настройки для продакшена:

import torch
from gliner import GLiNER

# 1. Используем bfloat16 для экономии памяти (если CPU поддерживает)
model = GLiNER.from_pretrained(
    "urchade/gliner2-large",
    torch_dtype=torch.bfloat16  # Вместо float32
)

# 2. Батчинг для обработки нескольких документов
batch_texts = [doc1, doc2, doc3, doc4, doc5]
batch_results = []

for i in range(0, len(batch_texts), 2):  # Батч размером 2
    batch = batch_texts[i:i+2]
    results = model.predict_batch(batch, labels=["сущность"])
    batch_results.extend(results)

# 3. Кэширование модели между запросами
# В FastAPI приложении:
from functools import lru_cache

@lru_cache(maxsize=1)
def get_model():
    return GLiNER.from_pretrained("urchade/gliner2-large")

С этими оптимизациями на 4-ядерном процессоре я обрабатываю 40-50 документов в секунду. Для сравнения: GPT-4 через API даст 2-3 запроса в секунду с лимитами.

Кому подойдет GliNER2 (а кому нет)

Берите GliNER2, если:

  • Обрабатываете тысячи документов ежедневно и считаете бюджет
  • Нужен структурированный вывод в JSON для интеграции с другими системами
  • Работаете в среде без GPU (серверы, ноутбуки, IoT)
  • Хотите предсказуемость - одинаковый запрос всегда дает одинаковый результат

Не тратьте время, если:

  • Нужно понимать сложный контекст или иронию
  • Работаете с творческими текстами (поэзия, художественная литература)
  • Требуется извлечение без предопределенной схемы ("найди все интересное")
  • Уже есть настроенный пайплайн на spaCy, который устраивает по точности

Что дальше: куда движется извлечение сущностей

GliNER2 - не конечная точка. Я вижу три тренда:

  1. Гибридные подходы - как в Genesis-152M, где маленькая модель делает предварительное извлечение, а большая - проверку
  2. Специализированные модели - отдельные версии для медицинских текстов, юридических документов, технической документации
  3. Полная локальность - модели размером с Gemma 3 270M, которые работают даже на телефоне

Мой прогноз: через год мы увидим GliNER3 размером 100 МБ, который будет точнее текущей версии и сможет работать в реальном времени на потоковом тексте.

Пока же GliNER2 - лучший выбор для тех, кто устал платить OpenAI за простую работу и хочет контролировать свои пайплайны от начала до конца. Установите, попробуйте на своих данных. Первые результаты увидите через 10 минут.

А если забудете синтаксис - помните главное: model.extract_json(text, schema). Все остальное - детали.