Arabic NER — fine-tuned GLiNER
Zero-shot-capable span NER for Arabic, fine-tuned on 17 entity types
including Saudi national ID numbers and mobile numbers.
Quick start
1from gliner import GLiNER
2
3model = GLiNER.from_pretrained("Elafnawaf/gliner-arabic-ner")
4labels = ['شخص / person', 'منظمة / organization', 'مكان / place', 'عنوان / address']
5
6text = "زار المهندس فهد العتيبي مقر أرامكو في الظهران."
7for e in model.predict_entities(text, labels, threshold=0.6, flat_ner=False):
8 print(e["label"], "->", e["text"])
The model is half the system
This repo also ships pipeline.py, which adds the regex layer, the per-label thresholds and the format validator that the published metrics were measured with.
1from huggingface_hub import snapshot_download
2import sys; sys.path.insert(0, snapshot_download('Elafnawaf/gliner-arabic-ner'))
3from pipeline import extract
4
5for e in extract('سجل الدخول برقم الهوية 1098765432'):
6 print(e['source'], e['label'], e['text'])
11 of the 17 labels are answered by deterministic
regexes rather than the network — national IDs, phone numbers, percentages, money,
times and similar shapes. A regex is more reliable at those than any amount of
training, and it needs no data. The remaining 6 are the model's.
Labels
Model-owned (6): شخص / person, منظمة / organization, مكان / place, عنوان / address, مطار / airport, تاريخ / date
Rule-owned (11): ترتيب / ordinal, رقم الهوية الوطنية / national id number, رقم جوال / mobile number, عدد / cardinal number, عملة / currency, كمية / quantity, مبلغ مالي / money, موقع إلكتروني / website, نسبة مئوية / percentage, وحدة قياس / unit of measurement, وقت / time
Labels are model input in GLiNER, so you can ask for types outside this list —
accuracy on those is not measured here.
Results
Held-out test split, span-exact match, 14,707 gold entities.
| micro-F1 |
|---|
| zero-shot, before fine-tuning | 0.3859 |
| after fine-tuning | 0.7314 |
| model-owned labels only | 0.7179 |
Trained for 12069 steps.
Limitations — read these
Modern Standard Arabic only. Every training corpus is MSA. Published work on
Arabic NER reports losses of up to 38% F1 on out-of-distribution dialects, so
treat Gulf, Levantine or Maghrebi input as untested.
Measured on public corpora, not on production text. The test split is drawn
from the same corpora and annotation guidelines as the training data. Expect
lower accuracy on text from a different domain.
Span conventions are inherited from the training corpora. Whether a title like
الأمير or a head noun like شركة falls inside a span follows those corpora's
conventions, which may not match yours.
Normalize before you tokenize. Arabic diacritics are not matched by Python's
\w, so undiacritized input is required for correct spans — pipeline.py handles
this, and does the offset mapping back to your original string. If you call the
model directly, do it yourself.
Training data
WikiANN (ar), IAHLT MAFAT Arabic NER, the public Wojood sample, plus a synthetic
generator for Saudi ID and contact formats. Every ID and phone number in the
training data is randomly generated; no real personal data was used.
Citation