"""
Imports and manages EDI format definitions
"""

import os
import json

DEFAULT_FORMAT = [
    {   "id": "ISA", "type": "segment",
        "name": "Interchange Control Header",
        "req": "M",
        "max_uses": 1,
        "notes": "",
        "elements": [
            {   "id": "ISA01", "type": "element",
                "name": "Authorization Information Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"00": "(default)"},
                "length": {"min": 2, "max": 2},
                "notes": "Code to identify the type of information in the Authorization Information"
            },
            {   "id": "ISA02", "type": "element",
                "name": "Authorization Information",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 10, "max": 10},
                "notes": "Information used for additional identification or authorization of the interchange sender or the data in the interchange; the type of information is set by the Authorization Information Qualifier (I01)"
            },
            {   "id": "ISA03", "type": "element",
                "name": "Security Information Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"00": "(default)"},
                "length": {"min": 2, "max": 2},
                "notes": "Code to identify the type of information in the Security Information"
            },
            {   "id": "ISA04", "type": "element",
                "name": "Security Information",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 10, "max": 10},
                "notes": "This is used for identifying the security information about the interchange sender or the data in the interchange; the type of information is set by the Security Information Qualifier (I03)"
            },
            {   "id": "ISA05", "type": "element",
                "name": "Interchange Sender ID Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"ZZ": "Mutually Defined"},
                "length": {"min": 2, "max": 2},
                "notes": "Qualifier to designate the system/method of code structure used to designate the sender or receiver ID element being qualified"
            },
            {   "id": "ISA06", "type": "element",
                "name": "Interchange Sender ID",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 15, "max": 15},
                "notes": "Identification code published by the sender for other parties to use as the receiver ID to route data to them; the sender always codes this value in the sender ID element"
            },
            {   "id": "ISA07", "type": "element",
                "name": "Interchange Receiver ID Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"ZZ": "Mutually Defined"},
                "length": {"min": 2, "max": 2},
                "notes": "Qualifier to designate the system/method of code structure used to designate the sender or receiver ID element being qualified"
            },
            {   "id": "ISA08", "type": "element",
                "name": "Interchange Receiver ID",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 15, "max": 15},
                "notes": "Identification code published by the receiver of the data; When sending, it is used by the sender as their sending ID, thus other parties sending to them will use this as a receiving ID to route data to them"
            },
            {   "id": "ISA09", "type": "element",
                "name": "Interchange Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 6, "max": 6},
                "notes": "Date of the interchange"
            },
            {   "id": "ISA10", "type": "element",
                "name": "Interchange Time",
                "req": "M",
                "data_type": "TM",
                "data_type_ids": None,
                "length": {"min": 4, "max": 4},
                "notes": "Time of the interchange"
            },
            {   "id": "ISA11", "type": "element",
                "name": "Interchange Control Standards Identifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": None,
                "length": {"min": 1, "max": 1},
                "notes": "Code to identify the agency responsible for the control standard used by the message that is enclosed by the interchange header and trailer"
            },
            {   "id": "ISA12", "type": "element",
                "name": "Interchange Control Version Number",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"U": "(default)"},
                "length": {"min": 5, "max": 5},
                "notes": "This version number covers the interchange control segments"
            },
            {   "id": "ISA13", "type": "element",
                "name": "Interchange Control Number",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 9, "max": 9},
                "notes": "A control number assigned by the interchange sender"
            },
            {   "id": "ISA14", "type": "element",
                "name": "Acknowledgment Requested",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"0": "Requested"},
                "length": {"min": 1, "max": 1},
                "notes": "Code sent by the sender to request an interchange acknowledgment (TA1)"
            },
            {   "id": "ISA15", "type": "element",
                "name": "Usage Indicator",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"T": "Test", "P": "Production", "I": "Information"},
                "length": {"min": 1, "max": 1},
                "notes": "Code to indicate whether data enclosed by this interchange envelope is test, production or information"
            },
            {   "id": "ISA16", "type": "element",
                "name": "Component Element Separator",
                "req": "M",
                "data_type": "",
                "data_type_ids": {"T": "Test", "P": "Production", "I": "Information"},
                "length": {"min": 1, "max": 1},
                "notes": "Type is not applicable; the component element separator is a delimiter and not a data element; this field provides the delimiter used to separate component data elements within a composite data structure; this value must be different than the data element separator and the segment terminator"
            }
        ]
    },
    {   "id": "GS", "type": "segment",
        "name": "Functional Group Header",
        "req": "M",
        "max_uses": 1,
        "notes": "",
        "elements": [
            {   "id": "GS01", "type": "element",
                "name": "Functional Identifier Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"IN": "Invoice"},
                "length": {"min": 2, "max": 2},
                "notes": "Code identifying a group of application related transaction sets"
            },
            {   "id": "GS02", "type": "element",
                "name": "Application Sender's Code",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 2, "max": 15},
                "notes": "Code identifying party sending transmission; codes agreed to by trading partners"
            },
            {   "id": "GS03", "type": "element",
                "name": "Application Receiver's Code",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 2, "max": 15},
                "notes": "Code identifying party receiving transmission. Codes agreed to by trading partners"
            },
            {   "id": "GS04", "type": "element",
                "name": "Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Date expressed as CCYYMMDD"
            },
            {   "id": "GS05", "type": "element",
                "name": "Time",
                "req": "M",
                "data_type": "TM",
                "data_type_ids": None,
                "length": {"min": 4, "max": 8},
                "notes": "Time expressed in 24-hour clock time as follows: HHMM, or HHMMSS, or HHMMSSD, or HHMMSSDD"
            },
            {   "id": "GS06", "type": "element",
                "name": "Group Control Number",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 9},
                "notes": "Assigned number originated and maintained by the sender"
            },
            {   "id": "GS07", "type": "element",
                "name": "Responsible Agency Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"X": "", "T": ""},
                "length": {"min": 1, "max": 2},
                "notes": "Code used in conjunction with Data Element 480 to identify the issuer of the standard"
            },
            {   "id": "GS08", "type": "element",
                "name": "Version / Release / Industry Identifier Code",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 12},
                "notes": "Code indicating the version, release, subrelease, and industry identifier of the EDI standard being used, including the GS and GE segments; if code in DE455 in GS segment is X, then in DE 480 positions 1-3 are the version number; positions 4-6 are the release and subrelease, level of the version; and positions 7-12 are the industry or trade association identifiers (optionally assigned by user); if code in DE455 in GS segment is T, then other formats are allowed"
            }
        ]
    },
    {   "id": "ST", "type": "segment",
        "name": "Transaction Set Header",
        "req": "M",
        "max_uses": 1,
        "notes": "",
        "elements": [
            {   "id": "ST01", "type": "element",
                "name": "Transaction Set Identifier Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"810": "Invoice"},
                "length": {"min": 3, "max": 3},
                "notes": ""
            },
            {   "id": "ST02", "type": "element",
                "name": "Transaction Set Control Number",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 4, "max": 9},
                "notes": "This should be a unique control # for each transaction set functional group"
            }
        ]
    },
    {   "id": "BIG", "type": "segment",
        "name": "Beginning Segment for Invoice",
        "req": "M",
        "max_uses": 1,
        "notes": "",
        "elements": [
            {   "id": "BIG01", "type": "element",
                "name": "Invoice Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Invoice issue date"
            },
            {   "id": "BIG02", "type": "element",
                "name": "Invoice Number",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 22},
                "notes": "Identifying number assigned by supplier"
            },
            {   "id": "BIG03", "type": "element",
                "name": "Purchase Order Date",
                "req": "O",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Original date (assigned by hospital) of the purchase order"
            },
            {   "id": "BIG04", "type": "element",
                "name": "Purchase Order Number",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 22},
                "notes": "Identifying number for purchase order assigned by hospital"
            },
            {   "id": "BIG05", "type": "element",
                "name": "Release Number",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 30},
                "notes": "Only used if hospital sent the release # in original PO (element BEG04)"
            },
            {   "id": "BIG06", "type": "element",
                "name": "Change Order Seq. #",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 8},
                "notes": "Not used"
            },
            {   "id": "BIG07", "type": "element",
                "name": "Transaction Type Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {
                    "CN": "Credit Invoice",
                    "CR": "Credit Memo",
                    "DI": "Debit Invoice",
                    "DR": "Debit Memo",
                    "PR": "Product (or Service)"
                },
                "length": {"min": 1, "max": 22},
                "notes": "Identifying number for purchase order assigned by hospital"
            },
            {   "id": "BIG08", "type": "element",
                "name": "Transaction Set Purpose Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {
                    "00": "Original"
                },
                "length": {"min": 2, "max": 2},
                "notes": "Not used"
            }
        ]
    },
    {   "id": "NTE", "type": "segment",
        "name": "Note/Special Instruction",
        "req": "O",
        "max_uses": 100,
        "notes": "The NTE segment permits free-form information/data which, under ANSI X12 standard implementations, is not machine processable. The use of the NTE segment should therefore be avoided, if at all possible, in an automated environment.",
        "elements": [
            {   "id": "NTE01", "type": "element",
                "name": "Note Reference Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {"GEN": "Entire Transaction Set"},
                "length": {"min": 3, "max": 3},
                "notes": "Code identifying the functional area or purpose for which the note applies"
            },
            {   "id": "NTE02", "type": "element",
                "name": "Description",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 80},
                "notes": "A free-form description to clarify the related data elements and their content"
            }
        ]
    },
    {   "id": "CUR", "type": "segment",
        "name": "Currency",
        "req": "O",
        "max_uses": 1,
        "notes": "If the CUR segment is not used, monetary values are assumed to be expressed in the currency of the country of the transaction originator.",
        "elements": [
            {   "id": "CUR01", "type": "element",
                "name": "Entity Identifier Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"SE": "Selling Party"},
                "length": {"min": 2, "max": 3},
                "notes": "Code identifying an organizational entity, a physical location, property or an individual"
            },
            {   "id": "CUR02", "type": "element",
                "name": "Currency Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"USD": "US Dollars", "CAD": "Canadian Dollars"},
                "length": {"min": 3, "max": 3},
                "notes": "Code (Standard ISO) for country in whose currency the charges are specified"
            },
            {   "id": "CUR03", "type": "element",
                "name": "Exchange Rate",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 4, "max": 10},
                "notes": "Value to be used as a multiplier conversion factor to convert monetary value from one currency to another"
            }
        ]
    },
    {   "id": "REF", "type": "segment",
        "name": "Reference Identification",
        "req": "O",
        "max_uses": 12,
        "notes": "",
        "syntax": [
            {"rule": "ATLEASTONE", "criteria": [2, 3]}
        ],
        "elements": [
            {   "id": "REF01", "type": "element",
                "name": "Reference Identification Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {
                    "AP": "Accounts Receivable",
                    "BM": "Bill of Lading Number",
                    "CO": "Customer Order Number",
                    "CT": "Contract Number",
                    "LB": "Lock Box",
                    "RE": "Release Number",
                    "RY": "Rebate Number",
                    "SA": "Salesperson",
                    "SI": "Shipper's Identifying Number",
                    "VN": "Vendor Order Number",
                    "ZZ": "Mutually Defined"
                },
                "length": {"min": 2, "max": 3},
                "notes": "Code qualifying the Reference Identification"
            },
            {   "id": "REF02", "type": "element",
                "name": "Reference Identification Number",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 30},
                "notes": "Reference information as defined for a particular Transaction Set or as specified by the Reference Identification Qualifier"
            },
            {   "id": "REF03", "type": "element",
                "name": "Description",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 30},
                "notes": "A free-form description to clarify the related data elements and their content"
            }
        ]
    },
    {   "id": "L_N1", "type": "loop",
        "name": "Names",
        "req": "O",
        "repeat": 200,
        "segments": [
            {   "id": "N1", "type": "segment",
                "name": "Name",
                "req": "O",
                "max_uses": 1,
                "notes": "Vendor name or Buying party name",
                "elements": [
                    {   "id": "N101", "name": "Entity ID Code",
                        "type": "element",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {
                            "BT": "Bill-to-Party", 
                            "BY": "Buying Party", 
                            "CA": "Carrier", 
                            "DU": "Reseller", 
                            "EN": "End User", 
                            "II": "Issuer of Invoice", 
                            "PR": "Payer", 
                            "SE": "Selling Party", 
                            "SO": "Sold To If Different From Bill To", 
                            "ST": "Ship To",
                            "TO": "Supplier",
                            "VN": "Vendor"
                        },
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying an organizational entity, a physical location, property or an individual"
                    },
                    {   "id": "N102", "name": "Name",
                        "type": "element",
                        "req": "C",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 30},
                        "notes": "Free-form name"
                    },
                    {   "id": "N103", "name": "ID code qualifier",
                        "type": "element",
                        "req": "C",
                        "data_type": "ID",
                        "data_type_ids": {
                            "1": "DUNS Number", 
                            "9": "DUNS Number with 4-digit suffix", 
                            "21": "Health Care Industry ID No.",
                            "91": "Assigned by seller",
                            "92": "Assigned by Buyer or Agent",
                            "ZZ": "Mutually Defined"
                        },
                        "length": {"min": 1, "max": 2},
                        "notes": "Code designating the system/method of code structure used for Identification Code (N104)"
                    },
                    {   "id": "N104", "name": "ID code",
                        "short_name": "Location",
                        "type": "element",
                        "req": "C",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 17},
                        "notes": "Receiver ID Number"
                    }
                ]
            },
            {   "id": "N2", "type": "segment",
                "name": "Additional Name Information",
                "req": "O",
                "max_uses": 2,
                "notes": "To specify additional names or those longer than 35 characters in length",
                "elements": [
                    {   "id": "N201", "type": "element",
                        "name": "Name",
                        "req": "M",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 60},
                        "notes": "Free-form name"
                    },
                    {   "id": "N202", "type": "element",
                        "name": "Name",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 60},
                        "notes": "Free-form name"
                    }
                ]
            },
            {   "id": "N3", "type": "segment",
                "name": "Address Information",
                "req": "O",
                "max_uses": 2,
                "notes": "To specify the location of the named party",
                "elements": [
                    {   "id": "N301", "name": "Address Information",
                        "type": "element",
                        "req": "M",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 55},
                        "notes": "Address Information"
                    },
                    {   "id": "N302", "name": "Address Information",
                        "type": "element",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 55},
                        "notes": "Address Information"
                    }
                ]
            },
            {   "id": "N4", "type": "segment",
                "name": "Geographic Location",
                "req": "O",
                "max_uses": 1,
                "notes": "To specify the geographic place of the named party",
                "elements": [
                    {   "id": "N401", "type": "element",
                        "name": "City Name",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 30},
                        "notes": "Address Information"
                    },
                    {   "id": "N402", "type": "element",
                        "name": "State or Province Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 2},
                        "notes": "Code (Standard State/Province) as defined by appropriate government agency"
                    },
                    {   "id": "N403", "type": "element",
                        "name": "Postal Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 3, "max": 15},
                        "notes": "Code defining international postal zone code excluding punctuation and blanks (zip code for United States)"
                    },
                    {   "id": "N404", "type": "element",
                        "name": "Country Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 3},
                        "notes": "Code identifying the country"
                    }
                ]
            },
            {   "id": "PER", "type": "segment",
                "name": "Administrative Communications Contact",
                "req": "O",
                "max_uses": 3,
                "notes": "To identify a person or office to whom administrative communications should be directed",
                "elements": [
                    {   "id": "PER01", "type": "element",
                        "name": "Contact Function Code",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {"CN": "General Contact", "RE": "Contact For Problems"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the major duty or responsibility of the person or group named"
                    },
                    {   "id": "PER02", "type": "element",
                        "name": "Name",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 60},
                        "notes": "Free-form name"
                    },
                    {   "id": "PER03", "type": "element",
                        "name": "Communications Number Type",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"TE": "Telephone", "EM": "Email", "FX": "Facsimile"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the communications number type"
                    },
                    {   "id": "PER04", "type": "element",
                        "name": "Communications Number",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 80},
                        "notes": "Number for communications"
                    }
                ]
            }
        ]
    },
    {   "id": "ITD", "type": "segment",
        "name": "Terms of Sale/Deferred Terms of Sale",
        "req": "O",
        "max_uses": 10,
        "notes": "To specify terms of sale. In the Header position of the Invoice X12 EDI document, this segment is used to specify terms of the invoice. In the transitional period for the microcomputer industry, from paper to full automated EDI transactions, there may be a perceived need to send text data with the terms. Clearly the goal is to have the entire microcomputer industry participating in EDI. Therefore, if text data is needed to be sent for terms, ITD 12 will contain the free form text. If additional text is needed, additional ITD segments should be used.",
        "syntax": [
            {"rule": "IFATLEASTONE", "criteria": [3, 4, 5]},
            {"rule": "IFATLEASTONE", "criteria": [8, 4, 5]},
            {"rule": "IFATLEASTONE", "criteria": [9, 10, 11]}
        ],
        "elements": [
            {   "id": "ITD01", "type": "element",
                "name": "Terms Type Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {"14": "Previously agreed upon"},
                "length": {"min": 2, "max": 2},
                "notes": "Code identifying type of payment terms"
            },
            {   "id": "ITD02", "type": "element",
                "name": "Terms Basis Date Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {"3": "Invoice Date"},
                "length": {"min": 1, "max": 2},
                "notes": "Code identifying the beginning of the terms period"
            },
            {   "id": "ITD03", "type": "element",
                "name": "Terms Discount %",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 1, "max": 6},
                "notes": "Available to hospital if invoice is paid on or before Terms Discount Due Date"
            },
            {   "id": "ITD04", "type": "element",
                "name": "Terms Discount Due Date",
                "req": "O",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Date payment is due if discount is to be earned (CCYYMMDD)"
            },
            {   "id": "ITD05", "type": "element",
                "name": "Terms Discount Days Due",
                "req": "O",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 3},
                "notes": "Maximum number of days to pass before payment is due"
            },
            {   "id": "ITD06", "type": "element",
                "name": "Terms Net Due Date",
                "req": "O",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Date when total invoice amount is due"
            },
            {   "id": "ITD07", "type": "element",
                "name": "Terms Net Days",
                "req": "O",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 3},
                "notes": "Payment terms in net days"
            },
            {   "id": "ITD08", "type": "element",
                "name": "Terms Discount Amount",
                "req": "O",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 10},
                "notes": "Total amount of terms discount"
            },
            {   "id": "ITD09", "type": "element",
                "name": "Terms Deferred Due Date",
                "req": "O",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Date deferred payment or percent of invoice payable is due"
            },
            {   "id": "ITD10", "type": "element",
                "name": "Deferred Amount Due",
                "req": "O",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 10},
                "notes": "Deferred amount due for payment"
            },
            {   "id": "ITD11", "type": "element",
                "name": "% Invoice Payable",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 1, "max": 5},
                "notes": "Amount of invoice payable expressed in percent"
            },
            {   "id": "ITD12", "type": "element",
                "name": "Description",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 80},
                "notes": "Description of terms"
            }
        ]
    },
    {   "id": "DTM", "type": "segment",
        "name": "Date/Time Reference",
        "req": "O",
        "max_uses": 10,
        "notes": "To identify a date or time",
        "elements": [
            {   "id": "DTM01", "type": "element",
                "name": "Date/Time Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"002": "Delivery requested", "011": "Shipped", "036": "Expiration Date"},
                "length": {"min": 3, "max": 3},
                "notes": "Code specifying type of date or time, or both date and time"
            },
            {   "id": "DTM02", "type": "element",
                "name": "Date",
                "req": "O",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": "Date expressed as CCYYMMDD"
            },
            {   "id": "DTM03", "type": "element",
                "name": "Time",
                "req": "O",
                "data_type": "TM",
                "data_type_ids": None,
                "length": {"min": 4, "max": 8},
                "notes": "Time"
            }
        ]
    },
    {   "id": "N9", "type": "segment",
        "name": "Reference",
        "req": "O",
        "max_uses": 1,
        "notes": "Used with notes",
        "elements": [
            {   "id": "N901", "type": "element",
                "name": "Reference Ident. Qualifier",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"ZZ": "Mutually Defined"},
                "length": {"min": 2, "max": 3},
                "notes": "Code specifying type of date or time, or both date and time"
            },
            {   "id": "N902", "type": "element",
                "name": "Reference Identification",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 30},
                "notes": "MSG to Follow"
            },
            {   "id": "N903", "type": "element",
                "name": "Other",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 80},
                "notes": ""
            }
        ]
    },
    {   "id": "MSG", "type": "segment",
        "name": "Text Message",
        "req": "O",
        "max_uses": 10,
        "notes": "Free-form text",
        "elements": [
            {   "id": "MSG01", "type": "element",
                "name": "Message Text",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 264},
                "notes": "Free-form text"
            }
        ]
    },
    {   "id": "L_IT1", "type": "loop",
        "name": "Baseline Item Data Loop",
        "req": "O",
        "repeat": 200000,
        "segments": [
            {   "id": "IT1", "type": "segment",
                "name": "Baseline Item Data (Invoice)",
                "req": "M",
                "max_uses": 1,
                "notes": "To specify the basic and most frequently used line item data for the invoice and related transactions",
                "syntax": [
                    {"rule": "ALLORNONE", "criteria": [2, 3, 4]},
                    {"rule": "ALLORNONE", "criteria": [6, 7]},
                    {"rule": "ALLORNONE", "criteria": [8, 9]},
                    {"rule": "ALLORNONE", "criteria": [10, 11]},
                    {"rule": "ALLORNONE", "criteria": [12, 13]},
                    {"rule": "ALLORNONE", "criteria": [14, 15]},
                    {"rule": "ALLORNONE", "criteria": [16, 17]},
                    {"rule": "ALLORNONE", "criteria": [18, 19]},
                    {"rule": "ALLORNONE", "criteria": [20, 21]},
                    {"rule": "ALLORNONE", "criteria": [22, 23]},
                    {"rule": "ALLORNONE", "criteria": [24, 25]}
                ],
                "elements": [
                    {   "id": "IT101", "type": "element",
                        "name": "Assigned Identification",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "Alphanumeric characters assigned for differentiation within a transaction set. May be original line number from PO"
                    },
                    {   "id": "IT102", "type": "element",
                        "name": "Quantity Invoiced",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Date expressed as CCYYMMDD"
                    },
                    {   "id": "IT103", "type": "element",
                        "name": "Unit or Basis for Measurement Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"EA": "Each"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code specifying the units in which a value is being expressed, or manner in which a measurement has been taken"
                    },
                    {   "id": "IT104", "type": "element",
                        "name": "Unit Price",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 17},
                        "notes": "Price per unit of product, service, commodity, etc."
                    },
                    {   "id": "IT105", "type": "element",
                        "name": "Basis of Unit Price Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"CP": "Current Price (Subject to Change)", "NC": "No Cost"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the type of unit price for an item"
                    },
                    {   "id": "IT106", "type": "element",
                        "name": "Product/Service ID Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"VP": "Vendor's (Seller's) Part Number", "MG": "Manufacturer ID"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the type/source of the descriptive number used in Product/Service ID"
                    },
                    {   "id": "IT107", "type": "element",
                        "name": "Product/Service ID",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 48},
                        "notes": "Identifying number for a product or service"
                    },
                    {   "id": "IT108", "type": "element",
                        "name": "Product/Service ID Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"BP": "Buyer's Part Number"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the type/source of the descriptive number used in Product/Service ID"
                    },
                    {   "id": "IT109", "type": "element",
                        "name": "Product/Service ID",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 48},
                        "notes": "Identifying number for a product or service"
                    },
                    {   "id": "IT110", "type": "element",
                        "name": "Product/Service ID Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"UP": "U.P.C. Consumer Package Code (1-5-5-1)"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the type/source of the descriptive number used in Product/Service ID"
                    },
                    {   "id": "IT111", "type": "element",
                        "name": "Product/Service ID",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 48},
                        "notes": "Identifying number for a product or service"
                    }
                ]
            },
            {   "id": "TXI", "type": "segment",
                "name": "Tax Information",
                "req": "O",
                "max_uses": 1,
                "notes": "To specify tax information",
                "syntax": [
                    {"rule": "ATLEASTONE", "criteria": [2, 3, 6]},
                    {"rule": "ALLORNONE", "criteria": [4, 5]},
                    {"rule": "IFATLEASTONE", "criteria": [8, 3]}
                ],
                "elements": [
                    {   "id": "TXI01", "type": "element",
                        "name": "Tax Type Code",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {"ST": "State Sales Tax"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Amount before terms discount"
                    },
                    {   "id": "TXI02", "type": "element",
                        "name": "Monetary Amount",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 18},
                        "notes": "Monetary amount"
                    },
                    {   "id": "TXI03", "type": "element",
                        "name": "Percent",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Percentage expressed as a decimal"
                    },
                    {   "id": "TXI04", "type": "element",
                        "name": "Tax Jurisdiction Code Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"CD": "Customer Defined", "VD": "Vendor Defined"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the source of the data used in tax jurisdiction code"
                    },
                    {   "id": "TXI05", "type": "element",
                        "name": "Tax Jurisdiction Code",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Code identifying the taxing jurisdiction"
                    },
                    {   "id": "TXI06", "type": "element",
                        "name": "Tax Exempt Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {
                            "0": "Exempt (for Export)",
                            "1": "Yes (Tax Exempt)",
                            "2": "No (Not Tax Exempt)",
                            "3": "Exempt (For Resale)",
                            "4": "Not Exempt/For Resale",
                            "5": "Exempt (Not For Resale)",
                            "6": "Not Exempt, Not For Resale",
                            "7": "Direct Pay ID",
                            "8": "Exempt (Sale to U.S. Government)",
                            "9": "Exempt (Per State Law",
                            "A": "Labor Taxable, Material Exempt",
                            "B": "Material Taxable, Labor Exempt",
                            "C": "Not Taxable",
                            "V": "Exempt from State Property Tax",
                            "W": "Other Property Tax Exemption",
                            "X": "Exempt - Letter on file"
                        },
                        "length": {"min": 1, "max": 1},
                        "notes": "Code identifying exemption status from sales and use tax"
                    },
                    {   "id": "TXI07", "type": "element",
                        "name": "Relationship Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 1},
                        "notes": "Code indicating the relationship between entities"
                    },
                    {   "id": "TXI08", "type": "element",
                        "name": "Dollar Basis for Percent",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 9},
                        "notes": "Dollar basis to be used in the percent calculation of the allowance, charge, or tax"
                    },
                    {   "id": "TXI09", "type": "element",
                        "name": "Tax Identification Number",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "Number assigned to a purchaser (buyer, orderer) by a taxing jurisdiction (state, county, etc.); often called a tax exemption number or certificat number"
                    },
                    {   "id": "TXI10", "type": "element",
                        "name": "Assigned Identification",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "Alphanumeric characters assigned for differentiation within a transaction set"
                    }
                ]
            },
            {   "id": "L_PID", "type": "loop",
                "name": "Product/Item Description Loop",
                "req": "O",
                "repeat": 1000,
                "segments": [
                    {   "id": "PID", "type": "segment",
                        "name": "Product/Item Description",
                        "req": "O",
                        "max_uses": 1,
                        "notes": "To describe a product or process in coded or free-form format",
                        "syntax": [
                            {"rule": "IFATLEASTONE", "criteria": [4, 3]},
                            {"rule": "ATLEASTONE", "criteria": [4, 5]},
                            {"rule": "IFATLEASTONE", "criteria": [7, 3]},
                            {"rule": "IFATLEASTONE", "criteria": [8, 4]},
                            {"rule": "IFATLEASTONE", "criteria": [9, 5]}
                        ],
                        "elements": [
                            {   "id": "PID01", "type": "element",
                                "name": "Item Description Type",
                                "req": "M",
                                "data_type": "ID",
                                "data_type_ids": {"X": "Mutually Defined", "F": "Freeform"},
                                "length": {"min": 1, "max": 1},
                                "notes": "Code indicating the format of a description"
                            },
                            {   "id": "PID02", "type": "element",
                                "name": "Product/Process Characteristic Code",
                                "req": "O",
                                "data_type": "ID",
                                "data_type_ids": None,
                                "length": {"min": 2, "max": 3},
                                "notes": "Not used"
                            },
                            {   "id": "PID03", "type": "element",
                                "name": "Association Qualifier Code",
                                "req": "O",
                                "data_type": "ID",
                                "data_type_ids": None,
                                "length": {"min": 2, "max": 2},
                                "notes": "Not used"
                            },
                            {   "id": "PID04", "type": "element",
                                "name": "Product Description Code",
                                "req": "O",
                                "data_type": "ID",
                                "data_type_ids": None,
                                "length": {"min": 1, "max": 12},
                                "notes": "Not used"
                            },
                            {   "id": "PID05", "type": "element",
                                "name": "Description",
                                "req": "O",
                                "data_type": "AN",
                                "data_type_ids": None,
                                "length": {"min": 1, "max": 80},
                                "notes": "A free-form description to clarify the related data elements and their content"
                            }
                        ]
                    }
                ]
            },
            {   "id": "REF", "type": "segment",
                "name": "Reference Information",
                "req": "O",
                "max_uses": 10,
                "notes": "To specify other information",
                "syntax": [],
                "elements": [
                    {   "id": "REF01", "type": "element",
                        "name": "Reference Code Type",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {},
                        "length": {"min": 2, "max": 2},
                        "notes": ""
                    },
                    {   "id": "REF02", "type": "element",
                        "name": "Reference Code Value",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 80},
                        "notes": ""
                    }
                ]
            },
            {   "id": "DTM", "type": "segment",
                "name": "Date/Time Reference",
                "req": "O",
                "max_uses": 10,
                "notes": "To identify a person or office to whom administrative communications should be directed",
                "elements": [
                    {   "id": "DTM01", "type": "element",
                        "name": "Date/Time Qualifier",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {"002": "Delivery requested", "011": "Shipped", "036": "Expiration Date"},
                        "length": {"min": 3, "max": 3},
                        "notes": "Code specifying type of date or time, or both date and time"
                    },
                    {   "id": "DTM02", "type": "element",
                        "name": "Date",
                        "req": "O",
                        "data_type": "DT",
                        "data_type_ids": None,
                        "length": {"min": 8, "max": 8},
                        "notes": "Date expressed as CCYYMMDD"
                    },
                    {   "id": "DTM03", "type": "element",
                        "name": "Time",
                        "req": "O",
                        "data_type": "TM",
                        "data_type_ids": None,
                        "length": {"min": 4, "max": 8},
                        "notes": "Time"
                    }
                ]
            }
        ]
    },
    {   "id": "TDS", "type": "segment",
        "name": "Total Monetary Value Summary",
        "req": "M",
        "max_uses": 1,
        "notes": "To specify the total invoice discounts and amounts.",
        "elements": [
            {   "id": "TDS01", "type": "element",
                "name": "Total Invoice Amount",
                "req": "M",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 15},
                "notes": "Amount before terms discount"
            },
            {   "id": "TDS02", "type": "element",
                "name": "Amt. Subj. to Terms Discount",
                "req": "O",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 15},
                "notes": "Amount upon which the terms discount amount is calculated"
            },
            {   "id": "TDS03", "type": "element",
                "name": "Discounted Amount Due",
                "req": "O",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 15},
                "notes": "Amount of invoice due if paid by terms discount due date"
            },
            {   "id": "TDS04", "type": "element",
                "name": "Terms Discount Amount",
                "req": "O",
                "data_type": "N2",
                "data_type_ids": None,
                "length": {"min": 1, "max": 15},
                "notes": "Total amount of terms discount"
            }
        ]
    },
    {   "id": "TXI", "type": "segment",
        "name": "Tax Information",
        "req": "O",
        "max_uses": 10,
        "notes": "To specify tax information",
        "syntax": [
            {"rule": "ATLEASTONE", "criteria": [2, 3, 6]},
            {"rule": "ALLORNONE", "criteria": [4, 5]},
            {"rule": "IFATLEASTONE", "criteria": [8, 3]}
        ],
        "elements": [
            {   "id": "TXI01", "type": "element",
                "name": "Tax Type Code",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"ST": "State Sales Tax"},
                "length": {"min": 2, "max": 2},
                "notes": "Amount before terms discount"
            },
            {   "id": "TXI02", "type": "element",
                "name": "Monetary Amount",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 1, "max": 18},
                "notes": "Monetary amount"
            },
            {   "id": "TXI03", "type": "element",
                "name": "Percent",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 1, "max": 10},
                "notes": "Percentage expressed as a decimal"
            },
            {   "id": "TXI04", "type": "element",
                "name": "Tax Jurisdiction Code Qualifier",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {"CD": "Customer Defined", "VD": "Vendor Defined"},
                "length": {"min": 2, "max": 2},
                "notes": "Code identifying the source of the data used in tax jurisdiction code"
            },
            {   "id": "TXI05", "type": "element",
                "name": "Tax Jurisdiction Code",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 10},
                "notes": "Code identifying the taxing jurisdiction"
            },
            {   "id": "TXI06", "type": "element",
                "name": "Tax Exempt Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": {
                    "0": "Exempt (for Export)",
                    "1": "Yes (Tax Exempt)",
                    "2": "No (Not Tax Exempt)",
                    "3": "Exempt (For Resale)",
                    "4": "Not Exempt/For Resale",
                    "5": "Exempt (Not For Resale)",
                    "6": "Not Exempt, Not For Resale",
                    "7": "Direct Pay ID",
                    "8": "Exempt (Sale to U.S. Government)",
                    "9": "Exempt (Per State Law",
                    "A": "Labor Taxable, Material Exempt",
                    "B": "Material Taxable, Labor Exempt",
                    "C": "Not Taxable",
                    "V": "Exempt from State Property Tax",
                    "W": "Other Property Tax Exemption",
                    "X": "Exempt - Letter on file"
                },
                "length": {"min": 1, "max": 1},
                "notes": "Code identifying exemption status from sales and use tax"
            },
            {   "id": "TXI07", "type": "element",
                "name": "Relationship Code",
                "req": "O",
                "data_type": "ID",
                "data_type_ids": None,
                "length": {"min": 1, "max": 1},
                "notes": "Code indicating the relationship between entities"
            },
            {   "id": "TXI08", "type": "element",
                "name": "Dollar Basis for Percent",
                "req": "O",
                "data_type": "R",
                "data_type_ids": None,
                "length": {"min": 1, "max": 9},
                "notes": "Dollar basis to be used in the percent calculation of the allowance, charge, or tax"
            },
            {   "id": "TXI09", "type": "element",
                "name": "Tax Identification Number",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 20},
                "notes": "Number assigned to a purchaser (buyer, orderer) by a taxing jurisdiction (state, county, etc.); often called a tax exemption number or certificat number"
            },
            {   "id": "TXI10", "type": "element",
                "name": "Assigned Identification",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 20},
                "notes": "Alphanumeric characters assigned for differentiation within a transaction set"
            }
        ]
    },
    {   "id": "L_SAC", "type": "loop",
        "name": "Service, Promotion, Allowance, or Charge Information Loop",
        "req": "O",
        "repeat": 25,
        "segments": [
            {   "id": "SAC", "type": "segment",
                "name": "Service, Promotion, Allowance, or Charge Information",
                "req": "O",
                "max_uses": 1,
                "notes": "To request or identify a service, promotion, allowance, or charge; to specify the amount or percentage for the service, promotion, allowance, or charge",
                "syntax": [
                    {"rule": "ATLEASTONE", "criteria": [2, 3]},
                    {"rule": "ALLORNONE", "criteria": [3, 4]},
                    {"rule": "ALLORNONE", "criteria": [6, 7]},
                    {"rule": "ALLORNONE", "criteria": [9, 10]},
                    {"rule": "IFATLEASTONE", "criteria": [11, 10]},
                    {"rule": "IFATLEASTONE", "criteria": [13, 2, 4]},
                    {"rule": "IFATLEASTONE", "criteria": [14, 13]},
                    {"rule": "IFATLEASTONE", "criteria": [16, 15]}
                ],
                "elements": [
                    {   "id": "SAC01", "type": "element",
                        "name": "Allowance or Charge Indicator",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {"C": "Charge"},
                        "length": {"min": 1, "max": 1},
                        "notes": "Code which indicates an allowance or charge for the service specified"
                    },
                    {   "id": "SAC02", "type": "element",
                        "name": "Service, Promotion, Allowance, or Charge Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"D240": "Freight"},
                        "length": {"min": 4, "max": 4},
                        "notes": "Code identifying the service, promotion, allowance, or charge"
                    },
                    {   "id": "SAC03", "type": "element",
                        "name": "Agency Qualifier Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the agency assigning the code values"
                    },
                    {   "id": "SAC04", "type": "element",
                        "name": "Agency Service, Promotion, Allowance, or Charge Code",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Agency maintained code identifying the service, promotion, allowance, or charge"
                    },
                    {   "id": "SAC05", "type": "element",
                        "name": "Amount",
                        "req": "O",
                        "data_type": "N2",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 15},
                        "notes": "Monetary amount"
                    },
                    {   "id": "SAC06", "type": "element",
                        "name": "Allowance/Charge Percent Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 1},
                        "notes": "Code indicating on what basis allowance or charge percent is calculated"
                    },
                    {   "id": "SAC07", "type": "element",
                        "name": "Percent",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 6},
                        "notes": "Percent expressed as a percent"
                    },
                    {   "id": "SAC08", "type": "element",
                        "name": "Rate",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 9},
                        "notes": "Rate expressed in the standard monetary denomination for the currency specified"
                    },
                    {   "id": "SAC09", "type": "element",
                        "name": "Unit or Basis for Measurement Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 2},
                        "notes": "Code specifying the units in which a value is being expressed, or manner in which a measurement has been taken"
                    },
                    {   "id": "SAC10", "type": "element",
                        "name": "Quantity",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 15},
                        "notes": "Numeric value of quantity"
                    },
                    {   "id": "SAC11", "type": "element",
                        "name": "Quantity",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 15},
                        "notes": "Numeric value of quantity"
                    },
                    {   "id": "SAC12", "type": "element",
                        "name": "Allowance or Charge Method of Handling Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 2},
                        "notes": "Code indicating method of handling for an allowance or charge"
                    },
                    {   "id": "SAC13", "type": "element",
                        "name": "Reference Identification",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 30},
                        "notes": "Reference information as defined for a particular Transaction Set or as specified by the Reference Identification Qualifier"
                    },
                    {   "id": "SAC14", "type": "element",
                        "name": "Option Number",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "A unique number identifying available promotion or allowance options when more than one is offered"
                    },
                    {   "id": "SAC15", "type": "element",
                        "name": "Description",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 80},
                        "notes": "A free-form description to clarify the related data elements and their content"
                    }
                ]
            },
            {   "id": "TXI", "type": "segment",
                "name": "Tax Information",
                "req": "O",
                "max_uses": 1,
                "notes": "To specify tax information",
                "syntax": [
                    {"rule": "ATLEASTONE", "criteria": [2, 3, 6]},
                    {"rule": "ALLORNONE", "criteria": [4, 5]},
                    {"rule": "IFATLEASTONE", "criteria": [8, 3]}
                ],
                "elements": [
                    {   "id": "TXI01", "type": "element",
                        "name": "Tax Type Code",
                        "req": "M",
                        "data_type": "ID",
                        "data_type_ids": {"ST": "State Sales Tax"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Amount before terms discount"
                    },
                    {   "id": "TXI02", "type": "element",
                        "name": "Monetary Amount",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 18},
                        "notes": "Monetary amount"
                    },
                    {   "id": "TXI03", "type": "element",
                        "name": "Percent",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Percentage expressed as a decimal"
                    },
                    {   "id": "TXI04", "type": "element",
                        "name": "Tax Jurisdiction Code Qualifier",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {"CD": "Customer Defined", "VD": "Vendor Defined"},
                        "length": {"min": 2, "max": 2},
                        "notes": "Code identifying the source of the data used in tax jurisdiction code"
                    },
                    {   "id": "TXI05", "type": "element",
                        "name": "Tax Jurisdiction Code",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 10},
                        "notes": "Code identifying the taxing jurisdiction"
                    },
                    {   "id": "TXI06", "type": "element",
                        "name": "Tax Exempt Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": {
                            "0": "Exempt (for Export)",
                            "1": "Yes (Tax Exempt)",
                            "2": "No (Not Tax Exempt)",
                            "3": "Exempt (For Resale)",
                            "4": "Not Exempt/For Resale",
                            "5": "Exempt (Not For Resale)",
                            "6": "Not Exempt, Not For Resale",
                            "7": "Direct Pay ID",
                            "8": "Exempt (Sale to U.S. Government)",
                            "9": "Exempt (Per State Law",
                            "A": "Labor Taxable, Material Exempt",
                            "B": "Material Taxable, Labor Exempt",
                            "C": "Not Taxable",
                            "V": "Exempt from State Property Tax",
                            "W": "Other Property Tax Exemption",
                            "X": "Exempt - Letter on file"
                        },
                        "length": {"min": 1, "max": 1},
                        "notes": "Code identifying exemption status from sales and use tax"
                    },
                    {   "id": "TXI07", "type": "element",
                        "name": "Relationship Code",
                        "req": "O",
                        "data_type": "ID",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 1},
                        "notes": "Code indicating the relationship between entities"
                    },
                    {   "id": "TXI08", "type": "element",
                        "name": "Dollar Basis for Percent",
                        "req": "O",
                        "data_type": "R",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 9},
                        "notes": "Dollar basis to be used in the percent calculation of the allowance, charge, or tax"
                    },
                    {   "id": "TXI09", "type": "element",
                        "name": "Tax Identification Number",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "Number assigned to a purchaser (buyer, orderer) by a taxing jurisdiction (state, county, etc.); often called a tax exemption number or certificat number"
                    },
                    {   "id": "TXI10", "type": "element",
                        "name": "Assigned Identification",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 20},
                        "notes": "Alphanumeric characters assigned for differentiation within a transaction set"
                    }
                ]
            }
        ]
    },
    {   "id": "SE",
        "type": "segment",
        "name": "Transaction Set Trailer",
        "req": "M",
        "max_uses": 1,
        "notes": "To indicate the end of the transaction set and provide the count of the transmitted segments (including the beginning (ST) and ending (SE) segments)",
        "elements": [
            {   "id": "SE01", "type": "element",
                "name": "Number of Included Segments",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 10},
                "notes": "Total number of segments included in a transaction set including ST and SE segments"
            },
            {   "id": "SE02", "type": "element",
                "name": "Transaction Set Control Number",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 4, "max": 9},
                "notes": "Identifying control number that must be unique within the transaction set functional group assigned by the originator for a transaction set. Must match the control # in ST02"
            }
        ]
    },
    {   "id": "GE", "type": "segment",
        "name": "Functional Group Trailer",
        "req": "M",
        "max_uses": 1,
        "notes": "To indicate the end of a functional group and to provide control information",
        "elements": [
            {   "id": "GE01", "type": "element",
                "name": "Number of Transaction Sets Included",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 6},
                "notes": "Total number of transaction sets included in the functional group or interchange (transmission) group terminated by the trailer containing this data element"
            },
            {   "id": "GE02", "type": "element",
                "name": "Group Control Number",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 9},
                "notes": "Assigned number originated and maintained by the sender"
            }
        ]
    },
    {   "id": "IEA", "type": "segment",
        "name": "Interchange Control Trailer",
        "req": "M",
        "max_uses": 1,
        "notes": "To define the end of an interchange of zero or more functional groups and interchange-related control segments",
        "elements": [
            {   "id": "IEA01", "type": "element",
                "name": "Number of Included Functional Groups",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 1, "max": 5},
                "notes": "A count of the number of functional groups included in an interchange"
            },
            {   "id": "IEA02", "type": "element",
                "name": "Interchange Control Number",
                "req": "M",
                "data_type": "N0",
                "data_type_ids": None,
                "length": {"min": 9, "max": 9},
                "notes": "A control number assigned by the interchange sender"
            }
        ]
    },
    {   "id": "BFR", "type": "segment",
        "name": "Beginning Segment for Planning Schedule",
        "req": "M",
        "max_uses": 1,
        "notes": "",
        "elements": [
            {   "id": "BFR01", "type": "element",
                "name": "Transaction Set Purpose code",
                "short_name": "Transaction Purpose",
                "req": "M",
                "data_type": "ID",
                "data_type_ids": {"00": "Original"},
                "length": {"min": 2, "max": 2},
                "notes": "Transaction Set Purpose code. Code value : 00=Original"
            },
            {   "id": "BFR02", "type": "element",
                "name": "Reference Number",
                "short_name": "Reference ID",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 0, "max": 19},
                "notes": "This field is use by NG to track documents"
            },
            {   "id": "BFR03", "type": "element",
                "name": "Release",
                "short_name": "Release #",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 0, "max": 0},
                "notes": "None"
            },
            {   "id": "BFR04", "type": "element",
                "name": "Schedule Type qualifier",
                "short_name": "Schedule Type",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": {"BB": "Customer production"},
                "length": {"min": 2, "max": 15},
                "notes": "Code value: BB= Customer production"
            },
            {   "id": "BFR05", "type": "element",
                "name": "Schedule qty qualifier",
                "short_name": "Qty Type",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": {"A": "Cumulative quantities"},
                "length": {"min": 1, "max": 1},
                "notes": "Code value: A= Cumulative quantities"
            },
            {   "id": "BFR06", "type": "element",
                "name": "Starting date of the forecast",
                "short_name": "Start Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": ""
            },
            {   "id": "BFR07", "type": "element",
                "name": "End data of the forecast ",
                "short_name": "End Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": ""
            },
            {   "id": "BFR08", "type": "element",
                "name": "Run Date of forecast",
                "short_name": "Create Date",
                "req": "M",
                "data_type": "DT",
                "data_type_ids": None,
                "length": {"min": 8, "max": 8},
                "notes": ""
            },
            {   "id": "BFR09", "type": "element",
                "name": "None",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 0, "max": 0},
                "notes": "None"
            },
            {   "id": "BFR10", "type": "element",
                "name": "None",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 0, "max": 0},
                "notes": "None"
            },
            {   "id": "BFR11", "type": "element",
                "name": "None",
                "req": "O",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 0, "max": 0},
                "notes": "None"
            },
            {   "id": "BFR12", "type": "element",
                "name": "Planning Schedule Type Code",
                "short_name": "Planning Schedule Type",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": {"MN": "Consumer Sales Forecast", "AA": "Customized Ordering Forecast"},
                "length": {"min": 2, "max": 2},
                "notes": "MN = Consumer Sales Forecast, AA = Customized Ordering Forecast"
            }
        ]
    },
    {   "id": "L_LIN", "type": "loop",
        "name": "Item Descriptions",
        "req": "O",
        "repeat": 200000,
        "segments": [
            {   "id": "LIN", "type": "segment",
                "name": "Item Description",
                "req": "M",
                "notes": "",
                "max_uses": 1,
                "elements": [
                    {   "id": "LIN01", "type": "element",
                        "name": "Buyer Part",
                        "short_name": "Buyer Part",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 0, "max": 0},
                        "notes": "None"
                    },
                    {   "id": "LIN02", "type": "element",
                        "name": "Product Service Id qualifier 2",
                        "req": "M",
                        "data_type": "AN",
                        "data_type_ids": {
                            "UP": "UPC consumer package code",
                            "UK": "UPC/EAN shipping container"
                        },
                        "length": {"min": 2, "max": 2},
                        "notes": "Code value: UP= UPC consumer package code"
                    },
                    {   "id": "LIN03", "type": "element",
                        "name": "Product Service Id 2",
                        "short_name": "GTIN",
                        "req": "M",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 12, "max": 12},
                        "notes": "Retail UPC number. Format 1-5-5-1"
                    },
                    {   "id": "LIN04", "type": "element",
                        "name": "Product Service Id qualifier 4",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": {
                            "UP": "UPC consumer package code",
                            "UK": "UPC/EAN shipping container"
                        },
                        "length": {"min": 2, "max": 2},
                        "notes": "Code value: UK= UPC/EAN shipping container"
                    },
                    {   "id": "LIN05", "type": "element",
                        "name": "Product Service Id 4",
                        "short_name": "Retail UPC number 12",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 14, "max": 14},
                        "notes": "Retail UPC number. Format 1-2-5-5-1"
                    },
                    {   "id": "LIN06", "type": "element",
                        "name": "Product Service Id qualifier 6",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": {
                            "F7": "Item description"
                        },
                        "length": {"min": 2, "max": 2},
                        "notes": "Code value: F7= Item description"
                    },
                    {   "id": "LIN07", "type": "element",
                        "name": "Product Service Id 6",
                        "short_name": "Item Description",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 30},
                        "notes": "Item description"
                    }
                ]
            },
            {   "id": "PO4", "type": "segment",
                "name": "Item Physical Details",
                "req": "M",
                "notes": "",
                "max_uses": 1,
                "elements": [
                    {   "id": "PO401", "type": "element",
                        "name": "Pack",
                        "short_name": "Pack Qty",
                        "req": "O",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 6},
                        "notes": "Number of pack in a case"
                    },
                    {   "id": "PO402", "type": "element",
                        "name": "Size",
                        "req": "C",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 1, "max": 8},
                        "notes": "Size of unit in a case"
                    },
                    {   "id": "PO403", "type": "element",
                        "name": "Unit/Basis for measurement code ",
                        "req": "C",
                        "data_type": "AN",
                        "data_type_ids": None,
                        "length": {"min": 2, "max": 2},
                        "notes": "Measurement relating to size"
                    }
                ]
            },
            {   "id": "L_FST", "type": "loop",
                "name": "Forecast Schedule Loop",
                "req": "O",
                "repeat": 200000,
                "segments": [
                    {   "id": "FST", "type": "segment",
                        "name": "Forecast Schedule",
                        "req": "M",
                        "notes": "",
                        "max_uses": 1,
                        "elements": [
                            {   "id": "FST01", "type": "element",
                                "name": "Quantity",
                                "short_name": "Qty",
                                "req": "M",
                                "data_type": "AN",
                                "data_type_ids": None,
                                "length": {"min": 1, "max": 15},
                                "notes": "Estimated quantity needed by NG. Sum SDQ"
                            },
                            {   "id": "FST02", "type": "element",
                                "name": "Forecast qualifier",
                                "short_name": "Forecast Type",
                                "req": "M",
                                "data_type": "AN",
                                "data_type_ids": {"D": "Planning"},
                                "length": {"min": 1, "max": 1},
                                "notes": "Code value D= Planning"
                            },
                            {   "id": "FST03", "type": "element",
                                "name": "Forecast timing qualifier",
                                "short_name": "Forecast Timing",
                                "req": "M",
                                "data_type": "AN",
                                "data_type_ids": {"X": "Weekly Bucker"},
                                "length": {"min": 1, "max": 1},
                                "notes": "Code value: X = Weekly Bucker"
                            },
                            {   "id": "FST04", "type": "element",
                                "name": "DATE",
                                "short_name": "Start Date",
                                "req": "M",
                                "data_type": "DT",
                                "data_type_ids": None,
                                "length": {"min": 8, "max": 8},
                                "notes": "Start date of Forecast"
                            },
                            {   "id": "FST05", "type": "element",
                                "name": "DATE",
                                "short_name": "End Date",
                                "req": "M",
                                "data_type": "DT",
                                "data_type_ids": None,
                                "length": {"min": 8, "max": 8},
                                "notes": "End date of Forecast"
                            }
                        ]
                    },
                    {   "id": "L_SDQ", "type": "loop",
                        "name": "Destination Quantity Loop",
                        "req": "O",
                        "repeat": 200000,
                        "segments": [
                            {   "id": "SDQ", "type": "segment",
                                "name": "Destination Quantity",
                                "req": "M",
                                "notes": "",
                                "max_uses": 1,
                                "elements": [
                                    {   "id": "SDQ01", "type": "element",
                                        "name": "Unit or Basis for Measurement Code",
                                        "short_name": "Qty per Store UOM",
                                        "req": "M",
                                        "data_type": "AN",
                                        "data_type_ids": {"CA": "Case"},
                                        "length": {"min": 2, "max": 2},
                                        "notes": "CA = Case"
                                    },
                                    {   "id": "SDQ02", "type": "element",
                                        "name": "Identification Code Qualifier",
                                        "req": "M",
                                        "data_type": "AN",
                                        "data_type_ids": {"92": "Assigned by Buyer or Buyer’s Agent"},
                                        "length": {"min": 2, "max": 2},
                                        "notes": "92 = Assigned by Buyer or Buyer’s Agent"
                                    },
                                    {   "id": "SDQ03", "type": "element",
                                        "name": "Identification code",
                                        "short_name": "Store",
                                        "req": "M",
                                        "data_type": "AN",
                                        "data_type_ids": None,
                                        "length": {"min": 5, "max": 45},
                                        "notes": "LCL’s location"
                                    },
                                    {   "id": "SDQ04", "type": "element",
                                        "name": "Quantity",
                                        "short_name": "Qty per Store #",
                                        "req": "M",
                                        "data_type": "AN",
                                        "data_type_ids": None,
                                        "length": {"min": 1, "max": 45},
                                        "notes": "Estimated quantity"
                                    },
                                    {   "id": "SDQ23", "type": "element",
                                        "name": "Location Identifier",
                                        "req": "M",
                                        "data_type": "AN",
                                        "data_type_ids": None,
                                        "length": {"min": 40, "max": 40},
                                        "notes": "Ad Program Name"
                                    }
                                ]
                            }
                        ]
                    }
                ]
            }
        ]
    },
    {   "id": "CTT", "type": "segment",
        "name": "Transaction Total",
        "req": "M",
        "notes": "",
        "max_uses": 1,
        "elements": [
            {   "id": "CTT01", "type": "element",
                "name": "Number of line Items",
                "req": "M",
                "data_type": "AN",
                "data_type_ids": None,
                "length": {"min": 1, "max": 6},
                "notes": "Sum of LIN segments"
            }
        ]
    }
]

def load_supported_formats(formats_path):
    supported_formats = {}
    for filename in os.listdir(formats_path):
        if filename.endswith(".json"):
            format_name = filename[:-5]
            with open(os.path.join(formats_path, filename)) as format_file:
                format_def = json.load(format_file)
            if type(format_def) is not list:
                raise TypeError("Imported definition {} is not a list of segments".format(format_name))
            supported_formats[format_name] = format_def
    return supported_formats

supported_formats = load_supported_formats(os.path.join(os.path.dirname(__file__), "formats"))
