Beispiel #1
0
def test_extract_fails_with_invalid_date(ai_code: str, bad_value: str) -> None:
    ai = GS1ApplicationIdentifier.extract(ai_code)

    with pytest.raises(ParseError) as exc_info:
        GS1ElementString.extract(f"{ai_code}{bad_value}")

    assert (str(exc_info.value) ==
            f"Failed to parse GS1 AI {ai} date from {bad_value!r}.")
Beispiel #2
0
def test_filter_element_strings_by_ai_instance() -> None:
    ai = GS1ApplicationIdentifier.extract("01")
    msg = GS1Message.parse("010703206980498815210526100329")

    element_string = msg.get(ai=ai)

    assert element_string is not None
    assert element_string.value == "07032069804988"
Beispiel #3
0
def test_extract_fails_when_not_matching_pattern(ai_code: str,
                                                 bad_value: str) -> None:
    ai = GS1ApplicationIdentifier.extract(ai_code)

    with pytest.raises(ParseError) as exc_info:
        GS1ElementString.extract(bad_value)

    assert (
        str(exc_info.value) ==
        f"Failed to match {bad_value!r} with GS1 AI {ai} pattern '{ai.pattern}'."
    )
Beispiel #4
0
    def extract(
        cls,
        value: str,
        *,
        rcn_region: Optional[RcnRegion] = None,
        separator_chars: Iterable[str] = DEFAULT_SEPARATOR_CHARS,
    ) -> GS1ElementString:
        """Extract the first GS1 Element String from the given value.

        Args:
            value: The string to extract an Element String from. May contain
                more than one Element String.
            rcn_region: The geographical region whose rules should be used to
                interpret Restricted Circulation Numbers (RCN).
                Needed to extract e.g. variable weight/price from GTIN.
            separator_chars: Characters used in place of the FNC1 symbol.
                Defaults to `<GS>` (ASCII value 29).
                If variable-length fields are not terminated with a separator
                character, the parser might greedily consume later fields.

        Returns:
            A data class with the Element String's parts and data extracted from it.

        Raises:
            ValueError: If the ``separator_char`` isn't exactly 1 character long.
            ParseError: If the parsing fails.
        """
        if any(len(char) != 1 for char in separator_chars):
            raise ValueError(
                "All separator characters must be exactly 1 character long, "
                f"got {list(separator_chars)!r}.")

        ai = GS1ApplicationIdentifier.extract(value)

        for separator_char in separator_chars:
            value = value.split(separator_char, maxsplit=1)[0]

        pattern = ai.pattern[:-1] if ai.pattern.endswith("$") else ai.pattern
        matches = re.match(pattern, value)
        if not matches:
            raise ParseError(
                f"Failed to match {value!r} with GS1 AI {ai} pattern '{ai.pattern}'."
            )
        pattern_groups = list(matches.groups())
        value = "".join(pattern_groups)

        element = cls(ai=ai, value=value, pattern_groups=pattern_groups)
        element._set_gln()
        element._set_gtin(rcn_region=rcn_region)
        element._set_sscc()
        element._set_date()
        element._set_decimal()

        return element
Beispiel #5
0
def parse(html_content: str) -> List[GS1ApplicationIdentifier]:
    """Parse the data from HTML to GS1ApplicationIdentifier objects."""
    result = []

    page = BeautifulSoup(html_content, "html.parser")
    datatable = page.find("table", {"class": ["datatable"]})
    tbody = datatable.find("tbody")

    for row in tbody.find_all("tr"):
        columns = row.find_all("td")
        result.append(
            GS1ApplicationIdentifier(
                ai=columns[0].text.strip(),
                description=columns[1].text.strip(),
                format=columns[2].text.strip(),
                data_title=columns[3].text.strip(),
                fnc1_required=columns[4].text.strip() == "Yes",
                pattern=columns[5].text.strip(),
            ))

    return result
Beispiel #6
0
import pytest

from biip import ParseError
from biip.gln import Gln
from biip.gs1 import GS1ApplicationIdentifier, GS1ElementString, GS1Prefix
from biip.gtin import Gtin, GtinFormat
from biip.sscc import Sscc


@pytest.mark.parametrize(
    "value, expected",
    [
        (
            "00373400306809981733",
            GS1ElementString(
                ai=GS1ApplicationIdentifier.extract("00"),
                value="373400306809981733",
                pattern_groups=["373400306809981733"],
                sscc=Sscc(
                    value="373400306809981733",
                    prefix=GS1Prefix(value="734", usage="GS1 Sweden"),
                    extension_digit=3,
                    payload="37340030680998173",
                    check_digit=3,
                ),
            ),
        ),
        (
            "0107032069804988",
            GS1ElementString(
                ai=GS1ApplicationIdentifier.extract("01"),
Beispiel #7
0
from biip.gtin import Gtin, GtinFormat


@pytest.mark.parametrize(
    "value, expected",
    [
        (
            "010703206980498815210526100329",
            GS1Message(
                value="010703206980498815210526100329",
                element_strings=[
                    GS1ElementString(
                        ai=GS1ApplicationIdentifier(
                            ai="01",
                            description="Global Trade Item Number (GTIN)",
                            data_title="GTIN",
                            fnc1_required=False,
                            format="N2+N14",
                            pattern="^01(\\d{14})$",
                        ),
                        value="07032069804988",
                        pattern_groups=["07032069804988"],
                        gtin=Gtin(
                            value="07032069804988",
                            format=GtinFormat.GTIN_13,
                            prefix=GS1Prefix(value="703", usage="GS1 Norway"),
                            payload="703206980498",
                            check_digit=8,
                        ),
                    ),
                    GS1ElementString(
                        ai=GS1ApplicationIdentifier(
Beispiel #8
0
def test_extract_unknown_gs1_ai(unknown_ai: str) -> None:
    with pytest.raises(ParseError) as exc_info:
        GS1ApplicationIdentifier.extract(unknown_ai)

    assert (str(exc_info.value) ==
            f"Failed to get GS1 Application Identifier from {unknown_ai!r}.")
Beispiel #9
0
def test_is_hashable() -> None:
    ai = GS1ApplicationIdentifier.extract("01")

    assert hash(ai) is not None
Beispiel #10
0
def test_gs1_ai_object_len_is_ai_str_len() -> None:
    ai = GS1ApplicationIdentifier.extract("01")

    assert len(ai) == len("01")
Beispiel #11
0
def test_extract_gs1_ai(value: str,
                        expected: GS1ApplicationIdentifier) -> None:
    assert GS1ApplicationIdentifier.extract(value) == expected
Beispiel #12
0
    with pytest.raises(ParseError) as exc_info:
        GS1ApplicationIdentifier.extract(unknown_ai)

    assert (str(exc_info.value) ==
            f"Failed to get GS1 Application Identifier from {unknown_ai!r}.")


@pytest.mark.parametrize(
    "value, expected",
    [
        (
            "0195012345678903",
            GS1ApplicationIdentifier(
                ai="01",
                description="Global Trade Item Number (GTIN)",
                data_title="GTIN",
                fnc1_required=False,
                format="N2+N14",
                pattern=r"^01(\d{14})$",
            ),
        ),
        (
            "90SE011\x1d2501611262",
            GS1ApplicationIdentifier(
                ai="90",
                description=
                "Information mutually agreed between trading partners",
                data_title="INTERNAL",
                fnc1_required=True,
                format="N2+X..30",
                pattern=(r"^90([\x21-\x22\x25-\x2F\x30-\x39\x3A-\x3F\x41-"
                         r"\x5A\x5F\x61-\x7A]{0,30})$"),
Beispiel #13
0
     # GTIN-8
     "96385074",
     ParseResult(
         value="96385074",
         gtin=Gtin(
             value="96385074",
             format=GtinFormat.GTIN_8,
             prefix=GS1Prefix(value="00009", usage="GS1 US"),
             payload="9638507",
             check_digit=4,
         ),
         gs1_message=GS1Message(
             value="96385074",
             element_strings=[
                 GS1ElementString(
                     ai=GS1ApplicationIdentifier.extract("96"),
                     value="385074",
                     pattern_groups=["385074"],
                 )
             ],
         ),
         sscc_error=
         ("Failed to parse '96385074' as SSCC: Expected 18 digits, got 8."
          ),
     ),
 ),
 (
     # GTIN-12
     "123601057072",
     ParseResult(
         value="123601057072",