Skip to content

Instantly share code, notes, and snippets.

@skylarmt
Last active November 20, 2025 05:41
Show Gist options
  • Select an option

  • Save skylarmt/e817c0ac9bbc4cc4bd4f671348619142 to your computer and use it in GitHub Desktop.

Select an option

Save skylarmt/e817c0ac9bbc4cc4bd4f671348619142 to your computer and use it in GitHub Desktop.
Parse the barcode on the back of a North America AAMVA drivers license/ID card and extract basic info. Code originally from PostalPoint Retail Shipping Software, https://postalpoint.app
/*
* Copyright 2024-2025 PostalPortal LLC, Netsyms Technologies LLC. All rights reserved.
* This code file is hereby optionally made available under the MIT license.
*/
export function parseLicenseBarcode(data) {
var fields = getLicenseDataStructure();
if (!data.startsWith("@") || data.substring(4, 9) != "ANSI ") {
throw new Error("Not a valid AAMVA license barcode.");
}
var dataElSep = data.charAt(1);
var recordSep = data.charAt(2);
var segmentTerminator = data.charAt(3);
var issuerIIN = data.substring(9, 15);
var aamvaVersionNumber = data.substring(15, 17);
var numberOfEntries = data.substring(19, 21) * 1;
var entryList = chunkString(data.substring(21, 21 + (numberOfEntries * 10)), 10);
var type = "";
var subfileOffset = 0;
var subfileLength = 0;
for (let i = 0; i < entryList.length; i++) {
if (entryList[i].startsWith("Z")) {
continue;
}
if (["DL", "ID", "EN"].includes(entryList[i].substring(0, 2))) {
type = entryList[i].substring(0, 2);
subfileOffset = entryList[i].substring(2, 6) * 1;
subfileLength = entryList[i].substring(6, 10) * 1;
break;
}
}
// +2 offset because the subfile starts with its two-character type code
var datafieldstr = data.substring(subfileOffset + 2, subfileLength + subfileOffset);
var datafieldstrings = datafieldstr.split(dataElSep);
var datafields = {};
for (let i = 0; i < datafieldstrings.length; i++) {
if (datafieldstrings[i].length > 3) {
datafields[datafieldstrings[i].substring(0, 3)] = datafieldstrings[i].substring(3);
}
}
var firstname = datafields["DAC"] ?? "";
var lastname = datafields["DCS"] ?? "";
var middlename = (datafields["DAD"] ?? "").replaceAll(",", " ");
var namesuffix = datafields["DCU"] ?? "";
fields.name = [firstname, middlename, lastname, namesuffix].filter(Boolean).join(" ");
var street1 = (datafields["DAG"] ?? "").trim();
var street2 = (datafields["DAH"] ?? "").trim();
fields.address = [street1, street2].filter(Boolean).join(", ");
fields.city = datafields["DAI"] ?? "";
fields.state = datafields["DAJ"] ?? "";
fields.zip = datafields["DAK"] ?? "";
if (fields.zip.endsWith("0000")) {
fields.zip = fields.zip.substring(0, 5);
}
fields.zip = fields.zip.trim();
fields.number = datafields["DAQ"] ?? "";
fields.country = (datafields["DCG"] ?? "").substring(0, 2);
if ((datafields["DCG"] ?? "") == "USA") {
// Expiration date in MMDDYYYY
fields.exp = `${datafields["DBA"].substring(4, 8)}-${datafields["DBA"].substring(0, 2)}-${datafields["DBA"].substring(2, 4)}`;
} else if ((datafields["DCG"] ?? "") == "CAN") {
// Expiration date in YYYYMMDD
fields.exp = `${datafields["DBA"].substring(0, 4)}-${datafields["DBA"].substring(4, 6)}-${datafields["DBA"].substring(6, 8)}`;
}
if (typeof IIN_LIST[issuerIIN] != "undefined") {
fields.issuer = IIN_LIST[issuerIIN].name;
}
return fields;
}
/**
* Get blank data fields in the format used internally by the PS Form 1583 code
*/
export function getLicenseDataStructure() {
return {
type: "DL/ID",
name: "",
number: "",
issuer: "",
exp: "",
address: "",
city: "",
state: "",
zip: "",
country: ""
};
}
function chunkString(str, chunksize) {
return [].concat.apply([],
str.split('').map(function (x, i) {
return i % chunksize ? [] : str.slice(i, i + chunksize)
}, str)
);
}
const IIN_LIST = {
"604426": {name: "Prince Edward Island", abbr: "PE", country: "Canada"},
"604427": {name: "American Samoa", abbr: "AS", country: "USA"},
"604428": {name: "Quebec", abbr: "QC", country: "Canada"},
"604429": {name: "Yukon", abbr: "YT", country: "Canada"},
"604430": {name: "Norther Marianna Islands", abbr: "MP", country: "USA"},
"604431": {name: "Puerto Rico", abbr: "PR", country: "USA"},
"604432": {name: "Alberta", abbr: "AB", country: "Canada"},
"604433": {name: "Nunavut", abbr: "NU", country: "Canada"},
"604434": {name: "Northwest Territories", abbr: "NT", country: "Canada"},
"636000": {name: "Virginia", abbr: "VA", country: "USA"},
"636001": {name: "New York", abbr: "NY", country: "USA"},
"636002": {name: "Massachusetts", abbr: "MA", country: "USA"},
"636003": {name: "Maryland", abbr: "MD", country: "USA"},
"636004": {name: "North Carolina", abbr: "NC", country: "USA"},
"636005": {name: "South Carolina", abbr: "SC", country: "USA"},
"636006": {name: "Connecticut", abbr: "CT", country: "USA"},
"636007": {name: "Louisiana", abbr: "LA", country: "USA"},
"636008": {name: "Montana", abbr: "MT", country: "USA"},
"636009": {name: "New Mexico", abbr: "NM", country: "USA"},
"636010": {name: "Florida", abbr: "FL", country: "USA"},
"636011": {name: "Delaware", abbr: "DE", country: "USA"},
"636012": {name: "Ontario", abbr: "ON", country: "Canada"},
"636013": {name: "Nova Scotia", abbr: "NS", country: "Canada"},
"636014": {name: "California", abbr: "CA", country: "USA"},
"636015": {name: "Texas", abbr: "TX", country: "USA"},
"636016": {name: "Newfoundland", abbr: "NF", country: "Canada"},
"636017": {name: "New Brunswick", abbr: "NB", country: "Canada"},
"636018": {name: "Iowa", abbr: "IA", country: "USA"},
"636019": {name: "Guam", abbr: "GU", country: "USA"},
"636020": {name: "Colorado", abbr: "GM", country: "USA"},
"636021": {name: "Arkansas", abbr: "AR", country: "USA"},
"636022": {name: "Kansas", abbr: "KS", country: "USA"},
"636023": {name: "Ohio", abbr: "OH", country: "USA"},
"636024": {name: "Vermont", abbr: "VT", country: "USA"},
"636025": {name: "Pennsylvania", abbr: "PA", country: "USA"},
"636026": {name: "Arizona", abbr: "AZ", country: "USA"},
"636027": {name: "USA State Dept.", abbr: "", country: "USA"},
"636028": {name: "British Columbia", abbr: "BC", country: "Canada"},
"636029": {name: "Oregon", abbr: "OR", country: "USA"},
"636030": {name: "Missouri", abbr: "MO", country: "USA"},
"636031": {name: "Wisconsin", abbr: "WI", country: "USA"},
"636032": {name: "Michigan", abbr: "MI", country: "USA"},
"636033": {name: "Alabama", abbr: "AL", country: "USA"},
"636034": {name: "North Dakota", abbr: "ND", country: "USA"},
"636035": {name: "Illinois", abbr: "IL", country: "USA"},
"636036": {name: "New Jersey", abbr: "NJ", country: "USA"},
"636037": {name: "Indiana", abbr: "IN", country: "USA"},
"636038": {name: "Minnesota", abbr: "MN", country: "USA"},
"636039": {name: "New Hampshire", abbr: "NH", country: "USA"},
"636040": {name: "Utah", abbr: "UT", country: "USA"},
"636041": {name: "Maine", abbr: "ME", country: "USA"},
"636042": {name: "South Dakota", abbr: "SD", country: "USA"},
"636043": {name: "District of Columbia", abbr: "DC", country: "USA"},
"636044": {name: "Saskatchewan", abbr: "SK", country: "Canada"},
"636045": {name: "Washington", abbr: "WA", country: "USA"},
"636046": {name: "Kentucky", abbr: "KY", country: "USA"},
"636047": {name: "Hawaii", abbr: "HI", country: "USA"},
"636048": {name: "Manitoba", abbr: "MB", country: "Canada"},
"636049": {name: "Nevada", abbr: "NV", country: "USA"},
"636050": {name: "Idaho", abbr: "ID", country: "USA"},
"636051": {name: "Mississippi", abbr: "MS", country: "USA"},
"636052": {name: "Rhode Island", abbr: "RI", country: "USA"},
"636053": {name: "Tennessee", abbr: "TN", country: "USA"},
"636054": {name: "Nebraska", abbr: "NE", country: "USA"},
"636055": {name: "Georgia", abbr: "GA", country: "USA"},
"636056": {name: "Coahuila", abbr: "CU", country: "Mexico"},
"636057": {name: "Hidalgo", abbr: "HL", country: "Mexico"},
"636058": {name: "Oklahoma", abbr: "OK", country: "USA"},
"636059": {name: "Alaska", abbr: "AK", country: "USA"},
"636060": {name: "Wyoming", abbr: "WY", country: "USA"},
"636061": {name: "West Virginia", abbr: "WV", country: "USA"},
"636062": {name: "Virgin Islands", abbr: "VI", country: "USA"}
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment