codingutf8 2022 the huggingface inc team licensed under the apache license version 2 0 the license you may not use this file except in compliance with the license you may obtain a copy of the license at http www apache orglicenseslicense2 0 unless required by applicable law or agreed to in writing software distributed under the license is distributed on an as is basis without warranties or conditions of any kind either express or implied see the license for the specific language governing permissions and limitations under the license testing suite for the tensorflow layoutlmv3 model from future import annotations import copy import inspect import unittest import numpy as np from transformers import istfavailable isvisionavailable from transformers models auto import getvalues from transformers testingutils import requiretf slow from transformers utils import cachedproperty from testconfigurationcommon import configtester from testmodelingtfcommon import tfmodeltestermixin floatstensor idstensor randomattentionmask from testpipelinemixin import pipelinetestermixin if istfavailable import tensorflow as tf from transformers import tflayoutlmv3pretrainedmodelarchivelist tfmodelformultiplechoicemapping tfmodelforquestionansweringmapping tfmodelforsequenceclassificationmapping tfmodelfortokenclassificationmapping layoutlmv3config tflayoutlmv3forquestionanswering tflayoutlmv3forsequenceclassification tflayoutlmv3fortokenclassification tflayoutlmv3model if isvisionavailable from pil import image from transformers import layoutlmv3imageprocessor class tflayoutlmv3modeltester def init self parent batchsize2 numchannels3 imagesize4 patchsize2 textseqlength7 istrainingtrue useinputmasktrue usetokentypeidstrue uselabelstrue vocabsize99 hiddensize36 numhiddenlayers2 numattentionheads4 intermediatesize37 hiddenactgelu hiddendropoutprob0 1 attentionprobsdropoutprob0 1 maxpositionembeddings512 typevocabsize16 typesequencelabelsize2 initializerrange0 02 coordinatesize6 shapesize6 numlabels3 numchoices4 scopenone rangebbox1000 self parent parent self batchsize batchsize self numchannels numchannels self imagesize imagesize self patchsize patchsize self istraining istraining self useinputmask useinputmask self usetokentypeids usetokentypeids self uselabels uselabels self vocabsize vocabsize self hiddensize hiddensize self numhiddenlayers numhiddenlayers self numattentionheads numattentionheads self intermediatesize intermediatesize self hiddenact hiddenact self hiddendropoutprob hiddendropoutprob self attentionprobsdropoutprob attentionprobsdropoutprob self maxpositionembeddings maxpositionembeddings self typevocabsize typevocabsize self typesequencelabelsize typesequencelabelsize self initializerrange initializerrange self coordinatesize coordinatesize self shapesize shapesize self numlabels numlabels self numchoices numchoices self scope scope self rangebbox rangebbox layoutlmv3 s sequence length equals the number of text tokens number of patches 1 we add 1 for the cls token self textseqlength textseqlength self imageseqlength imagesize patchsize 2 1 self seqlength self textseqlength self imageseqlength def prepareconfigandinputsself inputids idstensorself batchsize self textseqlength self vocabsize bbox idstensorself batchsize self textseqlength 4 self rangebbox bbox bbox numpy ensure that bbox is legal for i in rangebbox shape0 for j in rangebbox shape1 if bboxi j 3 bboxi j 1 tmpcoordinate bboxi j 3 bboxi j 3 bboxi j 1 bboxi j 1 tmpcoordinate if bboxi j 2 bboxi j 0 tmpcoordinate bboxi j 2 bboxi j 2 bboxi j 0 bboxi j 0 tmpcoordinate bbox tf constantbbox pixelvalues floatstensorself batchsize self numchannels self imagesize self imagesize inputmask none if self useinputmask inputmask randomattentionmaskself batchsize self textseqlength tokentypeids none if self usetokentypeids tokentypeids idstensorself batchsize self textseqlength self typevocabsize sequencelabels none tokenlabels none if self uselabels sequencelabels idstensorself batchsize self typesequencelabelsize tokenlabels idstensorself batchsize self textseqlength self numlabels config layoutlmv3config vocabsizeself vocabsize hiddensizeself hiddensize numhiddenlayersself numhiddenlayers numattentionheadsself numattentionheads intermediatesizeself intermediatesize hiddenactself hiddenact hiddendropoutprobself hiddendropoutprob attentionprobsdropoutprobself attentionprobsdropoutprob maxpositionembeddingsself maxpositionembeddings typevocabsizeself typevocabsize initializerrangeself initializerrange coordinatesizeself coordinatesize shapesizeself shapesize inputsizeself imagesize patchsizeself patchsize return config inputids bbox pixelvalues tokentypeids inputmask sequencelabels tokenlabels def createandcheckmodelself config inputids bbox pixelvalues tokentypeids inputmask model tflayoutlmv3modelconfigconfig text image result modelinputids pixelvaluespixelvalues trainingfalse result model inputids bboxbbox pixelvaluespixelvalues attentionmaskinputmask tokentypeidstokentypeids trainingfalse result modelinputids bboxbbox pixelvaluespixelvalues trainingfalse self parent assertequalresult lasthiddenstate shape self batchsize self seqlength self hiddensize text only result modelinputids trainingfalse self parent assertequal result lasthiddenstate shape self batchsize self textseqlength self hiddensize image only result modelpixelvalues pixelvalues trainingfalse self parent assertequal result lasthiddenstate shape self batchsize self imageseqlength self hiddensize def createandcheckforsequenceclassification self config inputids bbox pixelvalues tokentypeids inputmask sequencelabels config numlabels self numlabels model tflayoutlmv3forsequenceclassificationconfigconfig result model inputids bboxbbox pixelvaluespixelvalues attentionmaskinputmask tokentypeidstokentypeids labelssequencelabels trainingfalse self parent assertequalresult logits shape self batchsize self numlabels def createandcheckfortokenclassification self config inputids bbox pixelvalues tokentypeids inputmask tokenlabels config numlabels self numlabels model tflayoutlmv3fortokenclassificationconfigconfig result model inputids bboxbbox pixelvaluespixelvalues attentionmaskinputmask tokentypeidstokentypeids labelstokenlabels trainingfalse self parent assertequalresult logits shape self batchsize self textseqlength self numlabels def createandcheckforquestionanswering self config inputids bbox pixelvalues tokentypeids inputmask sequencelabels config numlabels 2 model tflayoutlmv3forquestionansweringconfigconfig result model inputids bboxbbox pixelvaluespixelvalues attentionmaskinputmask tokentypeidstokentypeids startpositionssequencelabels endpositionssequencelabels trainingfalse self parent assertequalresult startlogits shape self batchsize self seqlength self parent assertequalresult endlogits shape self batchsize self seqlength def prepareconfigandinputsforcommonself configandinputs self prepareconfigandinputs config inputids bbox pixelvalues tokentypeids inputmask configandinputs inputsdict inputids inputids bbox bbox pixelvalues pixelvalues tokentypeids tokentypeids attentionmask inputmask return config inputsdict requiretf class tflayoutlmv3modeltesttfmodeltestermixin pipelinetestermixin unittest testcase allmodelclasses tflayoutlmv3model tflayoutlmv3forquestionanswering tflayoutlmv3forsequenceclassification tflayoutlmv3fortokenclassification if istfavailable else pipelinemodelmapping documentquestionanswering tflayoutlmv3forquestionanswering featureextraction tflayoutlmv3model if istfavailable else testpruning false testresizeembeddings false testonnx false todo fix the failed tests def ispipelinetesttoskip self pipelinetestcassename configclass modelarchitecture tokenizername processorname return true def prepareforclassself inputsdict modelclass returnlabelsfalse dict inputsdict copy deepcopyinputsdict if modelclass in getvaluestfmodelformultiplechoicemapping inputsdict k tf tiletf expanddimsv 1 1 self modeltester numchoices 1 v ndim 1 if isinstancev tf tensor and v ndim 0 else v for k v in inputsdict items if returnlabels if modelclass in getvaluestfmodelformultiplechoicemapping inputsdictlabels tf onesself modeltester batchsize dtypetf int32 elif modelclass in getvaluestfmodelforquestionansweringmapping inputsdictstartpositions tf zerosself modeltester batchsize dtypetf int32 inputsdictendpositions tf zerosself modeltester batchsize dtypetf int32 elif modelclass in getvaluestfmodelforsequenceclassificationmapping inputsdictlabels tf zerosself modeltester batchsize dtypetf int32 elif modelclass in getvaluestfmodelfortokenclassificationmapping inputsdictlabels tf zeros self modeltester batchsize self modeltester textseqlength dtypetf int32 return inputsdict def setupself self modeltester tflayoutlmv3modeltesterself self configtester configtesterself configclasslayoutlmv3config hiddensize37 def testconfigself self configtester runcommontests def testlosscomputationself config inputsdict self modeltester prepareconfigandinputsforcommon for modelclass in self allmodelclasses model modelclassconfig if getattrmodel hfcomputeloss none the number of elements in the loss should be the same as the number of elements in the label preparedforclass self prepareforclassinputsdict copy modelclass returnlabelstrue addedlabel preparedforclass sortedpreparedforclass keys inputsdict keys reversetrue0 expectedlosssize addedlabel shape aslist 1 test that model correctly compute the loss with kwargs preparedforclass self prepareforclassinputsdict copy modelclass returnlabelstrue inputids preparedforclass popinputids loss modelinputids preparedforclass0 self asserttrueloss shape aslist expectedlosssize or loss shape aslist 1 test that model correctly compute the loss when we mask some positions preparedforclass self prepareforclassinputsdict copy modelclass returnlabelstrue inputids preparedforclass popinputids if labels in preparedforclass labels preparedforclasslabels numpy if lenlabels shape 1 and labels shape1 1 labels0 100 preparedforclasslabels tf converttotensorlabels loss modelinputids preparedforclass0 self asserttrueloss shape aslist expectedlosssize or loss shape aslist 1 self asserttruenot np anynp isnanloss numpy test that model correctly compute the loss with a dict preparedforclass self prepareforclassinputsdict copy modelclass returnlabelstrue loss modelpreparedforclass0 self asserttrueloss shape aslist expectedlosssize or loss shape aslist 1 test that model correctly compute the loss with a tuple preparedforclass self prepareforclassinputsdict copy modelclass returnlabelstrue get keys that were added with the prepareforclass function labelkeys preparedforclass keys inputsdict keys signature inspect signaturemodel call parameters signaturenames listsignature keys create a dictionary holding the location of the tensors in the tuple tupleindexmapping 0 inputids for labelkey in labelkeys labelkeyindex signaturenames indexlabelkey tupleindexmappinglabelkeyindex labelkey sortedtupleindexmapping sortedtupleindexmapping items initialize a list with their default values update the values and convert to a tuple listinput for name in signaturenames if name kwargs listinput appendsignaturename default for index value in sortedtupleindexmapping listinputindex preparedforclassvalue tupleinput tuplelistinput send to model loss modeltupleinput 10 self asserttrueloss shape aslist expectedlosssize or loss shape aslist 1 def testmodelself config inputids bbox pixelvalues tokentypeids inputmask self modeltester prepareconfigandinputs self modeltester createandcheckmodelconfig inputids bbox pixelvalues tokentypeids inputmask def testmodelvariousembeddingsself config inputids bbox pixelvalues tokentypeids inputmask self modeltester prepareconfigandinputs for type in absolute relativekey relativekeyquery config positionembeddingtype type self modeltester createandcheckmodelconfig inputids bbox pixelvalues tokentypeids inputmask def testforsequenceclassificationself config inputids bbox pixelvalues tokentypeids inputmask sequencelabels self modeltester prepareconfigandinputs self modeltester createandcheckforsequenceclassification config inputids bbox pixelvalues tokentypeids inputmask sequencelabels def testfortokenclassificationself config inputids bbox pixelvalues tokentypeids inputmask tokenlabels self modeltester prepareconfigandinputs self modeltester createandcheckfortokenclassification config inputids bbox pixelvalues tokentypeids inputmask tokenlabels def testforquestionansweringself config inputids bbox pixelvalues tokentypeids inputmask sequencelabels self modeltester prepareconfigandinputs self modeltester createandcheckforquestionanswering config inputids bbox pixelvalues tokentypeids inputmask sequencelabels slow def testmodelfrompretrainedself for modelname in tflayoutlmv3pretrainedmodelarchivelist 1 model tflayoutlmv3model frompretrainedmodelname self assertisnotnonemodel we will verify our results on an image of cute cats def prepareimg image image open testsfixturestestssamplescoco000000039769 png return image requiretf class tflayoutlmv3modelintegrationtestunittest testcase cachedproperty def defaultimageprocessorself return layoutlmv3imageprocessorapplyocrfalse if isvisionavailable else none slow def testinferencenoheadself model tflayoutlmv3model frompretrainedmicrosoftlayoutlmv3base imageprocessor self defaultimageprocessor image prepareimg pixelvalues imageprocessorimagesimage returntensorstf pixelvalues inputids tf constant1 2 bbox tf expanddimstf constant1 2 3 4 5 6 7 8 axis0 forward pass outputs modelinputidsinputids bboxbbox pixelvaluespixelvalues trainingfalse verify the logits expectedshape 1 199 768 self assertequaloutputs lasthiddenstate shape expectedshape expectedslice tf constant 0 0529 0 3618 0 1632 0 1587 0 1667 0 0400 0 1557 0 1671 0 0505 self asserttruenp allcloseoutputs lasthiddenstate0 3 3 expectedslice atol1e4 coding utf 8 2022 the huggingface inc team licensed under the apache license version 2 0 the license you may not use this file except in compliance with the license you may obtain a copy of the license at http www apache org licenses license 2 0 unless required by applicable law or agreed to in writing software distributed under the license is distributed on an as is basis without warranties or conditions of any kind either express or implied see the license for the specific language governing permissions and limitations under the license testing suite for the tensorflow layoutlmv3 model layoutlmv3 s sequence length equals the number of text tokens number of patches 1 we add 1 for the cls token ensure that bbox is legal text image text only image only todo fix the failed tests the number of elements in the loss should be the same as the number of elements in the label test that model correctly compute the loss with kwargs test that model correctly compute the loss when we mask some positions test that model correctly compute the loss with a dict test that model correctly compute the loss with a tuple get keys that were added with the _prepare_for_class function create a dictionary holding the location of the tensors in the tuple initialize a list with their default values update the values and convert to a tuple send to model we will verify our results on an image of cute cats forward pass verify the logits
from __future__ import annotations

import copy
import inspect
import unittest

import numpy as np

from transformers import is_tf_available, is_vision_available
from transformers.models.auto import get_values
from transformers.testing_utils import require_tf, slow
from transformers.utils import cached_property

from ...test_configuration_common import ConfigTester
from ...test_modeling_tf_common import TFModelTesterMixin, floats_tensor, ids_tensor, random_attention_mask
from ...test_pipeline_mixin import PipelineTesterMixin


if is_tf_available():
    import tensorflow as tf

    from transformers import (
        TF_LAYOUTLMV3_PRETRAINED_MODEL_ARCHIVE_LIST,
        TF_MODEL_FOR_MULTIPLE_CHOICE_MAPPING,
        TF_MODEL_FOR_QUESTION_ANSWERING_MAPPING,
        TF_MODEL_FOR_SEQUENCE_CLASSIFICATION_MAPPING,
        TF_MODEL_FOR_TOKEN_CLASSIFICATION_MAPPING,
        LayoutLMv3Config,
        TFLayoutLMv3ForQuestionAnswering,
        TFLayoutLMv3ForSequenceClassification,
        TFLayoutLMv3ForTokenClassification,
        TFLayoutLMv3Model,
    )

if is_vision_available():
    from PIL import Image

    from transformers import LayoutLMv3ImageProcessor


class TFLayoutLMv3ModelTester:
    def __init__(
        self,
        parent,
        batch_size=2,
        num_channels=3,
        image_size=4,
        patch_size=2,
        text_seq_length=7,
        is_training=True,
        use_input_mask=True,
        use_token_type_ids=True,
        use_labels=True,
        vocab_size=99,
        hidden_size=36,
        num_hidden_layers=2,
        num_attention_heads=4,
        intermediate_size=37,
        hidden_act="gelu",
        hidden_dropout_prob=0.1,
        attention_probs_dropout_prob=0.1,
        max_position_embeddings=512,
        type_vocab_size=16,
        type_sequence_label_size=2,
        initializer_range=0.02,
        coordinate_size=6,
        shape_size=6,
        num_labels=3,
        num_choices=4,
        scope=None,
        range_bbox=1000,
    ):
        self.parent = parent
        self.batch_size = batch_size
        self.num_channels = num_channels
        self.image_size = image_size
        self.patch_size = patch_size
        self.is_training = is_training
        self.use_input_mask = use_input_mask
        self.use_token_type_ids = use_token_type_ids
        self.use_labels = use_labels
        self.vocab_size = vocab_size
        self.hidden_size = hidden_size
        self.num_hidden_layers = num_hidden_layers
        self.num_attention_heads = num_attention_heads
        self.intermediate_size = intermediate_size
        self.hidden_act = hidden_act
        self.hidden_dropout_prob = hidden_dropout_prob
        self.attention_probs_dropout_prob = attention_probs_dropout_prob
        self.max_position_embeddings = max_position_embeddings
        self.type_vocab_size = type_vocab_size
        self.type_sequence_label_size = type_sequence_label_size
        self.initializer_range = initializer_range
        self.coordinate_size = coordinate_size
        self.shape_size = shape_size
        self.num_labels = num_labels
        self.num_choices = num_choices
        self.scope = scope
        self.range_bbox = range_bbox

        
        self.text_seq_length = text_seq_length
        self.image_seq_length = (image_size // patch_size) ** 2 + 1
        self.seq_length = self.text_seq_length + self.image_seq_length

    def prepare_config_and_inputs(self):
        input_ids = ids_tensor([self.batch_size, self.text_seq_length], self.vocab_size)

        bbox = ids_tensor([self.batch_size, self.text_seq_length, 4], self.range_bbox)
        bbox = bbox.numpy()
        
        for i in range(bbox.shape[0]):
            for j in range(bbox.shape[1]):
                if bbox[i, j, 3] < bbox[i, j, 1]:
                    tmp_coordinate = bbox[i, j, 3]
                    bbox[i, j, 3] = bbox[i, j, 1]
                    bbox[i, j, 1] = tmp_coordinate
                if bbox[i, j, 2] < bbox[i, j, 0]:
                    tmp_coordinate = bbox[i, j, 2]
                    bbox[i, j, 2] = bbox[i, j, 0]
                    bbox[i, j, 0] = tmp_coordinate
        bbox = tf.constant(bbox)

        pixel_values = floats_tensor([self.batch_size, self.num_channels, self.image_size, self.image_size])

        input_mask = None
        if self.use_input_mask:
            input_mask = random_attention_mask([self.batch_size, self.text_seq_length])

        token_type_ids = None
        if self.use_token_type_ids:
            token_type_ids = ids_tensor([self.batch_size, self.text_seq_length], self.type_vocab_size)

        sequence_labels = None
        token_labels = None
        if self.use_labels:
            sequence_labels = ids_tensor([self.batch_size], self.type_sequence_label_size)
            token_labels = ids_tensor([self.batch_size, self.text_seq_length], self.num_labels)

        config = LayoutLMv3Config(
            vocab_size=self.vocab_size,
            hidden_size=self.hidden_size,
            num_hidden_layers=self.num_hidden_layers,
            num_attention_heads=self.num_attention_heads,
            intermediate_size=self.intermediate_size,
            hidden_act=self.hidden_act,
            hidden_dropout_prob=self.hidden_dropout_prob,
            attention_probs_dropout_prob=self.attention_probs_dropout_prob,
            max_position_embeddings=self.max_position_embeddings,
            type_vocab_size=self.type_vocab_size,
            initializer_range=self.initializer_range,
            coordinate_size=self.coordinate_size,
            shape_size=self.shape_size,
            input_size=self.image_size,
            patch_size=self.patch_size,
        )

        return config, input_ids, bbox, pixel_values, token_type_ids, input_mask, sequence_labels, token_labels

    def create_and_check_model(self, config, input_ids, bbox, pixel_values, token_type_ids, input_mask):
        model = TFLayoutLMv3Model(config=config)

        
        result = model(input_ids, pixel_values=pixel_values, training=False)
        result = model(
            input_ids,
            bbox=bbox,
            pixel_values=pixel_values,
            attention_mask=input_mask,
            token_type_ids=token_type_ids,
            training=False,
        )
        result = model(input_ids, bbox=bbox, pixel_values=pixel_values, training=False)

        self.parent.assertEqual(result.last_hidden_state.shape, (self.batch_size, self.seq_length, self.hidden_size))

        
        result = model(input_ids, training=False)
        self.parent.assertEqual(
            result.last_hidden_state.shape, (self.batch_size, self.text_seq_length, self.hidden_size)
        )

        
        result = model({"pixel_values": pixel_values}, training=False)
        self.parent.assertEqual(
            result.last_hidden_state.shape, (self.batch_size, self.image_seq_length, self.hidden_size)
        )

    def create_and_check_for_sequence_classification(
        self, config, input_ids, bbox, pixel_values, token_type_ids, input_mask, sequence_labels
    ):
        config.num_labels = self.num_labels
        model = TFLayoutLMv3ForSequenceClassification(config=config)
        result = model(
            input_ids,
            bbox=bbox,
            pixel_values=pixel_values,
            attention_mask=input_mask,
            token_type_ids=token_type_ids,
            labels=sequence_labels,
            training=False,
        )
        self.parent.assertEqual(result.logits.shape, (self.batch_size, self.num_labels))

    def create_and_check_for_token_classification(
        self, config, input_ids, bbox, pixel_values, token_type_ids, input_mask, token_labels
    ):
        config.num_labels = self.num_labels
        model = TFLayoutLMv3ForTokenClassification(config=config)
        result = model(
            input_ids,
            bbox=bbox,
            pixel_values=pixel_values,
            attention_mask=input_mask,
            token_type_ids=token_type_ids,
            labels=token_labels,
            training=False,
        )
        self.parent.assertEqual(result.logits.shape, (self.batch_size, self.text_seq_length, self.num_labels))

    def create_and_check_for_question_answering(
        self, config, input_ids, bbox, pixel_values, token_type_ids, input_mask, sequence_labels
    ):
        config.num_labels = 2
        model = TFLayoutLMv3ForQuestionAnswering(config=config)
        result = model(
            input_ids,
            bbox=bbox,
            pixel_values=pixel_values,
            attention_mask=input_mask,
            token_type_ids=token_type_ids,
            start_positions=sequence_labels,
            end_positions=sequence_labels,
            training=False,
        )
        self.parent.assertEqual(result.start_logits.shape, (self.batch_size, self.seq_length))
        self.parent.assertEqual(result.end_logits.shape, (self.batch_size, self.seq_length))

    def prepare_config_and_inputs_for_common(self):
        config_and_inputs = self.prepare_config_and_inputs()
        (config, input_ids, bbox, pixel_values, token_type_ids, input_mask, _, _) = config_and_inputs
        inputs_dict = {
            "input_ids": input_ids,
            "bbox": bbox,
            "pixel_values": pixel_values,
            "token_type_ids": token_type_ids,
            "attention_mask": input_mask,
        }
        return config, inputs_dict


@require_tf
class TFLayoutLMv3ModelTest(TFModelTesterMixin, PipelineTesterMixin, unittest.TestCase):
    all_model_classes = (
        (
            TFLayoutLMv3Model,
            TFLayoutLMv3ForQuestionAnswering,
            TFLayoutLMv3ForSequenceClassification,
            TFLayoutLMv3ForTokenClassification,
        )
        if is_tf_available()
        else ()
    )
    pipeline_model_mapping = (
        {"document-question-answering": TFLayoutLMv3ForQuestionAnswering, "feature-extraction": TFLayoutLMv3Model}
        if is_tf_available()
        else {}
    )

    test_pruning = False
    test_resize_embeddings = False
    test_onnx = False

    
    def is_pipeline_test_to_skip(
        self, pipeline_test_casse_name, config_class, model_architecture, tokenizer_name, processor_name
    ):
        return True

    def _prepare_for_class(self, inputs_dict, model_class, return_labels=False) -> dict:
        inputs_dict = copy.deepcopy(inputs_dict)

        if model_class in get_values(TF_MODEL_FOR_MULTIPLE_CHOICE_MAPPING):
            inputs_dict = {
                k: tf.tile(tf.expand_dims(v, 1), (1, self.model_tester.num_choices) + (1,) * (v.ndim - 1))
                if isinstance(v, tf.Tensor) and v.ndim > 0
                else v
                for k, v in inputs_dict.items()
            }

        if return_labels:
            if model_class in get_values(TF_MODEL_FOR_MULTIPLE_CHOICE_MAPPING):
                inputs_dict["labels"] = tf.ones(self.model_tester.batch_size, dtype=tf.int32)
            elif model_class in get_values(TF_MODEL_FOR_QUESTION_ANSWERING_MAPPING):
                inputs_dict["start_positions"] = tf.zeros(self.model_tester.batch_size, dtype=tf.int32)
                inputs_dict["end_positions"] = tf.zeros(self.model_tester.batch_size, dtype=tf.int32)
            elif model_class in get_values(TF_MODEL_FOR_SEQUENCE_CLASSIFICATION_MAPPING):
                inputs_dict["labels"] = tf.zeros(self.model_tester.batch_size, dtype=tf.int32)
            elif model_class in get_values(TF_MODEL_FOR_TOKEN_CLASSIFICATION_MAPPING):
                inputs_dict["labels"] = tf.zeros(
                    (self.model_tester.batch_size, self.model_tester.text_seq_length), dtype=tf.int32
                )

        return inputs_dict

    def setUp(self):
        self.model_tester = TFLayoutLMv3ModelTester(self)
        self.config_tester = ConfigTester(self, config_class=LayoutLMv3Config, hidden_size=37)

    def test_config(self):
        self.config_tester.run_common_tests()

    def test_loss_computation(self):
        config, inputs_dict = self.model_tester.prepare_config_and_inputs_for_common()
        for model_class in self.all_model_classes:
            model = model_class(config)
            if getattr(model, "hf_compute_loss", None):
                
                prepared_for_class = self._prepare_for_class(inputs_dict.copy(), model_class, return_labels=True)
                added_label = prepared_for_class[
                    sorted(prepared_for_class.keys() - inputs_dict.keys(), reverse=True)[0]
                ]
                expected_loss_size = added_label.shape.as_list()[:1]

                
                prepared_for_class = self._prepare_for_class(inputs_dict.copy(), model_class, return_labels=True)
                input_ids = prepared_for_class.pop("input_ids")

                loss = model(input_ids, **prepared_for_class)[0]
                self.assertTrue(loss.shape.as_list() == expected_loss_size or loss.shape.as_list() == [1])

                
                prepared_for_class = self._prepare_for_class(inputs_dict.copy(), model_class, return_labels=True)
                input_ids = prepared_for_class.pop("input_ids")
                if "labels" in prepared_for_class:
                    labels = prepared_for_class["labels"].numpy()
                    if len(labels.shape) > 1 and labels.shape[1] != 1:
                        labels[0] = -100
                        prepared_for_class["labels"] = tf.convert_to_tensor(labels)
                        loss = model(input_ids, **prepared_for_class)[0]
                        self.assertTrue(loss.shape.as_list() == expected_loss_size or loss.shape.as_list() == [1])
                        self.assertTrue(not np.any(np.isnan(loss.numpy())))

                
                prepared_for_class = self._prepare_for_class(inputs_dict.copy(), model_class, return_labels=True)
                loss = model(prepared_for_class)[0]
                self.assertTrue(loss.shape.as_list() == expected_loss_size or loss.shape.as_list() == [1])

                
                prepared_for_class = self._prepare_for_class(inputs_dict.copy(), model_class, return_labels=True)

                
                label_keys = prepared_for_class.keys() - inputs_dict.keys()
                signature = inspect.signature(model.call).parameters
                signature_names = list(signature.keys())

                
                tuple_index_mapping = {0: "input_ids"}
                for label_key in label_keys:
                    label_key_index = signature_names.index(label_key)
                    tuple_index_mapping[label_key_index] = label_key
                sorted_tuple_index_mapping = sorted(tuple_index_mapping.items())
                
                list_input = []

                for name in signature_names:
                    if name != "kwargs":
                        list_input.append(signature[name].default)

                for index, value in sorted_tuple_index_mapping:
                    list_input[index] = prepared_for_class[value]

                tuple_input = tuple(list_input)

                
                loss = model(tuple_input[:-1])[0]

                self.assertTrue(loss.shape.as_list() == expected_loss_size or loss.shape.as_list() == [1])

    def test_model(self):
        (
            config,
            input_ids,
            bbox,
            pixel_values,
            token_type_ids,
            input_mask,
            _,
            _,
        ) = self.model_tester.prepare_config_and_inputs()
        self.model_tester.create_and_check_model(config, input_ids, bbox, pixel_values, token_type_ids, input_mask)

    def test_model_various_embeddings(self):
        (
            config,
            input_ids,
            bbox,
            pixel_values,
            token_type_ids,
            input_mask,
            _,
            _,
        ) = self.model_tester.prepare_config_and_inputs()
        for type in ["absolute", "relative_key", "relative_key_query"]:
            config.position_embedding_type = type
            self.model_tester.create_and_check_model(config, input_ids, bbox, pixel_values, token_type_ids, input_mask)

    def test_for_sequence_classification(self):
        (
            config,
            input_ids,
            bbox,
            pixel_values,
            token_type_ids,
            input_mask,
            sequence_labels,
            _,
        ) = self.model_tester.prepare_config_and_inputs()
        self.model_tester.create_and_check_for_sequence_classification(
            config, input_ids, bbox, pixel_values, token_type_ids, input_mask, sequence_labels
        )

    def test_for_token_classification(self):
        (
            config,
            input_ids,
            bbox,
            pixel_values,
            token_type_ids,
            input_mask,
            _,
            token_labels,
        ) = self.model_tester.prepare_config_and_inputs()
        self.model_tester.create_and_check_for_token_classification(
            config, input_ids, bbox, pixel_values, token_type_ids, input_mask, token_labels
        )

    def test_for_question_answering(self):
        (
            config,
            input_ids,
            bbox,
            pixel_values,
            token_type_ids,
            input_mask,
            sequence_labels,
            _,
        ) = self.model_tester.prepare_config_and_inputs()
        self.model_tester.create_and_check_for_question_answering(
            config, input_ids, bbox, pixel_values, token_type_ids, input_mask, sequence_labels
        )

    @slow
    def test_model_from_pretrained(self):
        for model_name in TF_LAYOUTLMV3_PRETRAINED_MODEL_ARCHIVE_LIST[:1]:
            model = TFLayoutLMv3Model.from_pretrained(model_name)
            self.assertIsNotNone(model)



def prepare_img():
    image = Image.open("./tests/fixtures/tests_samples/COCO/000000039769.png")
    return image


@require_tf
class TFLayoutLMv3ModelIntegrationTest(unittest.TestCase):
    @cached_property
    def default_image_processor(self):
        return LayoutLMv3ImageProcessor(apply_ocr=False) if is_vision_available() else None

    @slow
    def test_inference_no_head(self):
        model = TFLayoutLMv3Model.from_pretrained("microsoft/layoutlmv3-base")

        image_processor = self.default_image_processor
        image = prepare_img()
        pixel_values = image_processor(images=image, return_tensors="tf").pixel_values

        input_ids = tf.constant([[1, 2]])
        bbox = tf.expand_dims(tf.constant([[1, 2, 3, 4], [5, 6, 7, 8]]), axis=0)

        
        outputs = model(input_ids=input_ids, bbox=bbox, pixel_values=pixel_values, training=False)

        
        expected_shape = (1, 199, 768)
        self.assertEqual(outputs.last_hidden_state.shape, expected_shape)

        expected_slice = tf.constant(
            [[-0.0529, 0.3618, 0.1632], [-0.1587, -0.1667, -0.0400], [-0.1557, -0.1671, -0.0505]]
        )

        self.assertTrue(np.allclose(outputs.last_hidden_state[0, :3, :3], expected_slice, atol=1e-4))