NivinSithija commited on
Commit
0b88048
·
verified ·
1 Parent(s): be11c38

Add fine-tuned LaBSE checkpoint and model card

Browse files
Files changed (6) hide show
  1. .gitattributes +1 -0
  2. README.md +163 -0
  3. config.json +46 -0
  4. model.safetensors +3 -0
  5. tokenizer.json +3 -0
  6. tokenizer_config.json +17 -0
.gitattributes CHANGED
@@ -33,3 +33,4 @@ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
35
  *tfevents* filter=lfs diff=lfs merge=lfs -text
 
 
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
35
  *tfevents* filter=lfs diff=lfs merge=lfs -text
36
+ tokenizer.json filter=lfs diff=lfs merge=lfs -text
README.md ADDED
@@ -0,0 +1,163 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ---
2
+ language:
3
+ - en
4
+ - si
5
+ - ta
6
+ license: cc-by-4.0
7
+ base_model: sentence-transformers/LaBSE
8
+ pipeline_tag: text-classification
9
+ tags:
10
+ - banking
11
+ - priority-classification
12
+ - ticket-triage
13
+ - labse
14
+ - multilingual
15
+ - code-mixed
16
+ - sinhala
17
+ - tamil
18
+ metrics:
19
+ - f1
20
+ ---
21
+
22
+ # Swift-Support LaBSE Priority Classifier (v1.0)
23
+
24
+ A fine-tuned **LaBSE** (Language-Agnostic BERT Sentence Embedding) model that assigns an
25
+ escalation priority — **Low / Medium / High** — to a banking support ticket written in any of five
26
+ language tracks. Built for the **Swift** support-ticket triage project, alongside
27
+ [`Swift-Support/labse-intent-1.0`](https://huggingface.co/Swift-Support/labse-intent-1.0).
28
+
29
+ ## Model details
30
+
31
+ * **Base architecture:** `sentence-transformers/LaBSE` (471M parameters, 501k vocabulary)
32
+ * **Task:** 3-class text classification (priority / urgency)
33
+ * **Classes:** `Low`, `Medium`, `High`
34
+ * **Languages:** English, Sinhala, Tamil, Singlish (romanized Sinhala), Tanglish (romanized Tamil)
35
+ * **Regime:** one multilingual model over all five tracks — *not* five per-language models
36
+
37
+ The headline metric is **macro-F1**, never accuracy: the class distribution is roughly
38
+ 55% Low / 36% Medium / 9% High, so accuracy flatters a model that neglects `High`.
39
+
40
+ ## Evaluation
41
+
42
+ Trained on `train+dev` (49,990 rows = 9,998 tickets × 5 languages), scored **once** on the
43
+ held-out test set (15,395 rows = 3,079 tickets × 5 languages). Frozen split `e7b5934392cd`; test
44
+ tickets come from the official BANKING77 test file and were never used for model selection.
45
+
46
+ **Pooled test macro-F1: 0.8901** (accuracy 0.9008)
47
+
48
+ Per-class F1: `Low` 0.9206 · `Medium` 0.8760 · `High` 0.8735
49
+
50
+ ### Against the alternatives (pooled test macro-F1)
51
+
52
+ | model | macro-F1 |
53
+ |---|---:|
54
+ | `gemma-3-1b` multitask (shared head) | 0.8904 |
55
+ | **LaBSE (this model)** | **0.8901** |
56
+ | `gemma-3-1b` (LoRA, single-task) | 0.8898 |
57
+ | mmBERT | 0.8887 |
58
+ | XLM-RoBERTa base | 0.8872 |
59
+ | TF-IDF + LinearSVC (classical champion) | 0.8722 |
60
+ | TF-IDF + logistic regression | 0.8683 |
61
+
62
+ The classical champion's 95% CI is [0.8605, 0.8831], so this model clears its upper bound — a
63
+ real, if modest, win. The Gemma multitask variant is a statistical tie, not a better model.
64
+
65
+ ### Per language, on test
66
+
67
+ | track | LaBSE (this model) | classical TF-IDF | delta |
68
+ |---|---:|---:|---:|
69
+ | English | **0.9229** | 0.9032 | +0.0197 |
70
+ | Sinhala | **0.9179** | 0.8745 | +0.0434 |
71
+ | Singlish (romanized) | 0.8817 | **0.8915** | −0.0098 |
72
+ | Tamil | **0.9130** | 0.8905 | +0.0225 |
73
+ | Tanglish (romanized) | **0.8142** | 0.7994 | +0.0148 |
74
+ | **ALL (pooled)** | **0.8901** | 0.8722 | +0.0179 |
75
+
76
+ Two things worth stating plainly:
77
+
78
+ 1. **The classical baseline still wins on Singlish.** LaBSE gives back most of its native-script
79
+ advantage on romanized text — a pattern that also shows up in linear probing, where LaBSE has
80
+ the *largest* native-minus-romanized gap of any backbone in the roster.
81
+ 2. **Tanglish is the weak track**, 7–10 points below every other language for both model families.
82
+
83
+ ## ⚠️ The label ceiling — read this before quoting 0.89
84
+
85
+ The training labels were generated by an LLM prompt, not by human annotators. On a 500-ticket
86
+ benchmark set that *was* annotated by hand, those prompt labels agree with human judgement at
87
+ **0.7722 macro-F1** (95% CI [0.7263, 0.8147]; raw agreement 0.804, Cohen's κ = 0.644).
88
+
89
+ This does **not** cap the number above — against the prompt labels a model could in principle
90
+ reach 1.0. It caps what the number *means*. This model has learned the labeling rule well; the
91
+ rule itself agrees with a human 77% of the time. **Quoting 0.89 as "priority accuracy" overstates
92
+ what a human reviewer would call correct.** Any external write-up should state the 0.7722 figure
93
+ alongside it.
94
+
95
+ ## Usage
96
+
97
+ ```python
98
+ import torch
99
+ from transformers import AutoModelForSequenceClassification, AutoTokenizer
100
+
101
+ repo = "Swift-Support/labse-priority-1.0"
102
+ tok = AutoTokenizer.from_pretrained(repo)
103
+ model = AutoModelForSequenceClassification.from_pretrained(repo).eval()
104
+
105
+ texts = ["Someone has taken money from my account and nobody is helping me!",
106
+ "How do I activate my new card?"]
107
+
108
+ with torch.no_grad():
109
+ batch = tok(texts, return_tensors="pt", padding=True, truncation=True, max_length=128)
110
+ probs = model(**batch).logits.softmax(-1)
111
+
112
+ for text, p in zip(texts, probs):
113
+ print(model.config.id2label[int(p.argmax())], f"{p.max():.3f}", "|", text)
114
+ ```
115
+
116
+ Two things that will silently corrupt results if you get them wrong:
117
+
118
+ * **`max_length=128` must match training.** It is not stored in the checkpoint.
119
+ * **Read the label from `model.config.id2label`, never from a hardcoded index.** This checkpoint
120
+ carries an explicit mapping (`0: Low, 1: Medium, 2: High`). A wrong index guess does not raise —
121
+ it silently returns the wrong priority.
122
+
123
+ Cost: ~1.9 GB resident, roughly 100–300 ms per ticket on CPU. Load the model once at process
124
+ start, never per request.
125
+
126
+ ## Training
127
+
128
+ | | |
129
+ |---|---|
130
+ | base | `sentence-transformers/LaBSE` |
131
+ | fit portion | `train+dev`, 49,990 rows |
132
+ | epochs | 3 (best epoch: 3 of 3) |
133
+ | learning rate | 2e-5 |
134
+ | batch size | 32 |
135
+ | max sequence length | 128 |
136
+ | class imbalance | `class_weight` (balanced) |
137
+ | precision | fp16 |
138
+ | hardware | Kaggle T4, ~112 rows/s, 22 min wall |
139
+
140
+ `best_epoch = 3 of 3` — the model was still improving when training stopped, which is what a
141
+ consistent labeling target looks like.
142
+
143
+ ## Limitations
144
+
145
+ * **Romanized text is synthetic.** Singlish is rule-generated from Sinhala and Tanglish is
146
+ machine-translated, so both are cleaner and more regular than text a human would type. The
147
+ Singlish and Tanglish numbers above are an optimistic upper bound, and no romanized-specific
148
+ conclusion from this model should be trusted until it is re-measured on human-typed data.
149
+ * **Labels are LLM-generated** — see the label ceiling section.
150
+ * **Domain-bound.** Derived from BANKING77; behaviour outside retail-banking support is untested.
151
+ * **Not calibrated.** The softmax scores are not probabilities you should threshold on without
152
+ re-calibrating; a threshold tuned by cross-validation on a sibling task failed to transfer to
153
+ test in this project.
154
+ * Trained and evaluated only on the five tracks listed. LaBSE covers 109 languages, but nothing
155
+ here measures the other 104.
156
+
157
+ ## Citation & provenance
158
+
159
+ Derived from [BANKING77](https://huggingface.co/datasets/PolyAI/banking77) (PolyAI, CC-BY-4.0),
160
+ translated into Sinhala and Tamil and romanized into Singlish and Tanglish. Priority labels were
161
+ generated by an LLM prompt and benchmarked against human annotation as described above.
162
+
163
+ Training data: [`Swift-Support/swift-support-tickets-1.0`](https://huggingface.co/datasets/Swift-Support/swift-support-tickets-1.0)
config.json ADDED
@@ -0,0 +1,46 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "add_cross_attention": false,
3
+ "architectures": [
4
+ "BertForSequenceClassification"
5
+ ],
6
+ "attention_probs_dropout_prob": 0.1,
7
+ "bos_token_id": null,
8
+ "classifier_dropout": null,
9
+ "directionality": "bidi",
10
+ "dtype": "float32",
11
+ "eos_token_id": null,
12
+ "gradient_checkpointing": false,
13
+ "hidden_act": "gelu",
14
+ "hidden_dropout_prob": 0.1,
15
+ "hidden_size": 768,
16
+ "id2label": {
17
+ "0": "Low",
18
+ "1": "Medium",
19
+ "2": "High"
20
+ },
21
+ "initializer_range": 0.02,
22
+ "intermediate_size": 3072,
23
+ "is_decoder": false,
24
+ "label2id": {
25
+ "Low": 0,
26
+ "Medium": 1,
27
+ "High": 2
28
+ },
29
+ "layer_norm_eps": 1e-12,
30
+ "max_position_embeddings": 512,
31
+ "model_type": "bert",
32
+ "num_attention_heads": 12,
33
+ "num_hidden_layers": 12,
34
+ "pad_token_id": 0,
35
+ "pooler_fc_size": 768,
36
+ "pooler_num_attention_heads": 12,
37
+ "pooler_num_fc_layers": 3,
38
+ "pooler_size_per_head": 128,
39
+ "pooler_type": "first_token_transform",
40
+ "position_embedding_type": "absolute",
41
+ "tie_word_embeddings": true,
42
+ "transformers_version": "5.0.0",
43
+ "type_vocab_size": 2,
44
+ "use_cache": true,
45
+ "vocab_size": 501153
46
+ }
model.safetensors ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ version https://git-lfs.github.com/spec/v1
2
+ oid sha256:03729b2bfd1373577ec344e3b45b41a82933bae2231e1ce66d1ceb2d05861157
3
+ size 1883740532
tokenizer.json ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ version https://git-lfs.github.com/spec/v1
2
+ oid sha256:6f72b993b05e566e04415720e03409ca251bf620ae9e003abe0aad1c08c10b6b
3
+ size 13632017
tokenizer_config.json ADDED
@@ -0,0 +1,17 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "backend": "tokenizers",
3
+ "cls_token": "[CLS]",
4
+ "do_basic_tokenize": true,
5
+ "do_lower_case": false,
6
+ "full_tokenizer_file": null,
7
+ "is_local": false,
8
+ "mask_token": "[MASK]",
9
+ "model_max_length": 512,
10
+ "never_split": null,
11
+ "pad_token": "[PAD]",
12
+ "sep_token": "[SEP]",
13
+ "strip_accents": null,
14
+ "tokenize_chinese_chars": true,
15
+ "tokenizer_class": "BertTokenizer",
16
+ "unk_token": "[UNK]"
17
+ }