A document field has a field type. The field type tells Identità what kind of value to extract, how to validate it, and which input and output controls to show.
Field types answer whether a value is present and correctly shaped. Business or SOP decisions belong to flow validation rules instead. See How validation works for the full path from flow configuration to officer decision.
For example:
DocumentField(
name="identity_document_number",
field_type="MaltaIDCardNumber",
)
Use the exact, case-sensitive name shown in the registry below.
Field type and validation field type¶
Most fields need only field_type:
DocumentField(
name="expiry_date",
field_type="SixMonthsToFutureDate",
)
When extraction and validation need different shapes, use
validation_field_type as well:
DocumentField(
name="advertised_job_titles",
field_type="StringList",
validation_field_type="JobTitleList",
)
Here, StringList supplies the editor and display, while JobTitleList gives
the extraction model more precise instructions.
Do not use a strict field constraint for a policy threshold that may legitimately be missed by the source document. Store the truthful value, then evaluate the threshold as a named flow validation rule. See Where should a new rule live?.
Supported field-type registry¶
Every name in this table is checked automatically against the running application. A documented name must resolve, and every supported field type must appear here.
| Type | Category | Use |
|---|---|---|
Text |
Basic | One line of text. |
LongText |
Basic | Multiple lines of text. |
Integer |
Basic | A whole number. |
DecimalNumber |
Basic | A decimal number. |
Boolean |
Basic | A yes/no value. |
Date |
Basic | A calendar date. |
DateTime |
Basic | A date and time. |
StringList |
Basic | A list of text values. |
Select |
Basic | A list selected from configured choices. |
JsonDict |
Basic | A JSON object with text keys. |
Signature |
Document | A signature location on a PDF page. |
SkillsPassQRCode |
Document | A Skills Pass QR verification URL and result. |
Country |
Pydantic | An ISO 3166-1 alpha-3 country code. |
DirectoryPath |
Pydantic | An existing directory path. |
EmailStr |
Pydantic | A validated email address. |
Email |
Pydantic | Alias of EmailStr. |
FilePath |
Pydantic | An existing file path. |
FiniteFloat |
Pydantic | A finite floating-point number. |
FutureDate |
Pydantic | A date after today. |
FutureDatetime |
Pydantic | A date and time in the future. |
Url |
Pydantic | An HTTP or HTTPS URL. |
HttpUrl |
Pydantic | An HTTP or HTTPS URL. |
Json |
Pydantic | JSON supplied as a string or bytes. |
JsonValue |
Pydantic | Any valid JSON value. |
NaiveDatetime |
Pydantic | A date and time without a timezone. |
NegativeFloat |
Pydantic | A floating-point number below zero. |
NegativeInt |
Pydantic | A whole number below zero. |
NewPath |
Pydantic | A path that does not yet exist. |
NonNegativeFloat |
Pydantic | A floating-point number of zero or more. |
NonNegativeInt |
Pydantic | A whole number of zero or more. |
NonPositiveFloat |
Pydantic | A floating-point number of zero or less. |
NonPositiveInt |
Pydantic | A whole number of zero or less. |
PastDate |
Pydantic | A date before today. |
PastDatetime |
Pydantic | A date and time in the past. |
PaymentCardNumber |
Pydantic | A validated payment-card number. |
PaymentCardBrand |
Pydantic | A recognised payment-card brand. |
PositiveFloat |
Pydantic | A floating-point number above zero. |
PositiveInt |
Pydantic | A whole number above zero. |
PhoneNumber |
Pydantic | A validated international phone number. |
StrictBool |
Pydantic | A boolean without type coercion. |
StrictBytes |
Pydantic | Bytes without type coercion. |
StrictFloat |
Pydantic | A float without type coercion. |
StrictInt |
Pydantic | An integer without type coercion. |
StrictStr |
Pydantic | Text without type coercion. |
MaltaAlpha3 |
Malta | The country code MLT only. |
ThreeMonthSincePastDate |
Date window | A past date within the previous three months. |
SixMonthSincePastDate |
Date window | A past date within the previous six months. |
TwelveMonthSincePastDate |
Date window | A past date within the previous twelve months. |
ThreeMonthSincePastDateOrToday |
Date window | Today or a date within the previous three months. |
SixMonthSincePastDateOrToday |
Date window | Today or a date within the previous six months. |
TwelveMonthSincePastDateOrToday |
Date window | Today or a date within the previous twelve months. |
SixMonthsToFutureDate |
Date window | Today through six months in the future. |
EightMonthsToFutureDate |
Date window | Today through eight months in the future. |
TwelveMonthsToFutureDate |
Date window | Today through twelve months in the future. |
PositivePriceField |
Money | A non-negative decimal with at most ten digits and two decimal places. |
PriceField |
Money | A signed decimal with at most ten digits and two decimal places. |
MoneyAmount |
Money | A non-negative scalar amount normalized and stored in EUR. |
Gender |
Choice | male, female, or other. |
PersonClass |
Choice | The legal classification of a relevant person. |
DirectorRole |
Choice | A director or company-secretary role. |
LiabilityStatus |
Choice | GENERAL or LIMITED. |
InstrumentType |
Choice | The kind of investment instrument. |
TransactionType |
Choice | The kind of bank transaction. |
WealthSourceCategory |
Choice | A source-of-wealth category. |
FundsSourceCategory |
Choice | A source-of-funds category. |
NatureType |
Choice | GOODS or SERVICES. |
CostType |
Choice | CAPEX or OPEX. |
ConfidenceLevel |
Choice | HIGH, MEDIUM, or LOW. |
EmploymentStatus |
Choice | EMPLOYED or SELF_EMPLOYED. |
EmploymentType |
Choice | FULL_TIME or PART_TIME. |
EmploymentNature |
Choice | The nature of an employment relationship. |
EmployeeListEmploymentType |
Choice | A Jobsplus employee-list employment type. |
EmployeeListEmploymentNature |
Choice | A Jobsplus employee-list employment nature. |
ServiceName |
Choice | A supported corporate-service name. |
ScreeningCategory |
Choice | A compliance-screening category. |
ScreeningResultStatus |
Choice | A compliance-screening result. |
WorkPermitJobCategory |
Choice | Canonical Single Permit occupation route. |
AdvertisingChannel |
Choice | One canonical vacancy-advertising channel. |
AdvertisingChannels |
Collection | One or more canonical vacancy-advertising channels. |
PayPeriod |
Choice | Canonical hourly, daily, weekly, monthly, or annual pay period. |
ProfessionalRole |
Choice | Lawyer, notary, or legal procurator. |
InvoiceLineItem |
Structured | One invoice line, including price and VAT information. |
InvoiceLineItemWithExtra |
Structured | An invoice line with nature, cost type, and confidence. |
IntegrationContact |
Structured | A contact from an accounting integration. |
IntegrationAccount |
Structured | A cost or revenue account from an accounting integration. |
EmploymentEntry |
Structured | One Jobsplus employment-history row. |
EmployeeListEntry |
Structured | One Jobsplus employee-list row. |
ServiceLine |
Structured | One corporate service and its dates. |
ScreeningResult |
Structured | One screening category and its result. |
MRZStr |
Identity | A validated TD3 passport MRZ line 2. |
VATRate |
Malta | A VAT percentage of 0, 5, 7, or 18. |
InvoiceLineItems |
Collection | A list of InvoiceLineItem values. |
PastDateOrToday |
Date window | Today or any earlier date. |
ConstrMin2Str |
Text | Trimmed text containing at least two characters. |
ConstrMin8Str |
Text | Trimmed text containing at least eight characters. |
MaltaIDCardNumber |
Identity | Six or seven digits followed by M, L, or G. |
MaltaPassportNumber |
Identity | Seven digits, or MT followed by six digits. |
MaltaResidencePermitIDNumber |
Identity | Seven digits followed by A. |
MaltaVATNumber |
Malta | MT followed by eight digits. |
MaltaCompanyRegistrationNumber |
Malta | C followed by five digits. |
JobTitle |
Text | One trimmed job title containing at least two characters. |
JobTitleList |
Collection | One or more separately stored job titles. |
SalaryBand |
Structured | Currency plus minimum and maximum salary amounts. |
Party |
Structured | One natural or legal party to a document. |
PartyList |
Collection | A list of Party values. |
RelevantPerson |
Structured | Common identity details for a relevant person. |
RelevantPersons |
Collection | A list of RelevantPerson values. |
Director |
Structured | A director or company secretary. |
Shareholder |
Structured | A registered member or shareholder. |
BeneficialOwner |
Structured | A beneficial owner or SMO fallback. |
Partner |
Structured | A partner in a partnership. |
Trustee |
Structured | A trustee of a trust. |
Settlor |
Structured | A settlor of a trust. |
Beneficiary |
Structured | A beneficiary of a trust or will. |
Protector |
Structured | A protector of a trust. |
Administrator |
Structured | An administrator of an association. |
Founder |
Structured | A founder of a foundation. |
Heir |
Structured | An heir named in an estate document. |
Shareholders |
Collection | A list of Shareholder values. |
BeneficialOwners |
Collection | A list of BeneficialOwner values. |
Partners |
Collection | A list of Partner values. |
Trustees |
Collection | A list of Trustee values. |
Settlors |
Collection | A list of Settlor values. |
Beneficiaries |
Collection | A list of Beneficiary values. |
Protectors |
Collection | A list of Protector values. |
Administrators |
Collection | A list of Administrator values. |
Founders |
Collection | A list of Founder values. |
Heirs |
Collection | A list of Heir values. |
Holding |
Structured | One security on an investment statement. |
BankTransaction |
Structured | One bank-statement transaction. |
BankTransactions |
Collection | A list of BankTransaction values. |
SourceOfWealthEntry |
Structured | One declared source of accumulated wealth. |
SourceOfFundsEntry |
Structured | One declared source of funds for a transaction. |
Any |
Built-in | Any Python value. |
bool |
Built-in | A Python boolean. |
bytes |
Built-in | Python bytes. |
dict |
Built-in | A Python dictionary. |
float |
Built-in | A Python floating-point number. |
frozenset |
Built-in | A Python immutable set. |
int |
Built-in | A Python integer. |
list |
Built-in | A Python list. |
None |
Built-in | No value. |
set |
Built-in | A Python set. |
str |
Built-in | Python text. |
tuple |
Built-in | A Python tuple. |
Important specialised types¶
Recent and future dates¶
The *SincePastDate types accept a date before today and within the named
calendar-month window. Their *OrToday variants also accept today.
The future-window types are inclusive at both ends:
| Type | Earliest date | Latest date |
|---|---|---|
SixMonthsToFutureDate |
Today | Today plus 6 calendar months |
EightMonthsToFutureDate |
Today | Today plus 8 calendar months |
TwelveMonthsToFutureDate |
Today | Today plus 12 calendar months |
Calendar months are used instead of a fixed number of days. This matters around months of different lengths.
MoneyAmount¶
MoneyAmount stores a single non-negative EUR amount with up to 12 digits and
2 decimal places. Its JSON value remains a plain number:
1248.50
The extractor follows these rules:
- amounts already printed in EUR are returned without conversion;
- an explicitly non-EUR amount is converted with the
convert_money_to_eurtool, using a three-letter ISO 4217 source code and embedded European Central Bank rates; - when a date clearly governs the amount, such as a statement, pay-period, policy-effective, or contract-effective date, that historical date is used;
- without a clear date, the latest rate bundled with the application is used; and
- if the source currency or rate cannot be established, the field is omitted and the reason is added to the extraction notes. An unconverted foreign amount must never be returned as EUR.
The converter uses the last known rate for a missing day such as a weekend or bank holiday. It does not substitute a rate when the requested date is outside the currency's available history. Converted values are rounded to euro cents.
The editor and output component always show a fixed EUR indicator. Manual
entries are therefore also interpreted as EUR. Source currency, exchange rate,
and conversion date are not persisted.
SalaryBand¶
SalaryBand keeps a printed salary range as structured data:
{
"currency": "EUR",
"minimum": "15000",
"maximum": "20000"
}
currencyis a three-letter ISO 4217 code. Symbols are converted, such as€toEUR.minimumandmaximumare decimal amounts without currency symbols or thousands separators.
The field description helps the extraction model split a printed range into these three values.
Signature¶
Signature records the signature's position:
{
"page_number": 1,
"x_coord": 120,
"y_coord": 640,
"length": 260,
"height": 90
}
The page number starts at 1. Coordinates and dimensions use a page-normalised 0–1000 coordinate system. Width and height must be positive, and the complete box must fit on the page.
SkillsPassQRCode¶
SkillsPassQRCode stores:
{
"url": "https://certificates.skillspass.org.mt/certificate/9277e4221f965968af52ca5bcf32cd34?format=json",
"valid": true
}
The extraction model is told to read the URL encoded in the QR image near the bottom of the Skills Pass certificate. It must not copy a nearby printed website address.
Identità adds format=json to the URL and verifies the downloaded certificate
data. Verification checks the expected Skills Pass host and certificate path,
valid Blockcerts-shaped JSON, and a matching certificate identifier. The
valid value records that result; it is not a cryptographic proof of the
underlying blockchain claim.
Maltese identifiers¶
| Type | Accepted form |
|---|---|
MaltaIDCardNumber |
6 or 7 digits followed by M, L, or G |
MaltaPassportNumber |
7 digits, or MT followed by 6 digits |
MaltaResidencePermitIDNumber |
7 digits followed by A |
MaltaVATNumber |
MT followed by 8 digits |
MaltaCompanyRegistrationNumber |
C followed by 5 digits |
MRZStr is specifically TD3 passport MRZ line 2. It normalises the text and
checks the ICAO check digits.
Parties and relevant people¶
Use Party for a natural person or legal entity acting as a party to a
property or accommodation document. It contains the printed name, party type,
identifier, optional VAT number, and whether the party is foreign. Use
PartyList when the document can contain co-lessors, co-lessees, co-vendors,
or co-purchasers.
RelevantPerson contains the common details used by corporate and compliance
records: name, identification number, address, nationality, date of birth, and
person class. Role-specific types such as Director, Shareholder, and
Trustee add the fields needed for that role. Their plural forms are the
corresponding collection types.
Validation-only helpers¶
These types provide precise extraction or validation instructions but do not
have their own dedicated editor and output component. Pair them with a
renderable field_type through validation_field_type.
| Type | Suggested field type | Purpose |
|---|---|---|
PartyType |
Text |
natural_person or legal_person. |
PersonName |
Text |
A trimmed full printed name without separable titles. |
JobTitle |
Text |
One trimmed job title containing at least two characters. |
JobTitleList |
StringList |
One or more job titles, with every advertised vacancy kept as a separate list item. |
WorkPermitJobCategory |
Text |
Canonical Single Permit occupation route, such as driver_lptv, nursing, sports, or tourism_hospitality. |
AdvertisingChannel |
Text |
One canonical vacancy channel: jobsplus, eures, local, or other. |
AdvertisingChannels |
StringList |
Every canonical channel on which a vacancy appeared. |
PayPeriod |
Text |
Canonical wage period: hourly, daily, weekly, monthly, or annual. |
ProfessionalRole |
Text |
Attesting professional role: lawyer, notary, or legal_procurator. |
Adding a field type¶
Adding a field type is a four-part change:
- Define the type in
backend/src/apps/zf_documents/field_types.py. - Add it to this registry.
- Add its input component under
backend/src/templates/cotton/field_types/input/. - Add its output component under
backend/src/templates/cotton/field_types/output/.
Component filenames use the snake-case form of the type name. For example,
SalaryBand uses salary_band.html in both component directories.
The input component receives field, value, errors, and the generated
form-field name. The output component receives field and value. Reuse an
existing component only when the value has the same shape and interaction.