fix(layoutlm): resolve invoices question answering support - #1181
fix(layoutlm): resolve invoices question answering support#1181拂柳残声 (fuliucansheng) wants to merge 12 commits into
Conversation
96b7317 to
3c58f1a
Compare
|
APPROVE Reviewed head Exact-head verification:
The final body has the required hierarchy, recipe-authoritative commands, exact CPU fp32/fp16 auto-config reproduction, and a self-contained real-invoice semantic harness that reproduces perf, peak-RSS memory measurement, and parity without random inputs or local scratch dependencies. Lane A PR gim-home/ModelKitArtifacts#231 is draft/labeled at Coverage is full for the declared CPUExecutionProvider/cpu fp32 and fp16 target; no target tuples are deferred. Residual risks are the L3 dataset-URI blocker, no accelerator runtime claims, and host-sensitive absolute timing. |
3c58f1a to
5d53293
Compare
Qiong Wu (qiowu) (DingmaomaoBJTU)
left a comment
There was a problem hiding this comment.
Two task-contract issues are noted inline.
|
REQUEST_CHANGES Reviewed exact head Blocking findings:
Required owner actions:
Otherwise verified:
These are fixable evidence/reproduction and knowledge-capture gaps, so the verdict is |
|
Addressed all three Reviewer findings on exact head
The structured PR body has been refreshed with exact-head provenance while preserving the original execution SHAs for reused L0-L2 and Analyze evidence. The existing Reviewer verdict and resolved review threads were not edited. |
|
APPROVE Reviewed exact head The three prior blockers are resolved:
Independent review evidence:
Coverage is full for the declared |
Qiong Wu (qiowu) (DingmaomaoBJTU)
left a comment
There was a problem hiding this comment.
Two issues block approval:
-
src/winml/modelkit/loader/resolution.py:205now auto-resolves LayoutLM todocument-question-answering, buteval/evaluate.pyonly registersquestion-answering;_resolve_task()therefore rejects the automatically inferred task before selecting the new evaluator. The documented smoke passes--task question-answering, so it bypasses this path. Please normalize at the eval/runtime boundary or registerdocument-question-answeringend-to-end, and add a regression test that evaluates without--task. -
src/winml/modelkit/eval/question_answering_evaluator.py:64treatsbox_coords=autoas absolute only when some coordinate exceeds 1000. Raw pixel boxes from common images at or below 1000 px are silently treated as already normalized, producing incorrectly scaled LayoutLM positions. Please make ambiguous coordinate input explicit (or otherwise avoid the heuristic) and cover sub-1000 absolute boxes in a test.
|
Qiong Wu (qiowu) (@DingmaomaoBJTU) Both blocking issues from the CHANGES_REQUESTED review are addressed in
Fresh independent validation: 8,558 ordinary CI tests passed; Ruff passed; mypy passed across 442 source files; sealed evidence reverified 108/108 files. Please re-review when convenient. |
Summary
This PR adds
DmitrySpartak/layoutlm-invoicessupport for invoice and document question answering with CPU FP32 and FP16 recipes, metadata-driven automatic loader selection, and reusable bbox-aware document evaluation. It ships Effort L2 / Outcome L2 and reaches Goal L3 PASS through one bounded real-data FP32 CPU functional smoke; ANLS0.0is operability evidence only, not an accuracy claim. The checkpoint is licensed CC-BY-NC-SA-4.0 for noncommercial use.Model metadata
What the model does
LayoutLMForQuestionAnsweringconsumes tokenized document text together with normalized 2D token bounding boxes and predicts start and end logits for extracting an answer span; this checkpoint is fine-tuned for questions about invoices and other documents.verified).Primary user stories
A user supplies an invoice or document question plus OCR-aligned words and boxes to obtain the document text span answering fields such as invoice number or purchase amount.
verified).Supported tasks
question-answeringacross the Transformers, Optimum ONNX, and WinML support surfaces (verifiedfrom the pinned checkpoint architecture, checked-in recipes, and Reproduce commands).document-question-answeringas the checkpoint's document-domain task (verifiedfrom the pinned model card).Model architecture
LayoutLMForQuestionAnsweringsource (verified).Validation and support evidence
Baseline
WinML
0.2.0baseline evidence was executed at commit48bfd0f91478a8e281b205b0449222024729f3ea; pinned main is2b9ec0e9e57bba8003d25eaff85f8c7c9e30d75a. Baseline automatic config selectednext-sentence-prediction/AutoModelForNextSentencePrediction; build exited 2 because that class does not recognizeLayoutLMConfig, so perf and Eval were not reached. The Optimum probe exposed feature extraction, fill mask, text classification, and token classification; WinML's override additionally exposed question answering.The planner recorded
REUSEbecause pinned main is unchanged from the prior current-main assessment. This retains baseline execution provenance and does not relabel it as newly executed on candidate head61ffb5f5651573b22f47fed47571e163a1013335.Goal
document-question-answering; the concrete model isLayoutLMForQuestionAnswering, and the exporter boundary usesLayoutLMQAIOConfig. Checked-in recipes retainquestion-answeringas the export/runtime identity while document-aware evaluation is selected from the declaredbboxinput and document columns.Outcome
Overall verdict is PASS; highest reached Goal is L3 PASS and shipped Outcome is L2. Coverage is full for the declared
CPUExecutionProvider / cpuFP32 and FP16 tuples, with no deferred tuples. The PR ships both CPU recipes, generalized architecture/config-driven resolution, LayoutLM export input derivation, bbox-aware QA evaluation and forwarding, ANLS, document schema support, an explicit native OCR contract, and regression tests. Model findings retain the contiguous start/end span limitation; no non-consecutive answer-decoding claim is made. No methodology finding was triggered.Execution provenance is split without upgrading reused measurements:
61ffb5f5651573b22f47fed47571e163a1013335: source/lock identity; exact checkpoint snapshot materialization; pinned-snapshot inspect/config/Eval; native Tesseract contract and runtime capture; fresh DocVQA L3 smoke; affected Eval/commands tests; OCR-focused tests; Ruff, mypy, license, lock, and docs validation.2007e13ab59532f1a20a099babc432da9c1aa47dagainst artifacts originating at5274a714997a8d03cc3b3048590aac2389419805. The final OCR-validation/docs-only repair does not change recipes, export, optimization, precision, graphs, or runtime forwarding, so their byte-identity evidence is retained.5274a714997a8d03cc3b3048590aac2389419805and validated on2007e13ab59532f1a20a099babc432da9c1aa47dthrough byte-identical explicit artifacts. They remain reused on61ffb5f5651573b22f47fed47571e163a1013335for the same path-invariance reason.2007e13ab59532f1a20a099babc432da9c1aa47dand retained as path-invariant. All nine GitHub checks independently completed successfully on exact head61ffb5f5651573b22f47fed47571e163a1013335.The Lane A
layoutlm-003knowledge entry now names the two shipped recipe files exactly:examples/recipes/DmitrySpartak_layoutlm-invoices/cpu/cpu/question-answering_fp32_config.jsonandexamples/recipes/DmitrySpartak_layoutlm-invoices/cpu/cpu/question-answering_fp16_config.json. That correction is preserved in a dedicated local Lane A commit and is intentionally unpushed; it is not mixed into this model-support PR.Per-EP/device/precision results and Functional smoke Eval
Automatic recipe-free acceptance
At execution head
2007e13ab59532f1a20a099babc432da9c1aa47d, automatic inspection selected taskdocument-question-answering, model classLayoutLMForQuestionAnswering, and exporterLayoutLMQAIOConfigwithout a recipe or task/model-class override. Metadata produced a usable sequence capacity of 512 frommodel_max_length=512,max_position_embeddings=514, andpad_token_id=1; paired question/document tokenization reserves four special tokens, leaving a 508-token content budget. FP32 and FP16 automatic configs consistently use[1, 512]forinput_ids,attention_mask, andtoken_type_ids,[1, 512, 4]forbbox, and[0, 1)fortoken_type_idsfromtype_vocab_size=1.The recipe-free CPU FP32 build passed. CPU ORT inference used all four int32 inputs, zero-only
token_type_ids, bbox values within[0, 1000], and produced finitestart_logitsandend_logits, each shaped[1, 512]. Exact head61ffb5f5651573b22f47fed47571e163a1013335freshly materialized checkpoint revisionce2422049c250384731eccef90bf6d92e846b09c; inspect and config passed against that local snapshot with the same task, model class, exporter, and four-input schema.Explicit tuple builds and L1 perf
Recipe-authoritative FP32 and FP16 builds passed at
2007e13ab59532f1a20a099babc432da9c1aa47d; the explicit artifacts were byte-identical to those measured at5274a714997a8d03cc3b3048590aac2389419805. L1 used a synthetic invoice-like OCR fixture with namedinput_ids,bbox,attention_mask, andtoken_type_ids, 5 warmups, and 20 timed iterations. It is not presented as real-data performance.FP32 produced an IR 8, opset 17 graph with 394 nodes and FLOAT initializers. FP16 produced an IR 8, opset 17 graph with 396 nodes and 206 FLOAT16 initializers. Both expose
input_ids,bbox,attention_mask, andtoken_type_idsand producestart_logits/end_logits.L2 PyTorch/ONNX parity
Parity used the same synthetic invoice-like OCR inputs, with 65 non-padding tokens and exact named input shapes:
input_ids,attention_mask, andtoken_type_idsare[1, 512]int32;bboxis[1, 512, 4]int32.Functional smoke Eval
L3 PASS: the FP32 CPU DocVQA smoke was freshly executed on exact head
61ffb5f5651573b22f47fed47571e163a1013335against the locally materialized checkpoint revision. ANLS0.0proves end-to-end operability only; it is not representative accuracy or benchmark quality.3.11.16, ModelKit0.3.0, Transformers5.14.1, datasets5.0.0, pytesseract0.3.13, Pillow12.3.0, JPEG decoder8.0, zlib1.3.1.zlib-ng, and native Tesseract5.5.3.lmms-lab-encoder/DocVQA, configDocVQA, revision539088ef8a8ada01ac8e2e6d4e372586748a265e, validation row index 2, questionId57349; dataset card licenseApache-2.0.itc limited,ITC Limited; prediction:ITC's.5.5.3OCR pass produced 141 words and 141 normalized boxes in range[0, 997]; bbox forwarding was verified as[1, 512, 4]int64 alongside all four declared inputs.0.0,n_samples=1,skipped_samples=0,windows_processed=1,ocr_samples=1,precomputed_samples=0,ocr_engine_version=5.5.3.words/boxespath forwards the same four named inputs without importing or probing pytesseract or native Tesseract; it reportedocr_samples=0andprecomputed_samples=1.Delta
Baseline had no usable automatic recipe: it selected next-sentence prediction and failed before generating an authoritative starting recipe. The checked-in CPU recipes explicitly select
question-answering/LayoutLMForQuestionAnswering, use 512-position inputs with normalized bbox and zero-only token types, enable constant clamping, and select FP32 or FP16 realization. The final OCR repair does not modify either recipe; retained explicit artifacts remain byte-identical. The production recipe README remains untouched.The automatic-path repair replaces the prior raw position-table interpretation with metadata-derived usable capacity and exposes the valid token-type range at config generation. The prior automatic path's 514-position configuration and build failure are fixed-delta context only; accepted automatic shapes are 512 and recipe-free build/ORT pass.
Bug fix explanation: architecture/config-driven task and loader selection
LayoutLMForQuestionAnsweringarchitecture selected loader behavior that Transformers could not instantiate forLayoutLMConfig; the concrete recipe masked the automatic-path defect.MODEL_FOR_DOCUMENT_QUESTION_ANSWERING_MAPPING_NAMESandMODEL_FOR_QUESTION_ANSWERING_MAPPING_NAMES, choose document QA only for configurations supported exclusively there, and canonicalize the exporter boundary soLayoutLMQAIOConfigremains available.config.architecturesand Transformers config mappings, with no checkpoint ID or repository-name branch.BertForQuestionAnsweringstays plainquestion-answering, and only document-only configurations take the document path.Bug fix explanation: metadata-derived LayoutLM export inputs
max_position_embeddingsincludes the RoBERTa-style offset, while post-processing generated token types to zero happened too late for serialized config reconstruction.LayoutLMQAIOConfigapplies the existing position-embedding adjustment before shape resolution; the LayoutLM input generator derivestoken_type_idsdirectly fromtype_vocab_size.sequence_lengthremains authoritative.[0, 1)token types; recipe-free build and CPU ORT pass; explicit FP32/FP16 artifacts remain byte-identical; models/loader/datasets/export coverage reports 1,538 passed, 6 skipped, and 2 xfailed.Bug fix explanation: bbox-aware document evaluation and native OCR validation
bboxinput, decode OCR-aligned document spans, or emit a document metric; the initial image-only implementation also depended on an undeclared native Tesseract executable.bboxmodel input plus document columns or an explicit request, not a checkpoint identifier. Precomputed words/boxes are preferred; image rows use one optional, version-validated OCR pass.Analyze summary - component level and op level
Analyze completed with
ANALYZE-PARTIAL-SUCCESS(exit 1) and seven parseable rows per artifact at execution SHA5274a714997a8d03cc3b3048590aac2389419805; byte-identical artifact validation at2007e13ab59532f1a20a099babc432da9c1aa47dremains reusable on exact head61ffb5f5651573b22f47fed47571e163a1013335. This is static rule compatibility analysis, not runtime execution. There were no actionable partial or unsupported findings, andruntime_support=falseis not runtime EP evidence.Component-level summary
Op-level summary
NvTensorRTRTX/GPU reports all 15 types unknown. CUDA/GPU, MIGraphX/GPU, TensorRT/GPU, and DML/GPU have no shipped classifications; unknown is not unsupported. There are no component mapping gaps.
Reproduce commands