


'''simple docstring'''
import html

from ...feature_extraction_utils import BatchFeature, FeatureExtractionMixin
from ...utils import is_bsa_available, logging, requires_backends


if is_bsa_available():
		import bsa
		from bsa import BeautifulSoup


__snake_case				 =	logging.get_logger(__name__)
class   lowercase      (				A__   ):

		"""simple docstring"""

		def __init__(						self       ,  **UpperCamelCase_				):

							'''simple docstring'''


							requires_backends(self       ,  ['''bs4''']				)
							super().__init__(**UpperCamelCase_				)




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_				):

							'''simple docstring'''


							UpperCamelCase__  :str				   =					[]
							UpperCamelCase__  :int				   =					[]
							UpperCamelCase__  :int				   =					element if element.name else element.parent
							for parent in child.parents:  # type: bs4.element.Tag
												UpperCamelCase__  :int				   =					parent.find_all(child.name       ,  recursive=UpperCamelCase_				)
												xpath_tags.append(child.name				)
												xpath_subscripts.append(
												    0 if 1 == len(UpperCamelCase_				) else next(i for i, s in enumerate(UpperCamelCase_       ,  1				) if s is child				)				)
												UpperCamelCase__  :Optional[int]				   =					parent
							xpath_tags.reverse()
							xpath_subscripts.reverse()
							return xpath_tags, xpath_subscripts




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_				):

							'''simple docstring'''


							UpperCamelCase__  :int				   =					BeautifulSoup(UpperCamelCase_       ,  '''html.parser'''				)

							UpperCamelCase__  :List[Any]				   =					[]
							UpperCamelCase__  :Optional[int]				   =					[]
							UpperCamelCase__  :Optional[int]				   =					[]

							for element in html_code.descendants:
												if type(UpperCamelCase_				) == bsa.element.NavigableString:
																	if type(element.parent				) != bsa.element.Tag:
																						continue

																	UpperCamelCase__  :List[str]				   =					html.unescape(UpperCamelCase_				).strip()
																	if not text_in_this_tag:
																						continue

																	all_doc_strings.append(UpperCamelCase_				)

																	UpperCamelCase__   ,							UpperCamelCase__  :Any				   =					self.xpath_soup(UpperCamelCase_				)
																	stringaxtag_seq.append(UpperCamelCase_				)
																	stringaxsubs_seq.append(UpperCamelCase_				)

							if len(UpperCamelCase_				) != len(UpperCamelCase_				):
												raise ValueError('''Number of doc strings and xtags does not correspond'''				)
							if len(UpperCamelCase_				) != len(UpperCamelCase_				):
												raise ValueError('''Number of doc strings and xsubs does not correspond'''				)

							return all_doc_strings, stringaxtag_seq, stringaxsubs_seq




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_       ,  UpperCamelCase_				):

							'''simple docstring'''


							UpperCamelCase__  :Union[str, Any]				   =					''''''
							for tagname, subs in zip(UpperCamelCase_       ,  UpperCamelCase_				):
												xpath += F'''/{tagname}'''
												if subs != 0:
																	xpath += F'''[{subs}]'''
							return xpath




		def __call__(						self       ,  UpperCamelCase_				):

							'''simple docstring'''


							UpperCamelCase__  :Dict				   =					False

							# Check that strings has a valid type
							if isinstance(UpperCamelCase_       ,  UpperCamelCase_				):
												UpperCamelCase__  :Optional[int]				   =					True
							elif isinstance(UpperCamelCase_       ,  (list, tuple)				):
												if len(UpperCamelCase_				) == 0 or isinstance(html_strings[0]       ,  UpperCamelCase_				):
																	UpperCamelCase__  :Optional[Any]				   =					True

							if not valid_strings:
												raise ValueError(
												    '''HTML strings must of type `str`, `List[str]` (batch of examples), '''
												    F'''but is of type {type(UpperCamelCase_				)}.'''				)

							UpperCamelCase__  :List[str]				   =					bool(isinstance(UpperCamelCase_       ,  (list, tuple)				) and (isinstance(html_strings[0]       ,  UpperCamelCase_				))				)

							if not is_batched:
												UpperCamelCase__  :List[Any]				   =					[html_strings]

							# Get nodes + xpaths
							UpperCamelCase__  :Union[str, Any]				   =					[]
							UpperCamelCase__  :Dict				   =					[]
							for html_string in html_strings:
												UpperCamelCase__   ,							UpperCamelCase__   ,							UpperCamelCase__  :int				   =					self.get_three_from_single(UpperCamelCase_				)
												nodes.append(UpperCamelCase_				)
												UpperCamelCase__  :Optional[Any]				   =					[]
												for node, tag_list, sub_list in zip(UpperCamelCase_       ,  UpperCamelCase_       ,  UpperCamelCase_				):
																	UpperCamelCase__  :List[str]				   =					self.construct_xpath(UpperCamelCase_       ,  UpperCamelCase_				)
																	xpath_strings.append(UpperCamelCase_				)
												xpaths.append(UpperCamelCase_				)

							# return as Dict
							UpperCamelCase__  :int				   =					{'''nodes''': nodes, '''xpaths''': xpaths}
							UpperCamelCase__  :Tuple				   =					BatchFeature(data=UpperCamelCase_       ,  tensor_type=UpperCamelCase_				)

							return encoded_inputs



'''simple docstring'''
import json
from typing import List, Optional, Tuple

from tokenizers import normalizers

from ...tokenization_utils_fast import PreTrainedTokenizerFast
from .tokenization_electra import ElectraTokenizer


__snake_case				 =	{'''vocab_file''': '''vocab.txt''', '''tokenizer_file''': '''tokenizer.json'''}

__snake_case				 =	{
    '''vocab_file''': {
        '''google/electra-small-generator''': (
            '''https://huggingface.co/google/electra-small-generator/resolve/main/vocab.txt'''
        ),
        '''google/electra-base-generator''': '''https://huggingface.co/google/electra-base-generator/resolve/main/vocab.txt''',
        '''google/electra-large-generator''': (
            '''https://huggingface.co/google/electra-large-generator/resolve/main/vocab.txt'''
        ),
        '''google/electra-small-discriminator''': (
            '''https://huggingface.co/google/electra-small-discriminator/resolve/main/vocab.txt'''
        ),
        '''google/electra-base-discriminator''': (
            '''https://huggingface.co/google/electra-base-discriminator/resolve/main/vocab.txt'''
        ),
        '''google/electra-large-discriminator''': (
            '''https://huggingface.co/google/electra-large-discriminator/resolve/main/vocab.txt'''
        ),
    },
    '''tokenizer_file''': {
        '''google/electra-small-generator''': (
            '''https://huggingface.co/google/electra-small-generator/resolve/main/tokenizer.json'''
        ),
        '''google/electra-base-generator''': (
            '''https://huggingface.co/google/electra-base-generator/resolve/main/tokenizer.json'''
        ),
        '''google/electra-large-generator''': (
            '''https://huggingface.co/google/electra-large-generator/resolve/main/tokenizer.json'''
        ),
        '''google/electra-small-discriminator''': (
            '''https://huggingface.co/google/electra-small-discriminator/resolve/main/tokenizer.json'''
        ),
        '''google/electra-base-discriminator''': (
            '''https://huggingface.co/google/electra-base-discriminator/resolve/main/tokenizer.json'''
        ),
        '''google/electra-large-discriminator''': (
            '''https://huggingface.co/google/electra-large-discriminator/resolve/main/tokenizer.json'''
        ),
    },
}

__snake_case				 =	{
    '''google/electra-small-generator''': 512,
    '''google/electra-base-generator''': 512,
    '''google/electra-large-generator''': 512,
    '''google/electra-small-discriminator''': 512,
    '''google/electra-base-discriminator''': 512,
    '''google/electra-large-discriminator''': 512,
}

__snake_case				 =	{
    '''google/electra-small-generator''': {'''do_lower_case''': True},
    '''google/electra-base-generator''': {'''do_lower_case''': True},
    '''google/electra-large-generator''': {'''do_lower_case''': True},
    '''google/electra-small-discriminator''': {'''do_lower_case''': True},
    '''google/electra-base-discriminator''': {'''do_lower_case''': True},
    '''google/electra-large-discriminator''': {'''do_lower_case''': True},
}
class   lowercase      (				A__   ):

		"""simple docstring"""

		_a       					=							VOCAB_FILES_NAMES
		_a       					=							PRETRAINED_VOCAB_FILES_MAP
		_a       					=							PRETRAINED_INIT_CONFIGURATION
		_a       					=							PRETRAINED_POSITIONAL_EMBEDDINGS_SIZES
		_a       					=							ElectraTokenizer




		def __init__(						self       ,  UpperCamelCase_=None       ,  UpperCamelCase_=None       ,  UpperCamelCase_=True       ,  UpperCamelCase_="[UNK]"       ,  UpperCamelCase_="[SEP]"       ,  UpperCamelCase_="[PAD]"       ,  UpperCamelCase_="[CLS]"       ,  UpperCamelCase_="[MASK]"       ,  UpperCamelCase_=True       ,  UpperCamelCase_=None       ,  **UpperCamelCase_       ,  ):

							'''simple docstring'''


							super().__init__(
							    UpperCamelCase_       ,  tokenizer_file=UpperCamelCase_       ,  do_lower_case=UpperCamelCase_       ,  unk_token=UpperCamelCase_       ,  sep_token=UpperCamelCase_       ,  pad_token=UpperCamelCase_       ,  cls_token=UpperCamelCase_       ,  mask_token=UpperCamelCase_       ,  tokenize_chinese_chars=UpperCamelCase_       ,  strip_accents=UpperCamelCase_       ,  **UpperCamelCase_       ,  )

							UpperCamelCase__  :str				   =					json.loads(self.backend_tokenizer.normalizer.__getstate__()				)
							if (
							    normalizer_state.get('''lowercase'''       ,  UpperCamelCase_				) != do_lower_case
							    or normalizer_state.get('''strip_accents'''       ,  UpperCamelCase_				) != strip_accents
							    or normalizer_state.get('''handle_chinese_chars'''       ,  UpperCamelCase_				) != tokenize_chinese_chars
							):
												UpperCamelCase__  :Any				   =					getattr(UpperCamelCase_       ,  normalizer_state.pop('''type'''				)				)
												UpperCamelCase__  :Any				   =					do_lower_case
												UpperCamelCase__  :Dict				   =					strip_accents
												UpperCamelCase__  :Optional[int]				   =					tokenize_chinese_chars
												UpperCamelCase__  :Dict				   =					normalizer_class(**UpperCamelCase_				)

							UpperCamelCase__  :str				   =					do_lower_case




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_       ,  UpperCamelCase_=None				):

							'''simple docstring'''


							UpperCamelCase__  :Dict				   =					[self.cls_token_id] + token_ids_a + [self.sep_token_id]

							if token_ids_a:
												output += token_ids_a + [self.sep_token_id]

							return output




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_       ,  UpperCamelCase_ = None				):

							'''simple docstring'''


							UpperCamelCase__  :Union[str, Any]				   =					[self.sep_token_id]
							UpperCamelCase__  :str				   =					[self.cls_token_id]
							if token_ids_a is None:
												return len(cls + token_ids_a + sep				) * [0]
							return len(cls + token_ids_a + sep				) * [0] + len(token_ids_a + sep				) * [1]




		def        lowerCAmelCase__							(						self       ,  UpperCamelCase_       ,  UpperCamelCase_ = None				):

							'''simple docstring'''


							UpperCamelCase__  :str				   =					self._tokenizer.model.save(UpperCamelCase_       ,  name=UpperCamelCase_				)
							return tuple(UpperCamelCase_				)