UNPKG

@platform/cell.schema

Version:

URI and database schemas for the `cell.os`.

307 lines (306 loc) 12.3 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.Uri = exports.DEFAULT = void 0; var tslib_1 = require("tslib"); var common_1 = require("../common"); var ALLOW = { NS: [] }; exports.DEFAULT = { ALLOW: ALLOW }; var stripQuotes = function (text) { return text.trim().replace(/^"/, '').replace(/"$/, '').replace(/^'/, '').replace(/'$/, '').trim(); }; var Uri = (function () { function Uri() { } Uri.clean = function (input) { var text = stripQuotes(input || ''); text = text.replace(/^=/, '').trim(); text = stripQuotes(text); text = text.split('?')[0].trim(); return text; }; Uri.parse = function (input) { var text = Uri.clean(input); var data = { type: 'UNKNOWN' }; var error; var toString = function () { return text; }; var setError = function (isError, message) { if (!error && isError) { error = { type: 'URI', message: message, uri: text }; } }; setError(!text, 'URI not specified'); var index = text.indexOf(':'); setError(index < 0, 'Not a valid multi-part URI'); if (!error) { var left = text.substring(0, index); var right = text.substring(index + 1).trim(); if (left === 'ns') { var id = right; setError(!id, 'Namespace URI identifier not found'); setError(!Uri.is.valid.ns(id), "URI contains an invalid \"ns\" identifier (\"".concat(id, "\")")); var uri = { type: 'NS', id: id, toString: toString }; data = uri; } else if (left === 'file') { var id = right; setError(!id, 'File URI identifier not found'); var parts = id.split(':'); var ns = (parts[0] || '').trim(); var file = (parts[1] || '').trim(); setError(!file, "File identifier within namespace \"".concat(ns, "\" not found")); var uri = { type: 'FILE', id: id, ns: ns, file: file, toString: toString }; data = uri; } else if (left === 'cell') { var id = right || ''; setError(!id, "ID of 'cell' not found"); var type = 'CELL'; var key = ''; var ns = ''; if (!id.includes(':')) { setError(true, "The 'cell' URI does not have a coordinate address, eg. \":A1\" in \"cell:foo:A1\""); } else { var bang = id.replace(/:/g, '!'); var parts = common_1.coord.cell.toCell(bang); type = common_1.coord.cell.toType(bang); key = parts.key; ns = parts.ns; setError(!key, "Coordinate key of '".concat(type || '<empty>', "' not found")); setError(!ns, "Coordinate namespace of '".concat(type || '<empty>', "' not found")); if (!error) { text = toUri('cell', type, ns, key); } } data = { type: type, id: id, ns: ns, key: key, toString: toString }; } } var ok = !error && data.type !== 'UNKNOWN'; var res = { ok: ok, uri: text, type: data.type, parts: data, toString: toString, }; return error ? tslib_1.__assign(tslib_1.__assign({}, res), { error: error }) : res; }; Uri.ns = function (input, throwError) { input = typeof input === 'string' && !input.includes(':') ? "ns:".concat(input.trim()) : input; return parseOrThrow(input, 'NS', throwError); }; Uri.cell = function (input, throwError) { return parseOrThrow(input, 'CELL', throwError); }; Uri.row = function (input, throwError) { return parseOrThrow(input, 'ROW', throwError); }; Uri.column = function (input, throwError) { return parseOrThrow(input, 'COLUMN', throwError); }; Uri.file = function (input, throwError) { return parseOrThrow(input, 'FILE', throwError); }; Uri.eq = function (a, b) { var toString = function (input) { input = input === undefined || input === null ? '' : input; var text = input.toString().trim(); return !text.includes(':') ? "ns:".concat(text) : text; }; return toString(a) === toString(b); }; Uri.toNs = function (input) { if (input === undefined) { return Uri.ns((0, common_1.cuid)()); } if (typeof input === 'string') { input = Uri.clean(input); } if (typeof input === 'string' && !input.includes(':')) { return Uri.ns(input); } var obj = typeof input === 'string' ? Uri.parse(input).parts : input; if (obj.type === 'NS') { return obj; } if (obj.type === 'CELL' || obj.type === 'COLUMN' || obj.type === 'ROW') { return Uri.ns(obj.ns); } if (obj.type === 'FILE') { return Uri.ns(obj.ns); } throw new Error("A namespace cannot be derived from the uri (".concat(input.toString(), ")")); }; Uri.toRowIndex = function (input) { var uri = typeof input === 'object' ? input : Uri.parse(input).parts; if (uri.type === 'CELL' || uri.type === 'COLUMN' || uri.type === 'ROW') { return common_1.coord.cell.toRowIndex(uri.key); } else { return -1; } }; Uri.toColumnIndex = function (input) { var uri = typeof input === 'object' ? input : Uri.parse(input).parts; if (uri.type === 'CELL' || uri.type === 'COLUMN' || uri.type === 'ROW') { return common_1.coord.cell.toColumnIndex(uri.key); } else { return -1; } }; Uri.cuid = common_1.cuid; Uri.slug = common_1.slug; Uri.ALLOW = tslib_1.__assign({}, exports.DEFAULT.ALLOW); Uri.create = { ns: function (id) { return toUri('ns', 'NS', id); }, cell: function (ns, key) { return toUri('cell', 'CELL', ns, key); }, row: function (ns, key) { return toUri('cell', 'ROW', ns, key); }, column: function (ns, key) { return toUri('cell', 'COLUMN', ns, key); }, file: function (ns, fileid) { return toUri('file', 'FILE', ns, fileid); }, A1: function () { return Uri.create.cell((0, common_1.cuid)(), 'A1'); }, }; Uri.is = { uri: function (input) { try { return Uri.parse(input).ok; } catch (error) { return false; } }, type: function (type, input) { try { var uri_1 = Uri.parse(input); var types = Array.isArray(type) ? type : [type]; return types.some(function (type) { return uri_1.parts.type === type && (type === 'UNKNOWN' ? true : uri_1.ok); }); } catch (error) { return false; } }, ns: function (input) { return Uri.is.type('NS', input); }, file: function (input) { return Uri.is.type('FILE', input); }, cell: function (input) { return Uri.is.type('CELL', input); }, row: function (input) { return Uri.is.type('ROW', input); }, column: function (input) { return Uri.is.type('COLUMN', input); }, valid: { ns: function (input) { var value = (input || '').replace(/^ns:/, ''); if (!value) { return false; } if (isCuid(value)) { return true; } var matchLegal = value.match(/^[A-Za-z0-9.]*$/); if (!matchLegal || (matchLegal && matchLegal[0] !== value)) { return false; } return Uri.ALLOW.NS.some(function (pattern) { return typeof pattern === 'string' ? pattern.includes('*') ? common_1.wildcard.isMatch(value, pattern) : pattern === value : pattern(value); }); }, }, }; Uri.strip = { ns: function (input) { return stripPrefix(input, 'ns'); }, cell: function (input) { return stripPrefix(input, 'cell'); }, file: function (input) { return stripPrefix(input, 'file'); }, }; return Uri; }()); exports.Uri = Uri; var alphaNumeric = new RegExp(/^[a-z0-9]+$/i); function trimPrefix(prefix, input) { var regex = new RegExp("^".concat(prefix, ":+")); return input.trim().replace(regex, ''); } function toUri(prefix, type, id, suffix) { id = (id || '').trim(); id = id === ':' ? '' : id; if (id) { ['ns', 'cell', 'file'].forEach(function (prefix) { return (id = trimPrefix(prefix, id)); }); } if (!id) { throw new Error("The \"".concat(prefix, "\" URI was not supplied with a namespace identifier. (\"").concat(id, "\")")); } if (!Uri.is.valid.ns(id)) { var err = "URI contains an invalid \"".concat(prefix, "\" identifier, must be an alpha-numeric cuid. (\"").concat(id, "\")"); throw new Error(err); } if (typeof suffix === 'string') { suffix = (suffix || '').trim().replace(/^:*/, ''); if (!suffix) { throw new Error("The \"".concat(prefix, "\" URI was not supplied with a suffix key.")); } if (prefix === 'file') { if (!alphaNumeric.test(suffix)) { var err = "The \"file\" URI contains an invalid file-identifier, must be alpha-numeric (\"".concat(suffix, "\")."); throw new Error(err); } suffix = ":".concat(suffix); } else { if (suffix === 'undefined') { var err = "The suffix \"undefined\" (string) was given - this it likely an upstream error where an [undefined] value has been converted into a string."; throw new Error(err); } suffix = suffix || ''; var suffixType = common_1.coord.cell.toType(suffix) || ''; if (suffixType !== type) { var key = suffix || ''; var err = "The \"".concat(prefix, ":\" URI was not supplied with a valid ").concat(type, " key (given key \"").concat(key, "\")."); throw new Error(err); } suffix = ":".concat(suffix); } } return "".concat(prefix, ":").concat(id).concat(suffix || ''); } function isCuid(input) { return input.length === 25 && input[0] === 'c' && alphaNumeric.test(input); } function parseOrThrow(input, type, throwError) { if (typeof input === 'object') { return input; } else { var parsed = Uri.parse(input); var isTypeMismatch = type && parsed.type !== type; var hasError = Boolean(parsed.error) || isTypeMismatch; throwError = throwError === undefined ? true : throwError; if (hasError) { var text = (input === null || input === void 0 ? void 0 : input.toString()) || ''; if (!parsed.error && isTypeMismatch) { parsed.ok = false; parsed.error = { uri: text, message: "The uri (".concat(text, ") is not of type ").concat(type), type: 'URI', }; } if (typeof throwError === 'function') { throwError(parsed); } if (throwError === true) { if (parsed.error) { throw new Error(parsed.error.message); } } } return parsed.parts; } } function stripPrefix(input, prefix) { var left = "".concat(prefix, ":"); input = (input || '').trim(); input = input.startsWith(left) ? input.substring(left.length) : input; return input; }