UNPKG

parse-siwe

Version:

Standalone, high-performance, validating 'ERC-4361: Sign in with Ethereum' Parser

331 lines (329 loc) 11.5 kB
import { identifiers, utilities } from './parser.js'; export const cb = { ffscheme: function ffscheme(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fscheme = utilities.charsToString(chars, phraseIndex, sysData.phraseLength).slice(0, -3); } }, fdomain: function fdomain(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fdomain = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, faddress: function faddress(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.faddress = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, authority: function authority(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.authority = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, fstatement: function fstatement(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fstatement = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, preUri: function preUri(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.NOMATCH || sysData.state === identifiers.EMPTY) { data.error = 'URI missing or invalid prefix "URI: "'; } }, furi: function furi(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.furi = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, preVersion: function preVersion(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.NOMATCH || sysData.state === identifiers.EMPTY) { data.error = 'Version missing or invalid prefix "Version: "'; } }, fversion: function fversion(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fversion = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, preChainId: function preChainId(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.NOMATCH || sysData.state === identifiers.EMPTY) { data.error = 'Chain ID missing or invalid prefex "Chain ID: "'; } }, fchainId: function fchainId(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fchainId = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, preNonce: function preNonce(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.NOMATCH || sysData.state === identifiers.EMPTY) { data.error = 'Nonce missing or invalid Nonce prefex "Nonce: "'; } }, fnonce: function fnonce(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fnonce = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, preIssuedAt: function preIssuedAt(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.NOMATCH || sysData.state === identifiers.EMPTY) { data.error = 'Issued At missing or invalid Issued At prefex "Issued At: "'; } }, fissuedAt: function fissuedAt(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fissuedAt = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, fexpirationTime: function fexpirationTime(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fexpirationTime = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, fnotBefore: function fnotBefore(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fnotBefore = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, frequestId: function frequestId(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.frequestId = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } else if (sysData.state === identifiers.EMPTY) { data.frequestId = ''; } }, fresources: function fresources(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.ACTIVE) { data.fresources = []; } }, fresource: function fresource(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fresources.push(utilities.charsToString(chars, phraseIndex, sysData.phraseLength).slice(2)); } }, emptyStatement: function emptyStatement(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fstatement = ''; } }, noStatement: function noStatement(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fstatement = undefined; } }, actualStatement: function actualStatement(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.fstatement = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } }, // handle the URI URI: function URI(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.ACTIVE: data.errorslength = 0; break; case identifiers.MATCH: data.uri = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; case identifiers.EMPTY: sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; break; } }, scheme: function scheme(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.scheme = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; } }, userinfo: function userinfo(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.userinfo = utilities.charsToString(chars, phraseIndex, sysData.phraseLength - 1); break; } }, host: function host(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.ACTIVE: data.iplit = false; break; case identifiers.MATCH: if (data.iplit) { // strip leading "[" and trailing "]" brackets data.host = utilities.charsToString(chars, phraseIndex + 1, sysData.phraseLength - 2); } else { data.host = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); } break; case identifiers.EMPTY: data.host = ''; break; } }, ipLiteral: function ipLiteral(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.iplit = true; } }, port: function port(sysData, chars, phraseIndex, data) { let parsed = 0; let port = ''; switch (sysData.state) { case identifiers.MATCH: port = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); parsed = parseInt(port); if (Number.isNaN(parsed)) { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } else { data.port = parsed; } break; case identifiers.EMPTY: data.port = ''; break; } }, pathAbempty: function pathAbempty(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.path = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; case identifiers.EMPTY: data.path = ''; break; } }, pathAbsolute: function pathAbsolute(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.path = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; } }, pathRootless: function pathRootless(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.path = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; } }, pathEmpty: function pathEmpty(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: case identifiers.NOMATCH: sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; case identifiers.EMPTY: data.path = ''; break; } }, query: function query(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.query = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; case identifiers.EMPTY: data.query = ''; break; } }, fragment: function fragment(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.fragment = utilities.charsToString(chars, phraseIndex, sysData.phraseLength); break; case identifiers.EMPTY: data.fragment = ''; break; } }, ipv4: function ipv4(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.ipv4 = true; } }, h16: function h16(sysData, chars, phraseIndex, data) { if (sysData.state === identifiers.MATCH) { data.h16count += 1; } }, nodcolon: function nodcolon(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.ACTIVE: data.h16count = 0; data.ipv4 = false; break; case identifiers.MATCH: // semantically validate the number of 16-bit digits if (data.ipv4) { if (data.h16count === 6) { sysData.state = identifiers.MATCH; } else { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } } else { if (data.h16count === 8) { sysData.state = identifiers.MATCH; } else { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } } break; } }, dcolon: function dcolon(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.ACTIVE: data.h16count = 0; data.ipv4 = false; break; case identifiers.MATCH: // semantically validate the number of 16-bit digits if (data.ipv4) { if (data.h16count < 6) { sysData.state = identifiers.MATCH; } else { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } } else { if (data.h16count < 8) { sysData.state = identifiers.MATCH; } else { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } } break; } }, decOctet: function decOctet(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.ACTIVE: data.octet = 0; break; case identifiers.MATCH: // semantically validate the octet if (data.octet > 255) { sysData.state = identifiers.NOMATCH; sysData.phraseLength = 0; } break; } }, decDigit: function decDigit(sysData, chars, phraseIndex, data) { switch (sysData.state) { case identifiers.MATCH: data.octet = 10 * data.octet + chars[phraseIndex] - 48; break; } }, };