2024-01-23 11:06:49 -07:00
var doip = ( function ( exports , openpgp$2 , fetcher ) {
2023-07-09 04:05:21 -06:00
'use strict' ;
function _interopNamespaceDefault ( e ) {
var n = Object . create ( null ) ;
if ( e ) {
Object . keys ( e ) . forEach ( function ( k ) {
if ( k !== 'default' ) {
var d = Object . getOwnPropertyDescriptor ( e , k ) ;
Object . defineProperty ( n , k , d . get ? d : {
enumerable : true ,
get : function ( ) { return e [ k ] ; }
} ) ;
}
} ) ;
}
n . default = e ;
return Object . freeze ( n ) ;
}
var fetcher _ _namespace = /*#__PURE__*/ _interopNamespaceDefault ( fetcher ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* Contains enums
* @ module enums
* /
/ * *
* The proxy policy that decides how to fetch a proof
* @ readonly
* @ enum { string }
* /
const ProxyPolicy = {
/** Proxy usage decision depends on environment and service provider */
ADAPTIVE : 'adaptive' ,
/** Always use a proxy */
ALWAYS : 'always' ,
/** Never use a proxy, skip a verification if a proxy is inevitable */
NEVER : 'never'
} ;
/ * *
* Methods for fetching proofs
* @ readonly
* @ enum { string }
* /
const Fetcher = {
/** HTTP requests to ActivityPub */
ACTIVITYPUB : 'activitypub' ,
2024-01-23 11:06:49 -07:00
/** ASPE HTTP requests */
ASPE : 'aspe' ,
2023-07-09 04:05:21 -06:00
/** DNS module from Node.js */
DNS : 'dns' ,
/** GraphQL over HTTP requests */
GRAPHQL : 'graphql' ,
/** Basic HTTP requests */
HTTP : 'http' ,
/** IRC module from Node.js */
IRC : 'irc' ,
/** HTTP request to Matrix API */
MATRIX : 'matrix' ,
2024-01-23 11:06:49 -07:00
/** HKP and WKS request for OpenPGP */
OPENPGP : 'openpgp' ,
2023-07-09 04:05:21 -06:00
/** HTTP request to Telegram API */
TELEGRAM : 'telegram' ,
/** XMPP module from Node.js */
XMPP : 'xmpp'
} ;
/ * *
* Entity encoding format
* @ readonly
* @ enum { string }
* /
const EntityEncodingFormat = {
/** No special formatting */
PLAIN : 'plain' ,
/** HTML encoded entities */
HTML : 'html' ,
/** XML encoded entities */
XML : 'xml'
} ;
/ * *
* Levels of access restriction for proof fetching
* @ readonly
* @ enum { string }
* /
const ProofAccessRestriction = {
/** Any HTTP request will work */
NONE : 'none' ,
/** CORS requests are denied */
NOCORS : 'nocors' ,
/** HTTP requests must contain API or access tokens */
GRANTED : 'granted' ,
/** Not accessible by HTTP request, needs server software */
SERVER : 'server'
} ;
/ * *
* Format of proof
* @ readonly
* @ enum { string }
* /
const ProofFormat = {
/** JSON format */
JSON : 'json' ,
/** Plaintext format */
TEXT : 'text'
} ;
/ * *
* Format of claim
* @ readonly
* @ enum { string }
* /
const ClaimFormat = {
/** `openpgp4fpr:123123123` */
URI : 'uri' ,
/** `123123123` */
FINGERPRINT : 'fingerprint'
} ;
/ * *
2024-02-01 09:06:40 -07:00
* How to find the proof inside the fetched data
2023-07-09 04:05:21 -06:00
* @ readonly
* @ enum { string }
* /
const ClaimRelation = {
/** Claim is somewhere in the JSON field's textual content */
CONTAINS : 'contains' ,
/** Claim is equal to the JSON field's textual content */
EQUALS : 'equals' ,
/** Claim is equal to an element of the JSON field's array of strings */
ONEOF : 'oneof'
} ;
/ * *
* Status of the Claim instance
* @ readonly
* @ enum { number }
* /
const ClaimStatus = {
/** Claim has been initialized */
INIT : 100 ,
/** Claim has matched its URI to candidate claim definitions */
MATCHED : 101 ,
/** Claim was successfully verified */
VERIFIED : 200 ,
/** Claim was successfully verified using proxied data */
VERIFIED _VIA _PROXY : 201 ,
/** Unknown matching error */
MATCHING _ERROR : 300 ,
/** No matched service providers */
NO _MATCHES : 301 ,
/** Unknown matching error */
VERIFICATION _ERROR : 400 ,
/** No proof found in data returned by service providers */
NO _PROOF _FOUND : 401
} ;
/ * *
* Profile type
* @ readonly
* @ enum { string }
* /
const ProfileType = {
/** ASP profile */
ASP : 'asp' ,
/** OpenPGP profile */
OPENPGP : 'openpgp'
} ;
/ * *
* Public key type
* @ readonly
* @ enum { string }
* /
const PublicKeyType = {
EDDSA : 'eddsa' ,
ES256 : 'es256' ,
OPENPGP : 'openpgp' ,
2023-07-13 02:41:31 -06:00
UNKNOWN : 'unknown' ,
2023-07-09 04:05:21 -06:00
NONE : 'none'
} ;
/ * *
* Public key format
* @ readonly
* @ enum { string }
* /
const PublicKeyEncoding = {
PEM : 'pem' ,
JWK : 'jwk' ,
ARMORED _PGP : 'armored_pgp' ,
NONE : 'none'
} ;
/ * *
* Method to fetch the public key
* @ readonly
* @ enum { string }
* /
const PublicKeyFetchMethod = {
ASPE : 'aspe' ,
HKP : 'hkp' ,
WKD : 'wkd' ,
HTTP : 'http' ,
NONE : 'none'
} ;
2024-01-23 11:06:49 -07:00
/ * *
* Protocol to query OpenPGP public keys
* @ readonly
* @ enum { string }
* /
const OpenPgpQueryProtocol = {
HKP : 'hkp' ,
WKD : 'wkd'
} ;
2023-07-09 04:05:21 -06:00
var enums = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
ClaimFormat : ClaimFormat ,
ClaimRelation : ClaimRelation ,
ClaimStatus : ClaimStatus ,
EntityEncodingFormat : EntityEncodingFormat ,
Fetcher : Fetcher ,
2024-01-23 11:06:49 -07:00
OpenPgpQueryProtocol : OpenPgpQueryProtocol ,
2023-07-09 04:05:21 -06:00
ProfileType : ProfileType ,
ProofAccessRestriction : ProofAccessRestriction ,
ProofFormat : ProofFormat ,
ProxyPolicy : ProxyPolicy ,
PublicKeyEncoding : PublicKeyEncoding ,
PublicKeyFetchMethod : PublicKeyFetchMethod ,
PublicKeyType : PublicKeyType
} ) ;
var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : { } ;
function getDefaultExportFromCjs ( x ) {
return x && x . _ _esModule && Object . prototype . hasOwnProperty . call ( x , 'default' ) ? x [ 'default' ] : x ;
}
function getAugmentedNamespace ( n ) {
if ( n . _ _esModule ) return n ;
var f = n . default ;
if ( typeof f == "function" ) {
var a = function a ( ) {
if ( this instanceof a ) {
2024-01-23 11:06:49 -07:00
return Reflect . construct ( f , arguments , this . constructor ) ;
2023-07-09 04:05:21 -06:00
}
return f . apply ( this , arguments ) ;
} ;
a . prototype = f . prototype ;
} else a = { } ;
Object . defineProperty ( a , '__esModule' , { value : true } ) ;
Object . keys ( n ) . forEach ( function ( k ) {
var d = Object . getOwnPropertyDescriptor ( n , k ) ;
Object . defineProperty ( a , k , d . get ? d : {
enumerable : true ,
get : function ( ) {
return n [ k ] ;
}
} ) ;
} ) ;
return a ;
}
var isAlphanumeric$1 = { } ;
var assertString = { exports : { } } ;
( function ( module , exports ) {
Object . defineProperty ( exports , "__esModule" , {
value : true
} ) ;
exports . default = assertString ;
function _typeof ( obj ) { "@babel/helpers - typeof" ; if ( typeof Symbol === "function" && typeof Symbol . iterator === "symbol" ) { _typeof = function _typeof ( obj ) { return typeof obj ; } ; } else { _typeof = function _typeof ( obj ) { return obj && typeof Symbol === "function" && obj . constructor === Symbol && obj !== Symbol . prototype ? "symbol" : typeof obj ; } ; } return _typeof ( obj ) ; }
function assertString ( input ) {
var isString = typeof input === 'string' || input instanceof String ;
if ( ! isString ) {
var invalidType = _typeof ( input ) ;
if ( input === null ) invalidType = 'null' ; else if ( invalidType === 'object' ) invalidType = input . constructor . name ;
throw new TypeError ( "Expected a string but received a " . concat ( invalidType ) ) ;
}
}
module . exports = exports . default ;
module . exports . default = exports . default ;
} ( assertString , assertString . exports ) ) ;
var assertStringExports = assertString . exports ;
var alpha$2 = { } ;
Object . defineProperty ( alpha$2 , "__esModule" , {
value : true
} ) ;
alpha$2 . commaDecimal = alpha$2 . dotDecimal = alpha$2 . bengaliLocales = alpha$2 . farsiLocales = alpha$2 . arabicLocales = alpha$2 . englishLocales = alpha$2 . decimal = alpha$2 . alphanumeric = alpha$2 . alpha = void 0 ;
var alpha$1 = {
'en-US' : /^[A-Z]+$/i ,
'az-AZ' : /^[A-VXYZÇƏĞİı ÖŞÜ]+$/i ,
'bg-BG' : /^[А -Я]+$/i ,
'cs-CZ' : /^[A-ZÁČĎÉĚÍŇÓŘŠŤÚŮÝŽ]+$/i ,
'da-DK' : /^[A-ZÆØÅ]+$/i ,
'de-DE' : /^[A-ZÄÖÜß]+$/i ,
'el-GR' : /^[Α -ώ]+$/i ,
'es-ES' : /^[A-ZÁÉÍÑÓÚÜ]+$/i ,
'fa-IR' : /^[ابپتثجچحخدذرزژسشصضطظعغفقکگلمنوهی]+$/i ,
'fi-FI' : /^[A-ZÅÄÖ]+$/i ,
'fr-FR' : /^[A-ZÀÂÆÇÉÈÊËÏÎÔŒÙÛÜŸ]+$/i ,
'it-IT' : /^[A-ZÀÉÈÌÎÓÒÙ]+$/i ,
'ja-JP' : /^[ぁ-んァ-ヶヲ-゚一-龠ー・。、]+$/i ,
'nb-NO' : /^[A-ZÆØÅ]+$/i ,
'nl-NL' : /^[A-ZÁÉËÏÓÖÜÚ]+$/i ,
'nn-NO' : /^[A-ZÆØÅ]+$/i ,
'hu-HU' : /^[A-ZÁÉÍÓÖŐÚÜŰ]+$/i ,
'pl-PL' : /^[A-ZĄĆĘŚŁŃÓŻŹ]+$/i ,
'pt-PT' : /^[A-ZÃÁÀÂÄÇÉÊËÍÏÕÓÔÖÚÜ]+$/i ,
'ru-RU' : /^[А -ЯЁ]+$/i ,
2024-01-23 11:06:49 -07:00
'kk-KZ' : /^[А -ЯЁ\u04D8\u04B0\u0406\u04A2\u0492\u04AE\u049A\u04E8\u04BA]+$/i ,
2023-07-09 04:05:21 -06:00
'sl-SI' : /^[A-ZČĆĐŠŽ]+$/i ,
'sk-SK' : /^[A-ZÁČĎÉÍŇÓŠŤÚÝŽĹŔĽÄÔ]+$/i ,
'sr-RS@latin' : /^[A-ZČĆŽŠĐ]+$/i ,
'sr-RS' : /^[А -ЯЂЈЉЊЋЏ]+$/i ,
'sv-SE' : /^[A-ZÅÄÖ]+$/i ,
'th-TH' : /^[ก-๐ \s]+$/i ,
'tr-TR' : /^[A-ZÇĞİı ÖŞÜ]+$/i ,
'uk-UA' : /^[А -ЩЬ ЮЯЄIЇҐі ]+$/i ,
'vi-VN' : /^[A-ZÀÁẠẢÃÂẦẤẬẨẪĂẰẮẶẲẴĐÈÉẸẺẼÊỀẾỆỂỄÌÍỊỈĨÒÓỌỎÕÔỒỐỘỔỖƠỜỚỢỞỠÙÚỤỦŨƯỪỨỰỬỮỲÝỴỶỸ]+$/i ,
'ko-KR' : /^[ㄱ-ㅎㅏ-ㅣ가-힣]*$/ ,
'ku-IQ' : /^[ئابپتجچحخدرڕزژسشعغفڤقکگلڵمنوۆھەیێيطؤثآإأكضصةظذ]+$/i ,
ar : /^[ءآأؤإئابةتثجحخدذرزسشصضطظعغفقكلمنهوىيًٌٍَُِّْٰ]+$/ ,
he : /^[א-ת]+$/ ,
fa : /^['آاءأؤئبپتثجچحخدذرزژسشصضطظعغفقکگلمنوهةی']+$/i ,
bn : /^['ঀঁংঃঅআইঈউঊঋঌএঐওঔকখগঘঙচছজঝঞটঠডঢণতথদধনপফবভমযরলশষসহ়ঽািীুূৃৄেৈোৌ্ৎৗড়ঢ়য়ৠৡৢৣৰৱ৲৳৴৵৶৷৸৹৺৻']+$/ ,
'hi-IN' : /^[\u0900-\u0961]+[\u0972-\u097F]*$/i ,
'si-LK' : /^[\u0D80-\u0DFF]+$/
} ;
alpha$2 . alpha = alpha$1 ;
var alphanumeric = {
'en-US' : /^[0-9A-Z]+$/i ,
'az-AZ' : /^[0-9A-VXYZÇƏĞİı ÖŞÜ]+$/i ,
'bg-BG' : /^[0-9А -Я]+$/i ,
'cs-CZ' : /^[0-9A-ZÁČĎÉĚÍŇÓŘŠŤÚŮÝŽ]+$/i ,
'da-DK' : /^[0-9A-ZÆØÅ]+$/i ,
'de-DE' : /^[0-9A-ZÄÖÜß]+$/i ,
'el-GR' : /^[0-9Α -ω]+$/i ,
'es-ES' : /^[0-9A-ZÁÉÍÑÓÚÜ]+$/i ,
'fi-FI' : /^[0-9A-ZÅÄÖ]+$/i ,
'fr-FR' : /^[0-9A-ZÀÂÆÇÉÈÊËÏÎÔŒÙÛÜŸ]+$/i ,
'it-IT' : /^[0-9A-ZÀÉÈÌÎÓÒÙ]+$/i ,
'ja-JP' : /^[0-90 -9ぁ-んァ-ヶヲ-゚一-龠ー・。、]+$/i ,
'hu-HU' : /^[0-9A-ZÁÉÍÓÖŐÚÜŰ]+$/i ,
'nb-NO' : /^[0-9A-ZÆØÅ]+$/i ,
'nl-NL' : /^[0-9A-ZÁÉËÏÓÖÜÚ]+$/i ,
'nn-NO' : /^[0-9A-ZÆØÅ]+$/i ,
'pl-PL' : /^[0-9A-ZĄĆĘŚŁŃÓŻŹ]+$/i ,
'pt-PT' : /^[0-9A-ZÃÁÀÂÄÇÉÊËÍÏÕÓÔÖÚÜ]+$/i ,
'ru-RU' : /^[0-9А -ЯЁ]+$/i ,
2024-01-23 11:06:49 -07:00
'kk-KZ' : /^[0-9А -ЯЁ\u04D8\u04B0\u0406\u04A2\u0492\u04AE\u049A\u04E8\u04BA]+$/i ,
2023-07-09 04:05:21 -06:00
'sl-SI' : /^[0-9A-ZČĆĐŠŽ]+$/i ,
'sk-SK' : /^[0-9A-ZÁČĎÉÍŇÓŠŤÚÝŽĹŔĽÄÔ]+$/i ,
'sr-RS@latin' : /^[0-9A-ZČĆŽŠĐ]+$/i ,
'sr-RS' : /^[0-9А -ЯЂЈЉЊЋЏ]+$/i ,
'sv-SE' : /^[0-9A-ZÅÄÖ]+$/i ,
'th-TH' : /^[ก-๙\s]+$/i ,
'tr-TR' : /^[0-9A-ZÇĞİı ÖŞÜ]+$/i ,
'uk-UA' : /^[0-9А -ЩЬ ЮЯЄIЇҐі ]+$/i ,
'ko-KR' : /^[0-9ㄱ-ㅎㅏ-ㅣ가-힣]*$/ ,
'ku-IQ' : /^[٠ ١ ٢٣٤٥ ٦٧ ٨٩0-9ئا بپتجچحخدرڕزژسشعغفڤقکگلڵمنوۆھ ە یێيطؤثآإأكضصةظذ]+$/i ,
'vi-VN' : /^[0-9A-ZÀÁẠẢÃÂẦẤẬẨẪĂẰẮẶẲẴĐÈÉẸẺẼÊỀẾỆỂỄÌÍỊỈĨÒÓỌỎÕÔỒỐỘỔỖƠỜỚỢỞỠÙÚỤỦŨƯỪỨỰỬỮỲÝỴỶỸ]+$/i ,
ar : /^[٠ ١ ٢٣٤٥ ٦٧ ٨٩0-9ءآأؤإئا بةتثجحخدذرزسشصضطظعغفقكلمنه وىيًٌٍَُِّْٰ]+$/ ,
he : /^[0-9א-ת]+$/ ,
fa : /^['0-9آا ءأؤئبپتثجچحخدذرزژسشصضطظعغفقکگلمنوه ةی۱ ۲۳۴۵ ۶۷ ۸۹۰ ']+$/i ,
bn : /^['ঀঁংঃঅআইঈউঊঋঌএঐওঔকখগঘঙচছজঝঞটঠডঢণতথদধনপফবভমযরলশষসহ়ঽািীুূৃৄেৈোৌ্ৎৗড়ঢ়য়ৠৡৢৣ০১২৩৪৫৬৭৮৯ৰৱ৲৳৴৵৶৷৸৹৺৻']+$/ ,
'hi-IN' : /^[\u0900-\u0963]+[\u0966-\u097F]*$/i ,
'si-LK' : /^[0-9\u0D80-\u0DFF]+$/
} ;
alpha$2 . alphanumeric = alphanumeric ;
var decimal = {
'en-US' : '.' ,
ar : '٫ '
} ;
alpha$2 . decimal = decimal ;
var englishLocales = [ 'AU' , 'GB' , 'HK' , 'IN' , 'NZ' , 'ZA' , 'ZM' ] ;
alpha$2 . englishLocales = englishLocales ;
for ( var locale , i = 0 ; i < englishLocales . length ; i ++ ) {
locale = "en-" . concat ( englishLocales [ i ] ) ;
alpha$1 [ locale ] = alpha$1 [ 'en-US' ] ;
alphanumeric [ locale ] = alphanumeric [ 'en-US' ] ;
decimal [ locale ] = decimal [ 'en-US' ] ;
} // Source: http://www.localeplanet.com/java/
var arabicLocales = [ 'AE' , 'BH' , 'DZ' , 'EG' , 'IQ' , 'JO' , 'KW' , 'LB' , 'LY' , 'MA' , 'QM' , 'QA' , 'SA' , 'SD' , 'SY' , 'TN' , 'YE' ] ;
alpha$2 . arabicLocales = arabicLocales ;
for ( var _locale , _i = 0 ; _i < arabicLocales . length ; _i ++ ) {
_locale = "ar-" . concat ( arabicLocales [ _i ] ) ;
alpha$1 [ _locale ] = alpha$1 . ar ;
alphanumeric [ _locale ] = alphanumeric . ar ;
decimal [ _locale ] = decimal . ar ;
}
var farsiLocales = [ 'IR' , 'AF' ] ;
alpha$2 . farsiLocales = farsiLocales ;
for ( var _locale2 , _i2 = 0 ; _i2 < farsiLocales . length ; _i2 ++ ) {
_locale2 = "fa-" . concat ( farsiLocales [ _i2 ] ) ;
alphanumeric [ _locale2 ] = alphanumeric . fa ;
decimal [ _locale2 ] = decimal . ar ;
}
var bengaliLocales = [ 'BD' , 'IN' ] ;
alpha$2 . bengaliLocales = bengaliLocales ;
for ( var _locale3 , _i3 = 0 ; _i3 < bengaliLocales . length ; _i3 ++ ) {
_locale3 = "bn-" . concat ( bengaliLocales [ _i3 ] ) ;
alpha$1 [ _locale3 ] = alpha$1 . bn ;
alphanumeric [ _locale3 ] = alphanumeric . bn ;
decimal [ _locale3 ] = decimal [ 'en-US' ] ;
} // Source: https://en.wikipedia.org/wiki/Decimal_mark
var dotDecimal = [ 'ar-EG' , 'ar-LB' , 'ar-LY' ] ;
alpha$2 . dotDecimal = dotDecimal ;
2024-01-23 11:06:49 -07:00
var commaDecimal = [ 'bg-BG' , 'cs-CZ' , 'da-DK' , 'de-DE' , 'el-GR' , 'en-ZM' , 'es-ES' , 'fr-CA' , 'fr-FR' , 'id-ID' , 'it-IT' , 'ku-IQ' , 'hi-IN' , 'hu-HU' , 'nb-NO' , 'nn-NO' , 'nl-NL' , 'pl-PL' , 'pt-PT' , 'ru-RU' , 'kk-KZ' , 'si-LK' , 'sl-SI' , 'sr-RS@latin' , 'sr-RS' , 'sv-SE' , 'tr-TR' , 'uk-UA' , 'vi-VN' ] ;
2023-07-09 04:05:21 -06:00
alpha$2 . commaDecimal = commaDecimal ;
for ( var _i4 = 0 ; _i4 < dotDecimal . length ; _i4 ++ ) {
decimal [ dotDecimal [ _i4 ] ] = decimal [ 'en-US' ] ;
}
for ( var _i5 = 0 ; _i5 < commaDecimal . length ; _i5 ++ ) {
decimal [ commaDecimal [ _i5 ] ] = ',' ;
}
alpha$1 [ 'fr-CA' ] = alpha$1 [ 'fr-FR' ] ;
alphanumeric [ 'fr-CA' ] = alphanumeric [ 'fr-FR' ] ;
alpha$1 [ 'pt-BR' ] = alpha$1 [ 'pt-PT' ] ;
alphanumeric [ 'pt-BR' ] = alphanumeric [ 'pt-PT' ] ;
decimal [ 'pt-BR' ] = decimal [ 'pt-PT' ] ; // see #862
alpha$1 [ 'pl-Pl' ] = alpha$1 [ 'pl-PL' ] ;
alphanumeric [ 'pl-Pl' ] = alphanumeric [ 'pl-PL' ] ;
decimal [ 'pl-Pl' ] = decimal [ 'pl-PL' ] ; // see #1455
alpha$1 [ 'fa-AF' ] = alpha$1 . fa ;
Object . defineProperty ( isAlphanumeric$1 , "__esModule" , {
value : true
} ) ;
var _default = isAlphanumeric$1 . default = isAlphanumeric ;
isAlphanumeric$1 . locales = void 0 ;
var _assertString = _interopRequireDefault ( assertStringExports ) ;
var _alpha = alpha$2 ;
function _interopRequireDefault ( obj ) { return obj && obj . _ _esModule ? obj : { default : obj } ; }
function isAlphanumeric ( _str ) {
var locale = arguments . length > 1 && arguments [ 1 ] !== undefined ? arguments [ 1 ] : 'en-US' ;
var options = arguments . length > 2 && arguments [ 2 ] !== undefined ? arguments [ 2 ] : { } ;
( 0 , _assertString . default ) ( _str ) ;
var str = _str ;
var ignore = options . ignore ;
if ( ignore ) {
if ( ignore instanceof RegExp ) {
str = str . replace ( ignore , '' ) ;
} else if ( typeof ignore === 'string' ) {
str = str . replace ( new RegExp ( "[" . concat ( ignore . replace ( /[-[\]{}()*+?.,\\^$|#\\s]/g , '\\$&' ) , "]" ) , 'g' ) , '' ) ; // escape regex for ignore
} else {
throw new Error ( 'ignore should be instance of a String or RegExp' ) ;
}
}
if ( locale in _alpha . alphanumeric ) {
return _alpha . alphanumeric [ locale ] . test ( str ) ;
}
throw new Error ( "Invalid locale '" . concat ( locale , "'" ) ) ;
}
var locales = Object . keys ( _alpha . alphanumeric ) ;
isAlphanumeric$1 . locales = locales ;
var validUrl = { exports : { } } ;
( function ( module ) {
( function ( module ) {
module . exports . is _uri = is _iri ;
module . exports . is _http _uri = is _http _iri ;
module . exports . is _https _uri = is _https _iri ;
module . exports . is _web _uri = is _web _iri ;
// Create aliases
module . exports . isUri = is _iri ;
module . exports . isHttpUri = is _http _iri ;
module . exports . isHttpsUri = is _https _iri ;
module . exports . isWebUri = is _web _iri ;
// private function
// internal URI spitter method - direct from RFC 3986
var splitUri = function ( uri ) {
var splitted = uri . match ( /(?:([^:\/?#]+):)?(?:\/\/([^\/?#]*))?([^?#]*)(?:\?([^#]*))?(?:#(.*))?/ ) ;
return splitted ;
} ;
function is _iri ( value ) {
if ( ! value ) {
return ;
}
// check for illegal characters
if ( /[^a-z0-9\:\/\?\#\[\]\@\!\$\&\'\(\)\*\+\,\;\=\.\-\_\~\%]/i . test ( value ) ) return ;
// check for hex escapes that aren't complete
if ( /%[^0-9a-f]/i . test ( value ) ) return ;
if ( /%[0-9a-f](:?[^0-9a-f]|$)/i . test ( value ) ) return ;
var splitted = [ ] ;
var scheme = '' ;
var authority = '' ;
var path = '' ;
var query = '' ;
var fragment = '' ;
var out = '' ;
// from RFC 3986
splitted = splitUri ( value ) ;
scheme = splitted [ 1 ] ;
authority = splitted [ 2 ] ;
path = splitted [ 3 ] ;
query = splitted [ 4 ] ;
fragment = splitted [ 5 ] ;
// scheme and path are required, though the path can be empty
if ( ! ( scheme && scheme . length && path . length >= 0 ) ) return ;
// if authority is present, the path must be empty or begin with a /
if ( authority && authority . length ) {
if ( ! ( path . length === 0 || /^\// . test ( path ) ) ) return ;
} else {
// if authority is not present, the path must not start with //
if ( /^\/\// . test ( path ) ) return ;
}
// scheme must begin with a letter, then consist of letters, digits, +, ., or -
if ( ! /^[a-z][a-z0-9\+\-\.]*$/ . test ( scheme . toLowerCase ( ) ) ) return ;
// re-assemble the URL per section 5.3 in RFC 3986
out += scheme + ':' ;
if ( authority && authority . length ) {
out += '//' + authority ;
}
out += path ;
if ( query && query . length ) {
out += '?' + query ;
}
if ( fragment && fragment . length ) {
out += '#' + fragment ;
}
return out ;
}
function is _http _iri ( value , allowHttps ) {
if ( ! is _iri ( value ) ) {
return ;
}
var splitted = [ ] ;
var scheme = '' ;
var authority = '' ;
var path = '' ;
var port = '' ;
var query = '' ;
var fragment = '' ;
var out = '' ;
// from RFC 3986
splitted = splitUri ( value ) ;
scheme = splitted [ 1 ] ;
authority = splitted [ 2 ] ;
path = splitted [ 3 ] ;
query = splitted [ 4 ] ;
fragment = splitted [ 5 ] ;
if ( ! scheme ) return ;
if ( allowHttps ) {
if ( scheme . toLowerCase ( ) != 'https' ) return ;
} else {
if ( scheme . toLowerCase ( ) != 'http' ) return ;
}
// fully-qualified URIs must have an authority section that is
// a valid host
if ( ! authority ) {
return ;
}
// enable port component
if ( /:(\d+)$/ . test ( authority ) ) {
port = authority . match ( /:(\d+)$/ ) [ 0 ] ;
authority = authority . replace ( /:\d+$/ , '' ) ;
}
out += scheme + ':' ;
out += '//' + authority ;
if ( port ) {
out += port ;
}
out += path ;
if ( query && query . length ) {
out += '?' + query ;
}
if ( fragment && fragment . length ) {
out += '#' + fragment ;
}
return out ;
}
function is _https _iri ( value ) {
return is _http _iri ( value , true ) ;
}
function is _web _iri ( value ) {
return ( is _http _iri ( value ) || is _https _iri ( value ) ) ;
}
} ) ( module ) ;
} ( validUrl ) ) ;
var validUrlExports = validUrl . exports ;
var isPlainObj = value => {
if ( Object . prototype . toString . call ( value ) !== '[object Object]' ) {
return false ;
}
const prototype = Object . getPrototypeOf ( value ) ;
return prototype === null || prototype === Object . prototype ;
} ;
const isOptionObject = isPlainObj ;
2024-01-23 11:06:49 -07:00
const { hasOwnProperty : hasOwnProperty$1 } = Object . prototype ;
2023-07-09 04:05:21 -06:00
const { propertyIsEnumerable } = Object ;
const defineProperty = ( object , name , value ) => Object . defineProperty ( object , name , {
value ,
writable : true ,
enumerable : true ,
configurable : true
} ) ;
const globalThis$1 = commonjsGlobal ;
const defaultMergeOptions = {
concatArrays : false ,
ignoreUndefined : false
} ;
const getEnumerableOwnPropertyKeys = value => {
const keys = [ ] ;
for ( const key in value ) {
2024-01-23 11:06:49 -07:00
if ( hasOwnProperty$1 . call ( value , key ) ) {
2023-07-09 04:05:21 -06:00
keys . push ( key ) ;
}
}
/* istanbul ignore else */
if ( Object . getOwnPropertySymbols ) {
const symbols = Object . getOwnPropertySymbols ( value ) ;
for ( const symbol of symbols ) {
if ( propertyIsEnumerable . call ( value , symbol ) ) {
keys . push ( symbol ) ;
}
}
}
return keys ;
} ;
function clone ( value ) {
if ( Array . isArray ( value ) ) {
return cloneArray ( value ) ;
}
if ( isOptionObject ( value ) ) {
return cloneOptionObject ( value ) ;
}
return value ;
}
function cloneArray ( array ) {
const result = array . slice ( 0 , 0 ) ;
getEnumerableOwnPropertyKeys ( array ) . forEach ( key => {
defineProperty ( result , key , clone ( array [ key ] ) ) ;
} ) ;
return result ;
}
function cloneOptionObject ( object ) {
const result = Object . getPrototypeOf ( object ) === null ? Object . create ( null ) : { } ;
getEnumerableOwnPropertyKeys ( object ) . forEach ( key => {
defineProperty ( result , key , clone ( object [ key ] ) ) ;
} ) ;
return result ;
}
/ * *
* @ param { * } merged already cloned
* @ param { * } source something to merge
* @ param { string [ ] } keys keys to merge
* @ param { Object } config Config Object
* @ returns { * } cloned Object
* /
const mergeKeys = ( merged , source , keys , config ) => {
keys . forEach ( key => {
if ( typeof source [ key ] === 'undefined' && config . ignoreUndefined ) {
return ;
}
// Do not recurse into prototype chain of merged
if ( key in merged && merged [ key ] !== Object . getPrototypeOf ( merged ) ) {
defineProperty ( merged , key , merge$2 ( merged [ key ] , source [ key ] , config ) ) ;
} else {
defineProperty ( merged , key , clone ( source [ key ] ) ) ;
}
} ) ;
return merged ;
} ;
/ * *
* @ param { * } merged already cloned
* @ param { * } source something to merge
* @ param { Object } config Config Object
* @ returns { * } cloned Object
*
* see [ Array . prototype . concat ( ... arguments ) ] ( http : //www.ecma-international.org/ecma-262/6.0/#sec-array.prototype.concat)
* /
const concatArrays = ( merged , source , config ) => {
let result = merged . slice ( 0 , 0 ) ;
let resultIndex = 0 ;
[ merged , source ] . forEach ( array => {
const indices = [ ] ;
// `result.concat(array)` with cloning
for ( let k = 0 ; k < array . length ; k ++ ) {
2024-01-23 11:06:49 -07:00
if ( ! hasOwnProperty$1 . call ( array , k ) ) {
2023-07-09 04:05:21 -06:00
continue ;
}
indices . push ( String ( k ) ) ;
if ( array === merged ) {
// Already cloned
defineProperty ( result , resultIndex ++ , array [ k ] ) ;
} else {
defineProperty ( result , resultIndex ++ , clone ( array [ k ] ) ) ;
}
}
// Merge non-index keys
result = mergeKeys ( result , array , getEnumerableOwnPropertyKeys ( array ) . filter ( key => ! indices . includes ( key ) ) , config ) ;
} ) ;
return result ;
} ;
/ * *
* @ param { * } merged already cloned
* @ param { * } source something to merge
* @ param { Object } config Config Object
* @ returns { * } cloned Object
* /
function merge$2 ( merged , source , config ) {
if ( config . concatArrays && Array . isArray ( merged ) && Array . isArray ( source ) ) {
return concatArrays ( merged , source , config ) ;
}
if ( ! isOptionObject ( source ) || ! isOptionObject ( merged ) ) {
return clone ( source ) ;
}
return mergeKeys ( merged , source , getEnumerableOwnPropertyKeys ( source ) , config ) ;
}
var mergeOptions = function ( ... options ) {
const config = merge$2 ( clone ( defaultMergeOptions ) , ( this !== globalThis$1 && this ) || { } , defaultMergeOptions ) ;
let merged = { _ : { } } ;
for ( const option of options ) {
if ( option === undefined ) {
continue ;
}
if ( ! isOptionObject ( option ) ) {
throw new TypeError ( '`' + option + '` is not an Option Object' ) ;
}
merged = merge$2 ( merged , { _ : option } , config ) ;
}
return merged . _ ;
} ;
var mergeOptions$1 = /*@__PURE__*/ getDefaultExportFromCjs ( mergeOptions ) ;
var global$1 = ( typeof global !== "undefined" ? global :
typeof self !== "undefined" ? self :
typeof window !== "undefined" ? window : { } ) ;
// shim for using process in browser
// based off https://github.com/defunctzombie/node-process/blob/master/browser.js
function defaultSetTimout ( ) {
throw new Error ( 'setTimeout has not been defined' ) ;
}
function defaultClearTimeout ( ) {
throw new Error ( 'clearTimeout has not been defined' ) ;
}
var cachedSetTimeout = defaultSetTimout ;
var cachedClearTimeout = defaultClearTimeout ;
if ( typeof global$1 . setTimeout === 'function' ) {
cachedSetTimeout = setTimeout ;
}
if ( typeof global$1 . clearTimeout === 'function' ) {
cachedClearTimeout = clearTimeout ;
}
function runTimeout ( fun ) {
if ( cachedSetTimeout === setTimeout ) {
//normal enviroments in sane situations
return setTimeout ( fun , 0 ) ;
}
// if setTimeout wasn't available but was latter defined
if ( ( cachedSetTimeout === defaultSetTimout || ! cachedSetTimeout ) && setTimeout ) {
cachedSetTimeout = setTimeout ;
return setTimeout ( fun , 0 ) ;
}
try {
// when when somebody has screwed with setTimeout but no I.E. maddness
return cachedSetTimeout ( fun , 0 ) ;
} catch ( e ) {
try {
// When we are in I.E. but the script has been evaled so I.E. doesn't trust the global object when called normally
return cachedSetTimeout . call ( null , fun , 0 ) ;
} catch ( e ) {
// same as above but when it's a version of I.E. that must have the global object for 'this', hopfully our context correct otherwise it will throw a global error
return cachedSetTimeout . call ( this , fun , 0 ) ;
}
}
}
function runClearTimeout ( marker ) {
if ( cachedClearTimeout === clearTimeout ) {
//normal enviroments in sane situations
return clearTimeout ( marker ) ;
}
// if clearTimeout wasn't available but was latter defined
if ( ( cachedClearTimeout === defaultClearTimeout || ! cachedClearTimeout ) && clearTimeout ) {
cachedClearTimeout = clearTimeout ;
return clearTimeout ( marker ) ;
}
try {
// when when somebody has screwed with setTimeout but no I.E. maddness
return cachedClearTimeout ( marker ) ;
} catch ( e ) {
try {
// When we are in I.E. but the script has been evaled so I.E. doesn't trust the global object when called normally
return cachedClearTimeout . call ( null , marker ) ;
} catch ( e ) {
// same as above but when it's a version of I.E. that must have the global object for 'this', hopfully our context correct otherwise it will throw a global error.
// Some versions of I.E. have different rules for clearTimeout vs setTimeout
return cachedClearTimeout . call ( this , marker ) ;
}
}
}
var queue = [ ] ;
var draining = false ;
var currentQueue ;
var queueIndex = - 1 ;
function cleanUpNextTick ( ) {
if ( ! draining || ! currentQueue ) {
return ;
}
draining = false ;
if ( currentQueue . length ) {
queue = currentQueue . concat ( queue ) ;
} else {
queueIndex = - 1 ;
}
if ( queue . length ) {
drainQueue ( ) ;
}
}
function drainQueue ( ) {
if ( draining ) {
return ;
}
var timeout = runTimeout ( cleanUpNextTick ) ;
draining = true ;
var len = queue . length ;
while ( len ) {
currentQueue = queue ;
queue = [ ] ;
while ( ++ queueIndex < len ) {
if ( currentQueue ) {
currentQueue [ queueIndex ] . run ( ) ;
}
}
queueIndex = - 1 ;
len = queue . length ;
}
currentQueue = null ;
draining = false ;
runClearTimeout ( timeout ) ;
}
function nextTick ( fun ) {
var args = new Array ( arguments . length - 1 ) ;
if ( arguments . length > 1 ) {
for ( var i = 1 ; i < arguments . length ; i ++ ) {
args [ i - 1 ] = arguments [ i ] ;
}
}
queue . push ( new Item ( fun , args ) ) ;
if ( queue . length === 1 && ! draining ) {
runTimeout ( drainQueue ) ;
}
}
// v8 likes predictible objects
function Item ( fun , array ) {
this . fun = fun ;
this . array = array ;
}
Item . prototype . run = function ( ) {
this . fun . apply ( null , this . array ) ;
} ;
var title = 'browser' ;
2024-01-23 11:06:49 -07:00
var platform$2 = 'browser' ;
2023-07-09 04:05:21 -06:00
var browser = true ;
var env = { } ;
var argv = [ ] ;
var version = '' ; // empty string to avoid regexp issues
var versions = { } ;
var release = { } ;
var config = { } ;
2024-01-23 11:06:49 -07:00
function noop$1 ( ) { }
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var on = noop$1 ;
var addListener = noop$1 ;
var once = noop$1 ;
var off = noop$1 ;
var removeListener = noop$1 ;
var removeAllListeners = noop$1 ;
var emit = noop$1 ;
2023-07-09 04:05:21 -06:00
function binding ( name ) {
throw new Error ( 'process.binding is not supported' ) ;
}
function cwd ( ) { return '/' }
function chdir ( dir ) {
throw new Error ( 'process.chdir is not supported' ) ;
} function umask ( ) { return 0 ; }
// from https://github.com/kumavis/browser-process-hrtime/blob/master/index.js
var performance = global$1 . performance || { } ;
var performanceNow =
performance . now ||
performance . mozNow ||
performance . msNow ||
performance . oNow ||
performance . webkitNow ||
function ( ) { return ( new Date ( ) ) . getTime ( ) } ;
// generate timestamp or delta
// see http://nodejs.org/api/process.html#process_process_hrtime
function hrtime ( previousTimestamp ) {
var clocktime = performanceNow . call ( performance ) * 1e-3 ;
var seconds = Math . floor ( clocktime ) ;
var nanoseconds = Math . floor ( ( clocktime % 1 ) * 1e9 ) ;
if ( previousTimestamp ) {
seconds = seconds - previousTimestamp [ 0 ] ;
nanoseconds = nanoseconds - previousTimestamp [ 1 ] ;
if ( nanoseconds < 0 ) {
seconds -- ;
nanoseconds += 1e9 ;
}
}
return [ seconds , nanoseconds ]
}
var startTime = new Date ( ) ;
function uptime ( ) {
var currentTime = new Date ( ) ;
var dif = currentTime - startTime ;
return dif / 1000 ;
}
var browser$1 = {
nextTick : nextTick ,
title : title ,
browser : browser ,
env : env ,
argv : argv ,
version : version ,
versions : versions ,
on : on ,
addListener : addListener ,
once : once ,
off : off ,
removeListener : removeListener ,
removeAllListeners : removeAllListeners ,
emit : emit ,
binding : binding ,
cwd : cwd ,
chdir : chdir ,
umask : umask ,
hrtime : hrtime ,
2024-01-23 11:06:49 -07:00
platform : platform$2 ,
2023-07-09 04:05:21 -06:00
release : release ,
config : config ,
uptime : uptime
} ;
2024-01-23 11:06:49 -07:00
var lib = { } ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
Object . defineProperty ( lib , "__esModule" , {
2023-07-09 04:05:21 -06:00
value : true
} ) ;
var _typeof = typeof Symbol === "function" && typeof Symbol . iterator === "symbol" ? function ( obj ) { return typeof obj ; } : function ( obj ) { return obj && typeof Symbol === "function" && obj . constructor === Symbol && obj !== Symbol . prototype ? "symbol" : typeof obj ; } ;
/* global window self */
var isBrowser = typeof window !== 'undefined' && typeof window . document !== 'undefined' ;
/* eslint-disable no-restricted-globals */
var isWebWorker = ( typeof self === 'undefined' ? 'undefined' : _typeof ( self ) ) === 'object' && self . constructor && self . constructor . name === 'DedicatedWorkerGlobalScope' ;
/* eslint-enable no-restricted-globals */
var isNode = typeof browser$1 !== 'undefined' && browser$1 . versions != null && browser$1 . versions . node != null ;
/ * *
* @ see https : //github.com/jsdom/jsdom/releases/tag/12.0.0
* @ see https : //github.com/jsdom/jsdom/issues/1537
* /
/* eslint-disable no-undef */
var isJsDom = function isJsDom ( ) {
return typeof window !== 'undefined' && window . name === 'nodejs' || navigator . userAgent . includes ( 'Node.js' ) || navigator . userAgent . includes ( 'jsdom' ) ;
} ;
2024-01-23 11:06:49 -07:00
lib . isBrowser = isBrowser ;
lib . isWebWorker = isWebWorker ;
var isNode _1 = lib . isNode = isNode ;
lib . isJsDom = isJsDom ;
2023-07-09 04:05:21 -06:00
var isFQDN$1 = { exports : { } } ;
var merge$1 = { exports : { } } ;
( function ( module , exports ) {
Object . defineProperty ( exports , "__esModule" , {
value : true
} ) ;
exports . default = merge ;
function merge ( ) {
var obj = arguments . length > 0 && arguments [ 0 ] !== undefined ? arguments [ 0 ] : { } ;
var defaults = arguments . length > 1 ? arguments [ 1 ] : undefined ;
for ( var key in defaults ) {
if ( typeof obj [ key ] === 'undefined' ) {
obj [ key ] = defaults [ key ] ;
}
}
return obj ;
}
module . exports = exports . default ;
module . exports . default = exports . default ;
} ( merge$1 , merge$1 . exports ) ) ;
var mergeExports = merge$1 . exports ;
( function ( module , exports ) {
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
Object . defineProperty ( exports , "__esModule" , {
value : true
} ) ;
exports . default = isFQDN ;
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
var _assertString = _interopRequireDefault ( assertStringExports ) ;
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
var _merge = _interopRequireDefault ( mergeExports ) ;
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
function _interopRequireDefault ( obj ) { return obj && obj . _ _esModule ? obj : { default : obj } ; }
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
var default _fqdn _options = {
require _tld : true ,
allow _underscores : false ,
allow _trailing _dot : false ,
allow _numeric _tld : false ,
allow _wildcard : false ,
ignore _max _length : false
} ;
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
function isFQDN ( str , options ) {
( 0 , _assertString . default ) ( str ) ;
options = ( 0 , _merge . default ) ( options , default _fqdn _options ) ;
/* Remove the optional trailing dot before checking validity */
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
if ( options . allow _trailing _dot && str [ str . length - 1 ] === '.' ) {
str = str . substring ( 0 , str . length - 1 ) ;
}
/* Remove the optional wildcard before checking validity */
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
if ( options . allow _wildcard === true && str . indexOf ( '*.' ) === 0 ) {
str = str . substring ( 2 ) ;
}
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
var parts = str . split ( '.' ) ;
var tld = parts [ parts . length - 1 ] ;
if ( options . require _tld ) {
// disallow fqdns without tld
if ( parts . length < 2 ) {
return false ;
}
if ( ! options . allow _numeric _tld && ! /^([a-z\u00A1-\u00A8\u00AA-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF]{2,}|xn[a-z0-9-]{2,})$/i . test ( tld ) ) {
return false ;
} // disallow spaces
if ( /\s/ . test ( tld ) ) {
return false ;
}
} // reject numeric TLDs
if ( ! options . allow _numeric _tld && /^\d+$/ . test ( tld ) ) {
return false ;
}
return parts . every ( function ( part ) {
if ( part . length > 63 && ! options . ignore _max _length ) {
return false ;
}
if ( ! /^[a-z_\u00a1-\uffff0-9-]+$/i . test ( part ) ) {
return false ;
} // disallow full-width chars
if ( /[\uff01-\uff5e]/ . test ( part ) ) {
return false ;
} // disallow parts starting or ending with hyphen
if ( /^-|-$/ . test ( part ) ) {
return false ;
}
if ( ! options . allow _underscores && /_/ . test ( part ) ) {
return false ;
}
return true ;
} ) ;
}
module . exports = exports . default ;
module . exports . default = exports . default ;
} ( isFQDN$1 , isFQDN$1 . exports ) ) ;
var isFQDNExports = isFQDN$1 . exports ;
var isFQDN = /*@__PURE__*/ getDefaultExportFromCjs ( isFQDNExports ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* @ module utils
* /
/ * *
* Generate an URL to request data from a proxy server
2024-02-01 09:06:40 -07:00
* @ param { string } type - The name of the fetcher the proxy must use
* @ param { object } data - The data the proxy must provide to the fetcher
* @ param { import ( './types' ) . VerificationConfig } opts - Options to enable the request
* @ returns { string } Generated proxy URL
2023-07-09 04:05:21 -06:00
* /
function generateProxyURL ( type , data , opts ) {
try {
isFQDN ( opts . proxy . hostname ) ;
} catch ( err ) {
throw new Error ( 'Invalid proxy hostname' )
}
const queryStrings = [ ] ;
Object . keys ( data ) . forEach ( ( key ) => {
queryStrings . push ( ` ${ key } = ${ encodeURIComponent ( data [ key ] ) } ` ) ;
} ) ;
2024-02-01 09:06:40 -07:00
const scheme = opts . proxy . scheme ? ? 'https' ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
return ` ${ scheme } :// ${ opts . proxy . hostname } /api/3/get/ ${ type } ? ${ queryStrings . join (
2023-07-08 00:36:57 -06:00
'&'
) } `
2023-07-09 04:05:21 -06:00
}
/ * *
* Generate the string that must be found in the proof to verify a claim
2024-02-01 09:06:40 -07:00
* @ param { string } fingerprint - The fingerprint of the claim
* @ param { ClaimFormat } format - The claim ' s format
* @ returns { string } Generate claim
2023-07-09 04:05:21 -06:00
* /
function generateClaim ( fingerprint , format ) {
switch ( format ) {
case ClaimFormat . URI :
if ( fingerprint . match ( /^(openpgp4fpr|aspe):/ ) ) {
return fingerprint
}
return ` openpgp4fpr: ${ fingerprint } `
case ClaimFormat . FINGERPRINT :
return fingerprint
default :
throw new Error ( 'No valid claim format' )
}
}
/ * *
* Get the URIs from a string and return them as an array
2024-02-01 09:06:40 -07:00
* @ param { string } text - The text that may contain URIs
* @ returns { Array < string > } List of URIs extracted from input
2023-07-09 04:05:21 -06:00
* /
function getUriFromString ( text ) {
const re = /((([A-Za-z0-9]+:(?:\/\/)?)(?:[-;:&=+$,\w]+@)?[A-Za-z0-9.-]+|(?:www\.|[-;:&=+$,\w]+@)[A-Za-z0-9.-]+)((?:\/[+~%/.\w\-_]*)?\??(?:[-+=&;%@.\w_]*)#?(?:[.!/\\\w]*))?)/gi ;
const res = text . match ( re ) ;
const urls = [ ] ;
if ( ! res ) {
return [ ]
}
res . forEach ( url => {
// Remove bad trailing characters
let hasBadTrailingChars = true ;
while ( hasBadTrailingChars ) {
const lastChar = url . charAt ( url . length - 1 ) ;
if ( '?!.' . indexOf ( lastChar ) === - 1 ) {
hasBadTrailingChars = false ;
continue
}
url = url . substring ( 0 , url . length - 1 ) ;
}
urls . push ( url ) ;
} ) ;
return urls
}
2024-01-23 11:06:49 -07:00
var utils$2 = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
generateClaim : generateClaim ,
generateProxyURL : generateProxyURL ,
getUriFromString : getUriFromString
} ) ;
2024-02-01 09:06:40 -07:00
/ *
Copyright 2023 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* A service provider matched to an identity claim
* @ class
* @ public
* /
class ServiceProvider {
/ * *
* @ param { import ( './types' ) . ServiceProviderObject } serviceProviderObject - JSON representation of a { @ link ServiceProvider }
* /
constructor ( serviceProviderObject ) {
/ * *
* Details about the service provider
* @ type { import ( './types' ) . ServiceProviderAbout }
* /
this . about = serviceProviderObject . about ;
/ * *
* What the profile would look like if a claim matches this service provider
* @ type { import ( './types' ) . ServiceProviderProfile }
* /
this . profile = serviceProviderObject . profile ;
/ * *
* Information about the claim matching process
* @ type { import ( './types' ) . ServiceProviderClaim }
* /
this . claim = serviceProviderObject . claim ;
/ * *
* Information for the proof verification process
* @ type { import ( './types' ) . ServiceProviderProof }
* /
this . proof = serviceProviderObject . proof ;
}
/ * *
* Get a JSON representation of the { @ link ServiceProvider }
* @ function
* @ returns { import ( './types' ) . ServiceProviderObject } JSON representation of a { @ link ServiceProvider }
* /
toJSON ( ) {
return {
about : this . about ,
profile : this . profile ,
claim : this . claim ,
proof : this . proof
}
}
}
2023-07-09 04:05:21 -06:00
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* @ module proofs
* /
/ * *
* Delegate the proof request to the correct fetcher .
* This method uses the current environment ( browser / node ) , certain values from
* the ` data ` parameter and the proxy policy set in the ` opts ` parameter to
* choose the right approach to fetch the proof . An error will be thrown if no
* approach is possible .
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
* @ param { import ( './types' ) . VerificationConfig } opts - Options to enable the request
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
async function fetch$2 ( data , opts ) {
if ( isNode _1 ) {
return handleNodeRequests ( data , opts )
}
return handleBrowserRequests ( data , opts )
}
/ * *
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
2023-07-09 04:05:21 -06:00
* @ param { object } opts - Options to enable the request
2024-02-01 09:06:40 -07:00
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
const handleBrowserRequests = ( data , opts ) => {
switch ( opts . proxy . policy ) {
case ProxyPolicy . ALWAYS :
return createProxyRequestPromise ( data , opts )
case ProxyPolicy . NEVER :
2023-07-13 02:41:31 -06:00
switch ( data . proof . request . accessRestriction ) {
2023-07-09 04:05:21 -06:00
case ProofAccessRestriction . NONE :
case ProofAccessRestriction . GRANTED :
return createDefaultRequestPromise ( data , opts )
case ProofAccessRestriction . NOCORS :
case ProofAccessRestriction . SERVER :
throw new Error (
'Impossible to fetch proof (bad combination of service access and proxy policy)'
)
default :
throw new Error ( 'Invalid proof access value' )
}
case ProxyPolicy . ADAPTIVE :
2023-07-13 02:41:31 -06:00
switch ( data . proof . request . accessRestriction ) {
2023-07-09 04:05:21 -06:00
case ProofAccessRestriction . NONE :
return createFallbackRequestPromise ( data , opts )
case ProofAccessRestriction . NOCORS :
return createProxyRequestPromise ( data , opts )
case ProofAccessRestriction . GRANTED :
return createFallbackRequestPromise ( data , opts )
case ProofAccessRestriction . SERVER :
return createProxyRequestPromise ( data , opts )
default :
throw new Error ( 'Invalid proof access value' )
}
default :
throw new Error ( 'Invalid proxy policy' )
}
} ;
/ * *
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
2023-07-09 04:05:21 -06:00
* @ param { object } opts - Options to enable the request
2024-02-01 09:06:40 -07:00
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
const handleNodeRequests = ( data , opts ) => {
switch ( opts . proxy . policy ) {
case ProxyPolicy . ALWAYS :
return createProxyRequestPromise ( data , opts )
case ProxyPolicy . NEVER :
return createDefaultRequestPromise ( data , opts )
case ProxyPolicy . ADAPTIVE :
return createFallbackRequestPromise ( data , opts )
default :
throw new Error ( 'Invalid proxy policy' )
}
} ;
/ * *
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
2023-07-09 04:05:21 -06:00
* @ param { object } opts - Options to enable the request
2024-02-01 09:06:40 -07:00
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
const createDefaultRequestPromise = ( data , opts ) => {
return new Promise ( ( resolve , reject ) => {
2023-07-10 03:46:53 -06:00
if ( ! ( data . proof . request . fetcher in fetcher _ _namespace ) ) {
reject ( new Error ( ` fetcher for ${ data . proof . request . fetcher } not found ` ) ) ;
}
fetcher _ _namespace [ data . proof . request . fetcher ]
2023-07-09 04:05:21 -06:00
. fn ( data . proof . request . data , opts )
. then ( ( res ) => {
return resolve ( {
2023-07-10 03:46:53 -06:00
fetcher : data . proof . request . fetcher ,
2023-07-09 04:05:21 -06:00
data ,
viaProxy : false ,
result : res
} )
} )
. catch ( ( err ) => {
return reject ( err )
} ) ;
} )
} ;
/ * *
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
2023-07-09 04:05:21 -06:00
* @ param { object } opts - Options to enable the request
2024-02-01 09:06:40 -07:00
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
const createProxyRequestPromise = ( data , opts ) => {
return new Promise ( ( resolve , reject ) => {
let proxyUrl ;
try {
proxyUrl = generateProxyURL (
2023-07-10 03:46:53 -06:00
data . proof . request . fetcher ,
2023-07-09 04:05:21 -06:00
data . proof . request . data ,
opts
) ;
} catch ( err ) {
reject ( err ) ;
}
const requestData = {
url : proxyUrl ,
2023-07-13 02:41:31 -06:00
format : data . proof . response . format ,
fetcherTimeout : data . proof . request . fetcher in fetcher _ _namespace ? fetcher _ _namespace [ data . proof . request . fetcher ] . timeout : 30000
2023-07-09 04:05:21 -06:00
} ;
fetcher _ _namespace . http
. fn ( requestData , opts )
. then ( ( res ) => {
return resolve ( {
2023-07-10 03:46:53 -06:00
fetcher : 'http' ,
2023-07-09 04:05:21 -06:00
data ,
viaProxy : true ,
result : res
} )
} )
. catch ( ( err ) => {
return reject ( err )
} ) ;
} )
} ;
/ * *
2024-02-01 09:06:40 -07:00
* @ param { ServiceProvider } data - Data from a claim definition
2023-07-09 04:05:21 -06:00
* @ param { object } opts - Options to enable the request
2024-02-01 09:06:40 -07:00
* @ returns { Promise < object | string > } Fetched proof data
2023-07-09 04:05:21 -06:00
* /
const createFallbackRequestPromise = ( data , opts ) => {
return new Promise ( ( resolve , reject ) => {
createDefaultRequestPromise ( data , opts )
. then ( ( res ) => {
return resolve ( res )
} )
. catch ( ( err1 ) => {
createProxyRequestPromise ( data , opts )
. then ( ( res ) => {
return resolve ( res )
} )
. catch ( ( err2 ) => {
return reject ( err2 )
} ) ;
} ) ;
} )
} ;
var proofs = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
fetch : fetch$2
} ) ;
/ * !
* hash - wasm ( https : //www.npmjs.com/package/hash-wasm)
* ( c ) Dani Biro
* @ license MIT
* /
2024-01-23 11:06:49 -07:00
/ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
2023-07-09 04:05:21 -06:00
Copyright ( c ) Microsoft Corporation .
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
Permission to use , copy , modify , and / or distribute this software for any
purpose with or without fee is hereby granted .
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
AND FITNESS . IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL , DIRECT ,
INDIRECT , OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
LOSS OF USE , DATA OR PROFITS , WHETHER IN AN ACTION OF CONTRACT , NEGLIGENCE OR
OTHER TORTIOUS ACTION , ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE .
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * /
2024-01-23 11:06:49 -07:00
/* global Reflect, Promise, SuppressedError, Symbol */
2023-07-08 00:36:57 -06:00
2023-07-09 04:05:21 -06:00
function _ _awaiter ( thisArg , _arguments , P , generator ) {
function adopt ( value ) { return value instanceof P ? value : new P ( function ( resolve ) { resolve ( value ) ; } ) ; }
return new ( P || ( P = Promise ) ) ( function ( resolve , reject ) {
function fulfilled ( value ) { try { step ( generator . next ( value ) ) ; } catch ( e ) { reject ( e ) ; } }
function rejected ( value ) { try { step ( generator [ "throw" ] ( value ) ) ; } catch ( e ) { reject ( e ) ; } }
function step ( result ) { result . done ? resolve ( result . value ) : adopt ( result . value ) . then ( fulfilled , rejected ) ; }
step ( ( generator = generator . apply ( thisArg , _arguments || [ ] ) ) . next ( ) ) ;
} ) ;
2024-01-23 11:06:49 -07:00
}
typeof SuppressedError === "function" ? SuppressedError : function ( error , suppressed , message ) {
var e = new Error ( message ) ;
return e . name = "SuppressedError" , e . error = error , e . suppressed = suppressed , e ;
} ;
2023-07-09 04:05:21 -06:00
class Mutex {
constructor ( ) {
this . mutex = Promise . resolve ( ) ;
}
lock ( ) {
let begin = ( ) => { } ;
this . mutex = this . mutex . then ( ( ) => new Promise ( begin ) ) ;
return new Promise ( ( res ) => {
begin = res ;
} ) ;
}
dispatch ( fn ) {
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
const unlock = yield this . lock ( ) ;
try {
return yield Promise . resolve ( fn ( ) ) ;
}
finally {
unlock ( ) ;
}
} ) ;
}
}
/* eslint-disable import/prefer-default-export */
/* eslint-disable no-bitwise */
var _a$1 ;
function getGlobal ( ) {
if ( typeof globalThis !== 'undefined' )
return globalThis ;
// eslint-disable-next-line no-restricted-globals
if ( typeof self !== 'undefined' )
return self ;
if ( typeof window !== 'undefined' )
return window ;
return global$1 ;
}
const globalObject = getGlobal ( ) ;
const nodeBuffer = ( _a$1 = globalObject . Buffer ) !== null && _a$1 !== void 0 ? _a$1 : null ;
const textEncoder = globalObject . TextEncoder ? new globalObject . TextEncoder ( ) : null ;
function hexCharCodesToInt ( a , b ) {
return ( ( ( a & 0xF ) + ( ( a >> 6 ) | ( ( a >> 3 ) & 0x8 ) ) ) << 4 ) | ( ( b & 0xF ) + ( ( b >> 6 ) | ( ( b >> 3 ) & 0x8 ) ) ) ;
}
function writeHexToUInt8 ( buf , str ) {
const size = str . length >> 1 ;
for ( let i = 0 ; i < size ; i ++ ) {
const index = i << 1 ;
buf [ i ] = hexCharCodesToInt ( str . charCodeAt ( index ) , str . charCodeAt ( index + 1 ) ) ;
}
}
function hexStringEqualsUInt8 ( str , buf ) {
if ( str . length !== buf . length * 2 ) {
return false ;
}
for ( let i = 0 ; i < buf . length ; i ++ ) {
const strIndex = i << 1 ;
if ( buf [ i ] !== hexCharCodesToInt ( str . charCodeAt ( strIndex ) , str . charCodeAt ( strIndex + 1 ) ) ) {
return false ;
}
}
return true ;
}
const alpha = 'a' . charCodeAt ( 0 ) - 10 ;
const digit = '0' . charCodeAt ( 0 ) ;
function getDigestHex ( tmpBuffer , input , hashLength ) {
let p = 0 ;
/* eslint-disable no-plusplus */
for ( let i = 0 ; i < hashLength ; i ++ ) {
let nibble = input [ i ] >>> 4 ;
tmpBuffer [ p ++ ] = nibble > 9 ? nibble + alpha : nibble + digit ;
nibble = input [ i ] & 0xF ;
tmpBuffer [ p ++ ] = nibble > 9 ? nibble + alpha : nibble + digit ;
}
/* eslint-enable no-plusplus */
return String . fromCharCode . apply ( null , tmpBuffer ) ;
}
const getUInt8Buffer = nodeBuffer !== null
? ( data ) => {
if ( typeof data === 'string' ) {
const buf = nodeBuffer . from ( data , 'utf8' ) ;
return new Uint8Array ( buf . buffer , buf . byteOffset , buf . length ) ;
}
if ( nodeBuffer . isBuffer ( data ) ) {
return new Uint8Array ( data . buffer , data . byteOffset , data . length ) ;
}
if ( ArrayBuffer . isView ( data ) ) {
return new Uint8Array ( data . buffer , data . byteOffset , data . byteLength ) ;
}
throw new Error ( 'Invalid data type!' ) ;
}
: ( data ) => {
if ( typeof data === 'string' ) {
return textEncoder . encode ( data ) ;
}
if ( ArrayBuffer . isView ( data ) ) {
return new Uint8Array ( data . buffer , data . byteOffset , data . byteLength ) ;
}
throw new Error ( 'Invalid data type!' ) ;
} ;
const base64Chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/' ;
const base64Lookup = new Uint8Array ( 256 ) ;
for ( let i = 0 ; i < base64Chars . length ; i ++ ) {
base64Lookup [ base64Chars . charCodeAt ( i ) ] = i ;
}
function encodeBase64$1 ( data , pad = true ) {
const len = data . length ;
const extraBytes = len % 3 ;
const parts = [ ] ;
const len2 = len - extraBytes ;
for ( let i = 0 ; i < len2 ; i += 3 ) {
const tmp = ( ( data [ i ] << 16 ) & 0xFF0000 )
+ ( ( data [ i + 1 ] << 8 ) & 0xFF00 )
+ ( data [ i + 2 ] & 0xFF ) ;
const triplet = base64Chars . charAt ( ( tmp >> 18 ) & 0x3F )
+ base64Chars . charAt ( ( tmp >> 12 ) & 0x3F )
+ base64Chars . charAt ( ( tmp >> 6 ) & 0x3F )
+ base64Chars . charAt ( tmp & 0x3F ) ;
parts . push ( triplet ) ;
}
if ( extraBytes === 1 ) {
const tmp = data [ len - 1 ] ;
const a = base64Chars . charAt ( tmp >> 2 ) ;
const b = base64Chars . charAt ( ( tmp << 4 ) & 0x3F ) ;
parts . push ( ` ${ a } ${ b } ` ) ;
if ( pad ) {
parts . push ( '==' ) ;
}
}
else if ( extraBytes === 2 ) {
const tmp = ( data [ len - 2 ] << 8 ) + data [ len - 1 ] ;
const a = base64Chars . charAt ( tmp >> 10 ) ;
const b = base64Chars . charAt ( ( tmp >> 4 ) & 0x3F ) ;
const c = base64Chars . charAt ( ( tmp << 2 ) & 0x3F ) ;
parts . push ( ` ${ a } ${ b } ${ c } ` ) ;
if ( pad ) {
parts . push ( '=' ) ;
}
}
return parts . join ( '' ) ;
}
function getDecodeBase64Length ( data ) {
let bufferLength = Math . floor ( data . length * 0.75 ) ;
const len = data . length ;
if ( data [ len - 1 ] === '=' ) {
bufferLength -= 1 ;
if ( data [ len - 2 ] === '=' ) {
bufferLength -= 1 ;
}
}
return bufferLength ;
}
function decodeBase64$1 ( data ) {
const bufferLength = getDecodeBase64Length ( data ) ;
const len = data . length ;
const bytes = new Uint8Array ( bufferLength ) ;
let p = 0 ;
for ( let i = 0 ; i < len ; i += 4 ) {
const encoded1 = base64Lookup [ data . charCodeAt ( i ) ] ;
const encoded2 = base64Lookup [ data . charCodeAt ( i + 1 ) ] ;
const encoded3 = base64Lookup [ data . charCodeAt ( i + 2 ) ] ;
const encoded4 = base64Lookup [ data . charCodeAt ( i + 3 ) ] ;
bytes [ p ] = ( encoded1 << 2 ) | ( encoded2 >> 4 ) ;
p += 1 ;
bytes [ p ] = ( ( encoded2 & 15 ) << 4 ) | ( encoded3 >> 2 ) ;
p += 1 ;
bytes [ p ] = ( ( encoded3 & 3 ) << 6 ) | ( encoded4 & 63 ) ;
p += 1 ;
}
return bytes ;
}
const MAX _HEAP = 16 * 1024 ;
const WASM _FUNC _HASH _LENGTH = 4 ;
const wasmMutex = new Mutex ( ) ;
const wasmModuleCache = new Map ( ) ;
function WASMInterface ( binary , hashLength ) {
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
let wasmInstance = null ;
let memoryView = null ;
let initialized = false ;
if ( typeof WebAssembly === 'undefined' ) {
throw new Error ( 'WebAssembly is not supported in this environment!' ) ;
}
const writeMemory = ( data , offset = 0 ) => {
memoryView . set ( data , offset ) ;
} ;
const getMemory = ( ) => memoryView ;
const getExports = ( ) => wasmInstance . exports ;
const setMemorySize = ( totalSize ) => {
wasmInstance . exports . Hash _SetMemorySize ( totalSize ) ;
const arrayOffset = wasmInstance . exports . Hash _GetBuffer ( ) ;
const memoryBuffer = wasmInstance . exports . memory . buffer ;
memoryView = new Uint8Array ( memoryBuffer , arrayOffset , totalSize ) ;
} ;
const getStateSize = ( ) => {
const view = new DataView ( wasmInstance . exports . memory . buffer ) ;
const stateSize = view . getUint32 ( wasmInstance . exports . STATE _SIZE , true ) ;
return stateSize ;
} ;
const loadWASMPromise = wasmMutex . dispatch ( ( ) => _ _awaiter ( this , void 0 , void 0 , function * ( ) {
if ( ! wasmModuleCache . has ( binary . name ) ) {
const asm = decodeBase64$1 ( binary . data ) ;
const promise = WebAssembly . compile ( asm ) ;
wasmModuleCache . set ( binary . name , promise ) ;
}
const module = yield wasmModuleCache . get ( binary . name ) ;
wasmInstance = yield WebAssembly . instantiate ( module , {
// env: {
// emscripten_memcpy_big: (dest, src, num) => {
// const memoryBuffer = wasmInstance.exports.memory.buffer;
// const memView = new Uint8Array(memoryBuffer, 0);
// memView.set(memView.subarray(src, src + num), dest);
// },
// print_memory: (offset, len) => {
// const memoryBuffer = wasmInstance.exports.memory.buffer;
// const memView = new Uint8Array(memoryBuffer, 0);
// console.log('print_int32', memView.subarray(offset, offset + len));
// },
// },
} ) ;
// wasmInstance.exports._start();
} ) ) ;
const setupInterface = ( ) => _ _awaiter ( this , void 0 , void 0 , function * ( ) {
if ( ! wasmInstance ) {
yield loadWASMPromise ;
}
const arrayOffset = wasmInstance . exports . Hash _GetBuffer ( ) ;
const memoryBuffer = wasmInstance . exports . memory . buffer ;
memoryView = new Uint8Array ( memoryBuffer , arrayOffset , MAX _HEAP ) ;
} ) ;
const init = ( bits = null ) => {
initialized = true ;
wasmInstance . exports . Hash _Init ( bits ) ;
} ;
const updateUInt8Array = ( data ) => {
let read = 0 ;
while ( read < data . length ) {
const chunk = data . subarray ( read , read + MAX _HEAP ) ;
read += chunk . length ;
memoryView . set ( chunk ) ;
wasmInstance . exports . Hash _Update ( chunk . length ) ;
}
} ;
const update = ( data ) => {
if ( ! initialized ) {
throw new Error ( 'update() called before init()' ) ;
}
const Uint8Buffer = getUInt8Buffer ( data ) ;
updateUInt8Array ( Uint8Buffer ) ;
} ;
const digestChars = new Uint8Array ( hashLength * 2 ) ;
const digest = ( outputType , padding = null ) => {
if ( ! initialized ) {
throw new Error ( 'digest() called before init()' ) ;
}
initialized = false ;
wasmInstance . exports . Hash _Final ( padding ) ;
if ( outputType === 'binary' ) {
// the data is copied to allow GC of the original memory object
return memoryView . slice ( 0 , hashLength ) ;
}
return getDigestHex ( digestChars , memoryView , hashLength ) ;
} ;
const save = ( ) => {
if ( ! initialized ) {
throw new Error ( 'save() can only be called after init() and before digest()' ) ;
}
const stateOffset = wasmInstance . exports . Hash _GetState ( ) ;
const stateLength = getStateSize ( ) ;
const memoryBuffer = wasmInstance . exports . memory . buffer ;
const internalState = new Uint8Array ( memoryBuffer , stateOffset , stateLength ) ;
// prefix is 4 bytes from SHA1 hash of the WASM binary
// it is used to detect incompatible internal states between different versions of hash-wasm
const prefixedState = new Uint8Array ( WASM _FUNC _HASH _LENGTH + stateLength ) ;
writeHexToUInt8 ( prefixedState , binary . hash ) ;
prefixedState . set ( internalState , WASM _FUNC _HASH _LENGTH ) ;
return prefixedState ;
} ;
const load = ( state ) => {
if ( ! ( state instanceof Uint8Array ) ) {
throw new Error ( 'load() expects an Uint8Array generated by save()' ) ;
}
const stateOffset = wasmInstance . exports . Hash _GetState ( ) ;
const stateLength = getStateSize ( ) ;
const overallLength = WASM _FUNC _HASH _LENGTH + stateLength ;
const memoryBuffer = wasmInstance . exports . memory . buffer ;
if ( state . length !== overallLength ) {
throw new Error ( ` Bad state length (expected ${ overallLength } bytes, got ${ state . length } ) ` ) ;
}
if ( ! hexStringEqualsUInt8 ( binary . hash , state . subarray ( 0 , WASM _FUNC _HASH _LENGTH ) ) ) {
throw new Error ( 'This state was written by an incompatible hash implementation' ) ;
}
const internalState = state . subarray ( WASM _FUNC _HASH _LENGTH ) ;
new Uint8Array ( memoryBuffer , stateOffset , stateLength ) . set ( internalState ) ;
initialized = true ;
} ;
const isDataShort = ( data ) => {
if ( typeof data === 'string' ) {
// worst case is 4 bytes / char
return data . length < MAX _HEAP / 4 ;
}
return data . byteLength < MAX _HEAP ;
} ;
let canSimplify = isDataShort ;
switch ( binary . name ) {
case 'argon2' :
case 'scrypt' :
canSimplify = ( ) => true ;
break ;
case 'blake2b' :
case 'blake2s' :
// if there is a key at blake2 then cannot simplify
canSimplify = ( data , initParam ) => initParam <= 512 && isDataShort ( data ) ;
break ;
case 'blake3' :
// if there is a key at blake3 then cannot simplify
canSimplify = ( data , initParam ) => initParam === 0 && isDataShort ( data ) ;
break ;
case 'xxhash64' : // cannot simplify
case 'xxhash3' :
case 'xxhash128' :
canSimplify = ( ) => false ;
break ;
}
// shorthand for (init + update + digest) for better performance
const calculate = ( data , initParam = null , digestParam = null ) => {
if ( ! canSimplify ( data , initParam ) ) {
init ( initParam ) ;
update ( data ) ;
return digest ( 'hex' , digestParam ) ;
}
const buffer = getUInt8Buffer ( data ) ;
memoryView . set ( buffer ) ;
wasmInstance . exports . Hash _Calculate ( buffer . length , initParam , digestParam ) ;
return getDigestHex ( digestChars , memoryView , hashLength ) ;
} ;
yield setupInterface ( ) ;
return {
getMemory ,
writeMemory ,
getExports ,
setMemorySize ,
init ,
update ,
digest ,
save ,
load ,
calculate ,
hashLength ,
} ;
} ) ;
}
new Mutex ( ) ;
var name$j = "blake2b" ;
2024-01-23 11:06:49 -07:00
var data$j = " AGFzbQEAAAABEQRgAAF / YAJ / fwBgAX8AYAAAAwoJAAECAwECAgABBQQBAQICBg4CfwFBsIsFC38AQYAICwdwCAZtZW1vcnkCAA5IYXNoX0dldEJ1ZmZlcgAACkhhc2hfRmluYWwAAwlIYXNoX0luaXQABQtIYXNoX1VwZGF0ZQAGDUhhc2hfR2V0U3RhdGUABw5IYXNoX0NhbGN1bGF0ZQAIClNUQVRFX1NJWkUDAQrTOAkFAEGACQvrAgIFfwF + AkAgAUEBSA0AAkACQAJAQYABQQAoAuCKASICayIDIAFIDQAgASEEDAELQQBBADYC4IoBAkAgAkH / AEoNACACQeCJAWohBSAAIQRBACEGA0AgBSAELQAAOgAAIARBAWohBCAFQQFqIQUgAyAGQQFqIgZB / wFxSg0ACwtBAEEAKQPAiQEiB0KAAXw3A8CJAUEAQQApA8iJASAHQv9 + Vq18NwPIiQFB4IkBEAIgACADaiEAAkAgASADayIEQYEBSA0AIAIgAWohBQNAQQBBACkDwIkBIgdCgAF8NwPAiQFBAEEAKQPIiQEgB0L / flatfDcDyIkBIAAQAiAAQYABaiEAIAVBgH9qIgVBgAJLDQALIAVBgH9qIQQMAQsgBEEATA0BC0EAIQUDQCAFQQAoAuCKAWpB4IkBaiAAIAVqLQAAOgAAIAQgBUEBaiIFQf8BcUoNAAsLQQBBACgC4IoBIARqNgLgigELC78uASR + QQBBACkD0IkBQQApA7CJASIBQQApA5CJAXwgACkDICICfCIDhULr + obav7X2wR + FQiCJIgRCq / DT9K / uvLc8fCIFIAGFQiiJIgYgA3wgACkDKCIBfCIHIASFQjCJIgggBXwiCSAGhUIBiSIKQQApA8iJAUEAKQOoiQEiBEEAKQOIiQF8IAApAxAiA3wiBYVCn9j52cKR2oKbf4VCIIkiC0K7zqqm2NDrs7t / fCIMIASFQiiJIg0gBXwgACkDGCIEfCIOfCAAKQNQIgV8Ig9BACkDwIkBQQApA6CJASIQQQApA4CJASIRfCAAKQMAIgZ8IhKFQtGFmu / 6 z5SH0QCFQiCJIhNCiJLznf / M + YTqAHwiFCAQhUIoiSIVIBJ8IAApAwgiEHwiFiAThUIwiSIXhUIgiSIYQQApA9iJAUEAKQO4iQEiE0EAKQOYiQF8IAApAzAiEnwiGYVC + cL4m5Gjs / DbAIVCIIkiGkLx7fT4paf9p6V / fCIbIBOFQiiJIhwgGXwgACkDOCITfCIZIBqFQjCJIhogG3wiG3wiHSAKhUIoiSIeIA98IAApA1giCnwiDyAYhUIwiSIYIB18Ih0gDiALhUIwiSIOIAx8Ih8gDYVCAYkiDCAWfCAAKQNAIgt8Ig0gGoVCIIkiFiAJfCIaIAyFQiiJIiAgDXwgACkDSCIJfCIhIBaFQjCJIhYgGyAchUIBiSIMIAd8IAApA2AiB3wiDSAOhUIgiSIOIBcgFHwiFHwiFyAMhUIoiSIbIA18IAApA2giDHwiHCAOhUIwiSIOIBd8IhcgG4VCAYkiGyAZIBQgFYVCAYkiFHwgACkDcCINfCIVIAiFQiCJIhkgH3wiHyAUhUIoiSIUIBV8IAApA3giCHwiFXwgDHwiIoVCIIkiI3wiJCAbhUIoiSIbICJ8IBJ8IiIgFyAYIBUgGYVCMIkiFSAffCIZIBSFQgGJIhQgIXwgDXwiH4VCIIkiGHwiFyAUhUIoiSIUIB98IAV8Ih8gGIVCMIkiGCAXfCIXIBSFQgGJIhR8IAF8IiEgFiAafCIWIBUgHSAehUIBiSIaIBx8IAl8IhyFQiCJIhV8Ih0gGoVCKIkiGiAcfCAIfCIcIBWFQjCJIhWFQiCJIh4gGSAOIBYgIIVCAYkiFiAPfCACfCIPhUIgiSIOfCIZIBaFQiiJIhYgD3wgC3wiDyAOhUIwiSIOIBl8Ihl8IiAgFIVCKIkiFCAhfCAEfCIhIB6FQjCJIh4gIHwiICAiICOFQjCJIiIgJHwiIyAbhUIBiSIbIBx8IAp8IhwgDoVCIIkiDiAXfCIXIBuFQiiJIhsgHHwgE3wiHCAOhUIwiSIOIBkgFoVCAYkiFiAffCAQfCIZICKFQiCJIh8gFSAdfCIVfCIdIBaFQiiJIhYgGXwgB3wiGSAfhUIwiSIfIB18Ih0gFoVCAYkiFiAVIBqFQgGJIhUgD3wgBnwiDyAYhUIgiSIYICN8IhogFYVCKIkiFSAPfCADfCIPfCAHfCIihUIgiSIjfCIkIBaFQiiJIhYgInwgBnwiIiAjhUIwiSIjICR8IiQgFoVCAYkiFiAOIBd8Ig4gDyAYhUIwiSIPICAgFIVCAYkiFCAZfCAKfCIXhUIgiSIYfCIZIBSFQiiJIhQgF3wgC3wiF3wgBXwiICAPIBp8Ig8gHyAOIBuFQgGJIg4gIXwgCHwiGoVCIIkiG3wiHyAOhUIoiSIOIBp8IAx8IhogG4VCMIkiG4VCIIkiISAdIB4gDyAVhUIBiSIPIBx8IAF8IhWFQiCJIhx8Ih0gD4VCKIkiDyAVfCADfCIVIByFQjCJIhwgHXwiHXwiHiAWhUIoiSIWICB8IA18IiAgIYVCMIkiISAefCIeIBogFyAYhUIwiSIXIBl8IhggFIVCAYkiFHwgCXwiGSAchUIgiSIaICR8IhwgFIVCKIkiFCAZfCACfCIZIBqFQjCJIhogHSAPhUIBiSIPICJ8IAR8Ih0gF4VCIIkiFyAbIB98Iht8Ih8gD4VCKIkiDyAdfCASfCIdIBeFQjCJIhcgH3wiHyAPhUIBiSIPIBsgDoVCAYkiDiAVfCATfCIVICOFQiCJIhsgGHwiGCAOhUIoiSIOIBV8IBB8IhV8IAx8IiKFQiCJIiN8IiQgD4VCKIkiDyAifCAHfCIiICOFQjCJIiMgJHwiJCAPhUIBiSIPIBogHHwiGiAVIBuFQjCJIhUgHiAWhUIBiSIWIB18IAR8IhuFQiCJIhx8Ih0gFoVCKIkiFiAbfCAQfCIbfCABfCIeIBUgGHwiFSAXIBogFIVCAYkiFCAgfCATfCIYhUIgiSIXfCIaIBSFQiiJIhQgGHwgCXwiGCAXhUIwiSIXhUIgiSIgIB8gISAVIA6FQgGJIg4gGXwgCnwiFYVCIIkiGXwiHyAOhUIoiSIOIBV8IA18IhUgGYVCMIkiGSAffCIffCIhIA + FQiiJIg8gHnwgBXwiHiAghUIwiSIgICF8IiEgGyAchUIwiSIbIB18IhwgFoVCAYkiFiAYfCADfCIYIBmFQiCJIhkgJHwiHSAWhUIoiSIWIBh8IBJ8IhggGYVCMIkiGSAfIA6FQgGJIg4gInwgAnwiHyAbhUIgiSIbIBcgGnwiF3wiGiAOhUIoiSIOIB98IAZ8Ih8gG4VCMIkiGyAafCIaIA6FQgGJIg4gFSAXIBSFQgGJIhR8IAh8IhUgI4VCIIkiFyAcfCIcIBSFQiiJIhQgFXwgC3wiFXwgBXwiIoVCIIkiI3wiJCAOhUIoiSIOICJ8IAh8IiIgGiAgIBUgF4VCMIkiFSAcfCIXIBSFQgGJIhQgGHwgCXwiGIVCIIkiHHwiGiAUhUIoiSIUIBh8IAZ8IhggHIVCMIkiHCAafCIaIBSFQgGJIhR8IAR8IiAgGSAdfCIZIBUgISAPhUIBiSIPIB98IAN8Ih2FQiCJIhV8Ih8gD4VCKIkiDyAdfCACfCIdIBWFQjCJIhWFQiCJIiEgFyAbIBkgFoVCAYkiFiAefCABfCIZhUIgiSIbfCIXIBaFQiiJIhYgGXwgE3wiGSAbhUIwiSIbIBd8Ihd8Ih4gFIVCKIkiFCAgfCAMfCIgICGFQjCJIiEgHnwiHiAiICOFQjCJIiIgJHwiIyAOhUIBiSIOIB18IBJ8Ih0gG4VCIIkiGyAafCIaIA6FQiiJIg4gHXwgC3wiHSAbhUIwiSIbIBcgFoVCAYkiFiAYfCANfCIXICKFQiCJIhggFSAffCIVfCIfIBaFQiiJIhYgF3wgEHwiFyAYhUIwiSIYIB98Ih8gFoVCAYkiFiAVIA + FQgGJIg8gGXwgCnwiFSAchUIgiSIZICN8Ihw
var hash$j = "656e0f66" ;
2023-07-09 04:05:21 -06:00
var wasmJson$j = {
name : name$j ,
data : data$j ,
hash : hash$j
} ;
new Mutex ( ) ;
function validateBits$4 ( bits ) {
if ( ! Number . isInteger ( bits ) || bits < 8 || bits > 512 || bits % 8 !== 0 ) {
return new Error ( 'Invalid variant! Valid values: 8, 16, ..., 512' ) ;
}
return null ;
}
function getInitParam$1 ( outputBits , keyBits ) {
// eslint-disable-next-line no-bitwise
return outputBits | ( keyBits << 16 ) ;
}
/ * *
* Creates a new BLAKE2b hash instance
* @ param bits Number of output bits , which has to be a number
* divisible by 8 , between 8 and 512. Defaults to 512.
* @ param key Optional key ( string , Buffer or TypedArray ) . Maximum length is 64 bytes .
* /
function createBLAKE2b ( bits = 512 , key = null ) {
if ( validateBits$4 ( bits ) ) {
return Promise . reject ( validateBits$4 ( bits ) ) ;
}
let keyBuffer = null ;
let initParam = bits ;
if ( key !== null ) {
keyBuffer = getUInt8Buffer ( key ) ;
if ( keyBuffer . length > 64 ) {
return Promise . reject ( new Error ( 'Max key length is 64 bytes' ) ) ;
}
initParam = getInitParam$1 ( bits , keyBuffer . length ) ;
}
const outputSize = bits / 8 ;
return WASMInterface ( wasmJson$j , outputSize ) . then ( ( wasm ) => {
if ( initParam > 512 ) {
wasm . writeMemory ( keyBuffer ) ;
}
wasm . init ( initParam ) ;
const obj = {
init : initParam > 512
? ( ) => {
wasm . writeMemory ( keyBuffer ) ;
wasm . init ( initParam ) ;
return obj ;
}
: ( ) => {
wasm . init ( initParam ) ;
return obj ;
} ,
update : ( data ) => { wasm . update ( data ) ; return obj ; } ,
digest : ( outputType ) => wasm . digest ( outputType ) ,
save : ( ) => wasm . save ( ) ,
load : ( data ) => { wasm . load ( data ) ; return obj ; } ,
blockSize : 128 ,
digestSize : outputSize ,
} ;
return obj ;
} ) ;
}
var name$i = "argon2" ;
2024-01-23 11:06:49 -07:00
var data$i = " AGFzbQEAAAABKQVgAX8Bf2AAAX9gEH9 / f39 / f39 / f39 / f39 / f38AYAR / f39 / AGACf38AAwYFAAECAwQFBgEBAoCAAgYIAX8BQZCoBAsHQQQGbWVtb3J5AgASSGFzaF9TZXRNZW1vcnlTaXplAAAOSGFzaF9HZXRCdWZmZXIAAQ5IYXNoX0NhbGN1bGF0ZQAECvkyBVgBAn9BACEBAkBBACgCiAgiAiAARg0AAkAgACACayIAQRB2IABBgIB8cSAASWoiAEAAQX9HDQBB / wHADwtBACEBQQBBACkDiAggAEEQdK18NwOICAsgAcALcAECfwJAQQAoAoAIIgANAEEAPwBBEHQiADYCgAhBACgCiAgiAUGAgCBGDQACQEGAgCAgAWsiAEEQdiAAQYCAfHEgAElqIgBAAEF / Rw0AQQAPC0EAQQApA4gIIABBEHStfDcDiAhBACgCgAghAAsgAAvcDgECfiAAIAQpAwAiECAAKQMAIhF8IBFCAYZC / v ///x+DIBBC/////w+DfnwiEDcDACAMIBAgDCkDAIVCIIkiEDcDACAIIBAgCCkDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgBCAQIAQpAwCFQiiJIhA3AwAgACAQIAApAwAiEXwgEEL/////D4MgEUIBhkL+////H4N+fCIQNwMAIAwgECAMKQMAhUIwiSIQNwMAIAggECAIKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACAEIBAgBCkDAIVCAYk3AwAgASAFKQMAIhAgASkDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgDSAQIA0pAwCFQiCJIhA3AwAgCSAQIAkpAwAiEXwgEUIBhkL+////H4MgEEL/////D4N+fCIQNwMAIAUgECAFKQMAhUIoiSIQNwMAIAEgECABKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACANIBAgDSkDAIVCMIkiEDcDACAJIBAgCSkDACIRfCAQQv////8PgyARQgGGQv7///8fg358IhA3AwAgBSAQIAUpAwCFQgGJNwMAIAIgBikDACIQIAIpAwAiEXwgEUIBhkL+////H4MgEEL/////D4N+fCIQNwMAIA4gECAOKQMAhUIgiSIQNwMAIAogECAKKQMAIhF8IBFCAYZC/v///x+DIBBC/////w+DfnwiEDcDACAGIBAgBikDAIVCKIkiEDcDACACIBAgAikDACIRfCAQQv////8PgyARQgGGQv7///8fg358IhA3AwAgDiAQIA4pAwCFQjCJIhA3AwAgCiAQIAopAwAiEXwgEEL/////D4MgEUIBhkL+////H4N+fCIQNwMAIAYgECAGKQMAhUIBiTcDACADIAcpAwAiECADKQMAIhF8IBFCAYZC/v///x+DIBBC/////w+DfnwiEDcDACAPIBAgDykDAIVCIIkiEDcDACALIBAgCykDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgByAQIAcpAwCFQiiJIhA3AwAgAyAQIAMpAwAiEXwgEEL/////D4MgEUIBhkL+////H4N+fCIQNwMAIA8gECAPKQMAhUIwiSIQNwMAIAsgECALKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACAHIBAgBykDAIVCAYk3AwAgACAFKQMAIhAgACkDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgDyAQIA8pAwCFQiCJIhA3AwAgCiAQIAopAwAiEXwgEUIBhkL+////H4MgEEL/////D4N+fCIQNwMAIAUgECAFKQMAhUIoiSIQNwMAIAAgECAAKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACAPIBAgDykDAIVCMIkiEDcDACAKIBAgCikDACIRfCAQQv////8PgyARQgGGQv7///8fg358IhA3AwAgBSAQIAUpAwCFQgGJNwMAIAEgBikDACIQIAEpAwAiEXwgEUIBhkL+////H4MgEEL/////D4N+fCIQNwMAIAwgECAMKQMAhUIgiSIQNwMAIAsgECALKQMAIhF8IBFCAYZC/v///x+DIBBC/////w+DfnwiEDcDACAGIBAgBikDAIVCKIkiEDcDACABIBAgASkDACIRfCAQQv////8PgyARQgGGQv7///8fg358IhA3AwAgDCAQIAwpAwCFQjCJIhA3AwAgCyAQIAspAwAiEXwgEEL/////D4MgEUIBhkL+////H4N+fCIQNwMAIAYgECAGKQMAhUIBiTcDACACIAcpAwAiECACKQMAIhF8IBFCAYZC/v///x+DIBBC/////w+DfnwiEDcDACANIBAgDSkDAIVCIIkiEDcDACAIIBAgCCkDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgByAQIAcpAwCFQiiJIhA3AwAgAiAQIAIpAwAiEXwgEEL/////D4MgEUIBhkL+////H4N+fCIQNwMAIA0gECANKQMAhUIwiSIQNwMAIAggECAIKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACAHIBAgBykDAIVCAYk3AwAgAyAEKQMAIhAgAykDACIRfCARQgGGQv7///8fgyAQQv////8Pg358IhA3AwAgDiAQIA4pAwCFQiCJIhA3AwAgCSAQIAkpAwAiEXwgEUIBhkL+////H4MgEEL/////D4N+fCIQNwMAIAQgECAEKQMAhUIoiSIQNwMAIAMgECADKQMAIhF8IBBC/////w+DIBFCAYZC/v///x+DfnwiEDcDACAOIBAgDikDAIVCMIkiEDcDACAJIBAgCSkDACIRfCAQQv////8PgyARQgGGQv7///8fg358IhA3AwAgBCAQIAQpAwCFQgGJNwMAC98aAQN/QQAhBEEAIAIpAwAgASkDAIU3A5AIQQAgAikDCCABKQMIhTcDmAhBACACKQMQIAEpAxCFNwOgCEEAIAIpAxggASkDGIU3A6gIQQAgAikDICABKQMghTcDsAhBACACKQMoIAEpAyiFNwO4CEEAIAIpAzAgASkDMIU3A8AIQQAgAikDOCABKQM4hTcDyAhBACACKQNAIAEpA0CFNwPQCEEAIAIpA0ggASkDSIU3A9gIQQAgAikDUCABKQNQhTcD4AhBACACKQNYIAEpA1iFNwPoCEEAIAIpA2AgASkDYIU3A/AIQQAgAikDaCABKQNohTcD+AhBACACKQNwIAEpA3CFNwOACUEAIAIpA3ggASkDeIU3A4gJQQAgAikDgAEgASkDgAGFNwOQCUEAIAIpA4gBIAEpA4gBhTcDmAlBACACKQOQASABKQOQAYU3A6AJQQAgAikDmAEgASkDmAGFNwOoCUEAIAIpA6ABIAEpA6ABhTcDsAlBACACKQOoASABKQOoAYU3A7gJQQAgAikDsAEgASkDsAGFNwPACUEAIAIpA7gBIAEpA7gBhTcDyAlBACACKQPAASABKQPAAYU3A9AJQQAgAikDyAEgASkDyAGFNwPYCUEAIAIpA9ABIAEpA9ABhTcD4AlBACACKQPYASABKQPYAYU3A+gJQQAgAikD4AEgASkD4AGFNwPwCUEAIAIpA+gBIAEpA+gBhTcD+AlBACACKQPwASABKQPwAYU3A4AKQQAgAikD+AEgASkD+AGFNwOICkEAIAIpA4ACIAEpA4AChTcDkApBACACKQOIAiABKQOIAoU3A5gKQQAgAikDkAIgASkDkAKFNwOgCkEAIAIpA5gCIAEpA5gChTcDqApBACACKQOgAiABKQOgAoU3A7AKQQAgAikDqAIgASkDqAKFNwO4CkEAIAIpA7ACIAEpA7AChTcDwApBACACKQO4AiABKQO4AoU3A8gKQQAgAikDwAIgASkDwAKFNwPQCkEAIAIpA8gCIAEpA8gChTcD2ApBACACKQPQAiABKQPQAoU3A+AKQQAgAikD2AIgASkD2AKFNwPoCkEAIAIpA+ACIAE
var hash$i = "7ab14c91" ;
2023-07-09 04:05:21 -06:00
var wasmJson$i = {
name : name$i ,
data : data$i ,
hash : hash$i
} ;
function encodeResult ( salt , options , res ) {
const parameters = [
` m= ${ options . memorySize } ` ,
` t= ${ options . iterations } ` ,
` p= ${ options . parallelism } ` ,
] . join ( ',' ) ;
return ` $ argon2 ${ options . hashType } $ v=19 $ ${ parameters } $ ${ encodeBase64$1 ( salt , false ) } $ ${ encodeBase64$1 ( res , false ) } ` ;
}
const uint32View = new DataView ( new ArrayBuffer ( 4 ) ) ;
function int32LE ( x ) {
uint32View . setInt32 ( 0 , x , true ) ;
return new Uint8Array ( uint32View . buffer ) ;
}
function hashFunc ( blake512 , buf , len ) {
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
if ( len <= 64 ) {
const blake = yield createBLAKE2b ( len * 8 ) ;
blake . update ( int32LE ( len ) ) ;
blake . update ( buf ) ;
return blake . digest ( 'binary' ) ;
}
const r = Math . ceil ( len / 32 ) - 2 ;
const ret = new Uint8Array ( len ) ;
blake512 . init ( ) ;
blake512 . update ( int32LE ( len ) ) ;
blake512 . update ( buf ) ;
let vp = blake512 . digest ( 'binary' ) ;
ret . set ( vp . subarray ( 0 , 32 ) , 0 ) ;
for ( let i = 1 ; i < r ; i ++ ) {
blake512 . init ( ) ;
blake512 . update ( vp ) ;
vp = blake512 . digest ( 'binary' ) ;
ret . set ( vp . subarray ( 0 , 32 ) , i * 32 ) ;
}
const partialBytesNeeded = len - 32 * r ;
let blakeSmall ;
if ( partialBytesNeeded === 64 ) {
blakeSmall = blake512 ;
blakeSmall . init ( ) ;
}
else {
blakeSmall = yield createBLAKE2b ( partialBytesNeeded * 8 ) ;
}
blakeSmall . update ( vp ) ;
vp = blakeSmall . digest ( 'binary' ) ;
ret . set ( vp . subarray ( 0 , partialBytesNeeded ) , r * 32 ) ;
return ret ;
} ) ;
}
function getHashType ( type ) {
switch ( type ) {
case 'd' :
return 0 ;
case 'i' :
return 1 ;
default :
return 2 ;
}
}
function argon2Internal ( options ) {
2024-01-23 11:06:49 -07:00
var _a ;
2023-07-09 04:05:21 -06:00
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
const { parallelism , iterations , hashLength } = options ;
const password = getUInt8Buffer ( options . password ) ;
const salt = getUInt8Buffer ( options . salt ) ;
const version = 0x13 ;
const hashType = getHashType ( options . hashType ) ;
const { memorySize } = options ; // in KB
2024-01-23 11:06:49 -07:00
const secret = getUInt8Buffer ( ( _a = options . secret ) !== null && _a !== void 0 ? _a : '' ) ;
2023-07-09 04:05:21 -06:00
const [ argon2Interface , blake512 ] = yield Promise . all ( [
WASMInterface ( wasmJson$i , 1024 ) ,
createBLAKE2b ( 512 ) ,
] ) ;
// last block is for storing the init vector
argon2Interface . setMemorySize ( memorySize * 1024 + 1024 ) ;
const initVector = new Uint8Array ( 24 ) ;
const initVectorView = new DataView ( initVector . buffer ) ;
initVectorView . setInt32 ( 0 , parallelism , true ) ;
initVectorView . setInt32 ( 4 , hashLength , true ) ;
initVectorView . setInt32 ( 8 , memorySize , true ) ;
initVectorView . setInt32 ( 12 , iterations , true ) ;
initVectorView . setInt32 ( 16 , version , true ) ;
initVectorView . setInt32 ( 20 , hashType , true ) ;
argon2Interface . writeMemory ( initVector , memorySize * 1024 ) ;
blake512 . init ( ) ;
blake512 . update ( initVector ) ;
blake512 . update ( int32LE ( password . length ) ) ;
blake512 . update ( password ) ;
blake512 . update ( int32LE ( salt . length ) ) ;
blake512 . update ( salt ) ;
2024-01-23 11:06:49 -07:00
blake512 . update ( int32LE ( secret . length ) ) ;
blake512 . update ( secret ) ;
2023-07-09 04:05:21 -06:00
blake512 . update ( int32LE ( 0 ) ) ; // associatedData length + associatedData
const segments = Math . floor ( memorySize / ( parallelism * 4 ) ) ; // length of each lane
const lanes = segments * 4 ;
const param = new Uint8Array ( 72 ) ;
const H0 = blake512 . digest ( 'binary' ) ;
param . set ( H0 ) ;
for ( let lane = 0 ; lane < parallelism ; lane ++ ) {
param . set ( int32LE ( 0 ) , 64 ) ;
param . set ( int32LE ( lane ) , 68 ) ;
let position = lane * lanes ;
let chunk = yield hashFunc ( blake512 , param , 1024 ) ;
argon2Interface . writeMemory ( chunk , position * 1024 ) ;
position += 1 ;
param . set ( int32LE ( 1 ) , 64 ) ;
chunk = yield hashFunc ( blake512 , param , 1024 ) ;
argon2Interface . writeMemory ( chunk , position * 1024 ) ;
}
const C = new Uint8Array ( 1024 ) ;
writeHexToUInt8 ( C , argon2Interface . calculate ( new Uint8Array ( [ ] ) , memorySize ) ) ;
const res = yield hashFunc ( blake512 , C , hashLength ) ;
if ( options . outputType === 'hex' ) {
const digestChars = new Uint8Array ( hashLength * 2 ) ;
return getDigestHex ( digestChars , res , hashLength ) ;
}
if ( options . outputType === 'encoded' ) {
return encodeResult ( salt , options , res ) ;
}
// return binary format
return res ;
} ) ;
}
const validateOptions$3 = ( options ) => {
2024-01-23 11:06:49 -07:00
var _a ;
2023-07-09 04:05:21 -06:00
if ( ! options || typeof options !== 'object' ) {
throw new Error ( 'Invalid options parameter. It requires an object.' ) ;
}
if ( ! options . password ) {
throw new Error ( 'Password must be specified' ) ;
}
options . password = getUInt8Buffer ( options . password ) ;
if ( options . password . length < 1 ) {
throw new Error ( 'Password must be specified' ) ;
}
if ( ! options . salt ) {
throw new Error ( 'Salt must be specified' ) ;
}
options . salt = getUInt8Buffer ( options . salt ) ;
if ( options . salt . length < 8 ) {
throw new Error ( 'Salt should be at least 8 bytes long' ) ;
}
2024-01-23 11:06:49 -07:00
options . secret = getUInt8Buffer ( ( _a = options . secret ) !== null && _a !== void 0 ? _a : '' ) ;
2023-07-09 04:05:21 -06:00
if ( ! Number . isInteger ( options . iterations ) || options . iterations < 1 ) {
throw new Error ( 'Iterations should be a positive number' ) ;
}
if ( ! Number . isInteger ( options . parallelism ) || options . parallelism < 1 ) {
throw new Error ( 'Parallelism should be a positive number' ) ;
}
if ( ! Number . isInteger ( options . hashLength ) || options . hashLength < 4 ) {
throw new Error ( 'Hash length should be at least 4 bytes.' ) ;
}
if ( ! Number . isInteger ( options . memorySize ) ) {
throw new Error ( 'Memory size should be specified.' ) ;
}
if ( options . memorySize < 8 * options . parallelism ) {
throw new Error ( 'Memory size should be at least 8 * parallelism.' ) ;
}
if ( options . outputType === undefined ) {
options . outputType = 'hex' ;
}
if ( ! [ 'hex' , 'binary' , 'encoded' ] . includes ( options . outputType ) ) {
throw new Error ( ` Insupported output type ${ options . outputType } . Valid values: ['hex', 'binary', 'encoded'] ` ) ;
}
} ;
2024-01-23 11:06:49 -07:00
const getHashParameters = ( password , encoded , secret ) => {
2023-07-09 04:05:21 -06:00
const regex = /^\$argon2(id|i|d)\$v=([0-9]+)\$((?:[mtp]=[0-9]+,){2}[mtp]=[0-9]+)\$([A-Za-z0-9+/]+)\$([A-Za-z0-9+/]+)$/ ;
const match = encoded . match ( regex ) ;
if ( ! match ) {
throw new Error ( 'Invalid hash' ) ;
}
const [ , hashType , version , parameters , salt , hash ] = match ;
if ( version !== '19' ) {
throw new Error ( ` Unsupported version: ${ version } ` ) ;
}
const parsedParameters = { } ;
const paramMap = { m : 'memorySize' , p : 'parallelism' , t : 'iterations' } ;
parameters . split ( ',' ) . forEach ( ( x ) => {
const [ n , v ] = x . split ( '=' ) ;
parsedParameters [ paramMap [ n ] ] = parseInt ( v , 10 ) ;
} ) ;
2024-01-23 11:06:49 -07:00
return Object . assign ( Object . assign ( { } , parsedParameters ) , { password ,
secret , hashType : hashType , salt : decodeBase64$1 ( salt ) , hashLength : getDecodeBase64Length ( hash ) , outputType : 'encoded' } ) ;
2023-07-09 04:05:21 -06:00
} ;
const validateVerifyOptions$1 = ( options ) => {
if ( ! options || typeof options !== 'object' ) {
throw new Error ( 'Invalid options parameter. It requires an object.' ) ;
}
if ( options . hash === undefined || typeof options . hash !== 'string' ) {
throw new Error ( 'Hash should be specified' ) ;
}
} ;
/ * *
* Verifies password using the argon2 password - hashing function
* @ returns True if the encoded hash matches the password
* /
function argon2Verify ( options ) {
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
validateVerifyOptions$1 ( options ) ;
2024-01-23 11:06:49 -07:00
const params = getHashParameters ( options . password , options . hash , options . secret ) ;
2023-07-09 04:05:21 -06:00
validateOptions$3 ( params ) ;
const hashStart = options . hash . lastIndexOf ( '$' ) + 1 ;
const result = yield argon2Internal ( params ) ;
return result . substring ( hashStart ) === options . hash . substring ( hashStart ) ;
} ) ;
}
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
new Mutex ( ) ;
var name$2 = "bcrypt" ;
2024-01-23 11:06:49 -07:00
var data$2 = " AGFzbQEAAAABFwRgAAF / YAR / f39 / AGADf39 / AGABfwF / AwUEAAECAwUEAQECAgYIAX8BQZCrBQsHNAQGbWVtb3J5AgAOSGFzaF9HZXRCdWZmZXIAAAZiY3J5cHQAAg1iY3J5cHRfdmVyaWZ5AAMK + GAEBQBBgCsL3lkEFH8Bfgh / AX4jAEHwAGshBCACQQA6AAIgAkGq4AA7AAACQCABLQAAQSpHDQAgAS0AAUEwRw0AIAJBMToAAQsCQCABLAAFIAEsAARBCmxqQfB7aiIFQQRJDQAgAS0AB0FgaiIGQd8ASw0AIAZBkAlqLQAAIgZBP0sNACABLQAIQWBqIgdB3wBLDQAgB0GQCWotAAAiB0E / Sw0AIAQgB0EEdiAGQQJ0cjoACCABLQAJQWBqIgZB3wBLDQAgBkGQCWotAAAiBkE / Sw0AIAQgBkECdiAHQQR0cjoACSABLQAKQWBqIgdB3wBLDQAgB0GQCWotAAAiB0E / Sw0AIAQgByAGQQZ0cjoACiABLQALQWBqIgZB3wBLDQAgBkGQCWotAAAiBkE / Sw0AIAEtAAxBYGoiB0HfAEsNACAHQZAJai0AACIHQT9LDQAgBCAHQQR2IAZBAnRyOgALIAEtAA1BYGoiBkHfAEsNACAGQZAJai0AACIGQT9LDQAgBCAGQQJ2IAdBBHRyOgAMIAEtAA5BYGoiB0HfAEsNACAHQZAJai0AACIHQT9LDQAgBCAHIAZBBnRyOgANIAEtAA9BYGoiBkHfAEsNACAGQZAJai0AACIGQT9LDQAgAS0AEEFgaiIHQd8ASw0AIAdBkAlqLQAAIgdBP0sNACAEIAdBBHYgBkECdHI6AA4gAS0AEUFgaiIGQd8ASw0AIAZBkAlqLQAAIgZBP0sNACAEIAZBAnYgB0EEdHI6AA8gAS0AEkFgaiIHQd8ASw0AIAdBkAlqLQAAIgdBP0sNACAEIAcgBkEGdHI6ABAgAS0AE0FgaiIGQd8ASw0AIAZBkAlqLQAAIgZBP0sNACABLQAUQWBqIgdB3wBLDQAgB0GQCWotAAAiB0E / Sw0AIAQgB0EEdiAGQQJ0cjoAESABLQAVQWBqIgZB3wBLDQAgBkGQCWotAAAiBkE / Sw0AIAQgBkECdiAHQQR0cjoAEiABLQAWQWBqIgdB3wBLDQAgB0GQCWotAAAiB0E / Sw0AIAQgByAGQQZ0cjoAEyABLQAXQWBqIgZB3wBLDQAgBkGQCWotAAAiBkE / Sw0AIAEtABhBYGoiB0HfAEsNACAHQZAJai0AACIHQT9LDQAgBCAHQQR2IAZBAnRyOgAUIAEtABlBYGoiBkHfAEsNACAGQZAJai0AACIGQT9LDQAgBCAGQQJ2IAdBBHRyOgAVIAEtABpBYGoiB0HfAEsNACAHQZAJai0AACIHQT9LDQAgBCAHIAZBBnRyOgAWIAEtABtBYGoiBkHfAEsNACAGQZAJai0AACIGQT9LDQAgAS0AHEFgaiIHQd8ASw0AIAdBkAlqLQAAIgdBP0sNAEEBIAV0IQggBCAHQQR2IAZBAnRyOgAXIAQgBCgCCCIFQRh0IAVBgP4DcUEIdHIgBUEIdkGA / gNxIAVBGHZyciIJNgIIIAQgBCgCDCIFQRh0IAVBgP4DcUEIdHIgBUEIdkGA / gNxIAVBGHZyciIKNgIMIAQgBCgCECIFQRh0IAVBgP4DcUEIdHIgBUEIdkGA / gNxIAVBGHZyciILNgIQIAQgBCgCFCIFQRh0IAVBgP4DcUEIdHIgBUEIdkGA / gNxIAVBGHZyciIMNgIUIARB6ABqIAEtAAJBnwdqLQAAIg1BAXFBAnRqIQ5BACEGQQAhD0EAIRAgACEFA0AgBEIANwJoIAUtAAAhByAEQQA2AmwgBCAHNgJoIAQgBSwAACIRNgJsIAUtAAAhEiAEIAdBCHQiBzYCaCAEIAcgBUEBaiAAIBIbIgUtAAByIgc2AmggBCARQQh0IhE2AmwgBCARIAUsAAAiEnIiETYCbCAFLQAAIRMgBCAHQQh0Igc2AmggBCAHIAVBAWogACATGyIFLQAAciIHNgJoIAQgEUEIdCIRNgJsIAQgESAFLAAAIhNyIhE2AmwgBS0AACEUIAQgB0EIdCIHNgJoIAQgByAFQQFqIAAgFBsiBS0AAHIiBzYCaCAEIBFBCHQiETYCbCAEIBEgBSwAACIUciIRNgJsIAUtAAAhFSAEQSBqIAZqIA4oAgAiFjYCACAGQfApaiIXIBYgFygCAHM2AgAgESAHcyAPciEPIAVBAWogACAVGyEFIBQgEyAScnJBgAFxIBByIRAgBkEEaiIGQcgARw0AC0EAQQAoAvApIBBBCXQgDUEPdHFBgIAEIA9B //8DcSAPQRB2cmtxczYC8ClCACEYQX4hBkHwKSEHA0BBACgCrCpBACgCqCpBACgCpCpBACgCoCpBACgCnCpBACgCmCpBACgClCpBACgCkCpBACgCjCpBACgCiCpBACgChCpBACgCgCpBACgC/ClBACgC+ClBACgC9CkgBEEIaiAGQQJqIgZBAnFBAnRqKQMAIBiFIhhCIIinc0EAKALwKSAYp3MiAEEWdkH8B3FB8AlqKAIAIABBDnZB/AdxQfARaigCAGogAEEGdkH8B3FB8BlqKAIAcyAAQf8BcUECdEHwIWooAgBqcyIFQRZ2QfwHcUHwCWooAgAgBUEOdkH8B3FB8BFqKAIAaiAFQQZ2QfwHcUHwGWooAgBzIAVB/wFxQQJ0QfAhaigCAGpzIABzIgBBFnZB/AdxQfAJaigCACAAQQ52QfwHcUHwEWooAgBqIABBBnZB/AdxQfAZaigCAHMgAEH/AXFBAnRB8CFqKAIAanMgBXMiBUEWdkH8B3FB8AlqKAIAIAVBDnZB/AdxQfARaigCAGogBUEGdkH8B3FB8BlqKAIAcyAFQf8BcUECdEHwIWooAgBqcyAAcyIAQRZ2QfwHcUHwCWooAgAgAEEOdkH8B3FB8BFqKAIAaiAAQQZ2QfwHcUHwGWooAgBzIABB/wFxQQJ0QfAhaigCAGpzIAVzIgVBFnZB/AdxQfAJaigCACAFQQ52QfwHcUHwEWooAgBqIAVBBnZB/AdxQfAZaigCAHMgBUH/AXFBAnRB8CFqKAIAanMgAHMiAEEWdkH8B3FB8AlqKAIAIABBDnZB/AdxQfARaigCAGogAEEGdkH8B3FB8BlqKAIAcyAAQf8BcUECdEHwIWooAgBqcyAFcyIFQRZ2QfwHcUHwCWooAgAgBUEOdkH8B3FB8BFqKAIAaiAFQQZ2QfwHcUHwGWooAgBzIAVB/wFxQQJ0QfAhaigCAGpzIABzIgBBFnZB/AdxQfAJaigCACAAQQ52QfwHcUHwEWooAgBqIABBBnZB/AdxQfAZaigCAHMgAEH/AXFBAnRB8CFqKAIAanMgBXMiBUEWdkH8B3FB8AlqKAIAIAVBDnZB/AdxQfARaigCAGogBUEGdkH8B3FB8BlqKAIAcyAFQf8BcUECdEHwIWooAgBqcyAAcyIAQRZ2QfwHcUHwCWooAgAgAEEOdkH8B3FB8BFqKAIAaiAAQQZ2QfwHcUHwGWooAgBzIABB/wFxQQJ0QfAhaigCAGpzIAVzIgVBFnZB/AdxQfAJaigCACAFQQ52QfwHcUHwEWooAgBqIAVBBnZB/AdxQfAZaigCAHMgBUH/AXFBAnRB8CFqKAIAanMgAHMiAEEWdkH8B3FB8AlqKAIAIABBDnZB/AdxQfARaigCAGogAEEGdkH8B3FB8BlqKAIAcyAAQf8BcUECdEHwIWooAgBqcyAFcyIFQRZ2QfwHcUHwCWooAgAgBUEOdkH8B3FB8BFqKAIAaiAFQQZ2QfwHcUHwGWooAgBzIAVB/wFxQQJ0QfAhaigCAGpzIABzIgBBFnZB/AdxQfAJaigCACAAQQ52QfwHcUHwEWooAgBqIABBBnZB/AdxQfAZaigCAHMgAEH/AXFBAnRB8CFqKAIAanMgBXMiBUH/AXFBAnRB8CFqKAIAIQ8gBUEGdkH8B3FB8BlqKAIAIRAgBUEWdkH8B3FB8AlqKAIAIREgBUEOdkH
var hash$2 = "497b89b2" ;
2023-07-09 04:05:21 -06:00
var wasmJson$2 = {
name : name$2 ,
data : data$2 ,
hash : hash$2
} ;
const validateHashCharacters = ( hash ) => {
if ( ! /^\$2[axyb]\$[0-3][0-9]\$[./A-Za-z0-9]{53}$/ . test ( hash ) ) {
return false ;
}
if ( hash [ 4 ] === '0' && parseInt ( hash [ 5 ] , 10 ) < 4 ) {
return false ;
}
if ( hash [ 4 ] === '3' && parseInt ( hash [ 5 ] , 10 ) > 1 ) {
return false ;
}
return true ;
} ;
const validateVerifyOptions = ( options ) => {
if ( ! options || typeof options !== 'object' ) {
throw new Error ( 'Invalid options parameter. It requires an object.' ) ;
}
if ( options . hash === undefined || typeof options . hash !== 'string' ) {
throw new Error ( 'Hash should be specified' ) ;
}
if ( options . hash . length !== 60 ) {
throw new Error ( 'Hash should be 60 bytes long' ) ;
}
if ( ! validateHashCharacters ( options . hash ) ) {
throw new Error ( 'Invalid hash' ) ;
}
options . password = getUInt8Buffer ( options . password ) ;
if ( options . password . length < 1 ) {
throw new Error ( 'Password should be at least 1 byte long' ) ;
}
if ( options . password . length > 72 ) {
throw new Error ( 'Password should be at most 72 bytes long' ) ;
}
} ;
/ * *
* Verifies password using bcrypt password - hashing function
* @ returns True if the encoded hash matches the password
* /
function bcryptVerify ( options ) {
return _ _awaiter ( this , void 0 , void 0 , function * ( ) {
validateVerifyOptions ( options ) ;
const { hash , password } = options ;
const bcryptInterface = yield WASMInterface ( wasmJson$2 , 0 ) ;
bcryptInterface . writeMemory ( getUInt8Buffer ( hash ) , 0 ) ;
const passwordBuffer = getUInt8Buffer ( password ) ;
bcryptInterface . writeMemory ( passwordBuffer , 60 ) ;
return ! ! bcryptInterface . getExports ( ) . bcrypt _verify ( passwordBuffer . length ) ;
} ) ;
}
new Mutex ( ) ;
new Mutex ( ) ;
// Generated using scripts/write-decode-map.ts
var htmlDecodeTree = new Uint16Array (
// prettier-ignore
" \u1d41 < \ xd5\u0131\u028a\u049d\u057b\u05d0\u0675\u06de\u07a2\u07d6\u080f\u0a4a\u0a91\u0da1\u0e6d\u0f09\u0f26\u10ca\u1228\u12e1\u1415\u149d\u14c3\u14df\u1525 \ 0 \ 0 \ 0 \ 0 \ 0 \ 0 \u156b\u16cd\u198d\u1c12\u1ddd\u1f7e\u2060\u21b0\u228d\u23c0\u23fb\u2442\u2824\u2912\u2d08\u2e48\u2fce\u3016\u32ba\u3639\u37ac\u38fe\u3a28\u3a71\u3ae0\u3b2e\u0800EMabcfglmnoprstu \ \ bfms \ x7f \ x84 \ x8b \ x90 \ x95 \ x98 \ xa6 \ xb3 \ xb9 \ xc8 \ xcflig\u803b \ xc6\u40c6P\u803b & \u4026cute\u803b \ xc1\u40c1reve ; \u4102\u0100iyx } rc\u803b \ xc2\u40c2 ; \u4410r ; \uc000\ud835\udd04rave\u803b \ xc0\u40c0pha ; \u4391acr ; \u4100d ; \u6a53\u0100gp \ x9d \ xa1on ; \u4104f ; \uc000\ud835\udd38plyFunction ; \u6061ing\u803b \ xc5\u40c5\u0100cs \ xbe \ xc3r ; \uc000\ud835\udc9cign ; \u6254ilde\u803b \ xc3\u40c3ml\u803b \ xc4\u40c4\u0400aceforsu \ xe5 \ xfb \ xfe\u0117\u011c\u0122\u0127\u012a\u0100cr \ xea \ xf2kslash ; \u6216\u0176 \ xf6 \ xf8 ; \u6ae7ed ; \u6306y ; \u4411\u0180crt\u0105\u010b\u0114ause ; \u6235noullis ; \u612ca ; \u4392r ; \uc000\ud835\udd05pf ; \uc000\ud835\udd39eve ; \u42d8c \ xf2\u0113mpeq ; \u624e\u0700HOacdefhilorsu\u014d\u0151\u0156\u0180\u019e\u01a2\u01b5\u01b7\u01ba\u01dc\u0215\u0273\u0278\u027ecy ; \u4427PY\u803b \ xa9\u40a9\u0180cpy\u015d\u0162\u017aute ; \u4106\u0100 ; i\u0167\u0168\u62d2talDifferentialD ; \u6145leys ; \u612d\u0200aeio\u0189\u018e\u0194\u0198ron ; \u410cdil\u803b \ xc7\u40c7rc ; \u4108nint ; \u6230ot ; \u410a\u0100dn\u01a7\u01adilla ; \u40b8terDot ; \u40b7 \ xf2\u017fi ; \u43a7rcle\u0200DMPT\u01c7\u01cb\u01d1\u01d6ot ; \u6299inus ; \u6296lus ; \u6295imes ; \u6297o\u0100cs\u01e2\u01f8kwiseContourIntegral ; \u6232eCurly\u0100DQ\u0203\u020foubleQuote ; \u601duote ; \u6019\u0200lnpu\u021e\u0228\u0247\u0255on\u0100 ; e\u0225\u0226\u6237 ; \u6a74\u0180git\u022f\u0236\u023aruent ; \u6261nt ; \u622fourIntegral ; \u622e\u0100fr\u024c\u024e ; \u6102oduct ; \u6210nterClockwiseContourIntegral ; \u6233oss ; \u6a2fcr ; \uc000\ud835\udc9ep\u0100 ; C\u0284\u0285\u62d3ap ; \u624d\u0580DJSZacefios\u02a0\u02ac\u02b0\u02b4\u02b8\u02cb\u02d7\u02e1\u02e6\u0333\u048d\u0100 ; o\u0179\u02a5trahd ; \u6911cy ; \u4402cy ; \u4405cy ; \u440f\u0180grs\u02bf\u02c4\u02c7ger ; \u6021r ; \u61a1hv ; \u6ae4\u0100ay\u02d0\u02d5ron ; \u410e ; \u4414l\u0100 ; t\u02dd\u02de\u6207a ; \u4394r ; \uc000\ud835\udd07\u0100af\u02eb\u0327\u0100cm\u02f0\u0322ritical\u0200ADGT\u0300\u0306\u0316\u031ccute ; \u40b4o\u0174\u030b\u030d ; \u42d9bleAcute ; \u42ddrave ; \u4060ilde ; \u42dcond ; \u62c4ferentialD ; \u6146\u0470\u033d \ 0 \ 0 \ 0 \u0342\u0354 \ 0 \u0405f ; \uc000\ud835\udd3b\u0180 ; DE\u0348\u0349\u034d\u40a8ot ; \u60dcqual ; \u6250ble\u0300CDLRUV\u0363\u0372\u0382\u03cf\u03e2\u03f8ontourIntegra \ xec\u0239o\u0274\u0379 \ 0 \ 0 \u037b \ xbb\u0349nArrow ; \u61d3\u0100eo\u0387\u03a4ft\u0180ART\u0390\u0396\u03a1rrow ; \u61d0ightArrow ; \u61d4e \ xe5\u02cang\u0100LR\u03ab\u03c4eft\u0100AR\u03b3\u03b9rrow ; \u67f8ightArrow ; \u67faightArrow ; \u67f9ight\u0100AT\u03d8\u03derrow ; \u61d2ee ; \u62a8p\u0241\u03e9 \ 0 \ 0 \u03efrrow ; \u61d1ownArrow ; \u61d5erticalBar ; \u6225n\u0300ABLRTa\u0412\u042a\u0430\u045e\u047f\u037crrow\u0180 ; BU\u041d\u041e\u0422\u6193ar ; \u6913pArrow ; \u61f5reve ; \u4311eft\u02d2\u043a \ 0 \u0446 \ 0 \u0450ightVector ; \u6950eeVector ; \u695eector\u0100 ; B\u0459\u045a\u61bdar ; \u6956ight\u01d4\u0467 \ 0 \u0471eeVector ; \u695fector\u0100 ; B\u047a\u047b\u61c1ar ; \u6957ee\u0100 ; A\u0486\u0487\u62a4rrow ; \u61a7\u0100ct\u0492\u0497r ; \uc000\ud835\udc9frok ; \u4110\u0800NTacdfglmopqstux\u04bd\u04c0\u04c4\u04cb\u04de\u04e2\u04e7\u04ee\u04f5\u0521\u052f\u0536\u0552\u055d\u0560\u0565G ; \u414aH\u803b \ xd0\u40d0cute\u803b \ xc9\u40c9\u0180aiy\u04d2\u04d7\u04dcron ; \u411arc\u803b \ xca\u40ca ; \u442dot ; \u4116r ; \uc000\ud835\udd08rave\u803b \ xc8\u40c8ement ; \u6208\u0100ap\u04fa\u04fecr ; \u4112ty\u0253\u0506 \ 0 \ 0 \u0512mallSquare ; \u65fberySmallSquare ; \u65ab\u0100gp\u0526\u052aon ; \u4118f ; \uc000\ud835\udd3csilon ; \u4395u\u0100ai\u053c\u0549l\u0100 ; T\u0542\u0543\u6a75ilde ; \u6242librium ; \u61cc\u0100ci\u0557\u055ar ; \u6130m ; \u6a73a ; \u4397ml\u803b \ xcb\u40cb\u0100ip\u056a\u056fsts ; \u6203onentialE ; \u6147\u0280cfios\u0585\u0588\u058d\u05b2\u05ccy ; \u4424r ; \uc000\ud835\udd09lled\u0253\u0597 \ 0 \ 0 \u05a3mallSquare ; \u65fcerySmallSquare ; \u65aa\u0370\u05ba \ 0 \u05bf \ 0 \ 0 \u05c4f ; \uc000\ud835\udd3dAll ; \u6200riertrf ; \u6131c \ xf2\u05cb\u0600JTabcdfgorst\u05e8\u05ec\u05ef\u05fa\u0600\u0612 \ u
. split ( "" )
. map ( ( c ) => c . charCodeAt ( 0 ) ) ) ;
// Generated using scripts/write-decode-map.ts
var xmlDecodeTree = new Uint16Array (
// prettier-ignore
"\u0200aglq\t\x15\x18\x1b\u026d\x0f\0\0\x12p;\u4026os;\u4027t;\u403et;\u403cuot;\u4022"
. split ( "" )
. map ( ( c ) => c . charCodeAt ( 0 ) ) ) ;
// Adapted from https://github.com/mathiasbynens/he/blob/36afe179392226cf1b6ccdb16ebbb7a5a844d93a/src/he.js#L106-L134
var _a ;
const decodeMap = new Map ( [
[ 0 , 65533 ] ,
2024-01-23 11:06:49 -07:00
// C1 Unicode control character reference replacements
2023-07-09 04:05:21 -06:00
[ 128 , 8364 ] ,
[ 130 , 8218 ] ,
[ 131 , 402 ] ,
[ 132 , 8222 ] ,
[ 133 , 8230 ] ,
[ 134 , 8224 ] ,
[ 135 , 8225 ] ,
[ 136 , 710 ] ,
[ 137 , 8240 ] ,
[ 138 , 352 ] ,
[ 139 , 8249 ] ,
[ 140 , 338 ] ,
[ 142 , 381 ] ,
[ 145 , 8216 ] ,
[ 146 , 8217 ] ,
[ 147 , 8220 ] ,
[ 148 , 8221 ] ,
[ 149 , 8226 ] ,
[ 150 , 8211 ] ,
[ 151 , 8212 ] ,
[ 152 , 732 ] ,
[ 153 , 8482 ] ,
[ 154 , 353 ] ,
[ 155 , 8250 ] ,
[ 156 , 339 ] ,
[ 158 , 382 ] ,
[ 159 , 376 ] ,
] ) ;
2024-01-23 11:06:49 -07:00
/ * *
* Polyfill for ` String.fromCodePoint ` . It is used to create a string from a Unicode code point .
* /
2023-07-09 04:05:21 -06:00
const fromCodePoint =
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, node/no-unsupported-features/es-builtins
( _a = String . fromCodePoint ) !== null && _a !== void 0 ? _a : function ( codePoint ) {
let output = "" ;
if ( codePoint > 0xffff ) {
codePoint -= 0x10000 ;
output += String . fromCharCode ( ( ( codePoint >>> 10 ) & 0x3ff ) | 0xd800 ) ;
codePoint = 0xdc00 | ( codePoint & 0x3ff ) ;
}
output += String . fromCharCode ( codePoint ) ;
return output ;
} ;
2024-01-23 11:06:49 -07:00
/ * *
* Replace the given code point with a replacement character if it is a
* surrogate or is outside the valid range . Otherwise return the code
* point unchanged .
* /
2023-07-09 04:05:21 -06:00
function replaceCodePoint ( codePoint ) {
var _a ;
if ( ( codePoint >= 0xd800 && codePoint <= 0xdfff ) || codePoint > 0x10ffff ) {
return 0xfffd ;
}
return ( _a = decodeMap . get ( codePoint ) ) !== null && _a !== void 0 ? _a : codePoint ;
}
var CharCodes ;
( function ( CharCodes ) {
CharCodes [ CharCodes [ "NUM" ] = 35 ] = "NUM" ;
CharCodes [ CharCodes [ "SEMI" ] = 59 ] = "SEMI" ;
2024-01-23 11:06:49 -07:00
CharCodes [ CharCodes [ "EQUALS" ] = 61 ] = "EQUALS" ;
2023-07-09 04:05:21 -06:00
CharCodes [ CharCodes [ "ZERO" ] = 48 ] = "ZERO" ;
CharCodes [ CharCodes [ "NINE" ] = 57 ] = "NINE" ;
CharCodes [ CharCodes [ "LOWER_A" ] = 97 ] = "LOWER_A" ;
CharCodes [ CharCodes [ "LOWER_F" ] = 102 ] = "LOWER_F" ;
CharCodes [ CharCodes [ "LOWER_X" ] = 120 ] = "LOWER_X" ;
2024-01-23 11:06:49 -07:00
CharCodes [ CharCodes [ "LOWER_Z" ] = 122 ] = "LOWER_Z" ;
CharCodes [ CharCodes [ "UPPER_A" ] = 65 ] = "UPPER_A" ;
CharCodes [ CharCodes [ "UPPER_F" ] = 70 ] = "UPPER_F" ;
CharCodes [ CharCodes [ "UPPER_Z" ] = 90 ] = "UPPER_Z" ;
2023-07-09 04:05:21 -06:00
} ) ( CharCodes || ( CharCodes = { } ) ) ;
2024-01-23 11:06:49 -07:00
/** Bit that needs to be set to convert an upper case ASCII character to lower case */
const TO _LOWER _BIT = 0b100000 ;
2023-07-09 04:05:21 -06:00
var BinTrieFlags ;
( function ( BinTrieFlags ) {
BinTrieFlags [ BinTrieFlags [ "VALUE_LENGTH" ] = 49152 ] = "VALUE_LENGTH" ;
BinTrieFlags [ BinTrieFlags [ "BRANCH_LENGTH" ] = 16256 ] = "BRANCH_LENGTH" ;
BinTrieFlags [ BinTrieFlags [ "JUMP_TABLE" ] = 127 ] = "JUMP_TABLE" ;
} ) ( BinTrieFlags || ( BinTrieFlags = { } ) ) ;
2024-01-23 11:06:49 -07:00
function isNumber$1 ( code ) {
return code >= CharCodes . ZERO && code <= CharCodes . NINE ;
}
function isHexadecimalCharacter ( code ) {
return ( ( code >= CharCodes . UPPER _A && code <= CharCodes . UPPER _F ) ||
( code >= CharCodes . LOWER _A && code <= CharCodes . LOWER _F ) ) ;
}
function isAsciiAlphaNumeric ( code ) {
return ( ( code >= CharCodes . UPPER _A && code <= CharCodes . UPPER _Z ) ||
( code >= CharCodes . LOWER _A && code <= CharCodes . LOWER _Z ) ||
isNumber$1 ( code ) ) ;
}
/ * *
* Checks if the given character is a valid end character for an entity in an attribute .
*
* Attribute values that aren 't terminated properly aren' t parsed , and shouldn ' t lead to a parser error .
* See the example in https : //html.spec.whatwg.org/multipage/parsing.html#named-character-reference-state
* /
function isEntityInAttributeInvalidEnd ( code ) {
return code === CharCodes . EQUALS || isAsciiAlphaNumeric ( code ) ;
}
var EntityDecoderState ;
( function ( EntityDecoderState ) {
EntityDecoderState [ EntityDecoderState [ "EntityStart" ] = 0 ] = "EntityStart" ;
EntityDecoderState [ EntityDecoderState [ "NumericStart" ] = 1 ] = "NumericStart" ;
EntityDecoderState [ EntityDecoderState [ "NumericDecimal" ] = 2 ] = "NumericDecimal" ;
EntityDecoderState [ EntityDecoderState [ "NumericHex" ] = 3 ] = "NumericHex" ;
EntityDecoderState [ EntityDecoderState [ "NamedEntity" ] = 4 ] = "NamedEntity" ;
} ) ( EntityDecoderState || ( EntityDecoderState = { } ) ) ;
var DecodingMode ;
( function ( DecodingMode ) {
/** Entities in text nodes that can end with any character. */
DecodingMode [ DecodingMode [ "Legacy" ] = 0 ] = "Legacy" ;
/** Only allow entities terminated with a semicolon. */
DecodingMode [ DecodingMode [ "Strict" ] = 1 ] = "Strict" ;
/** Entities in attributes have limitations on ending characters. */
DecodingMode [ DecodingMode [ "Attribute" ] = 2 ] = "Attribute" ;
} ) ( DecodingMode || ( DecodingMode = { } ) ) ;
/ * *
* Token decoder with support of writing partial entities .
* /
class EntityDecoder {
constructor (
/** The tree used to decode entities. */
decodeTree ,
/ * *
* The function that is called when a codepoint is decoded .
*
* For multi - byte named entities , this will be called multiple times ,
* with the second codepoint , and the same ` consumed ` value .
*
* @ param codepoint The decoded codepoint .
* @ param consumed The number of bytes consumed by the decoder .
* /
emitCodePoint ,
/** An object that is used to produce errors. */
errors ) {
this . decodeTree = decodeTree ;
this . emitCodePoint = emitCodePoint ;
this . errors = errors ;
/** The current state of the decoder. */
this . state = EntityDecoderState . EntityStart ;
/** Characters that were consumed while parsing an entity. */
this . consumed = 1 ;
/ * *
* The result of the entity .
*
* Either the result index of a numeric entity , or the codepoint of a
* numeric entity .
* /
this . result = 0 ;
/** The current index in the decode tree. */
this . treeIndex = 0 ;
/** The number of characters that were consumed in excess. */
this . excess = 1 ;
/** The mode in which the decoder is operating. */
this . decodeMode = DecodingMode . Strict ;
}
/** Resets the instance to make it reusable. */
startEntity ( decodeMode ) {
this . decodeMode = decodeMode ;
this . state = EntityDecoderState . EntityStart ;
this . result = 0 ;
this . treeIndex = 0 ;
this . excess = 1 ;
this . consumed = 1 ;
}
/ * *
* Write an entity to the decoder . This can be called multiple times with partial entities .
* If the entity is incomplete , the decoder will return - 1.
*
* Mirrors the implementation of ` getDecoder ` , but with the ability to stop decoding if the
* entity is incomplete , and resume when the next string is written .
*
* @ param string The string containing the entity ( or a continuation of the entity ) .
* @ param offset The offset at which the entity begins . Should be 0 if this is not the first call .
* @ returns The number of characters that were consumed , or - 1 if the entity is incomplete .
* /
write ( str , offset ) {
switch ( this . state ) {
case EntityDecoderState . EntityStart : {
if ( str . charCodeAt ( offset ) === CharCodes . NUM ) {
this . state = EntityDecoderState . NumericStart ;
this . consumed += 1 ;
return this . stateNumericStart ( str , offset + 1 ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
this . state = EntityDecoderState . NamedEntity ;
return this . stateNamedEntity ( str , offset ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
case EntityDecoderState . NumericStart : {
return this . stateNumericStart ( str , offset ) ;
}
case EntityDecoderState . NumericDecimal : {
return this . stateNumericDecimal ( str , offset ) ;
}
case EntityDecoderState . NumericHex : {
return this . stateNumericHex ( str , offset ) ;
}
case EntityDecoderState . NamedEntity : {
return this . stateNamedEntity ( str , offset ) ;
}
}
}
/ * *
* Switches between the numeric decimal and hexadecimal states .
*
* Equivalent to the ` Numeric character reference state ` in the HTML spec .
*
* @ param str The string containing the entity ( or a continuation of the entity ) .
* @ param offset The current offset .
* @ returns The number of characters that were consumed , or - 1 if the entity is incomplete .
* /
stateNumericStart ( str , offset ) {
if ( offset >= str . length ) {
return - 1 ;
}
if ( ( str . charCodeAt ( offset ) | TO _LOWER _BIT ) === CharCodes . LOWER _X ) {
this . state = EntityDecoderState . NumericHex ;
this . consumed += 1 ;
return this . stateNumericHex ( str , offset + 1 ) ;
}
this . state = EntityDecoderState . NumericDecimal ;
return this . stateNumericDecimal ( str , offset ) ;
}
addToNumericResult ( str , start , end , base ) {
if ( start !== end ) {
const digitCount = end - start ;
this . result =
this . result * Math . pow ( base , digitCount ) +
parseInt ( str . substr ( start , digitCount ) , base ) ;
this . consumed += digitCount ;
}
}
/ * *
* Parses a hexadecimal numeric entity .
*
* Equivalent to the ` Hexademical character reference state ` in the HTML spec .
*
* @ param str The string containing the entity ( or a continuation of the entity ) .
* @ param offset The current offset .
* @ returns The number of characters that were consumed , or - 1 if the entity is incomplete .
* /
stateNumericHex ( str , offset ) {
const startIdx = offset ;
while ( offset < str . length ) {
const char = str . charCodeAt ( offset ) ;
if ( isNumber$1 ( char ) || isHexadecimalCharacter ( char ) ) {
offset += 1 ;
}
else {
this . addToNumericResult ( str , startIdx , offset , 16 ) ;
return this . emitNumericEntity ( char , 3 ) ;
}
}
this . addToNumericResult ( str , startIdx , offset , 16 ) ;
return - 1 ;
}
/ * *
* Parses a decimal numeric entity .
*
* Equivalent to the ` Decimal character reference state ` in the HTML spec .
*
* @ param str The string containing the entity ( or a continuation of the entity ) .
* @ param offset The current offset .
* @ returns The number of characters that were consumed , or - 1 if the entity is incomplete .
* /
stateNumericDecimal ( str , offset ) {
const startIdx = offset ;
while ( offset < str . length ) {
const char = str . charCodeAt ( offset ) ;
if ( isNumber$1 ( char ) ) {
offset += 1 ;
}
else {
this . addToNumericResult ( str , startIdx , offset , 10 ) ;
return this . emitNumericEntity ( char , 2 ) ;
}
}
this . addToNumericResult ( str , startIdx , offset , 10 ) ;
return - 1 ;
}
/ * *
* Validate and emit a numeric entity .
*
* Implements the logic from the ` Hexademical character reference start
* state ` and ` Numeric character reference end state ` in the HTML spec.
*
* @ param lastCp The last code point of the entity . Used to see if the
* entity was terminated with a semicolon .
* @ param expectedLength The minimum number of characters that should be
* consumed . Used to validate that at least one digit
* was consumed .
* @ returns The number of characters that were consumed .
* /
emitNumericEntity ( lastCp , expectedLength ) {
var _a ;
// Ensure we consumed at least one digit.
if ( this . consumed <= expectedLength ) {
( _a = this . errors ) === null || _a === void 0 ? void 0 : _a . absenceOfDigitsInNumericCharacterReference ( this . consumed ) ;
return 0 ;
}
// Figure out if this is a legit end of the entity
if ( lastCp === CharCodes . SEMI ) {
this . consumed += 1 ;
}
else if ( this . decodeMode === DecodingMode . Strict ) {
return 0 ;
}
this . emitCodePoint ( replaceCodePoint ( this . result ) , this . consumed ) ;
if ( this . errors ) {
if ( lastCp !== CharCodes . SEMI ) {
this . errors . missingSemicolonAfterCharacterReference ( ) ;
}
this . errors . validateNumericCharacterReference ( this . result ) ;
}
return this . consumed ;
}
/ * *
* Parses a named entity .
*
* Equivalent to the ` Named character reference state ` in the HTML spec .
*
* @ param str The string containing the entity ( or a continuation of the entity ) .
* @ param offset The current offset .
* @ returns The number of characters that were consumed , or - 1 if the entity is incomplete .
* /
stateNamedEntity ( str , offset ) {
const { decodeTree } = this ;
let current = decodeTree [ this . treeIndex ] ;
// The mask is the number of bytes of the value, including the current byte.
let valueLength = ( current & BinTrieFlags . VALUE _LENGTH ) >> 14 ;
for ( ; offset < str . length ; offset ++ , this . excess ++ ) {
const char = str . charCodeAt ( offset ) ;
this . treeIndex = determineBranch ( decodeTree , current , this . treeIndex + Math . max ( 1 , valueLength ) , char ) ;
if ( this . treeIndex < 0 ) {
return this . result === 0 ||
// If we are parsing an attribute
( this . decodeMode === DecodingMode . Attribute &&
// We shouldn't have consumed any characters after the entity,
( valueLength === 0 ||
// And there should be no invalid characters.
isEntityInAttributeInvalidEnd ( char ) ) )
? 0
: this . emitNotTerminatedNamedEntity ( ) ;
}
current = decodeTree [ this . treeIndex ] ;
valueLength = ( current & BinTrieFlags . VALUE _LENGTH ) >> 14 ;
// If the branch is a value, store it and continue
if ( valueLength !== 0 ) {
// If the entity is terminated by a semicolon, we are done.
if ( char === CharCodes . SEMI ) {
return this . emitNamedEntityData ( this . treeIndex , valueLength , this . consumed + this . excess ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
// If we encounter a non-terminated (legacy) entity while parsing strictly, then ignore it.
if ( this . decodeMode !== DecodingMode . Strict ) {
this . result = this . treeIndex ;
this . consumed += this . excess ;
this . excess = 0 ;
}
}
}
return - 1 ;
}
/ * *
* Emit a named entity that was not terminated with a semicolon .
*
* @ returns The number of characters consumed .
* /
emitNotTerminatedNamedEntity ( ) {
var _a ;
const { result , decodeTree } = this ;
const valueLength = ( decodeTree [ result ] & BinTrieFlags . VALUE _LENGTH ) >> 14 ;
this . emitNamedEntityData ( result , valueLength , this . consumed ) ;
( _a = this . errors ) === null || _a === void 0 ? void 0 : _a . missingSemicolonAfterCharacterReference ( ) ;
return this . consumed ;
}
/ * *
* Emit a named entity .
*
* @ param result The index of the entity in the decode tree .
* @ param valueLength The number of bytes in the entity .
* @ param consumed The number of characters consumed .
*
* @ returns The number of characters consumed .
* /
emitNamedEntityData ( result , valueLength , consumed ) {
const { decodeTree } = this ;
this . emitCodePoint ( valueLength === 1
? decodeTree [ result ] & ~ BinTrieFlags . VALUE _LENGTH
: decodeTree [ result + 1 ] , consumed ) ;
if ( valueLength === 3 ) {
// For multi-byte values, we need to emit the second byte.
this . emitCodePoint ( decodeTree [ result + 2 ] , consumed ) ;
}
return consumed ;
}
/ * *
* Signal to the parser that the end of the input was reached .
*
* Remaining data will be emitted and relevant errors will be produced .
*
* @ returns The number of characters consumed .
* /
end ( ) {
var _a ;
switch ( this . state ) {
case EntityDecoderState . NamedEntity : {
// Emit a named entity if we have one.
return this . result !== 0 &&
( this . decodeMode !== DecodingMode . Attribute ||
this . result === this . treeIndex )
? this . emitNotTerminatedNamedEntity ( )
: 0 ;
}
// Otherwise, emit a numeric entity if we have one.
case EntityDecoderState . NumericDecimal : {
return this . emitNumericEntity ( 0 , 2 ) ;
}
case EntityDecoderState . NumericHex : {
return this . emitNumericEntity ( 0 , 3 ) ;
}
case EntityDecoderState . NumericStart : {
( _a = this . errors ) === null || _a === void 0 ? void 0 : _a . absenceOfDigitsInNumericCharacterReference ( this . consumed ) ;
return 0 ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
case EntityDecoderState . EntityStart : {
// Return 0 if we have no entity.
return 0 ;
2023-07-09 04:05:21 -06:00
}
}
2024-01-23 11:06:49 -07:00
}
}
/ * *
* Creates a function that decodes entities in a string .
*
* @ param decodeTree The decode tree .
* @ returns A function that decodes entities in a string .
* /
function getDecoder ( decodeTree ) {
let ret = "" ;
const decoder = new EntityDecoder ( decodeTree , ( str ) => ( ret += fromCodePoint ( str ) ) ) ;
return function decodeWithTrie ( str , decodeMode ) {
let lastIndex = 0 ;
let offset = 0 ;
while ( ( offset = str . indexOf ( "&" , offset ) ) >= 0 ) {
ret += str . slice ( lastIndex , offset ) ;
decoder . startEntity ( decodeMode ) ;
const len = decoder . write ( str ,
// Skip the "&"
offset + 1 ) ;
if ( len < 0 ) {
lastIndex = offset + decoder . end ( ) ;
break ;
}
lastIndex = offset + len ;
// If `len` is 0, skip the current `&` and continue.
offset = len === 0 ? lastIndex + 1 : lastIndex ;
}
const result = ret + str . slice ( lastIndex ) ;
// Make sure we don't keep a reference to the final string.
ret = "" ;
return result ;
2023-07-09 04:05:21 -06:00
} ;
}
2024-01-23 11:06:49 -07:00
/ * *
* Determines the branch of the current node that is taken given the current
* character . This function is used to traverse the trie .
*
* @ param decodeTree The trie .
* @ param current The current node .
* @ param nodeIdx The index right after the current node and its value .
* @ param char The current character .
* @ returns The index of the next node , or - 1 if no branch is taken .
* /
2023-07-09 04:05:21 -06:00
function determineBranch ( decodeTree , current , nodeIdx , char ) {
const branchCount = ( current & BinTrieFlags . BRANCH _LENGTH ) >> 7 ;
const jumpOffset = current & BinTrieFlags . JUMP _TABLE ;
// Case 1: Single branch encoded in jump offset
if ( branchCount === 0 ) {
return jumpOffset !== 0 && char === jumpOffset ? nodeIdx : - 1 ;
}
// Case 2: Multiple branches encoded in jump table
if ( jumpOffset ) {
const value = char - jumpOffset ;
return value < 0 || value >= branchCount
? - 1
: decodeTree [ nodeIdx + value ] - 1 ;
}
// Case 3: Multiple branches encoded in dictionary
// Binary search for the character.
let lo = nodeIdx ;
let hi = lo + branchCount - 1 ;
while ( lo <= hi ) {
const mid = ( lo + hi ) >>> 1 ;
const midVal = decodeTree [ mid ] ;
if ( midVal < char ) {
lo = mid + 1 ;
}
else if ( midVal > char ) {
hi = mid - 1 ;
}
else {
return decodeTree [ mid + branchCount ] ;
}
}
return - 1 ;
}
const htmlDecoder = getDecoder ( htmlDecodeTree ) ;
const xmlDecoder = getDecoder ( xmlDecodeTree ) ;
/ * *
2024-01-23 11:06:49 -07:00
* Decodes an HTML string .
2023-07-09 04:05:21 -06:00
*
* @ param str The string to decode .
2024-01-23 11:06:49 -07:00
* @ param mode The decoding mode .
2023-07-09 04:05:21 -06:00
* @ returns The decoded string .
* /
2024-01-23 11:06:49 -07:00
function decodeHTML ( str , mode = DecodingMode . Legacy ) {
return htmlDecoder ( str , mode ) ;
2023-07-09 04:05:21 -06:00
}
/ * *
2024-01-23 11:06:49 -07:00
* Decodes an XML string , requiring all entities to be terminated by a semicolon .
2023-07-09 04:05:21 -06:00
*
* @ param str The string to decode .
* @ returns The decoded string .
* /
function decodeXML ( str ) {
2024-01-23 11:06:49 -07:00
return xmlDecoder ( str , DecodingMode . Strict ) ;
2023-07-09 04:05:21 -06:00
}
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* @ module verifications
* @ ignore
* /
/ * *
2024-02-01 09:06:40 -07:00
* Check if string contains the proof
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } data - Data potentially containing the proof
* @ param { import ( './types' ) . VerificationParams } params - Verification parameters
* @ returns { Promise < boolean > } Whether the proof was found in the string
2023-07-09 04:05:21 -06:00
* /
const containsProof = async ( data , params ) => {
const fingerprintFormatted = generateClaim ( params . target , params . claimFormat ) ;
const fingerprintURI = generateClaim ( params . target , ClaimFormat . URI ) ;
let result = false ;
// Decode eventual special entities
switch ( params . proofEncodingFormat ) {
case EntityEncodingFormat . HTML :
data = decodeHTML ( data ) ;
break
case EntityEncodingFormat . XML :
data = decodeXML ( data ) ;
break
case EntityEncodingFormat . PLAIN :
}
data = decodeHTML ( data ) ;
// Check for plaintext proof
result = data
// remove newlines and carriage returns
. replace ( /\r?\n|\r/g , '' )
// remove spaces
. replace ( /\s/g , '' )
// normalize
. toLowerCase ( )
// search for fingerprint
. indexOf ( fingerprintFormatted . toLowerCase ( ) ) !== - 1 ;
// Check for hashed proof
if ( ! result ) {
const hashRe = /\$(argon2(?:id|d|i)|2a|2b|2y)(?:\$[a-zA-Z0-9=+\-,./]+)+/g ;
let match ;
while ( ! result && ( match = hashRe . exec ( data ) ) != null ) {
let timeoutHandle ;
const timeoutPromise = new Promise ( ( resolve , reject ) => {
timeoutHandle = setTimeout (
( ) => {
resolve ( false ) ;
} , 1000
) ;
} ) ;
switch ( match [ 1 ] ) {
case '2a' :
case '2b' :
case '2y' :
try {
// Patch until promise.race properly works on WASM
if ( parseInt ( match [ 0 ] . split ( '$' ) [ 2 ] ) > 12 ) continue
const hashPromise = bcryptVerify ( {
2023-09-22 03:00:36 -06:00
password : fingerprintURI . toLowerCase ( ) ,
2023-07-09 04:05:21 -06:00
hash : match [ 0 ]
} )
. then ( result => result )
. catch ( _ => false ) ;
result = await Promise . race ( [ hashPromise , timeoutPromise ] ) . then ( ( result ) => {
clearTimeout ( timeoutHandle ) ;
return result
} ) ;
} catch ( err ) {
result = false ;
}
2023-09-22 03:00:36 -06:00
// Accept mixed-case fingerprints until deadline
if ( ! result ) {
try {
// Patch until promise.race properly works on WASM
if ( parseInt ( match [ 0 ] . split ( '$' ) [ 2 ] ) > 12 ) continue
const hashPromise = bcryptVerify ( {
password : fingerprintURI ,
hash : match [ 0 ]
} )
. then ( result => result )
. catch ( _ => false ) ;
result = await Promise . race ( [ hashPromise , timeoutPromise ] ) . then ( ( result ) => {
clearTimeout ( timeoutHandle ) ;
return result
} ) ;
} catch ( err ) {
result = false ;
}
}
2023-07-09 04:05:21 -06:00
break
case 'argon2' :
case 'argon2i' :
case 'argon2d' :
case 'argon2id' :
try {
const hashPromise = argon2Verify ( {
2023-09-22 03:00:36 -06:00
password : fingerprintURI . toLowerCase ( ) ,
2023-07-09 04:05:21 -06:00
hash : match [ 0 ]
} )
. then ( result => result )
. catch ( _ => false ) ;
result = await Promise . race ( [ hashPromise , timeoutPromise ] ) . then ( ( result ) => {
clearTimeout ( timeoutHandle ) ;
return result
} ) ;
} catch ( err ) {
result = false ;
}
2023-09-22 03:00:36 -06:00
// Accept mixed-case fingerprints until deadline
if ( ! result ) {
try {
const hashPromise = argon2Verify ( {
password : fingerprintURI ,
hash : match [ 0 ]
} )
. then ( result => result )
. catch ( _ => false ) ;
result = await Promise . race ( [ hashPromise , timeoutPromise ] ) . then ( ( result ) => {
clearTimeout ( timeoutHandle ) ;
return result
} ) ;
} catch ( err ) {
result = false ;
}
}
2023-07-09 04:05:21 -06:00
break
}
}
}
// Check for HTTP proof
if ( ! result ) {
const uris = getUriFromString ( data ) ;
for ( let index = 0 ; index < uris . length ; index ++ ) {
if ( result ) continue
const candidate = uris [ index ] ;
/** @type {URL} */
let candidateURL ;
try {
candidateURL = new URL ( candidate ) ;
} catch ( _ ) {
continue
}
if ( candidateURL . protocol !== 'https:' ) {
continue
}
// Using fetch -> axios doesn't find the ariadne-identity-proof header
/** @type {Response} */
const response = await fetch ( candidate , {
method : 'HEAD'
} )
. catch ( e => {
return undefined
} ) ;
if ( ! response ) continue
if ( response . status !== 200 ) continue
if ( ! response . headers . get ( 'ariadne-identity-proof' ) ) continue
result = response . headers . get ( 'ariadne-identity-proof' )
. toLowerCase ( )
. indexOf ( fingerprintURI . toLowerCase ( ) ) !== - 1 ;
}
}
return result
} ;
/ * *
2024-02-01 09:06:40 -07:00
* Run a JSON object through the verification process
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { * } proofData - Data potentially containing the proof
* @ param { Array < string > } checkPath - Paths to check for proof
* @ param { import ( './types' ) . VerificationParams } params - Verification parameters
* @ returns { Promise < boolean > } Whether the proof was found in the object
2023-07-09 04:05:21 -06:00
* /
const runJSON = async ( proofData , checkPath , params ) => {
if ( ! proofData ) {
return false
}
if ( Array . isArray ( proofData ) ) {
let result = false ;
for ( let index = 0 ; index < proofData . length ; index ++ ) {
const item = proofData [ index ] ;
if ( result ) {
continue
}
result = await runJSON ( item , checkPath , params ) ;
}
return result
}
if ( checkPath . length === 0 ) {
switch ( params . claimRelation ) {
case ClaimRelation . ONEOF :
return await containsProof ( proofData . join ( '|' ) , params )
case ClaimRelation . CONTAINS :
case ClaimRelation . EQUALS :
default :
return await containsProof ( proofData , params )
}
}
if ( typeof proofData === 'object' && ! ( checkPath [ 0 ] in proofData ) ) {
throw new Error ( 'err_json_structure_incorrect' )
}
return await runJSON (
proofData [ checkPath [ 0 ] ] ,
checkPath . slice ( 1 ) ,
params
)
} ;
/ * *
2024-02-01 09:06:40 -07:00
* Run the verification by searching for the proof in the fetched data
* @ param { object } proofData - The proof data
* @ param { ServiceProvider } claimData - The claim data
* @ param { string } fingerprint - The fingerprint
* @ returns { Promise < import ( './types' ) . VerificationResult > } Result of the verification
2023-07-09 04:05:21 -06:00
* /
async function run ( proofData , claimData , fingerprint ) {
2024-02-01 09:06:40 -07:00
/** @type {import('./types').VerificationResult} */
2023-07-09 04:05:21 -06:00
const res = {
result : false ,
completed : false ,
errors : [ ]
} ;
switch ( claimData . proof . response . format ) {
case ProofFormat . JSON :
for ( let index = 0 ; index < claimData . proof . target . length ; index ++ ) {
const claimMethod = claimData . proof . target [ index ] ;
try {
res . result = res . result || await runJSON (
proofData ,
claimMethod . path ,
{
target : fingerprint ,
claimFormat : claimMethod . format ,
proofEncodingFormat : claimMethod . encoding ,
claimRelation : claimMethod . relation
}
) ;
} catch ( error ) {
res . errors . push ( error . message ? error . message : error ) ;
}
}
res . completed = true ;
break
case ProofFormat . TEXT :
for ( let index = 0 ; index < claimData . proof . target . length ; index ++ ) {
const claimMethod = claimData . proof . target [ index ] ;
try {
res . result = res . result || await containsProof (
proofData ,
{
target : fingerprint ,
claimFormat : claimMethod . format ,
proofEncodingFormat : claimMethod . encoding ,
claimRelation : claimMethod . relation
}
) ;
} catch ( error ) {
res . errors . push ( 'err_unknown_text_verification' ) ;
}
}
res . completed = true ;
break
}
// Reset the errors if one of the claim methods was successful
if ( res . result ) {
res . errors = [ ] ;
}
return res
}
var verifications = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
run : run
} ) ;
/ *
2024-02-01 09:06:40 -07:00
Copyright 2024 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
2024-02-01 09:06:40 -07:00
* ASPE service provider ( { @ link https : //docs.keyoxide.org/service-providers/aspe/|Keyoxide docs})
* @ module serviceProviders / aspe
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . activitypub . processURI ( 'aspe:domain.example:abc123def456' ) ;
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
const reURI$o = /^aspe:([a-zA-Z0-9.\-_]*):([a-zA-Z0-9]*)/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$o ( uri ) {
const match = uri . match ( reURI$o ) ;
2024-01-23 11:06:49 -07:00
if ( ! isFQDN ( match [ 1 ] ) ) {
return null
}
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2024-01-23 11:06:49 -07:00
id : 'aspe' ,
name : 'ASPE'
2023-07-09 04:05:21 -06:00
} ,
profile : {
2024-02-01 09:06:40 -07:00
display : uri ,
2024-01-23 11:06:49 -07:00
uri ,
2023-07-09 04:05:21 -06:00
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$o . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : null ,
2024-01-23 11:06:49 -07:00
fetcher : Fetcher . ASPE ,
accessRestriction : ProofAccessRestriction . NONE ,
2023-07-09 04:05:21 -06:00
data : {
2024-01-23 11:06:49 -07:00
aspeUri : uri
2023-07-09 04:05:21 -06:00
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
2024-01-23 11:06:49 -07:00
path : [ 'claims' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$o = [
2023-07-09 04:05:21 -06:00
{
2024-01-23 11:06:49 -07:00
uri : 'aspe:domain.tld:abc123def456' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'aspe:domain.tld' ,
shouldMatch : false
2023-07-09 04:05:21 -06:00
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'dns:domain.tld' ,
shouldMatch : false
} ,
{
uri : 'https://domain.tld' ,
2023-07-09 04:05:21 -06:00
shouldMatch : false
}
] ;
2024-01-23 11:06:49 -07:00
var aspe = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$o ,
reURI : reURI$o ,
tests : tests$o
2023-07-09 04:05:21 -06:00
} ) ;
/ *
2024-01-23 11:06:49 -07:00
Copyright 2024 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* OpenPGP service provider ( { @ link https : //docs.keyoxide.org/service-providers/openpgp/|Keyoxide docs})
* @ module serviceProviders / openpgp
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . openpgp . processURI ( 'openpgp4fpr:ABC123DEF456' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$n = /^(.*)/ ;
const reURIHkp = /^openpgp4fpr:(?:0x)?([a-zA-Z0-9.\-_]*)/ ;
const reURIWkdDirect = /^https:\/\/(.*)\/.well-known\/openpgpkey\/hu\/([a-zA-Z0-9]*)(?:\?l=(.*))?/ ;
const reURIWkdAdvanced = /^https:\/\/(openpgpkey.*)\/.well-known\/openpgpkey\/(.*)\/hu\/([a-zA-Z0-9]*)(?:\?l=(.*))?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$n ( uri ) {
2024-01-23 11:06:49 -07:00
let reURI = null ;
let mode = null ;
let match = null ;
if ( reURIHkp . test ( uri ) ) {
reURI = reURIHkp ;
mode = OpenPgpQueryProtocol . HKP ;
match = uri . match ( reURI ) ;
}
if ( ! mode && reURIWkdAdvanced . test ( uri ) ) {
reURI = reURIWkdAdvanced ;
mode = OpenPgpQueryProtocol . WKD ;
match = uri . match ( reURI ) ;
}
if ( ! mode && reURIWkdDirect . test ( uri ) ) {
reURI = reURIWkdDirect ;
mode = OpenPgpQueryProtocol . WKD ;
match = uri . match ( reURI ) ;
}
let output = null ;
switch ( mode ) {
case OpenPgpQueryProtocol . HKP :
output = new ServiceProvider ( {
about : {
id : 'openpgp' ,
name : 'OpenPGP'
} ,
profile : {
display : ` openpgp4fpr: ${ match [ 1 ] } ` ,
uri : ` https://keys.openpgp.org/search?q= ${ match [ 1 ] } ` ,
qr : null
} ,
claim : {
uriRegularExpression : reURI . toString ( ) ,
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : ` https://keys.openpgp.org/vks/v1/by-fingerprint/ ${ match [ 1 ] . toUpperCase ( ) } ` ,
fetcher : Fetcher . OPENPGP ,
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : ` https://keys.openpgp.org/vks/v1/by-fingerprint/ ${ match [ 1 ] . toUpperCase ( ) } ` ,
protocol : OpenPgpQueryProtocol . HKP
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'notations' , 'proof@ariadne.id' ]
} ]
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
} ) ;
break
case OpenPgpQueryProtocol . WKD :
output = new ServiceProvider ( {
about : {
id : 'openpgp' ,
name : 'OpenPGP'
} ,
profile : {
display : 'unknown fingerprint' ,
uri ,
qr : null
} ,
claim : {
uriRegularExpression : reURI . toString ( ) ,
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
fetcher : Fetcher . OPENPGP ,
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : uri ,
protocol : OpenPgpQueryProtocol . WKD
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'notations' , 'proof@ariadne.id' ]
} ]
}
} ) ;
break
}
return output
2023-07-09 04:05:21 -06:00
}
2024-02-01 09:06:40 -07:00
const tests$n = [
2023-07-09 04:05:21 -06:00
{
2024-01-23 11:06:49 -07:00
uri : 'openpgp4fpr:123456789' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'openpgp4fpr:abcdef123' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'https://openpgpkey.domain.tld/.well-known/openpgpkey/domain.tld/hu/123abc456def?l=name' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'https://openpgpkey.domain.tld/.well-known/openpgpkey/domain.tld/hu/123abc456def' ,
shouldMatch : true
} ,
{
uri : 'https://domain.tld/.well-known/openpgpkey/hu/123abc456def?l=name' ,
shouldMatch : true
} ,
{
uri : 'https://domain.tld/.well-known/openpgpkey/hu/123abc456def' ,
shouldMatch : true
} ,
// The following will not pass .processURI, but reURI currently accepts anything
{
uri : 'https://domain.tld' ,
shouldMatch : true
} ,
{
uri : 'https://openpgpkey.domain.tld/.well-known/openpgpkey/hu/123abc456def?l=name' ,
shouldMatch : true
} ,
{
uri : 'https://domain.tld/.well-known/openpgpkey/123abc456def?l=name' ,
shouldMatch : true
2023-07-09 04:05:21 -06:00
}
] ;
2024-01-23 11:06:49 -07:00
var openpgp$1 = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$n ,
reURI : reURI$n ,
tests : tests$n
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* DNS service provider ( { @ link https : //docs.keyoxide.org/service-providers/dns/|Keyoxide docs})
* @ module serviceProviders / dns
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . dns . processURI ( 'dns:domain.example?type=TXT' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$m = /^dns:([a-zA-Z0-9.\-_]*)(?:\?(.*))?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$m ( uri ) {
const match = uri . match ( reURI$m ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2024-01-23 11:06:49 -07:00
id : 'dns' ,
name : 'DNS'
2023-07-09 04:05:21 -06:00
} ,
profile : {
2024-01-23 11:06:49 -07:00
display : match [ 1 ] ,
uri : ` https:// ${ match [ 1 ] } ` ,
qr : null
2023-07-09 04:05:21 -06:00
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$m . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : null ,
2024-01-23 11:06:49 -07:00
fetcher : Fetcher . DNS ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . SERVER ,
data : {
2024-01-23 11:06:49 -07:00
domain : match [ 1 ]
2023-07-09 04:05:21 -06:00
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
2024-01-23 11:06:49 -07:00
path : [ 'records' , 'txt' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$m = [
2023-07-09 04:05:21 -06:00
{
2024-01-23 11:06:49 -07:00
uri : 'dns:domain.org' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2024-01-23 11:06:49 -07:00
uri : 'dns:domain.org?type=TXT' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org' ,
shouldMatch : false
}
] ;
var dns = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$m ,
reURI : reURI$m ,
tests : tests$m
2024-01-23 11:06:49 -07:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* IRC service provider ( { @ link https : //docs.keyoxide.org/service-providers/irc/|Keyoxide docs})
* @ module serviceProviders / irc
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . irc . processURI ( 'irc://domain.example/alice' ) ;
* /
2024-01-23 11:06:49 -07:00
2024-02-01 09:06:40 -07:00
const reURI$l = /^irc:\/\/(.*)\/([a-zA-Z0-9\-[\]\\`_^{|}]*)/ ;
2024-01-23 11:06:49 -07:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2024-01-23 11:06:49 -07:00
* /
2024-02-01 09:06:40 -07:00
function processURI$l ( uri ) {
const match = uri . match ( reURI$l ) ;
2024-01-23 11:06:49 -07:00
return new ServiceProvider ( {
about : {
id : 'irc' ,
name : 'IRC'
} ,
profile : {
display : ` ${ match [ 1 ] } / ${ match [ 2 ] } ` ,
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$l . toString ( ) ,
2024-01-23 11:06:49 -07:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : null ,
fetcher : Fetcher . IRC ,
accessRestriction : ProofAccessRestriction . SERVER ,
data : {
domain : match [ 1 ] ,
nick : match [ 2 ]
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$l = [
2024-01-23 11:06:49 -07:00
{
uri : 'irc://chat.ircserver.org/Alice1' ,
shouldMatch : true
} ,
{
uri : 'irc://chat.ircserver.org/alice?param=123' ,
shouldMatch : true
} ,
{
uri : 'irc://chat.ircserver.org/alice_bob' ,
shouldMatch : true
} ,
{
uri : 'https://chat.ircserver.org/alice' ,
shouldMatch : false
}
] ;
var irc = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$l ,
reURI : reURI$l ,
tests : tests$l
2024-01-23 11:06:49 -07:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* XMPP service provider ( { @ link https : //docs.keyoxide.org/service-providers/xmpp/|Keyoxide docs})
* @ module serviceProviders / xmpp
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . xmpp . processURI ( 'xmpp:alice@domain.example' ) ;
* /
2024-01-23 11:06:49 -07:00
2024-02-01 09:06:40 -07:00
const reURI$k = /^xmpp:([a-zA-Z0-9.\-_]*)@([a-zA-Z0-9.\-_]*)(?:\?(.*))?/ ;
2024-01-23 11:06:49 -07:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2024-01-23 11:06:49 -07:00
* /
2024-02-01 09:06:40 -07:00
function processURI$k ( uri ) {
const match = uri . match ( reURI$k ) ;
2024-01-23 11:06:49 -07:00
return new ServiceProvider ( {
about : {
id : 'xmpp' ,
name : 'XMPP' ,
homepage : 'https://xmpp.org'
} ,
profile : {
display : ` ${ match [ 1 ] } @ ${ match [ 2 ] } ` ,
uri ,
qr : uri
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$k . toString ( ) ,
2024-01-23 11:06:49 -07:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : null ,
fetcher : Fetcher . XMPP ,
accessRestriction : ProofAccessRestriction . SERVER ,
data : {
id : ` ${ match [ 1 ] } @ ${ match [ 2 ] } `
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$k = [
2024-01-23 11:06:49 -07:00
{
uri : 'xmpp:alice@domain.org' ,
shouldMatch : true
} ,
{
uri : 'xmpp:alice@domain.org?omemo-sid-123456789=A1B2C3D4E5F6G7H8I9' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
uri : 'https://domain.org' ,
shouldMatch : false
}
] ;
var xmpp = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$k ,
reURI : reURI$k ,
tests : tests$k
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Matrix service provider ( { @ link https : //docs.keyoxide.org/service-providers/matrix/|Keyoxide docs})
* @ module serviceProviders / matrix
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . matrix . processURI ( 'matrix:u/...' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$j = /^matrix:u\/(?:@)?([^@:]*:[^?]*)(\?.*)?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$j ( uri ) {
const match = uri . match ( reURI$j ) ;
2023-07-09 04:05:21 -06:00
if ( ! match [ 2 ] ) {
return null
}
const params = new URLSearchParams ( match [ 2 ] ) ;
if ( ! ( params . has ( 'org.keyoxide.e' ) && params . has ( 'org.keyoxide.r' ) ) ) {
return null
}
const paramRoomId = ` ${ params . get ( 'org.keyoxide.r' ) [ 0 ] !== '!' ? '!' : '' } ${ params . get ( 'org.keyoxide.r' ) } ` ;
const paramEventId = ` ${ params . get ( 'org.keyoxide.e' ) [ 0 ] !== '$' ? '$' : '' } ${ params . get ( 'org.keyoxide.e' ) } ` ;
const profileUrl = ` https://matrix.to/#/@ ${ match [ 1 ] } ` ;
const eventUrl = ` https://matrix.to/#/ ${ paramRoomId } / ${ paramEventId } ` ;
return new ServiceProvider ( {
about : {
id : 'matrix' ,
name : 'Matrix' ,
homepage : 'https://matrix.org'
} ,
profile : {
display : ` @ ${ match [ 1 ] } ` ,
uri : profileUrl ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$j . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : eventUrl ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . MATRIX ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . GRANTED ,
data : {
eventId : paramEventId ,
roomId : paramRoomId
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'content' , 'body' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$j = [
2023-07-09 04:05:21 -06:00
{
uri :
'matrix:u/alice:matrix.domain.org?org.keyoxide.r=123:domain.org&org.keyoxide.e=123' ,
shouldMatch : true
} ,
{
uri : 'matrix:u/alice:matrix.domain.org' ,
shouldMatch : true
} ,
{
uri :
'matrix:u/@alice:matrix.domain.org?org.keyoxide.r=!123:domain.org&org.keyoxide.e=$123' ,
shouldMatch : true
} ,
{
uri : 'xmpp:alice@domain.org' ,
shouldMatch : false
} ,
{
uri : 'https://domain.org/@alice' ,
shouldMatch : false
}
] ;
var matrix = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$j ,
reURI : reURI$j ,
tests : tests$j
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2022 Maximilian Siling
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Telegram service provider ( { @ link https : //docs.keyoxide.org/service-providers/telegram/|Keyoxide docs})
* @ module serviceProviders / telegram
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . telegram . processURI ( 'https://t.me/alice?proof=mygroup' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$i = /https:\/\/t.me\/([A-Za-z0-9_]{5,32})\?proof=([A-Za-z0-9_]{5,32})/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$i ( uri ) {
const match = uri . match ( reURI$i ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'telegram' ,
name : 'Telegram' ,
homepage : 'https://telegram.org'
} ,
profile : {
display : ` @ ${ match [ 1 ] } ` ,
uri : ` https://t.me/ ${ match [ 1 ] } ` ,
qr : ` https://t.me/ ${ match [ 1 ] } `
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$i . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : ` https://t.me/ ${ match [ 2 ] } ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . TELEGRAM ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . GRANTED ,
data : {
user : match [ 1 ] ,
chat : match [ 2 ]
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'text' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$i = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://t.me/alice?proof=foobar' ,
shouldMatch : true
} ,
{
uri : 'https://t.me/complex_user_1234?proof=complex_chat_1234' ,
shouldMatch : true
} ,
{
uri : 'https://t.me/foobar' ,
shouldMatch : false
} ,
{
uri : 'https://t.me/foobar?proof=' ,
shouldMatch : false
} ,
{
uri : 'https://t.me/?proof=foobar' ,
shouldMatch : false
}
] ;
var telegram = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$i ,
reURI : reURI$i ,
tests : tests$i
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Twitter service provider ( { @ link https : //docs.keyoxide.org/service-providers/twitter/|Keyoxide docs})
* @ module serviceProviders / twitter
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . twitter . processURI ( 'https://twitter.com/alice/status/123456789' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$h = /^https:\/\/twitter\.com\/(.*)\/status\/([0-9]*)(?:\?.*)?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$h ( uri ) {
const match = uri . match ( reURI$h ) ;
2023-07-09 04:05:21 -06:00
const urlsp = new URLSearchParams ( ) ;
urlsp . set ( 'url' , match [ 0 ] ) ;
urlsp . set ( 'omit_script' , '1' ) ;
return new ServiceProvider ( {
about : {
id : 'twitter' ,
name : 'Twitter' ,
homepage : 'https://twitter.com'
} ,
profile : {
display : ` @ ${ match [ 1 ] } ` ,
uri : ` https://twitter.com/ ${ match [ 1 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$h . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
// Returns an oembed json object with the tweet content in html form
url : ` https://publish.twitter.com/oembed? ${ urlsp } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'html' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$h = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://twitter.com/alice/status/1234567890123456789' ,
shouldMatch : true
} ,
{
uri : 'https://twitter.com/alice/status/1234567890123456789/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/status/1234567890123456789' ,
shouldMatch : false
}
] ;
var twitter = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$h ,
reURI : reURI$h ,
tests : tests$h
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Reddit service provider ( { @ link https : //docs.keyoxide.org/service-providers/reddit/|Keyoxide docs})
* @ module serviceProviders / reddit
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . reddit . processURI ( 'https://reddit.com/...' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$g = /^https:\/\/(?:www\.)?reddit\.com\/user\/(.*)\/comments\/(.*)\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$g ( uri ) {
const match = uri . match ( reURI$g ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'reddit' ,
name : 'Reddit' ,
homepage : 'https://reddit.com'
} ,
profile : {
display : match [ 1 ] ,
uri : ` https://www.reddit.com/user/ ${ match [ 1 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$g . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
url : ` https://www.reddit.com/user/ ${ match [ 1 ] } /comments/ ${ match [ 2 ] } .json ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'data' , 'children' , 'data' , 'selftext' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$g = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://www.reddit.com/user/Alice/comments/123456/post' ,
shouldMatch : true
} ,
{
uri : 'https://www.reddit.com/user/Alice/comments/123456/post/' ,
shouldMatch : true
} ,
{
uri : 'https://reddit.com/user/Alice/comments/123456/post' ,
shouldMatch : true
} ,
{
uri : 'https://reddit.com/user/Alice/comments/123456/post/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/user/Alice/comments/123456/post' ,
shouldMatch : false
}
] ;
var reddit = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$g ,
reURI : reURI$g ,
tests : tests$g
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Liberapay service provider ( { @ link https : //docs.keyoxide.org/service-providers/liberapay/|Keyoxide docs})
* @ module serviceProviders / liberapay
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . liberapay . processURI ( 'https://liberapay.com/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$f = /^https:\/\/liberapay\.com\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$f ( uri ) {
const match = uri . match ( reURI$f ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'liberapay' ,
name : 'Liberapay' ,
homepage : 'https://liberapay.com'
} ,
profile : {
display : match [ 1 ] ,
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$f . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : ` https://liberapay.com/ ${ match [ 1 ] } /public.json ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'statements' , 'content' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$f = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://liberapay.com/alice' ,
shouldMatch : true
} ,
{
uri : 'https://liberapay.com/alice/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice' ,
shouldMatch : false
}
] ;
var liberapay = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$f ,
reURI : reURI$f ,
tests : tests$f
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Lichess service provider ( { @ link https : //docs.keyoxide.org/service-providers/lichess/|Keyoxide docs})
* @ module serviceProviders / lichess
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . lichess . processURI ( 'https://lichess.org/@/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$e = /^https:\/\/lichess\.org\/@\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$e ( uri ) {
const match = uri . match ( reURI$e ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-10-03 04:05:09 -06:00
id : 'lichess' ,
name : 'Lichess' ,
homepage : 'https://lichess.org'
2023-07-09 04:05:21 -06:00
} ,
profile : {
display : match [ 1 ] ,
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$e . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : ` https://lichess.org/api/user/ ${ match [ 1 ] } ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : ` https://lichess.org/api/user/ ${ match [ 1 ] } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . FINGERPRINT ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'profile' , 'links' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$e = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://lichess.org/@/Alice' ,
shouldMatch : true
} ,
{
uri : 'https://lichess.org/@/Alice/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/@/Alice' ,
shouldMatch : false
}
] ;
var lichess = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$e ,
reURI : reURI$e ,
tests : tests$e
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Hackernews service provider ( { @ link https : //docs.keyoxide.org/service-providers/hackernews/|Keyoxide docs})
* @ module serviceProviders / hackernews
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . hackernews . processURI ( 'https://news.ycombinator.com/user?id=alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$d = /^https:\/\/news\.ycombinator\.com\/user\?id=(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$d ( uri ) {
const match = uri . match ( reURI$d ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'hackernews' ,
name : 'Hacker News' ,
homepage : 'https://news.ycombinator.com'
} ,
profile : {
display : match [ 1 ] ,
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$d . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri : ` https://hacker-news.firebaseio.com/v0/user/ ${ match [ 1 ] } .json ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
url : ` https://hacker-news.firebaseio.com/v0/user/ ${ match [ 1 ] } .json ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . HTML ,
relation : ClaimRelation . CONTAINS ,
path : [ 'about' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$d = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://news.ycombinator.com/user?id=Alice' ,
shouldMatch : true
} ,
{
uri : 'https://news.ycombinator.com/user?id=Alice/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/user?id=Alice' ,
shouldMatch : false
}
] ;
var hackernews = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$d ,
reURI : reURI$d ,
tests : tests$d
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Lobste . rs service provider ( { @ link https : //docs.keyoxide.org/service-providers/lobsters/|Keyoxide docs})
* @ module serviceProviders / lobsters
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . lobsters . processURI ( 'https://lobste.rs/~alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$c = /^https:\/\/lobste\.rs\/(?:~|u\/)(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$c ( uri ) {
const match = uri . match ( reURI$c ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'lobsters' ,
name : 'Lobsters' ,
homepage : 'https://lobste.rs'
} ,
profile : {
display : match [ 1 ] ,
2023-10-09 08:28:23 -06:00
uri : ` https://lobste.rs/~ ${ match [ 1 ] } ` ,
2023-07-09 04:05:21 -06:00
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$c . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
2023-10-09 08:28:23 -06:00
uri : ` https://lobste.rs/~ ${ match [ 1 ] } .json ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
2023-10-09 08:28:23 -06:00
url : ` https://lobste.rs/~ ${ match [ 1 ] } .json ` ,
2023-07-09 04:05:21 -06:00
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'about' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$c = [
2023-10-09 08:28:23 -06:00
{
uri : 'https://lobste.rs/~Alice' ,
shouldMatch : true
} ,
2023-07-09 04:05:21 -06:00
{
uri : 'https://lobste.rs/u/Alice' ,
shouldMatch : true
} ,
{
uri : 'https://lobste.rs/u/Alice/' ,
shouldMatch : true
} ,
2023-10-09 08:28:23 -06:00
{
uri : 'https://domain.org/~Alice' ,
shouldMatch : false
} ,
2023-07-09 04:05:21 -06:00
{
uri : 'https://domain.org/u/Alice' ,
shouldMatch : false
}
] ;
var lobsters = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$c ,
reURI : reURI$c ,
tests : tests$c
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Forem service provider ( { @ link https : //docs.keyoxide.org/service-providers/forem/|Keyoxide docs})
* @ module serviceProviders / forem
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . forem . processURI ( 'https://domain.example/alice/title' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$b = /^https:\/\/(.*)\/(.*)\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$b ( uri ) {
const match = uri . match ( reURI$b ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'forem' ,
name : 'Forem' ,
homepage : 'https://www.forem.com'
} ,
profile : {
display : ` ${ match [ 2 ] } @ ${ match [ 1 ] } ` ,
uri : ` https:// ${ match [ 1 ] } / ${ match [ 2 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$b . toString ( ) . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
uri ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
url : ` https:// ${ match [ 1 ] } /api/articles/ ${ match [ 2 ] } / ${ match [ 3 ] } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'body_markdown' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$b = [
2023-07-09 04:05:21 -06:00
{
uri : 'https://domain.org/alice/post' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/post/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice' ,
shouldMatch : false
}
] ;
var forem = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$b ,
reURI : reURI$b ,
tests : tests$b
2023-09-23 02:16:41 -06:00
} ) ;
/ *
Copyright 2023 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Forgejo service provider ( { @ link https : //docs.keyoxide.org/service-providers/forgejo/|Keyoxide docs})
* @ module serviceProviders / forgejo
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . forgejo . processURI ( 'https://domain.example/alice/repo' ) ;
* /
2023-09-23 02:16:41 -06:00
2024-02-01 09:06:40 -07:00
const reURI$a = /^https:\/\/(.*)\/(.*)\/(.*)\/?/ ;
2023-09-23 02:16:41 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-09-23 02:16:41 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$a ( uri ) {
const match = uri . match ( reURI$a ) ;
2023-09-23 02:16:41 -06:00
return new ServiceProvider ( {
about : {
id : 'forgejo' ,
name : 'Forgejo' ,
homepage : 'https://forgejo.org'
} ,
profile : {
display : ` ${ match [ 2 ] } @ ${ match [ 1 ] } ` ,
uri : ` https:// ${ match [ 1 ] } / ${ match [ 2 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$a . toString ( ) ,
2023-09-23 02:16:41 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
uri ,
fetcher : Fetcher . HTTP ,
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
url : ` https:// ${ match [ 1 ] } /api/v1/repos/ ${ match [ 2 ] } / ${ match [ 3 ] } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'description' ]
} ]
}
} )
}
const functions$1 = {
validate : async ( /** @type {ServiceProvider} */ claimData , proofData , opts ) => {
const url = ` https:// ${ new URL ( claimData . proof . request . uri ) . hostname } /api/forgejo/v1/version ` ;
const forgejoData = await fetcher _ _namespace . http . fn ( { url , format : ProofFormat . JSON } , opts ) ;
return forgejoData && 'version' in forgejoData
}
} ;
2024-02-01 09:06:40 -07:00
const tests$a = [
2023-09-23 02:16:41 -06:00
{
uri : 'https://domain.org/alice/forgejo_proof' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/forgejo_proof/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/other_proof' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice' ,
shouldMatch : false
}
] ;
var forgejo = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
functions : functions$1 ,
processURI : processURI$a ,
reURI : reURI$a ,
tests : tests$a
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Gitea service provider ( { @ link https : //docs.keyoxide.org/service-providers/gitea/|Keyoxide docs})
* @ module serviceProviders / gitea
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . gitea . processURI ( 'https://domain.example/alice/repo' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$9 = /^https:\/\/(.*)\/(.*)\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$9 ( uri ) {
const match = uri . match ( reURI$9 ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
id : 'gitea' ,
name : 'Gitea' ,
homepage : 'https://about.gitea.com'
} ,
profile : {
2023-09-21 06:49:15 -06:00
display : ` ${ match [ 2 ] } @ ${ match [ 1 ] } ` ,
uri : ` https:// ${ match [ 1 ] } / ${ match [ 2 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$9 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
uri ,
fetcher : Fetcher . HTTP ,
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
url : ` https:// ${ match [ 1 ] } /api/v1/repos/ ${ match [ 2 ] } / ${ match [ 3 ] } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'description' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$9 = [
2023-09-21 06:49:15 -06:00
{
uri : 'https://domain.org/alice/gitea_proof' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/gitea_proof/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/other_proof' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice' ,
shouldMatch : false
}
] ;
var gitea = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$9 ,
reURI : reURI$9 ,
tests : tests$9
2023-09-21 06:49:15 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Gitlab service provider ( { @ link https : //docs.keyoxide.org/service-providers/gitlab/|Keyoxide docs})
* @ module serviceProviders / gitlab
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . gitlab . processURI ( 'https://domain.example/alice/repo' ) ;
* /
2023-09-21 06:49:15 -06:00
2024-02-01 09:06:40 -07:00
const reURI$8 = /^https:\/\/(.*)\/(.*)\/gitlab_proof\/?/ ;
2023-09-21 06:49:15 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-09-21 06:49:15 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$8 ( uri ) {
const match = uri . match ( reURI$8 ) ;
2023-09-21 06:49:15 -06:00
return new ServiceProvider ( {
about : {
id : 'gitlab' ,
name : 'GitLab' ,
homepage : 'https://about.gitlab.com'
} ,
profile : {
display : ` ${ match [ 2 ] } @ ${ match [ 1 ] } ` ,
uri : ` https:// ${ match [ 1 ] } / ${ match [ 2 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$8 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
fetcher : Fetcher . HTTP ,
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : ` https:// ${ match [ 1 ] } /api/v4/projects/ ${ match [ 2 ] } %2Fgitlab_proof ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'description' ]
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$8 = [
2023-09-21 06:49:15 -06:00
{
uri : 'https://gitlab.domain.org/alice/gitlab_proof' ,
shouldMatch : true
} ,
{
uri : 'https://gitlab.domain.org/alice/gitlab_proof/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/alice/other_proof' ,
shouldMatch : false
}
] ;
var gitlab = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$8 ,
reURI : reURI$8 ,
tests : tests$8
2023-09-21 06:49:15 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Github service provider ( { @ link https : //docs.keyoxide.org/service-providers/github/|Keyoxide docs})
* @ module serviceProviders / github
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . github . processURI ( 'https://gist.github.com/alice/title' ) ;
* /
2023-09-21 06:49:15 -06:00
2024-02-01 09:06:40 -07:00
const reURI$7 = /^https:\/\/gist\.github\.com\/(.*)\/(.*)\/?/ ;
2023-09-21 06:49:15 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-09-21 06:49:15 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$7 ( uri ) {
const match = uri . match ( reURI$7 ) ;
2023-09-21 06:49:15 -06:00
return new ServiceProvider ( {
about : {
id : 'github' ,
name : 'GitHub' ,
homepage : 'https://github.com'
} ,
profile : {
display : match [ 1 ] ,
uri : ` https://github.com/ ${ match [ 1 ] } ` ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$7 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
fetcher : Fetcher . HTTP ,
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : ` https://api.github.com/gists/ ${ match [ 2 ] } ` ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
2023-10-09 08:28:23 -06:00
target : [
{
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'files' , 'proof.md' , 'content' ]
} ,
{
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'files' , 'openpgp.md' , 'content' ]
}
]
2023-09-21 06:49:15 -06:00
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$7 = [
2023-09-21 06:49:15 -06:00
{
uri : 'https://gist.github.com/Alice/123456789' ,
shouldMatch : true
} ,
{
uri : 'https://gist.github.com/Alice/123456789/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/Alice/123456789' ,
shouldMatch : false
}
] ;
var github = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$7 ,
reURI : reURI$7 ,
tests : tests$7
2023-09-21 06:49:15 -06:00
} ) ;
/ *
Copyright 2022 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* ActivityPub service provider ( { @ link https : //docs.keyoxide.org/service-providers/activitypub/|Keyoxide docs})
* @ module serviceProviders / activitypub
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . activitypub . processURI ( 'https://domain.example/@alice' ) ;
* /
2023-09-21 06:49:15 -06:00
2024-02-01 09:06:40 -07:00
const reURI$6 = /^https:\/\/(.*)\/?/ ;
2023-09-21 06:49:15 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-09-21 06:49:15 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$6 ( uri ) {
2023-09-21 06:49:15 -06:00
return new ServiceProvider ( {
about : {
id : 'activitypub' ,
name : 'ActivityPub' ,
homepage : 'https://activitypub.rocks'
} ,
profile : {
display : uri ,
uri ,
2023-07-09 04:05:21 -06:00
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$6 . toString ( ) . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
uri ,
2023-09-21 06:49:15 -06:00
fetcher : Fetcher . ACTIVITYPUB ,
accessRestriction : ProofAccessRestriction . NONE ,
2023-07-09 04:05:21 -06:00
data : {
2023-09-21 06:49:15 -06:00
url : uri
2023-07-09 04:05:21 -06:00
}
} ,
response : {
format : ProofFormat . JSON
} ,
2023-09-21 06:49:15 -06:00
target : [
{
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'summary' ]
} ,
{
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'attachment' , 'value' ]
} ,
{
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'content' ]
}
]
2023-07-09 04:05:21 -06:00
}
} )
}
2023-09-21 06:49:15 -06:00
const functions = {
postprocess : async ( /** @type {ServiceProvider} */ claimData , proofData , opts ) => {
switch ( proofData . result . type ) {
case 'Note' : {
claimData . profile . uri = proofData . result . attributedTo ;
claimData . profile . display = proofData . result . attributedTo ;
const personData = await fetcher _ _namespace . activitypub . fn ( { url : proofData . result . attributedTo } , opts )
. catch ( _ => null ) ;
if ( personData ) {
claimData . profile . display = ` @ ${ personData . preferredUsername } @ ${ new URL ( claimData . proof . request . uri ) . hostname } ` ;
}
break
}
case 'Person' :
claimData . profile . display = ` @ ${ proofData . result . preferredUsername } @ ${ new URL ( claimData . proof . request . uri ) . hostname } ` ;
break
}
// Attempt to fetch and process the instance's NodeInfo data
const nodeinfo = await _processNodeinfo ( new URL ( claimData . proof . request . uri ) . hostname ) ;
if ( nodeinfo ) {
claimData . about . name = nodeinfo . software . name ;
claimData . about . id = nodeinfo . software . name ;
claimData . about . homepage = nodeinfo . software . homepage ;
}
return { claimData , proofData }
}
} ;
const _processNodeinfo = async ( /** @type {string} */ domain ) => {
const nodeinfoRef = await fetch ( ` https:// ${ domain } /.well-known/nodeinfo ` )
. then ( res => {
if ( res . status !== 200 ) {
throw new Error ( 'HTTP Status was not 200' )
}
return res . json ( )
} )
. catch ( _ => {
return null
} ) ;
if ( ! nodeinfoRef ) return null
// NodeInfo version 2.1
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
const nodeinfo = nodeinfoRef . links . find ( x => { return x . rel === 'http://nodeinfo.diaspora.software/ns/schema/2.1' } ) ;
if ( nodeinfo ) {
return await fetch ( nodeinfo . href )
. then ( res => {
if ( res . status !== 200 ) {
throw new Error ( 'HTTP Status was not 200' )
}
return res . json ( )
} )
. then ( res => {
return {
software : {
name : res . software . name ,
version : res . software . version ,
homepage : res . software . homepage || 'https://activitypub.rocks'
}
}
} )
. catch ( _ => {
return null
} )
}
}
// NodeInfo version 2.0
{
const nodeinfo = nodeinfoRef . links . find ( x => { return x . rel === 'http://nodeinfo.diaspora.software/ns/schema/2.0' } ) ;
if ( nodeinfo ) {
return await fetch ( nodeinfo . href )
. then ( res => {
if ( res . status !== 200 ) {
throw new Error ( 'HTTP Status was not 200' )
}
return res . json ( )
} )
. then ( res => {
return {
software : {
name : res . software . name ,
version : res . software . version ,
homepage : 'https://activitypub.rocks'
}
}
} )
. catch ( _ => {
return null
} )
}
}
// NodeInfo version 1.1
{
const nodeinfo = nodeinfoRef . links . find ( x => { return x . rel === 'http://nodeinfo.diaspora.software/ns/schema/1.1' } ) ;
if ( nodeinfo ) {
return await fetch ( nodeinfo . href )
. then ( res => {
if ( res . status !== 200 ) {
throw new Error ( 'HTTP Status was not 200' )
}
return res . json ( )
} )
. then ( res => {
return {
software : {
name : res . software . name ,
version : res . software . version ,
homepage : 'https://activitypub.rocks'
}
}
} )
. catch ( _ => {
return null
} )
}
}
// NodeInfo version 1.0
{
const nodeinfo = nodeinfoRef . links . find ( x => { return x . rel === 'http://nodeinfo.diaspora.software/ns/schema/1.0' } ) ;
if ( nodeinfo ) {
return await fetch ( nodeinfo . href )
. then ( res => {
if ( res . status !== 200 ) {
throw new Error ( 'HTTP Status was not 200' )
}
return res . json ( )
} )
. then ( res => {
return {
software : {
name : res . software . name ,
version : res . software . version ,
homepage : 'https://activitypub.rocks'
}
}
} )
. catch ( _ => {
return null
} )
}
}
} ;
2024-02-01 09:06:40 -07:00
const tests$6 = [
2023-09-21 06:49:15 -06:00
{
uri : 'https://domain.org' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/@/alice/' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/@alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/@alice/123456' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/u/alice/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/users/alice/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/users/alice/123456' ,
shouldMatch : true
} ,
{
uri : 'http://domain.org/alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : false
}
] ;
2023-09-21 06:49:15 -06:00
var activitypub = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2023-09-21 06:49:15 -06:00
functions : functions ,
2024-02-01 09:06:40 -07:00
processURI : processURI$6 ,
reURI : reURI$6 ,
tests : tests$6
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Discourse service provider ( { @ link https : //docs.keyoxide.org/service-providers/discourse/|Keyoxide docs})
* @ module serviceProviders / discourse
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . activitypub . processURI ( 'https://domain.example/u/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$5 = /^https:\/\/(.*)\/u\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$5 ( uri ) {
const match = uri . match ( reURI$5 ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-09-21 06:49:15 -06:00
id : 'discourse' ,
name : 'Discourse' ,
homepage : 'https://www.discourse.org'
2023-07-09 04:05:21 -06:00
} ,
profile : {
display : ` ${ match [ 2 ] } @ ${ match [ 1 ] } ` ,
2023-09-21 06:49:15 -06:00
uri ,
2023-07-09 04:05:21 -06:00
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$5 . toString ( ) . toString ( ) ,
2023-07-09 04:05:21 -06:00
uriIsAmbiguous : true
} ,
proof : {
request : {
2023-09-21 06:49:15 -06:00
uri ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-09-21 06:49:15 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
2023-07-09 04:05:21 -06:00
data : {
2023-09-21 06:49:15 -06:00
url : ` https:// ${ match [ 1 ] } /u/ ${ match [ 2 ] } .json ` ,
2023-07-09 04:05:21 -06:00
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
2023-09-21 06:49:15 -06:00
relation : ClaimRelation . CONTAINS ,
path : [ 'user' , 'bio_raw' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$5 = [
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/u/alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/u/alice/' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : false
}
] ;
2023-09-21 06:49:15 -06:00
var discourse = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$5 ,
reURI : reURI$5 ,
tests : tests$5
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Owncast service provider ( { @ link https : //docs.keyoxide.org/service-providers/owncast/|Keyoxide docs})
* @ module serviceProviders / owncast
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . owncast . processURI ( 'https://domain.example' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$4 = /^https:\/\/(.*)/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$4 ( uri ) {
const match = uri . match ( reURI$4 ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-09-21 06:49:15 -06:00
id : 'owncast' ,
name : 'Owncast' ,
homepage : 'https://owncast.online'
2023-07-09 04:05:21 -06:00
} ,
profile : {
display : match [ 1 ] ,
2023-09-21 06:49:15 -06:00
uri ,
2023-07-09 04:05:21 -06:00
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$4 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : true
2023-07-09 04:05:21 -06:00
} ,
proof : {
request : {
2023-09-21 06:49:15 -06:00
uri : ` ${ uri } /api/config ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NONE ,
data : {
2023-09-21 06:49:15 -06:00
url : ` ${ uri } /api/config ` ,
2023-07-09 04:05:21 -06:00
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
2023-09-21 06:49:15 -06:00
format : ClaimFormat . FINGERPRINT ,
2023-07-09 04:05:21 -06:00
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
2023-09-21 06:49:15 -06:00
path : [ 'socialHandles' , 'url' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$4 = [
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
uri : 'https://live.domain.org' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://live.domain.org/' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/live' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/live/' ,
shouldMatch : true
2023-07-09 04:05:21 -06:00
}
] ;
2023-09-21 06:49:15 -06:00
var owncast = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$4 ,
reURI : reURI$4 ,
tests : tests$4
2023-07-09 04:05:21 -06:00
} ) ;
/ *
Copyright 2022 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* StackExchange service provider ( { @ link https : //docs.keyoxide.org/service-providers/stackexchange/|Keyoxide docs})
* @ module serviceProviders / stackexchange
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . stackexchange . processURI ( 'https://stackoverflow.com/users/123/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$3 = /^https:\/\/(.*(?:askubuntu|mathoverflow|serverfault|stackapps|stackoverflow|superuser)|.+\.stackexchange)\.com\/users\/(\d+)/ ;
2023-09-21 06:49:15 -06:00
const reStackExchange = /\.stackexchange$/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$3 ( uri ) {
const [ , domain , id ] = uri . match ( reURI$3 ) ;
2023-09-21 06:49:15 -06:00
const site = domain . replace ( reStackExchange , '' ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-09-21 06:49:15 -06:00
id : 'stackexchange' ,
name : 'Stack Exchange' ,
homepage : 'https://stackexchange.com'
2023-07-09 04:05:21 -06:00
} ,
profile : {
2023-09-21 06:49:15 -06:00
display : ` ${ id } @ ${ site } ` ,
2023-07-09 04:05:21 -06:00
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$3 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : false
2023-07-09 04:05:21 -06:00
} ,
proof : {
request : {
2023-09-21 06:49:15 -06:00
uri : ` https:// ${ domain } .com/users/ ${ id } ?tab=profile ` ,
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NONE ,
data : {
2023-09-21 06:49:15 -06:00
url : ` https://api.stackexchange.com/2.3/users/ ${ id } ?site= ${ site } &filter=!AH)b5JqVyImf ` ,
format : ProofFormat . JSON
2023-07-09 04:05:21 -06:00
}
} ,
response : {
format : ProofFormat . JSON
} ,
2023-09-21 06:49:15 -06:00
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'items' , 'about_me' ]
} ]
2023-09-18 09:46:54 -06:00
}
2023-09-21 06:49:15 -06:00
} )
}
2023-09-18 09:46:54 -06:00
2024-02-01 09:06:40 -07:00
const tests$3 = [
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
uri : 'https://stackoverflow.com/users/1234' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://stackoverflow.com/users/1234/alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://stackoverflow.com/users/1234?tab=topactivity' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://stackoverflow.com/users/1234/alice?tab=profile' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://meta.stackoverflow.com/users/1234' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://pt.stackoverflow.com/users/1234' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://pt.meta.stackoverflow.com/users/1234' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://serverfault.com/users/1234' ,
shouldMatch : true
} ,
{
uri : 'https://meta.stackexchange.com/users/1234' ,
shouldMatch : true
} ,
{
uri : 'https://gaming.meta.stackexchange.com/users/1234' ,
shouldMatch : true
} ,
{
uri : 'https://stackexchange.com/users/1234' ,
shouldMatch : false
} ,
{
uri : 'https://domain.com/users/1234' ,
shouldMatch : false
} ,
{
uri : 'https://meta.domain.com/users/1234' ,
2023-07-09 04:05:21 -06:00
shouldMatch : false
}
2023-09-21 06:49:15 -06:00
2023-07-09 04:05:21 -06:00
] ;
2023-09-21 06:49:15 -06:00
var stackexchange = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$3 ,
reURI : reURI$3 ,
tests : tests$3
2023-07-09 04:05:21 -06:00
} ) ;
/ *
2023-09-21 06:49:15 -06:00
Copyright 2023 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* Keybase service provider ( { @ link https : //docs.keyoxide.org/service-providers/keybase/|Keyoxide docs})
* @ module serviceProviders / keybase
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . keybase . processURI ( 'https://keybase.io/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$2 = /^https:\/\/keybase.io\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$2 ( uri ) {
const match = uri . match ( reURI$2 ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-10-03 04:05:09 -06:00
id : 'keybase' ,
name : 'keybase' ,
homepage : 'https://keybase.io'
2023-07-09 04:05:21 -06:00
} ,
profile : {
2023-09-21 06:49:15 -06:00
display : match [ 1 ] ,
2023-07-09 04:05:21 -06:00
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$2 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : false
2023-07-09 04:05:21 -06:00
} ,
proof : {
request : {
2023-09-21 06:49:15 -06:00
uri : ` https://keybase.io/_/api/1.0/user/lookup.json?username= ${ match [ 1 ] } ` ,
2023-07-10 03:46:53 -06:00
fetcher : Fetcher . HTTP ,
2023-07-09 04:05:21 -06:00
accessRestriction : ProofAccessRestriction . NOCORS ,
data : {
2023-09-21 06:49:15 -06:00
url : ` https://keybase.io/_/api/1.0/user/lookup.json?username= ${ match [ 1 ] } ` ,
2023-07-09 04:05:21 -06:00
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
2023-09-21 06:49:15 -06:00
format : ClaimFormat . FINGERPRINT ,
2023-07-09 04:05:21 -06:00
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
2023-09-21 06:49:15 -06:00
path : [ 'them' , 'public_keys' , 'primary' , 'key_fingerprint' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$2 = [
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
uri : 'https://keybase.io/Alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://keybase.io/Alice/' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/Alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : false
}
] ;
2023-09-21 06:49:15 -06:00
var keybase = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2024-02-01 09:06:40 -07:00
processURI : processURI$2 ,
reURI : reURI$2 ,
tests : tests$2
2023-07-09 04:05:21 -06:00
} ) ;
/ *
2023-09-21 06:49:15 -06:00
Copyright 2023 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
2024-02-01 09:06:40 -07:00
/ * *
* OpenCollective service provider ( { @ link https : //docs.keyoxide.org/service-providers/opencollective/|Keyoxide docs})
* @ module serviceProviders / opencollective
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . opencollective . processURI ( 'https://opencollective.com/alice' ) ;
* /
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
const reURI$1 = /^https:\/\/opencollective\.com\/(.*)\/?/ ;
2023-07-09 04:05:21 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
function processURI$1 ( uri ) {
const match = uri . match ( reURI$1 ) ;
2023-07-09 04:05:21 -06:00
return new ServiceProvider ( {
about : {
2023-09-21 06:49:15 -06:00
id : 'opencollective' ,
name : 'Open Collective' ,
homepage : 'https://opencollective.com'
2023-07-09 04:05:21 -06:00
} ,
profile : {
display : match [ 1 ] ,
uri ,
qr : null
} ,
claim : {
2024-02-01 09:06:40 -07:00
uriRegularExpression : reURI$1 . toString ( ) ,
2023-09-21 06:49:15 -06:00
uriIsAmbiguous : false
2023-07-09 04:05:21 -06:00
} ,
proof : {
request : {
2023-09-21 06:49:15 -06:00
uri ,
fetcher : Fetcher . GRAPHQL ,
accessRestriction : ProofAccessRestriction . NOCORS ,
2023-07-09 04:05:21 -06:00
data : {
2023-09-21 06:49:15 -06:00
url : 'https://api.opencollective.com/graphql/v2' ,
query : ` { "query": "query { account(slug: \\ " ${ match [ 1 ] } \\ ") { longDescription } }" } `
2023-07-09 04:05:21 -06:00
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
2023-09-21 06:49:15 -06:00
format : ClaimFormat . URI ,
2023-07-09 04:05:21 -06:00
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
2023-09-21 06:49:15 -06:00
path : [ 'data' , 'account' , 'longDescription' ]
2023-07-09 04:05:21 -06:00
} ]
}
} )
}
2024-02-01 09:06:40 -07:00
const tests$1 = [
2023-07-09 04:05:21 -06:00
{
2023-09-21 06:49:15 -06:00
uri : 'https://opencollective.com/Alice' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://opencollective.com/Alice/' ,
2023-07-09 04:05:21 -06:00
shouldMatch : true
} ,
{
2023-09-21 06:49:15 -06:00
uri : 'https://domain.org/Alice' ,
shouldMatch : false
}
] ;
var opencollective = /*#__PURE__*/ Object . freeze ( {
2024-02-01 09:06:40 -07:00
_ _proto _ _ : null ,
processURI : processURI$1 ,
reURI : reURI$1 ,
tests : tests$1
} ) ;
/ *
Copyright 2023 Tim Haase
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* ORCiD service provider ( { @ link https : //docs.keyoxide.org/service-providers/orcid/|Keyoxide docs})
* @ module serviceProviders / orcid
* @ example
* import { ServiceProviderDefinitions } from 'doipjs' ;
* const sp = ServiceProviderDefinitions . data . orcid . processURI ( 'https://orcid.org/123-456-789-123' ) ;
* /
const reURI = /^https:\/\/orcid\.org\/(.*)\/?/ ;
/ * *
* @ function
* @ param { string } uri - Claim URI to process
* @ returns { ServiceProvider } The service provider information based on the claim URI
* /
function processURI ( uri ) {
const match = uri . match ( reURI ) ;
return new ServiceProvider ( {
about : {
id : 'orcid' ,
name : 'ORCiD' ,
homepage : 'https://orcid.org/'
} ,
profile : {
display : match [ 1 ] ,
uri ,
qr : null
} ,
claim : {
uriRegularExpression : reURI . toString ( ) ,
uriIsAmbiguous : false
} ,
proof : {
request : {
uri ,
fetcher : Fetcher . HTTP ,
accessRestriction : ProofAccessRestriction . NONE ,
data : {
url : uri ,
format : ProofFormat . JSON
}
} ,
response : {
format : ProofFormat . JSON
} ,
target : [ {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . CONTAINS ,
path : [ 'person' , 'biography' , 'content' ]
} , {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'person' , 'researcher-urls' , 'researcher-url' , 'url' , 'value' ]
} , {
format : ClaimFormat . URI ,
encoding : EntityEncodingFormat . PLAIN ,
relation : ClaimRelation . EQUALS ,
path : [ 'person' , 'keywords' , 'keyword' , 'content' ]
} ]
}
} )
}
const tests = [
{
uri : 'https://orcid.org/0000-0000-0000-0000' ,
shouldMatch : true
} ,
{
uri : 'https://orcid.org/0000-0000-0000-0000/' ,
shouldMatch : true
} ,
{
uri : 'https://domain.org/0000-0000-0000-0000' ,
shouldMatch : false
}
] ;
var orcid = /*#__PURE__*/ Object . freeze ( {
2023-09-21 06:49:15 -06:00
_ _proto _ _ : null ,
processURI : processURI ,
reURI : reURI ,
tests : tests
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
const _data = {
2024-01-23 11:06:49 -07:00
aspe ,
openpgp : openpgp$1 ,
2023-09-21 06:49:15 -06:00
dns ,
irc ,
xmpp ,
matrix ,
telegram ,
twitter ,
reddit ,
liberapay ,
lichess ,
hackernews ,
lobsters ,
forem ,
2023-09-23 02:16:41 -06:00
forgejo ,
2023-09-21 06:49:15 -06:00
gitea ,
gitlab ,
github ,
activitypub ,
discourse ,
owncast ,
stackexchange ,
keybase ,
2024-02-01 09:06:40 -07:00
opencollective ,
orcid
2023-09-21 06:49:15 -06:00
} ;
const list = Object . keys ( _data ) ;
var index = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
data : _data ,
list : list
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* Contains default values
* @ module defaults
* /
/ * *
2024-02-01 09:06:40 -07:00
* The default claim verification config used throughout the library
* @ type { import ( './types' ) . VerificationConfig }
2023-09-21 06:49:15 -06:00
* /
const opts = {
proxy : {
hostname : null ,
policy : ProxyPolicy . NEVER
2023-07-09 04:05:21 -06:00
} ,
2023-09-21 06:49:15 -06:00
claims : {
activitypub : {
url : null ,
privateKey : null
} ,
irc : {
nick : null
} ,
matrix : {
instance : null ,
accessToken : null
} ,
telegram : {
token : null
} ,
xmpp : {
service : null ,
username : null ,
password : null
}
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var defaults$2 = /*#__PURE__*/ Object . freeze ( {
2023-07-09 04:05:21 -06:00
_ _proto _ _ : null ,
2023-09-21 06:49:15 -06:00
opts : opts
2023-07-09 04:05:21 -06:00
} ) ;
/ *
2023-09-21 06:49:15 -06:00
Copyright 2021 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
2023-09-21 06:49:15 -06:00
* @ class
* @ classdesc Identity claim
* @ property { string } uri - The claim ' s URI
* @ property { string } fingerprint - The fingerprint to verify the claim against
* @ property { number } status - The current status code of the claim
* @ property { Array < object > } matches - The claim definitions matched against the URI
2024-02-01 09:06:40 -07:00
* @ example
* const claim = doip . Claim ( ) ;
* const claim = doip . Claim ( 'dns:domain.tld?type=TXT' ) ;
* const claim = doip . Claim ( 'dns:domain.tld?type=TXT' , '123abc123abc' ) ;
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
class Claim {
/ * *
* Initialize a Claim object
* @ param { string } [ uri ] - The URI of the identity claim
* @ param { string } [ fingerprint ] - The fingerprint of the OpenPGP key
* /
constructor ( uri , fingerprint ) {
// Verify validity of URI
if ( uri && ! validUrlExports . isUri ( uri ) ) {
throw new Error ( 'Invalid URI' )
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// Verify validity of fingerprint
if ( fingerprint ) {
try {
// @ts-ignore
_default . default ( fingerprint ) ;
} catch ( err ) {
throw new Error ( 'Invalid fingerprint' )
}
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
* @ type { string }
* /
this . _uri = uri || '' ;
/ * *
* @ type { string }
* /
this . _fingerprint = fingerprint || '' ;
/ * *
* @ type { number }
* /
this . _status = ClaimStatus . INIT ;
/ * *
2024-02-01 09:06:40 -07:00
* @ type { Array < ServiceProvider > }
2023-09-21 06:49:15 -06:00
* /
this . _matches = [ ] ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
* @ function
2024-02-01 09:06:40 -07:00
* @ param { * } claimObject - JSON representation of a claim
* @ returns { Claim } Parsed claim
* @ throws Will throw an error if the JSON object can ' t be coerced into a Claim
2023-09-21 06:49:15 -06:00
* @ example
* doip . Claim . fromJSON ( JSON . stringify ( claim ) ) ;
* /
static fromJSON ( claimObject ) {
/** @type {Claim} */
let claim ;
let result ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( typeof claimObject === 'object' && 'claimVersion' in claimObject ) {
switch ( claimObject . claimVersion ) {
case 1 :
result = importJsonClaimVersion1 ( claimObject ) ;
if ( result instanceof Error ) {
throw result
}
claim = result ;
break
case 2 :
result = importJsonClaimVersion2 ( claimObject ) ;
if ( result instanceof Error ) {
throw result
}
claim = result ;
break
default :
throw new Error ( 'Invalid claim version' )
}
}
return claim
}
get uri ( ) {
return this . _uri
}
get fingerprint ( ) {
return this . _fingerprint
}
get status ( ) {
return this . _status
}
get matches ( ) {
if ( this . _status === ClaimStatus . INIT ) {
throw new Error ( 'This claim has not yet been matched' )
}
return this . _matches
}
set uri ( uri ) {
if ( this . _status !== ClaimStatus . INIT ) {
throw new Error (
'Cannot change the URI, this claim has already been matched'
)
}
// Verify validity of URI
if ( uri . length > 0 && ! validUrlExports . isUri ( uri ) ) {
throw new Error ( 'The URI was invalid' )
}
// Remove leading and trailing spaces
uri = uri . replace ( /^\s+|\s+$/g , '' ) ;
this . _uri = uri ;
}
set fingerprint ( fingerprint ) {
if ( this . _status === ClaimStatus . VERIFIED ) {
throw new Error (
'Cannot change the fingerprint, this claim has already been verified'
)
}
this . _fingerprint = fingerprint ;
}
set status ( anything ) {
throw new Error ( "Cannot change a claim's status" )
}
set matches ( anything ) {
throw new Error ( "Cannot change a claim's matches" )
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ * *
* Match the claim ' s URI to candidate definitions
* @ function
* /
match ( ) {
if ( this . _status !== ClaimStatus . INIT ) {
throw new Error ( 'This claim was already matched' )
}
if ( this . _uri . length === 0 || ! validUrlExports . isUri ( this . _uri ) ) {
throw new Error ( 'This claim has no URI' )
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
this . _matches = [ ] ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
list . every ( ( name , i ) => {
const def = _data [ name ] ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// If the candidate is invalid, continue matching
if ( ! def . reURI . test ( this . _uri ) ) {
return true
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
const candidate = def . processURI ( this . _uri ) ;
// If the candidate could not be processed, continue matching
if ( ! candidate ) {
return true
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( candidate . claim . uriIsAmbiguous ) {
// Add to the possible candidates
this . _matches . push ( candidate ) ;
} else {
// Set a single candidate and stop
this . _matches = [ candidate ] ;
return false
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// Continue matching
return true
} ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
this . _status = this . _matches . length === 0 ? ClaimStatus . NO _MATCHES : ClaimStatus . MATCHED ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
* Verify the claim . The proof for each candidate is sequentially fetched and
* checked for the fingerprint . The verification stops when either a positive
* result was obtained , or an unambiguous claim definition was processed
* regardless of the result .
* @ function
2024-02-01 09:06:40 -07:00
* @ param { import ( './types' ) . VerificationConfig } [ opts ] - Options for proxy , fetchers
2023-09-21 06:49:15 -06:00
* /
async verify ( opts$1 ) {
if ( this . _status === ClaimStatus . INIT ) {
throw new Error ( 'This claim has not yet been matched' )
}
if ( this . _status >= 200 ) {
throw new Error ( 'This claim has already been verified' )
}
if ( this . _fingerprint . length === 0 ) {
throw new Error ( 'This claim has no fingerprint' )
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// Handle options
opts$1 = mergeOptions$1 ( opts , opts$1 || { } ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// If there are no matches
if ( this . _matches . length === 0 ) {
this . status = ClaimStatus . NO _MATCHES ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
// For each match
for ( let index = 0 ; index < this . _matches . length ; index ++ ) {
// Continue if a result was already obtained
if ( this . _status >= 200 ) { continue }
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
let claimData = this . _matches [ index ] ;
2023-07-09 04:05:21 -06:00
2024-02-01 09:06:40 -07:00
/** @type {import('./types').VerificationResult | null} */
2023-09-21 06:49:15 -06:00
let verificationResult = null ;
let proofData = null ;
let proofFetchError ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
try {
proofData = await fetch$2 ( claimData , opts$1 ) ;
} catch ( err ) {
proofFetchError = err ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( proofData ) {
// Run the verification process
verificationResult = await run (
proofData . result ,
claimData ,
this . _fingerprint
) ;
verificationResult . proof = {
fetcher : proofData . fetcher ,
viaProxy : proofData . viaProxy
} ;
2023-07-09 04:05:21 -06:00
2023-09-23 02:16:41 -06:00
// Validate the result
2023-09-21 06:49:15 -06:00
const def = _data [ claimData . about . id ] ;
2023-09-23 02:16:41 -06:00
if ( def . functions ? . validate && verificationResult . completed && verificationResult . result ) {
try {
( verificationResult . result = await def . functions . validate ( claimData , proofData , verificationResult , opts$1 ) ) ;
} catch ( _ ) { }
}
// Post process the data
2023-09-21 06:49:15 -06:00
if ( def . functions ? . postprocess ) {
try {
( { claimData , proofData } = await def . functions . postprocess ( claimData , proofData , opts$1 ) ) ;
} catch ( _ ) { }
}
} else {
// Consider the proof completed but with a negative result
verificationResult = verificationResult || {
result : false ,
completed : true ,
2024-02-01 09:06:40 -07:00
proof : null ,
2023-09-21 06:49:15 -06:00
errors : [ proofFetchError ]
} ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( this . isAmbiguous ( ) && ! verificationResult . result ) {
// Assume a wrong match and continue
continue
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( verificationResult . result ) {
this . _status = verificationResult . proof . viaProxy ? ClaimStatus . VERIFIED _VIA _PROXY : ClaimStatus . VERIFIED ;
this . _matches = [ claimData ] ;
}
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
this . _status = this . _status >= 200 ? this . _status : ClaimStatus . NO _PROOF _FOUND ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ * *
* Determine the ambiguity of the claim . A claim is only unambiguous if any
* of the candidates is unambiguous . An ambiguous claim should never be
* displayed in an user interface when its result is negative .
* @ function
2024-02-01 09:06:40 -07:00
* @ returns { boolean } Whether the claim is ambiguous
2023-09-21 06:49:15 -06:00
* /
isAmbiguous ( ) {
2023-10-03 05:47:26 -06:00
if ( this . _status < ClaimStatus . MATCHED ) {
2023-09-21 06:49:15 -06:00
throw new Error ( 'The claim has not been matched yet' )
}
if ( this . _matches . length === 0 ) {
throw new Error ( 'The claim has no matches' )
}
2023-10-03 05:47:26 -06:00
if ( this . _status >= 200 && this . _status < 300 ) return false
2023-09-21 06:49:15 -06:00
return this . _matches . length > 1 || this . _matches [ 0 ] . claim . uriIsAmbiguous
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ * *
* Get a JSON representation of the Claim object . Useful when transferring
* data between instances / machines .
* @ function
2024-02-01 09:06:40 -07:00
* @ returns { object } JSON reprentation of the claim
2023-09-21 06:49:15 -06:00
* /
toJSON ( ) {
2023-10-04 01:13:43 -06:00
let displayProfileName = this . _uri ;
let displayProfileUrl = null ;
let displayProofUrl = null ;
2023-09-21 06:49:15 -06:00
let displayServiceProviderName = null ;
2023-10-03 04:05:09 -06:00
let displayServiceProviderId = null ;
2023-07-09 04:05:21 -06:00
2023-10-03 05:47:26 -06:00
if ( this . _status >= ClaimStatus . MATCHED && this . _matches . length > 0 && ! this . isAmbiguous ( ) ) {
2023-10-04 01:13:43 -06:00
displayProfileName = this . _matches [ 0 ] . profile . display ;
displayProfileUrl = this . _matches [ 0 ] . profile . uri ;
displayProofUrl = this . _matches [ 0 ] . proof . request . uri ;
2023-09-21 06:49:15 -06:00
displayServiceProviderName = this . _matches [ 0 ] . about . name ;
2023-10-03 04:05:09 -06:00
displayServiceProviderId = this . _matches [ 0 ] . about . id ;
2023-09-21 06:49:15 -06:00
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
return {
claimVersion : 2 ,
uri : this . _uri ,
proofs : [ this . _fingerprint ] ,
matches : this . _matches . map ( x => x . toJSON ( ) ) ,
status : this . _status ,
display : {
2023-10-04 01:13:43 -06:00
profileName : displayProfileName ,
profileUrl : displayProfileUrl ,
proofUrl : displayProofUrl ,
2023-10-03 04:05:09 -06:00
serviceProviderName : displayServiceProviderName ,
serviceProviderId : displayServiceProviderId
2023-09-21 06:49:15 -06:00
}
}
}
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* @ ignore
* @ param { object } claimObject - JSON representation of a claim
* @ returns { Claim | Error } Parsed claim
2023-09-21 06:49:15 -06:00
* /
function importJsonClaimVersion1 ( claimObject ) {
if ( ! ( 'claimVersion' in claimObject && claimObject . claimVersion === 1 ) ) {
return new Error ( 'Invalid claim' )
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
const claim = new Claim ( ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
claim . _uri = claimObject . uri ;
claim . _fingerprint = claimObject . fingerprint ;
claim . _matches = claimObject . matches . map ( x => new ServiceProvider ( x ) ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( claimObject . status === 'init' ) {
claim . _status = 100 ;
}
if ( claimObject . status === 'matched' ) {
if ( claimObject . matches . length === 0 ) {
claim . _status = 301 ;
}
claim . _status = 101 ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( ! ( 'result' in claimObject . verification && 'errors' in claimObject . verification ) ) {
claim . _status = 400 ;
}
if ( claimObject . verification . errors . length > 0 ) {
claim . _status = 400 ;
}
if ( claimObject . verification . result && claimObject . verification . proof . viaProxy ) {
claim . _status = 201 ;
}
if ( claimObject . verification . result && ! claimObject . verification . proof . viaProxy ) {
claim . _status = 200 ;
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
return claim
}
2023-07-09 04:05:21 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* @ ignore
* @ param { object } claimObject - JSON representation of a claim
* @ returns { Claim | Error } Parsed claim
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
function importJsonClaimVersion2 ( claimObject ) {
if ( ! ( 'claimVersion' in claimObject && claimObject . claimVersion === 2 ) ) {
return new Error ( 'Invalid claim' )
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
const claim = new Claim ( ) ;
claim . _uri = claimObject . uri ;
claim . _fingerprint = claimObject . proofs [ 0 ] ;
claim . _matches = claimObject . matches . map ( x => new ServiceProvider ( x ) ) ;
claim . _status = claimObject . status ;
return claim
}
2023-07-09 04:05:21 -06:00
/ *
2023-09-21 06:49:15 -06:00
Copyright 2023 Yarmo Mackenbach
2023-07-09 04:05:21 -06:00
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* @ class
2024-02-01 09:06:40 -07:00
* @ classdesc A persona with identity claims
2023-09-21 06:49:15 -06:00
* @ example
* const claim = Claim ( 'https://alice.tld' , '123' ) ;
* const pers = Persona ( 'Alice' , 'About Alice' , [ claim ] ) ;
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
class Persona {
2023-07-09 04:05:21 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* @ param { string } name - Name of the persona
* @ param { Array < Claim > } claims - Claims of the persona
2023-09-21 06:49:15 -06:00
* /
constructor ( name , claims ) {
2023-07-09 04:05:21 -06:00
/ * *
2023-09-21 06:49:15 -06:00
* Identifier of the persona
* @ type { string | null }
* @ public
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
this . identifier = null ;
2023-07-09 04:05:21 -06:00
/ * *
2023-09-21 06:49:15 -06:00
* Name to be displayed on the profile page
2023-07-09 04:05:21 -06:00
* @ type { string }
2023-09-21 06:49:15 -06:00
* @ public
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
this . name = name ;
2023-07-09 04:05:21 -06:00
/ * *
2023-09-21 06:49:15 -06:00
* Email address of the persona
* @ type { string | null }
* @ public
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
this . email = null ;
2023-07-09 04:05:21 -06:00
/ * *
2023-09-21 06:49:15 -06:00
* Description to be displayed on the profile page
* @ type { string | null }
* @ public
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
this . description = null ;
/ * *
* URL to an avatar image
* @ type { string | null }
* @ public
* /
this . avatarUrl = null ;
2023-10-05 03:14:38 -06:00
/ * *
* Theme color
* @ type { string | null }
* @ public
* /
this . themeColor = null ;
2023-09-21 06:49:15 -06:00
/ * *
* List of identity claims
2024-02-01 09:06:40 -07:00
* @ type { Array < Claim > }
2023-09-21 06:49:15 -06:00
* @ public
* /
this . claims = claims ;
/ * *
* Has the persona been revoked
* @ type { boolean }
* @ public
* /
this . isRevoked = false ;
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Parse a JSON object and convert it into a persona
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { object } personaObject - JSON representation of a persona
* @ param { number } profileVersion - Version of the Profile containing the persona
* @ returns { Persona | Error } Parsed persona
2023-07-09 04:05:21 -06:00
* @ example
2023-09-21 06:49:15 -06:00
* doip . Persona . fromJSON ( JSON . stringify ( persona ) , 2 ) ;
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
static fromJSON ( personaObject , profileVersion ) {
/** @type {Persona} */
let persona ;
2023-07-09 04:05:21 -06:00
let result ;
2023-09-21 06:49:15 -06:00
if ( typeof personaObject === 'object' && profileVersion ) {
switch ( profileVersion ) {
2023-07-09 04:05:21 -06:00
case 2 :
2023-09-21 06:49:15 -06:00
result = importJsonPersonaVersion2 ( personaObject ) ;
2023-07-09 04:05:21 -06:00
if ( result instanceof Error ) {
throw result
}
2023-09-21 06:49:15 -06:00
persona = result ;
2023-07-09 04:05:21 -06:00
break
default :
2023-09-21 06:49:15 -06:00
throw new Error ( 'Invalid persona version' )
2023-07-09 04:05:21 -06:00
}
}
2023-09-21 06:49:15 -06:00
return persona
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Set the persona ' s identifier
2023-09-21 06:49:15 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } identifier - Identifier of the persona
2023-09-21 06:49:15 -06:00
* /
setIdentifier ( identifier ) {
this . identifier = identifier ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Set the persona ' s description
2023-09-21 06:49:15 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } description - Description of the persona
2023-09-21 06:49:15 -06:00
* /
setDescription ( description ) {
this . description = description ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Set the persona ' s email address
2023-09-21 06:49:15 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } email - Email address of the persona
2023-09-21 06:49:15 -06:00
* /
setEmailAddress ( email ) {
this . email = email ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Set the URL to the persona ' s avatar
2023-09-21 06:49:15 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } avatarUrl - URL to the persona ' s avatar
2023-09-21 06:49:15 -06:00
* /
setAvatarUrl ( avatarUrl ) {
this . avatarUrl = avatarUrl ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Add a claim
2023-09-21 06:49:15 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { Claim } claim - Claim to add
2023-09-21 06:49:15 -06:00
* /
addClaim ( claim ) {
this . claims . push ( claim ) ;
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* Revoke the persona
2023-09-21 06:49:15 -06:00
* @ function
* /
revoke ( ) {
this . isRevoked = true ;
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Get a JSON representation of the persona
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ returns { object } JSON representation of the persona
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
toJSON ( ) {
return {
identifier : this . identifier ,
name : this . name ,
email : this . email ,
description : this . description ,
avatarUrl : this . avatarUrl ,
2023-10-05 03:14:38 -06:00
themeColor : this . themeColor ,
2023-09-21 06:49:15 -06:00
isRevoked : this . isRevoked ,
claims : this . claims . map ( x => x . toJSON ( ) )
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
}
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ * *
2024-02-01 09:06:40 -07:00
* @ ignore
* @ param { object } personaObject - JSON representation of a persona
* @ returns { Persona | Error } Parsed persona
2023-09-21 06:49:15 -06:00
* /
function importJsonPersonaVersion2 ( personaObject ) {
const claims = personaObject . claims . map ( x => Claim . fromJSON ( x ) ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
const persona = new Persona ( personaObject . name , claims ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
persona . identifier = personaObject . identifier ;
persona . email = personaObject . email ;
persona . description = personaObject . description ;
persona . avatarUrl = personaObject . avatarUrl ;
2023-10-05 03:14:38 -06:00
persona . themeColor = personaObject . avatarUrl ;
2023-09-21 06:49:15 -06:00
persona . isRevoked = personaObject . isRevoked ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
return persona
}
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
/ *
Copyright 2023 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
2024-02-01 09:06:40 -07:00
* @ class
* @ classdesc A profile of personas with identity claims
* @ param { Array < Persona > } personas - Personas of the profile
2023-09-21 06:49:15 -06:00
* @ example
* const claim = Claim ( 'https://alice.tld' , '123' ) ;
* const pers = Persona ( 'Alice' , 'About Alice' , [ claim ] ) ;
* const profile = Profile ( [ pers ] ) ;
* /
class Profile {
/ * *
* Create a new profile
* @ function
2024-02-01 09:06:40 -07:00
* @ param { ProfileType } profileType - Type of profile ( ASP , OpenPGP , etc . )
* @ param { string } identifier - Profile identifier ( fingerprint , URI , etc . )
* @ param { Array < Persona > } personas - Personas of the profile
2023-09-21 06:49:15 -06:00
* @ public
* /
constructor ( profileType , identifier , personas ) {
this . profileVersion = 2 ;
/ * *
* Profile version
2024-02-01 09:06:40 -07:00
* @ type { ProfileType }
2023-09-21 06:49:15 -06:00
* @ public
* /
this . profileType = profileType ;
/ * *
* Identifier of the profile ( fingerprint , email address , uri ... )
* @ type { string }
* @ public
* /
this . identifier = identifier ;
/ * *
* List of personas
2024-02-01 09:06:40 -07:00
* @ type { Array < Persona > }
2023-09-21 06:49:15 -06:00
* @ public
* /
this . personas = personas || [ ] ;
/ * *
* Index of primary persona ( to be displayed first or prominently )
* @ type { number }
* @ public
* /
this . primaryPersonaIndex = personas . length > 0 ? 0 : - 1 ;
/ * *
* The cryptographic key associated with the profile
2024-02-01 09:06:40 -07:00
* @ type { import ( './types' ) . ProfilePublicKey }
2023-09-21 06:49:15 -06:00
* @ public
* /
this . publicKey = {
keyType : PublicKeyType . NONE ,
fingerprint : null ,
encoding : PublicKeyEncoding . NONE ,
encodedKey : null ,
key : null ,
fetch : {
method : PublicKeyFetchMethod . NONE ,
query : null ,
resolvedUrl : null
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
} ;
/ * *
* List of verifier URLs
2024-02-01 09:06:40 -07:00
* @ type { Array < import ( './types' ) . ProfileVerifier > }
2023-09-21 06:49:15 -06:00
* @ public
* /
this . verifiers = [ ] ;
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Parse a JSON object and convert it into a profile
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { object } profileObject - JSON representation of a profile
* @ returns { Profile | Error } Parsed profile
2023-09-21 06:49:15 -06:00
* @ example
* doip . Profile . fromJSON ( JSON . stringify ( profile ) ) ;
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
static fromJSON ( profileObject ) {
/** @type {Profile} */
let profile ;
let result ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
if ( typeof profileObject === 'object' && 'profileVersion' in profileObject ) {
switch ( profileObject . profileVersion ) {
case 2 :
result = importJsonProfileVersion2 ( profileObject ) ;
if ( result instanceof Error ) {
throw result
}
profile = result ;
break
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
default :
throw new Error ( 'Invalid profile version' )
2023-07-09 04:05:21 -06:00
}
}
2023-09-21 06:49:15 -06:00
return profile
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Add profile verifier to the profile
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } name - Name of the verifier
* @ param { string } url - URL of the verifier
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
addVerifier ( name , url ) {
this . verifiers . push ( { name , url } ) ;
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Get a JSON representation of the profile
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ returns { object } JSON representation of the profile
2023-07-09 04:05:21 -06:00
* /
toJSON ( ) {
return {
2023-09-21 06:49:15 -06:00
profileVersion : this . profileVersion ,
profileType : this . profileType ,
identifier : this . identifier ,
personas : this . personas . map ( x => x . toJSON ( ) ) ,
primaryPersonaIndex : this . primaryPersonaIndex ,
publicKey : {
keyType : this . publicKey . keyType ,
fingerprint : this . publicKey . fingerprint ,
encoding : this . publicKey . encoding ,
encodedKey : this . publicKey . encodedKey ,
fetch : {
method : this . publicKey . fetch . method ,
query : this . publicKey . fetch . query ,
resolvedUrl : this . publicKey . fetch . resolvedUrl
}
} ,
verifiers : this . verifiers
2023-07-09 04:05:21 -06:00
}
}
}
/ * *
2024-02-01 09:06:40 -07:00
* @ ignore
* @ param { object } profileObject - JSON representation of the profile
* @ returns { Profile | Error } Parsed profile
2023-07-09 04:05:21 -06:00
* /
2023-09-21 06:49:15 -06:00
function importJsonProfileVersion2 ( profileObject ) {
if ( ! ( 'profileVersion' in profileObject && profileObject . profileVersion === 2 ) ) {
return new Error ( 'Invalid profile' )
2023-07-09 04:05:21 -06:00
}
2023-09-21 06:49:15 -06:00
const personas = profileObject . personas . map ( x => Persona . fromJSON ( x , 2 ) ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
const profile = new Profile ( profileObject . profileType , profileObject . identifier , personas ) ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
profile . primaryPersonaIndex = profileObject . primaryPersonaIndex ;
profile . publicKey = profileObject . publicKey ;
profile . verifiers = profileObject . verifiers ;
2023-07-09 04:05:21 -06:00
2023-09-21 06:49:15 -06:00
return profile
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
function bind ( fn , thisArg ) {
2023-07-09 04:05:21 -06:00
return function wrap ( ) {
2024-01-23 11:06:49 -07:00
return fn . apply ( thisArg , arguments ) ;
2023-07-09 04:05:21 -06:00
} ;
2024-01-23 11:06:49 -07:00
}
2023-07-09 04:05:21 -06:00
// utils is a library of generic helper functions non-specific to axios
2024-01-23 11:06:49 -07:00
const { toString : toString$1 } = Object . prototype ;
const { getPrototypeOf } = Object ;
const kindOf = ( cache => thing => {
const str = toString$1 . call ( thing ) ;
return cache [ str ] || ( cache [ str ] = str . slice ( 8 , - 1 ) . toLowerCase ( ) ) ;
} ) ( Object . create ( null ) ) ;
const kindOfTest = ( type ) => {
type = type . toLowerCase ( ) ;
return ( thing ) => kindOf ( thing ) === type
} ;
const typeOfTest = type => thing => typeof thing === type ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is an Array
*
* @ param { Object } val The value to test
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is an Array , otherwise false
* /
2024-01-23 11:06:49 -07:00
const { isArray : isArray$1 } = Array ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is undefined
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if the value is undefined , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isUndefined = typeOfTest ( 'undefined' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a Buffer
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a Buffer , otherwise false
* /
2024-01-23 11:06:49 -07:00
function isBuffer$1 ( val ) {
2023-07-09 04:05:21 -06:00
return val !== null && ! isUndefined ( val ) && val . constructor !== null && ! isUndefined ( val . constructor )
2024-01-23 11:06:49 -07:00
&& isFunction ( val . constructor . isBuffer ) && val . constructor . isBuffer ( val ) ;
2023-07-09 04:05:21 -06:00
}
/ * *
* Determine if a value is an ArrayBuffer
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is an ArrayBuffer , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isArrayBuffer = kindOfTest ( 'ArrayBuffer' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a view on an ArrayBuffer
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a view on an ArrayBuffer , otherwise false
* /
function isArrayBufferView ( val ) {
2024-01-23 11:06:49 -07:00
let result ;
2023-07-09 04:05:21 -06:00
if ( ( typeof ArrayBuffer !== 'undefined' ) && ( ArrayBuffer . isView ) ) {
result = ArrayBuffer . isView ( val ) ;
} else {
result = ( val ) && ( val . buffer ) && ( isArrayBuffer ( val . buffer ) ) ;
}
return result ;
}
/ * *
* Determine if a value is a String
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a String , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isString = typeOfTest ( 'string' ) ;
/ * *
* Determine if a value is a Function
*
* @ param { * } val The value to test
* @ returns { boolean } True if value is a Function , otherwise false
* /
const isFunction = typeOfTest ( 'function' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a Number
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a Number , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isNumber = typeOfTest ( 'number' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is an Object
*
2024-01-23 11:06:49 -07:00
* @ param { * } thing The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is an Object , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isObject$1 = ( thing ) => thing !== null && typeof thing === 'object' ;
/ * *
* Determine if a value is a Boolean
*
* @ param { * } thing The value to test
* @ returns { boolean } True if value is a Boolean , otherwise false
* /
const isBoolean = thing => thing === true || thing === false ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a plain Object
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
* @ returns { boolean } True if value is a plain Object , otherwise false
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const isPlainObject = ( val ) => {
if ( kindOf ( val ) !== 'object' ) {
2023-07-09 04:05:21 -06:00
return false ;
}
2024-01-23 11:06:49 -07:00
const prototype = getPrototypeOf ( val ) ;
return ( prototype === null || prototype === Object . prototype || Object . getPrototypeOf ( prototype ) === null ) && ! ( Symbol . toStringTag in val ) && ! ( Symbol . iterator in val ) ;
} ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a Date
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a Date , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isDate = kindOfTest ( 'Date' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a File
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a File , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isFile = kindOfTest ( 'File' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a Blob
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a Blob , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isBlob = kindOfTest ( 'Blob' ) ;
2023-07-09 04:05:21 -06:00
/ * *
2024-01-23 11:06:49 -07:00
* Determine if a value is a FileList
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
* @ returns { boolean } True if value is a File , otherwise false
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const isFileList = kindOfTest ( 'FileList' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a Stream
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a Stream , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isStream = ( val ) => isObject$1 ( val ) && isFunction ( val . pipe ) ;
/ * *
* Determine if a value is a FormData
*
* @ param { * } thing The value to test
*
* @ returns { boolean } True if value is an FormData , otherwise false
* /
const isFormData = ( thing ) => {
let kind ;
return thing && (
( typeof FormData === 'function' && thing instanceof FormData ) || (
isFunction ( thing . append ) && (
( kind = kindOf ( thing ) ) === 'formdata' ||
// detect form-data instance
( kind === 'object' && isFunction ( thing . toString ) && thing . toString ( ) === '[object FormData]' )
)
)
)
} ;
2023-07-09 04:05:21 -06:00
/ * *
* Determine if a value is a URLSearchParams object
*
2024-01-23 11:06:49 -07:00
* @ param { * } val The value to test
*
2023-07-09 04:05:21 -06:00
* @ returns { boolean } True if value is a URLSearchParams object , otherwise false
* /
2024-01-23 11:06:49 -07:00
const isURLSearchParams = kindOfTest ( 'URLSearchParams' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Trim excess whitespace off the beginning and end of a string
*
* @ param { String } str The String to trim
*
2024-01-23 11:06:49 -07:00
* @ returns { String } The String freed of excess whitespace
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const trim = ( str ) => str . trim ?
str . trim ( ) : str . replace ( /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g , '' ) ;
2023-07-09 04:05:21 -06:00
/ * *
* Iterate over an Array or an Object invoking a function for each item .
*
* If ` obj ` is an Array callback will be called passing
* the value , index , and complete array for each item .
*
* If 'obj' is an Object callback will be called passing
* the value , key , and complete object for each property .
*
* @ param { Object | Array } obj The object to iterate
* @ param { Function } fn The callback to invoke for each item
2024-01-23 11:06:49 -07:00
*
* @ param { Boolean } [ allOwnKeys = false ]
* @ returns { any }
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
function forEach ( obj , fn , { allOwnKeys = false } = { } ) {
2023-07-09 04:05:21 -06:00
// Don't bother if no value provided
if ( obj === null || typeof obj === 'undefined' ) {
return ;
}
2024-01-23 11:06:49 -07:00
let i ;
let l ;
2023-07-09 04:05:21 -06:00
// Force an array if not already something iterable
if ( typeof obj !== 'object' ) {
/*eslint no-param-reassign:0*/
obj = [ obj ] ;
}
2024-01-23 11:06:49 -07:00
if ( isArray$1 ( obj ) ) {
2023-07-09 04:05:21 -06:00
// Iterate over array values
2024-01-23 11:06:49 -07:00
for ( i = 0 , l = obj . length ; i < l ; i ++ ) {
2023-07-09 04:05:21 -06:00
fn . call ( null , obj [ i ] , i , obj ) ;
}
} else {
// Iterate over object keys
2024-01-23 11:06:49 -07:00
const keys = allOwnKeys ? Object . getOwnPropertyNames ( obj ) : Object . keys ( obj ) ;
const len = keys . length ;
let key ;
for ( i = 0 ; i < len ; i ++ ) {
key = keys [ i ] ;
fn . call ( null , obj [ key ] , key , obj ) ;
}
}
}
function findKey ( obj , key ) {
key = key . toLowerCase ( ) ;
const keys = Object . keys ( obj ) ;
let i = keys . length ;
let _key ;
while ( i -- > 0 ) {
_key = keys [ i ] ;
if ( key === _key . toLowerCase ( ) ) {
return _key ;
2023-07-09 04:05:21 -06:00
}
}
2024-01-23 11:06:49 -07:00
return null ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
const _global = ( ( ) => {
/*eslint no-undef:0*/
if ( typeof globalThis !== "undefined" ) return globalThis ;
return typeof self !== "undefined" ? self : ( typeof window !== 'undefined' ? window : global$1 )
} ) ( ) ;
const isContextDefined = ( context ) => ! isUndefined ( context ) && context !== _global ;
2023-07-09 04:05:21 -06:00
/ * *
* Accepts varargs expecting each argument to be an object , then
* immutably merges the properties of each object and returns result .
*
* When multiple objects contain the same key the later object in
* the arguments list will take precedence .
*
* Example :
*
* ` ` ` js
* var result = merge ( { foo : 123 } , { foo : 456 } ) ;
* console . log ( result . foo ) ; // outputs 456
* ` ` `
*
* @ param { Object } obj1 Object to merge
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ returns { Object } Result of all merge properties
* /
function merge ( /* obj1, obj2, obj3, ... */ ) {
2024-01-23 11:06:49 -07:00
const { caseless } = isContextDefined ( this ) && this || { } ;
const result = { } ;
const assignValue = ( val , key ) => {
const targetKey = caseless && findKey ( result , key ) || key ;
if ( isPlainObject ( result [ targetKey ] ) && isPlainObject ( val ) ) {
result [ targetKey ] = merge ( result [ targetKey ] , val ) ;
2023-07-09 04:05:21 -06:00
} else if ( isPlainObject ( val ) ) {
2024-01-23 11:06:49 -07:00
result [ targetKey ] = merge ( { } , val ) ;
} else if ( isArray$1 ( val ) ) {
result [ targetKey ] = val . slice ( ) ;
2023-07-09 04:05:21 -06:00
} else {
2024-01-23 11:06:49 -07:00
result [ targetKey ] = val ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
for ( let i = 0 , l = arguments . length ; i < l ; i ++ ) {
arguments [ i ] && forEach ( arguments [ i ] , assignValue ) ;
2023-07-09 04:05:21 -06:00
}
return result ;
}
/ * *
* Extends object a by mutably adding to it the properties of object b .
*
* @ param { Object } a The object to be extended
* @ param { Object } b The object to copy properties from
* @ param { Object } thisArg The object to bind function to
2024-01-23 11:06:49 -07:00
*
* @ param { Boolean } [ allOwnKeys ]
* @ returns { Object } The resulting value of object a
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const extend = ( a , b , thisArg , { allOwnKeys } = { } ) => {
forEach ( b , ( val , key ) => {
if ( thisArg && isFunction ( val ) ) {
a [ key ] = bind ( val , thisArg ) ;
2023-07-09 04:05:21 -06:00
} else {
a [ key ] = val ;
}
2024-01-23 11:06:49 -07:00
} , { allOwnKeys } ) ;
2023-07-09 04:05:21 -06:00
return a ;
2024-01-23 11:06:49 -07:00
} ;
2023-07-09 04:05:21 -06:00
/ * *
* Remove byte order marker . This catches EF BB BF ( the UTF - 8 BOM )
*
* @ param { string } content with BOM
2024-01-23 11:06:49 -07:00
*
* @ returns { string } content value without BOM
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const stripBOM = ( content ) => {
2023-07-09 04:05:21 -06:00
if ( content . charCodeAt ( 0 ) === 0xFEFF ) {
content = content . slice ( 1 ) ;
}
return content ;
2024-01-23 11:06:49 -07:00
} ;
2023-07-09 04:05:21 -06:00
/ * *
2024-01-23 11:06:49 -07:00
* Inherit the prototype methods from one constructor into another
* @ param { function } constructor
* @ param { function } superConstructor
* @ param { object } [ props ]
* @ param { object } [ descriptors ]
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ returns { void }
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const inherits = ( constructor , superConstructor , props , descriptors ) => {
constructor . prototype = Object . create ( superConstructor . prototype , descriptors ) ;
constructor . prototype . constructor = constructor ;
Object . defineProperty ( constructor , 'super' , {
value : superConstructor . prototype
} ) ;
props && Object . assign ( constructor . prototype , props ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Resolve object with deep prototype chain to a flat object
* @ param { Object } sourceObj source object
* @ param { Object } [ destObj ]
* @ param { Function | Boolean } [ filter ]
* @ param { Function } [ propFilter ]
*
* @ returns { Object }
* /
const toFlatObject = ( sourceObj , destObj , filter , propFilter ) => {
let props ;
let i ;
let prop ;
const merged = { } ;
destObj = destObj || { } ;
// eslint-disable-next-line no-eq-null,eqeqeq
if ( sourceObj == null ) return destObj ;
do {
props = Object . getOwnPropertyNames ( sourceObj ) ;
i = props . length ;
while ( i -- > 0 ) {
prop = props [ i ] ;
if ( ( ! propFilter || propFilter ( prop , sourceObj , destObj ) ) && ! merged [ prop ] ) {
destObj [ prop ] = sourceObj [ prop ] ;
merged [ prop ] = true ;
2023-07-09 04:05:21 -06:00
}
}
2024-01-23 11:06:49 -07:00
sourceObj = filter !== false && getPrototypeOf ( sourceObj ) ;
} while ( sourceObj && ( ! filter || filter ( sourceObj , destObj ) ) && sourceObj !== Object . prototype ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return destObj ;
2023-07-09 04:05:21 -06:00
} ;
2024-01-23 11:06:49 -07:00
/ * *
* Determines whether a string ends with the characters of a specified string
*
* @ param { String } str
* @ param { String } searchString
* @ param { Number } [ position = 0 ]
*
* @ returns { boolean }
* /
const endsWith = ( str , searchString , position ) => {
str = String ( str ) ;
if ( position === undefined || position > str . length ) {
position = str . length ;
}
position -= searchString . length ;
const lastIndex = str . indexOf ( searchString , position ) ;
return lastIndex !== - 1 && lastIndex === position ;
} ;
2023-07-09 04:05:21 -06:00
/ * *
2024-01-23 11:06:49 -07:00
* Returns new array from array like object or null if failed
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ param { * } [ thing ]
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ returns { ? Array }
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const toArray = ( thing ) => {
if ( ! thing ) return null ;
if ( isArray$1 ( thing ) ) return thing ;
let i = thing . length ;
if ( ! isNumber ( i ) ) return null ;
const arr = new Array ( i ) ;
while ( i -- > 0 ) {
arr [ i ] = thing [ i ] ;
}
return arr ;
2023-07-09 04:05:21 -06:00
} ;
/ * *
2024-01-23 11:06:49 -07:00
* Checking if the Uint8Array exists and if it does , it returns a function that checks if the
* thing passed in is an instance of Uint8Array
*
* @ param { TypedArray }
*
* @ returns { Array }
* /
// eslint-disable-next-line func-names
const isTypedArray = ( TypedArray => {
// eslint-disable-next-line func-names
return thing => {
return TypedArray && thing instanceof TypedArray ;
} ;
} ) ( typeof Uint8Array !== 'undefined' && getPrototypeOf ( Uint8Array ) ) ;
/ * *
* For each entry in the object , call the function with the key and value .
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ param { Object < any , any > } obj - The object to iterate over .
* @ param { Function } fn - The function to call for each entry .
*
* @ returns { void }
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const forEachEntry = ( obj , fn ) => {
const generator = obj && obj [ Symbol . iterator ] ;
const iterator = generator . call ( obj ) ;
let result ;
while ( ( result = iterator . next ( ) ) && ! result . done ) {
const pair = result . value ;
fn . call ( obj , pair [ 0 ] , pair [ 1 ] ) ;
2023-07-09 04:05:21 -06:00
}
} ;
/ * *
2024-01-23 11:06:49 -07:00
* It takes a regular expression and a string , and returns an array of all the matches
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ param { string } regExp - The regular expression to match against .
* @ param { string } str - The string to search .
2023-07-09 04:05:21 -06:00
*
2024-01-23 11:06:49 -07:00
* @ returns { Array < boolean > }
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const matchAll = ( regExp , str ) => {
let matches ;
const arr = [ ] ;
while ( ( matches = regExp . exec ( str ) ) !== null ) {
arr . push ( matches ) ;
}
return arr ;
} ;
/* Checking if the kindOfTest function returns true when passed an HTMLFormElement. */
const isHTMLForm = kindOfTest ( 'HTMLFormElement' ) ;
const toCamelCase = str => {
return str . toLowerCase ( ) . replace ( /[-_\s]([a-z\d])(\w*)/g ,
function replacer ( m , p1 , p2 ) {
return p1 . toUpperCase ( ) + p2 ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
) ;
2023-07-09 04:05:21 -06:00
} ;
2024-01-23 11:06:49 -07:00
/* Creating a function that will check if an object has a property. */
const hasOwnProperty = ( ( { hasOwnProperty } ) => ( obj , prop ) => hasOwnProperty . call ( obj , prop ) ) ( Object . prototype ) ;
/ * *
* Determine if a value is a RegExp object
*
* @ param { * } val The value to test
*
* @ returns { boolean } True if value is a RegExp object , otherwise false
* /
const isRegExp = kindOfTest ( 'RegExp' ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const reduceDescriptors = ( obj , reducer ) => {
const descriptors = Object . getOwnPropertyDescriptors ( obj ) ;
const reducedDescriptors = { } ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
forEach ( descriptors , ( descriptor , name ) => {
let ret ;
if ( ( ret = reducer ( descriptor , name , obj ) ) !== false ) {
reducedDescriptors [ name ] = ret || descriptor ;
2023-07-09 04:05:21 -06:00
}
} ) ;
2024-01-23 11:06:49 -07:00
Object . defineProperties ( obj , reducedDescriptors ) ;
2023-07-09 04:05:21 -06:00
} ;
/ * *
2024-01-23 11:06:49 -07:00
* Makes all methods read - only
* @ param { Object } obj
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
const freezeMethods = ( obj ) => {
reduceDescriptors ( obj , ( descriptor , name ) => {
// skip restricted props in strict mode
if ( isFunction ( obj ) && [ 'arguments' , 'caller' , 'callee' ] . indexOf ( name ) !== - 1 ) {
return false ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const value = obj [ name ] ;
if ( ! isFunction ( value ) ) return ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
descriptor . enumerable = false ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( 'writable' in descriptor ) {
descriptor . writable = false ;
return ;
}
if ( ! descriptor . set ) {
descriptor . set = ( ) => {
throw Error ( 'Can not rewrite read-only method \'' + name + '\'' ) ;
} ;
}
} ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const toObjectSet = ( arrayOrString , delimiter ) => {
const obj = { } ;
const define = ( arr ) => {
arr . forEach ( value => {
obj [ value ] = true ;
} ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
isArray$1 ( arrayOrString ) ? define ( arrayOrString ) : define ( String ( arrayOrString ) . split ( delimiter ) ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return obj ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const noop = ( ) => { } ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const toFiniteNumber = ( value , defaultValue ) => {
value = + value ;
return Number . isFinite ( value ) ? value : defaultValue ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const ALPHA = 'abcdefghijklmnopqrstuvwxyz' ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const DIGIT = '0123456789' ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const ALPHABET = {
DIGIT ,
ALPHA ,
ALPHA _DIGIT : ALPHA + ALPHA . toUpperCase ( ) + DIGIT
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const generateString = ( size = 16 , alphabet = ALPHABET . ALPHA _DIGIT ) => {
let str = '' ;
const { length } = alphabet ;
while ( size -- ) {
str += alphabet [ Math . random ( ) * length | 0 ] ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return str ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* If the thing is a FormData object , return true , otherwise return false .
*
* @ param { unknown } thing - The thing to check .
*
* @ returns { boolean }
* /
function isSpecCompliantForm ( thing ) {
return ! ! ( thing && isFunction ( thing . append ) && thing [ Symbol . toStringTag ] === 'FormData' && thing [ Symbol . iterator ] ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
const toJSONObject = ( obj ) => {
const stack = new Array ( 10 ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const visit = ( source , i ) => {
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( isObject$1 ( source ) ) {
if ( stack . indexOf ( source ) >= 0 ) {
return ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( ! ( 'toJSON' in source ) ) {
stack [ i ] = source ;
const target = isArray$1 ( source ) ? [ ] : { } ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
forEach ( source , ( value , key ) => {
const reducedValue = visit ( value , i + 1 ) ;
! isUndefined ( reducedValue ) && ( target [ key ] = reducedValue ) ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
stack [ i ] = undefined ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return target ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return source ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return visit ( obj , 0 ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const isAsyncFn = kindOfTest ( 'AsyncFunction' ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const isThenable = ( thing ) =>
thing && ( isObject$1 ( thing ) || isFunction ( thing ) ) && isFunction ( thing . then ) && isFunction ( thing . catch ) ;
var utils$1 = {
isArray : isArray$1 ,
isArrayBuffer ,
isBuffer : isBuffer$1 ,
isFormData ,
isArrayBufferView ,
isString ,
isNumber ,
isBoolean ,
isObject : isObject$1 ,
isPlainObject ,
isUndefined ,
isDate ,
isFile ,
isBlob ,
isRegExp ,
isFunction ,
isStream ,
isURLSearchParams ,
isTypedArray ,
isFileList ,
forEach ,
merge ,
extend ,
trim ,
stripBOM ,
inherits ,
toFlatObject ,
kindOf ,
kindOfTest ,
endsWith ,
toArray ,
forEachEntry ,
matchAll ,
isHTMLForm ,
hasOwnProperty ,
hasOwnProp : hasOwnProperty , // an alias to avoid ESLint no-prototype-builtins detection
reduceDescriptors ,
freezeMethods ,
toObjectSet ,
toCamelCase ,
noop ,
toFiniteNumber ,
findKey ,
global : _global ,
isContextDefined ,
ALPHABET ,
generateString ,
isSpecCompliantForm ,
toJSONObject ,
isAsyncFn ,
isThenable
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var lookup = [ ] ;
var revLookup = [ ] ;
var Arr = typeof Uint8Array !== 'undefined' ? Uint8Array : Array ;
var inited = false ;
function init ( ) {
inited = true ;
var code = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/' ;
for ( var i = 0 , len = code . length ; i < len ; ++ i ) {
lookup [ i ] = code [ i ] ;
revLookup [ code . charCodeAt ( i ) ] = i ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
revLookup [ '-' . charCodeAt ( 0 ) ] = 62 ;
revLookup [ '_' . charCodeAt ( 0 ) ] = 63 ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
function toByteArray ( b64 ) {
if ( ! inited ) {
init ( ) ;
}
var i , j , l , tmp , placeHolders , arr ;
var len = b64 . length ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( len % 4 > 0 ) {
throw new Error ( 'Invalid string. Length must be a multiple of 4' )
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// the number of equal signs (place holders)
// if there are two placeholders, than the two characters before it
// represent one byte
// if there is only one, then the three characters before it represent 2 bytes
// this is just a cheap hack to not do indexOf twice
placeHolders = b64 [ len - 2 ] === '=' ? 2 : b64 [ len - 1 ] === '=' ? 1 : 0 ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// base64 is 4/3 + up to two characters of the original data
arr = new Arr ( len * 3 / 4 - placeHolders ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// if there are placeholders, only get up to the last complete 4 chars
l = placeHolders > 0 ? len - 4 : len ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var L = 0 ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
for ( i = 0 , j = 0 ; i < l ; i += 4 , j += 3 ) {
tmp = ( revLookup [ b64 . charCodeAt ( i ) ] << 18 ) | ( revLookup [ b64 . charCodeAt ( i + 1 ) ] << 12 ) | ( revLookup [ b64 . charCodeAt ( i + 2 ) ] << 6 ) | revLookup [ b64 . charCodeAt ( i + 3 ) ] ;
arr [ L ++ ] = ( tmp >> 16 ) & 0xFF ;
arr [ L ++ ] = ( tmp >> 8 ) & 0xFF ;
arr [ L ++ ] = tmp & 0xFF ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( placeHolders === 2 ) {
tmp = ( revLookup [ b64 . charCodeAt ( i ) ] << 2 ) | ( revLookup [ b64 . charCodeAt ( i + 1 ) ] >> 4 ) ;
arr [ L ++ ] = tmp & 0xFF ;
} else if ( placeHolders === 1 ) {
tmp = ( revLookup [ b64 . charCodeAt ( i ) ] << 10 ) | ( revLookup [ b64 . charCodeAt ( i + 1 ) ] << 4 ) | ( revLookup [ b64 . charCodeAt ( i + 2 ) ] >> 2 ) ;
arr [ L ++ ] = ( tmp >> 8 ) & 0xFF ;
arr [ L ++ ] = tmp & 0xFF ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return arr
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
function tripletToBase64 ( num ) {
return lookup [ num >> 18 & 0x3F ] + lookup [ num >> 12 & 0x3F ] + lookup [ num >> 6 & 0x3F ] + lookup [ num & 0x3F ]
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
function encodeChunk ( uint8 , start , end ) {
var tmp ;
var output = [ ] ;
for ( var i = start ; i < end ; i += 3 ) {
tmp = ( uint8 [ i ] << 16 ) + ( uint8 [ i + 1 ] << 8 ) + ( uint8 [ i + 2 ] ) ;
output . push ( tripletToBase64 ( tmp ) ) ;
}
return output . join ( '' )
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
function fromByteArray ( uint8 ) {
if ( ! inited ) {
init ( ) ;
}
var tmp ;
var len = uint8 . length ;
var extraBytes = len % 3 ; // if we have 1 byte left, pad 2 bytes
var output = '' ;
var parts = [ ] ;
var maxChunkLength = 16383 ; // must be multiple of 3
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// go through the array every three bytes, we'll deal with trailing stuff later
for ( var i = 0 , len2 = len - extraBytes ; i < len2 ; i += maxChunkLength ) {
parts . push ( encodeChunk ( uint8 , i , ( i + maxChunkLength ) > len2 ? len2 : ( i + maxChunkLength ) ) ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// pad the end with zeros, but make sure to not forget the extra bytes
if ( extraBytes === 1 ) {
tmp = uint8 [ len - 1 ] ;
output += lookup [ tmp >> 2 ] ;
output += lookup [ ( tmp << 4 ) & 0x3F ] ;
output += '==' ;
} else if ( extraBytes === 2 ) {
tmp = ( uint8 [ len - 2 ] << 8 ) + ( uint8 [ len - 1 ] ) ;
output += lookup [ tmp >> 10 ] ;
output += lookup [ ( tmp >> 4 ) & 0x3F ] ;
output += lookup [ ( tmp << 2 ) & 0x3F ] ;
output += '=' ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
parts . push ( output ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return parts . join ( '' )
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
function read ( buffer , offset , isLE , mLen , nBytes ) {
var e , m ;
var eLen = nBytes * 8 - mLen - 1 ;
var eMax = ( 1 << eLen ) - 1 ;
var eBias = eMax >> 1 ;
var nBits = - 7 ;
var i = isLE ? ( nBytes - 1 ) : 0 ;
var d = isLE ? - 1 : 1 ;
var s = buffer [ offset + i ] ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
i += d ;
e = s & ( ( 1 << ( - nBits ) ) - 1 ) ;
s >>= ( - nBits ) ;
nBits += eLen ;
for ( ; nBits > 0 ; e = e * 256 + buffer [ offset + i ] , i += d , nBits -= 8 ) { }
m = e & ( ( 1 << ( - nBits ) ) - 1 ) ;
e >>= ( - nBits ) ;
nBits += mLen ;
for ( ; nBits > 0 ; m = m * 256 + buffer [ offset + i ] , i += d , nBits -= 8 ) { }
if ( e === 0 ) {
e = 1 - eBias ;
} else if ( e === eMax ) {
return m ? NaN : ( ( s ? - 1 : 1 ) * Infinity )
} else {
m = m + Math . pow ( 2 , mLen ) ;
e = e - eBias ;
}
return ( s ? - 1 : 1 ) * m * Math . pow ( 2 , e - mLen )
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
function write ( buffer , value , offset , isLE , mLen , nBytes ) {
var e , m , c ;
var eLen = nBytes * 8 - mLen - 1 ;
var eMax = ( 1 << eLen ) - 1 ;
var eBias = eMax >> 1 ;
var rt = ( mLen === 23 ? Math . pow ( 2 , - 24 ) - Math . pow ( 2 , - 77 ) : 0 ) ;
var i = isLE ? 0 : ( nBytes - 1 ) ;
var d = isLE ? 1 : - 1 ;
var s = value < 0 || ( value === 0 && 1 / value < 0 ) ? 1 : 0 ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
value = Math . abs ( value ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( isNaN ( value ) || value === Infinity ) {
m = isNaN ( value ) ? 1 : 0 ;
e = eMax ;
} else {
e = Math . floor ( Math . log ( value ) / Math . LN2 ) ;
if ( value * ( c = Math . pow ( 2 , - e ) ) < 1 ) {
e -- ;
c *= 2 ;
}
if ( e + eBias >= 1 ) {
value += rt / c ;
} else {
value += rt * Math . pow ( 2 , 1 - eBias ) ;
}
if ( value * c >= 2 ) {
e ++ ;
c /= 2 ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( e + eBias >= eMax ) {
m = 0 ;
e = eMax ;
} else if ( e + eBias >= 1 ) {
m = ( value * c - 1 ) * Math . pow ( 2 , mLen ) ;
e = e + eBias ;
} else {
m = value * Math . pow ( 2 , eBias - 1 ) * Math . pow ( 2 , mLen ) ;
e = 0 ;
}
}
for ( ; mLen >= 8 ; buffer [ offset + i ] = m & 0xff , i += d , m /= 256 , mLen -= 8 ) { }
e = ( e << mLen ) | m ;
eLen += mLen ;
for ( ; eLen > 0 ; buffer [ offset + i ] = e & 0xff , i += d , e /= 256 , eLen -= 8 ) { }
buffer [ offset + i - d ] |= s * 128 ;
}
var toString = { } . toString ;
var isArray = Array . isArray || function ( arr ) {
return toString . call ( arr ) == '[object Array]' ;
} ;
/ * !
* The buffer module from node . js , for the browser .
*
* @ author Feross Aboukhadijeh < feross @ feross . org > < http : //feross.org>
* @ license MIT
* /
var INSPECT _MAX _BYTES = 50 ;
/ * *
* If ` Buffer.TYPED_ARRAY_SUPPORT ` :
* === true Use Uint8Array implementation ( fastest )
* === false Use Object implementation ( most compatible , even IE6 )
*
* Browsers that support typed arrays are IE 10 + , Firefox 4 + , Chrome 7 + , Safari 5.1 + ,
* Opera 11.6 + , iOS 4.2 + .
*
* Due to various browser bugs , sometimes the Object implementation will be used even
* when the browser supports typed arrays .
*
* Note :
*
* - Firefox 4 - 29 lacks support for adding new properties to ` Uint8Array ` instances ,
* See : https : //bugzilla.mozilla.org/show_bug.cgi?id=695438.
*
* - Chrome 9 - 10 is missing the ` TypedArray.prototype.subarray ` function .
*
* - IE10 has a broken ` TypedArray.prototype.subarray ` function which returns arrays of
* incorrect length in some situations .
* We detect these buggy browsers and set ` Buffer.TYPED_ARRAY_SUPPORT ` to ` false ` so they
* get the Object implementation , which is slower but behaves correctly .
* /
Buffer . TYPED _ARRAY _SUPPORT = global$1 . TYPED _ARRAY _SUPPORT !== undefined
? global$1 . TYPED _ARRAY _SUPPORT
: true ;
/ *
* Export kMaxLength after typed array support is determined .
* /
kMaxLength ( ) ;
function kMaxLength ( ) {
return Buffer . TYPED _ARRAY _SUPPORT
? 0x7fffffff
: 0x3fffffff
}
function createBuffer ( that , length ) {
if ( kMaxLength ( ) < length ) {
throw new RangeError ( 'Invalid typed array length' )
}
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
// Return an augmented `Uint8Array` instance, for best performance
that = new Uint8Array ( length ) ;
that . _ _proto _ _ = Buffer . prototype ;
} else {
// Fallback: Return an object instance of the Buffer class
if ( that === null ) {
that = new Buffer ( length ) ;
}
that . length = length ;
}
return that
}
/ * *
* The Buffer constructor returns instances of ` Uint8Array ` that have their
* prototype changed to ` Buffer.prototype ` . Furthermore , ` Buffer ` is a subclass of
* ` Uint8Array ` , so the returned instances will have all the node ` Buffer ` methods
* and the ` Uint8Array ` methods . Square bracket notation works as expected -- it
* returns a single octet .
*
* The ` Uint8Array ` prototype remains unmodified .
* /
function Buffer ( arg , encodingOrOffset , length ) {
if ( ! Buffer . TYPED _ARRAY _SUPPORT && ! ( this instanceof Buffer ) ) {
return new Buffer ( arg , encodingOrOffset , length )
}
// Common case.
if ( typeof arg === 'number' ) {
if ( typeof encodingOrOffset === 'string' ) {
throw new Error (
'If encoding is specified then the first argument must be a string'
)
}
return allocUnsafe ( this , arg )
}
return from ( this , arg , encodingOrOffset , length )
}
Buffer . poolSize = 8192 ; // not used by this implementation
// TODO: Legacy, not needed anymore. Remove in next major version.
Buffer . _augment = function ( arr ) {
arr . _ _proto _ _ = Buffer . prototype ;
return arr
} ;
function from ( that , value , encodingOrOffset , length ) {
if ( typeof value === 'number' ) {
throw new TypeError ( '"value" argument must not be a number' )
}
if ( typeof ArrayBuffer !== 'undefined' && value instanceof ArrayBuffer ) {
return fromArrayBuffer ( that , value , encodingOrOffset , length )
}
if ( typeof value === 'string' ) {
return fromString ( that , value , encodingOrOffset )
}
return fromObject ( that , value )
}
/ * *
* Functionally equivalent to Buffer ( arg , encoding ) but throws a TypeError
* if value is a number .
* Buffer . from ( str [ , encoding ] )
* Buffer . from ( array )
* Buffer . from ( buffer )
* Buffer . from ( arrayBuffer [ , byteOffset [ , length ] ] )
* * /
Buffer . from = function ( value , encodingOrOffset , length ) {
return from ( null , value , encodingOrOffset , length )
} ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
Buffer . prototype . _ _proto _ _ = Uint8Array . prototype ;
Buffer . _ _proto _ _ = Uint8Array ;
if ( typeof Symbol !== 'undefined' && Symbol . species &&
Buffer [ Symbol . species ] === Buffer ) ;
}
function assertSize ( size ) {
if ( typeof size !== 'number' ) {
throw new TypeError ( '"size" argument must be a number' )
} else if ( size < 0 ) {
throw new RangeError ( '"size" argument must not be negative' )
}
}
function alloc ( that , size , fill , encoding ) {
assertSize ( size ) ;
if ( size <= 0 ) {
return createBuffer ( that , size )
}
if ( fill !== undefined ) {
// Only pay attention to encoding if it's a string. This
// prevents accidentally sending in a number that would
// be interpretted as a start offset.
return typeof encoding === 'string'
? createBuffer ( that , size ) . fill ( fill , encoding )
: createBuffer ( that , size ) . fill ( fill )
}
return createBuffer ( that , size )
}
/ * *
* Creates a new filled Buffer instance .
* alloc ( size [ , fill [ , encoding ] ] )
* * /
Buffer . alloc = function ( size , fill , encoding ) {
return alloc ( null , size , fill , encoding )
} ;
function allocUnsafe ( that , size ) {
assertSize ( size ) ;
that = createBuffer ( that , size < 0 ? 0 : checked ( size ) | 0 ) ;
if ( ! Buffer . TYPED _ARRAY _SUPPORT ) {
for ( var i = 0 ; i < size ; ++ i ) {
that [ i ] = 0 ;
}
}
return that
}
/ * *
* Equivalent to Buffer ( num ) , by default creates a non - zero - filled Buffer instance .
* * /
Buffer . allocUnsafe = function ( size ) {
return allocUnsafe ( null , size )
} ;
/ * *
* Equivalent to SlowBuffer ( num ) , by default creates a non - zero - filled Buffer instance .
* /
Buffer . allocUnsafeSlow = function ( size ) {
return allocUnsafe ( null , size )
} ;
function fromString ( that , string , encoding ) {
if ( typeof encoding !== 'string' || encoding === '' ) {
encoding = 'utf8' ;
}
if ( ! Buffer . isEncoding ( encoding ) ) {
throw new TypeError ( '"encoding" must be a valid string encoding' )
}
var length = byteLength ( string , encoding ) | 0 ;
that = createBuffer ( that , length ) ;
var actual = that . write ( string , encoding ) ;
if ( actual !== length ) {
// Writing a hex string, for example, that contains invalid characters will
// cause everything after the first invalid character to be ignored. (e.g.
// 'abxxcd' will be treated as 'ab')
that = that . slice ( 0 , actual ) ;
}
return that
}
function fromArrayLike ( that , array ) {
var length = array . length < 0 ? 0 : checked ( array . length ) | 0 ;
that = createBuffer ( that , length ) ;
for ( var i = 0 ; i < length ; i += 1 ) {
that [ i ] = array [ i ] & 255 ;
}
return that
}
function fromArrayBuffer ( that , array , byteOffset , length ) {
array . byteLength ; // this throws if `array` is not a valid ArrayBuffer
if ( byteOffset < 0 || array . byteLength < byteOffset ) {
throw new RangeError ( '\'offset\' is out of bounds' )
}
if ( array . byteLength < byteOffset + ( length || 0 ) ) {
throw new RangeError ( '\'length\' is out of bounds' )
}
if ( byteOffset === undefined && length === undefined ) {
array = new Uint8Array ( array ) ;
} else if ( length === undefined ) {
array = new Uint8Array ( array , byteOffset ) ;
} else {
array = new Uint8Array ( array , byteOffset , length ) ;
}
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
// Return an augmented `Uint8Array` instance, for best performance
that = array ;
that . _ _proto _ _ = Buffer . prototype ;
} else {
// Fallback: Return an object instance of the Buffer class
that = fromArrayLike ( that , array ) ;
}
return that
}
function fromObject ( that , obj ) {
if ( internalIsBuffer ( obj ) ) {
var len = checked ( obj . length ) | 0 ;
that = createBuffer ( that , len ) ;
if ( that . length === 0 ) {
return that
}
obj . copy ( that , 0 , 0 , len ) ;
return that
}
if ( obj ) {
if ( ( typeof ArrayBuffer !== 'undefined' &&
obj . buffer instanceof ArrayBuffer ) || 'length' in obj ) {
if ( typeof obj . length !== 'number' || isnan ( obj . length ) ) {
return createBuffer ( that , 0 )
}
return fromArrayLike ( that , obj )
}
if ( obj . type === 'Buffer' && isArray ( obj . data ) ) {
return fromArrayLike ( that , obj . data )
}
}
throw new TypeError ( 'First argument must be a string, Buffer, ArrayBuffer, Array, or array-like object.' )
}
function checked ( length ) {
// Note: cannot use `length < kMaxLength()` here because that fails when
// length is NaN (which is otherwise coerced to zero.)
if ( length >= kMaxLength ( ) ) {
throw new RangeError ( 'Attempt to allocate Buffer larger than maximum ' +
'size: 0x' + kMaxLength ( ) . toString ( 16 ) + ' bytes' )
}
return length | 0
}
Buffer . isBuffer = isBuffer ;
function internalIsBuffer ( b ) {
return ! ! ( b != null && b . _isBuffer )
}
Buffer . compare = function compare ( a , b ) {
if ( ! internalIsBuffer ( a ) || ! internalIsBuffer ( b ) ) {
throw new TypeError ( 'Arguments must be Buffers' )
}
if ( a === b ) return 0
var x = a . length ;
var y = b . length ;
for ( var i = 0 , len = Math . min ( x , y ) ; i < len ; ++ i ) {
if ( a [ i ] !== b [ i ] ) {
x = a [ i ] ;
y = b [ i ] ;
break
}
}
if ( x < y ) return - 1
if ( y < x ) return 1
return 0
} ;
Buffer . isEncoding = function isEncoding ( encoding ) {
switch ( String ( encoding ) . toLowerCase ( ) ) {
case 'hex' :
case 'utf8' :
case 'utf-8' :
case 'ascii' :
case 'latin1' :
case 'binary' :
case 'base64' :
case 'ucs2' :
case 'ucs-2' :
case 'utf16le' :
case 'utf-16le' :
return true
default :
return false
}
} ;
Buffer . concat = function concat ( list , length ) {
if ( ! isArray ( list ) ) {
throw new TypeError ( '"list" argument must be an Array of Buffers' )
}
if ( list . length === 0 ) {
return Buffer . alloc ( 0 )
}
var i ;
if ( length === undefined ) {
length = 0 ;
for ( i = 0 ; i < list . length ; ++ i ) {
length += list [ i ] . length ;
}
}
var buffer = Buffer . allocUnsafe ( length ) ;
var pos = 0 ;
for ( i = 0 ; i < list . length ; ++ i ) {
var buf = list [ i ] ;
if ( ! internalIsBuffer ( buf ) ) {
throw new TypeError ( '"list" argument must be an Array of Buffers' )
}
buf . copy ( buffer , pos ) ;
pos += buf . length ;
}
return buffer
} ;
function byteLength ( string , encoding ) {
if ( internalIsBuffer ( string ) ) {
return string . length
}
if ( typeof ArrayBuffer !== 'undefined' && typeof ArrayBuffer . isView === 'function' &&
( ArrayBuffer . isView ( string ) || string instanceof ArrayBuffer ) ) {
return string . byteLength
}
if ( typeof string !== 'string' ) {
string = '' + string ;
}
var len = string . length ;
if ( len === 0 ) return 0
// Use a for loop to avoid recursion
var loweredCase = false ;
for ( ; ; ) {
switch ( encoding ) {
case 'ascii' :
case 'latin1' :
case 'binary' :
return len
case 'utf8' :
case 'utf-8' :
case undefined :
return utf8ToBytes ( string ) . length
case 'ucs2' :
case 'ucs-2' :
case 'utf16le' :
case 'utf-16le' :
return len * 2
case 'hex' :
return len >>> 1
case 'base64' :
return base64ToBytes ( string ) . length
default :
if ( loweredCase ) return utf8ToBytes ( string ) . length // assume utf8
encoding = ( '' + encoding ) . toLowerCase ( ) ;
loweredCase = true ;
}
}
}
Buffer . byteLength = byteLength ;
function slowToString ( encoding , start , end ) {
var loweredCase = false ;
// No need to verify that "this.length <= MAX_UINT32" since it's a read-only
// property of a typed array.
// This behaves neither like String nor Uint8Array in that we set start/end
// to their upper/lower bounds if the value passed is out of range.
// undefined is handled specially as per ECMA-262 6th Edition,
// Section 13.3.3.7 Runtime Semantics: KeyedBindingInitialization.
if ( start === undefined || start < 0 ) {
start = 0 ;
}
// Return early if start > this.length. Done here to prevent potential uint32
// coercion fail below.
if ( start > this . length ) {
return ''
}
if ( end === undefined || end > this . length ) {
end = this . length ;
}
if ( end <= 0 ) {
return ''
}
// Force coersion to uint32. This will also coerce falsey/NaN values to 0.
end >>>= 0 ;
start >>>= 0 ;
if ( end <= start ) {
return ''
}
if ( ! encoding ) encoding = 'utf8' ;
while ( true ) {
switch ( encoding ) {
case 'hex' :
return hexSlice ( this , start , end )
case 'utf8' :
case 'utf-8' :
return utf8Slice ( this , start , end )
case 'ascii' :
return asciiSlice ( this , start , end )
case 'latin1' :
case 'binary' :
return latin1Slice ( this , start , end )
case 'base64' :
return base64Slice ( this , start , end )
case 'ucs2' :
case 'ucs-2' :
case 'utf16le' :
case 'utf-16le' :
return utf16leSlice ( this , start , end )
default :
if ( loweredCase ) throw new TypeError ( 'Unknown encoding: ' + encoding )
encoding = ( encoding + '' ) . toLowerCase ( ) ;
loweredCase = true ;
}
}
}
// The property is used by `Buffer.isBuffer` and `is-buffer` (in Safari 5-7) to detect
// Buffer instances.
Buffer . prototype . _isBuffer = true ;
function swap ( b , n , m ) {
var i = b [ n ] ;
b [ n ] = b [ m ] ;
b [ m ] = i ;
}
Buffer . prototype . swap16 = function swap16 ( ) {
var len = this . length ;
if ( len % 2 !== 0 ) {
throw new RangeError ( 'Buffer size must be a multiple of 16-bits' )
}
for ( var i = 0 ; i < len ; i += 2 ) {
swap ( this , i , i + 1 ) ;
}
return this
} ;
Buffer . prototype . swap32 = function swap32 ( ) {
var len = this . length ;
if ( len % 4 !== 0 ) {
throw new RangeError ( 'Buffer size must be a multiple of 32-bits' )
}
for ( var i = 0 ; i < len ; i += 4 ) {
swap ( this , i , i + 3 ) ;
swap ( this , i + 1 , i + 2 ) ;
}
return this
} ;
Buffer . prototype . swap64 = function swap64 ( ) {
var len = this . length ;
if ( len % 8 !== 0 ) {
throw new RangeError ( 'Buffer size must be a multiple of 64-bits' )
}
for ( var i = 0 ; i < len ; i += 8 ) {
swap ( this , i , i + 7 ) ;
swap ( this , i + 1 , i + 6 ) ;
swap ( this , i + 2 , i + 5 ) ;
swap ( this , i + 3 , i + 4 ) ;
}
return this
} ;
Buffer . prototype . toString = function toString ( ) {
var length = this . length | 0 ;
if ( length === 0 ) return ''
if ( arguments . length === 0 ) return utf8Slice ( this , 0 , length )
return slowToString . apply ( this , arguments )
} ;
Buffer . prototype . equals = function equals ( b ) {
if ( ! internalIsBuffer ( b ) ) throw new TypeError ( 'Argument must be a Buffer' )
if ( this === b ) return true
return Buffer . compare ( this , b ) === 0
} ;
Buffer . prototype . inspect = function inspect ( ) {
var str = '' ;
var max = INSPECT _MAX _BYTES ;
if ( this . length > 0 ) {
str = this . toString ( 'hex' , 0 , max ) . match ( /.{2}/g ) . join ( ' ' ) ;
if ( this . length > max ) str += ' ... ' ;
}
return '<Buffer ' + str + '>'
} ;
Buffer . prototype . compare = function compare ( target , start , end , thisStart , thisEnd ) {
if ( ! internalIsBuffer ( target ) ) {
throw new TypeError ( 'Argument must be a Buffer' )
}
if ( start === undefined ) {
start = 0 ;
}
if ( end === undefined ) {
end = target ? target . length : 0 ;
}
if ( thisStart === undefined ) {
thisStart = 0 ;
}
if ( thisEnd === undefined ) {
thisEnd = this . length ;
}
if ( start < 0 || end > target . length || thisStart < 0 || thisEnd > this . length ) {
throw new RangeError ( 'out of range index' )
}
if ( thisStart >= thisEnd && start >= end ) {
return 0
}
if ( thisStart >= thisEnd ) {
return - 1
}
if ( start >= end ) {
return 1
}
start >>>= 0 ;
end >>>= 0 ;
thisStart >>>= 0 ;
thisEnd >>>= 0 ;
if ( this === target ) return 0
var x = thisEnd - thisStart ;
var y = end - start ;
var len = Math . min ( x , y ) ;
var thisCopy = this . slice ( thisStart , thisEnd ) ;
var targetCopy = target . slice ( start , end ) ;
for ( var i = 0 ; i < len ; ++ i ) {
if ( thisCopy [ i ] !== targetCopy [ i ] ) {
x = thisCopy [ i ] ;
y = targetCopy [ i ] ;
break
}
}
if ( x < y ) return - 1
if ( y < x ) return 1
return 0
} ;
// Finds either the first index of `val` in `buffer` at offset >= `byteOffset`,
// OR the last index of `val` in `buffer` at offset <= `byteOffset`.
//
// Arguments:
// - buffer - a Buffer to search
// - val - a string, Buffer, or number
// - byteOffset - an index into `buffer`; will be clamped to an int32
// - encoding - an optional encoding, relevant is val is a string
// - dir - true for indexOf, false for lastIndexOf
function bidirectionalIndexOf ( buffer , val , byteOffset , encoding , dir ) {
// Empty buffer means no match
if ( buffer . length === 0 ) return - 1
// Normalize byteOffset
if ( typeof byteOffset === 'string' ) {
encoding = byteOffset ;
byteOffset = 0 ;
} else if ( byteOffset > 0x7fffffff ) {
byteOffset = 0x7fffffff ;
} else if ( byteOffset < - 0x80000000 ) {
byteOffset = - 0x80000000 ;
}
byteOffset = + byteOffset ; // Coerce to Number.
if ( isNaN ( byteOffset ) ) {
// byteOffset: it it's undefined, null, NaN, "foo", etc, search whole buffer
byteOffset = dir ? 0 : ( buffer . length - 1 ) ;
}
// Normalize byteOffset: negative offsets start from the end of the buffer
if ( byteOffset < 0 ) byteOffset = buffer . length + byteOffset ;
if ( byteOffset >= buffer . length ) {
if ( dir ) return - 1
else byteOffset = buffer . length - 1 ;
} else if ( byteOffset < 0 ) {
if ( dir ) byteOffset = 0 ;
else return - 1
}
// Normalize val
if ( typeof val === 'string' ) {
val = Buffer . from ( val , encoding ) ;
}
// Finally, search either indexOf (if dir is true) or lastIndexOf
if ( internalIsBuffer ( val ) ) {
// Special case: looking for empty string/buffer always fails
if ( val . length === 0 ) {
return - 1
}
return arrayIndexOf ( buffer , val , byteOffset , encoding , dir )
} else if ( typeof val === 'number' ) {
val = val & 0xFF ; // Search for a byte value [0-255]
if ( Buffer . TYPED _ARRAY _SUPPORT &&
typeof Uint8Array . prototype . indexOf === 'function' ) {
if ( dir ) {
return Uint8Array . prototype . indexOf . call ( buffer , val , byteOffset )
} else {
return Uint8Array . prototype . lastIndexOf . call ( buffer , val , byteOffset )
}
}
return arrayIndexOf ( buffer , [ val ] , byteOffset , encoding , dir )
}
throw new TypeError ( 'val must be string, number or Buffer' )
}
function arrayIndexOf ( arr , val , byteOffset , encoding , dir ) {
var indexSize = 1 ;
var arrLength = arr . length ;
var valLength = val . length ;
if ( encoding !== undefined ) {
encoding = String ( encoding ) . toLowerCase ( ) ;
if ( encoding === 'ucs2' || encoding === 'ucs-2' ||
encoding === 'utf16le' || encoding === 'utf-16le' ) {
if ( arr . length < 2 || val . length < 2 ) {
return - 1
}
indexSize = 2 ;
arrLength /= 2 ;
valLength /= 2 ;
byteOffset /= 2 ;
}
}
function read ( buf , i ) {
if ( indexSize === 1 ) {
return buf [ i ]
} else {
return buf . readUInt16BE ( i * indexSize )
}
}
var i ;
if ( dir ) {
var foundIndex = - 1 ;
for ( i = byteOffset ; i < arrLength ; i ++ ) {
if ( read ( arr , i ) === read ( val , foundIndex === - 1 ? 0 : i - foundIndex ) ) {
if ( foundIndex === - 1 ) foundIndex = i ;
if ( i - foundIndex + 1 === valLength ) return foundIndex * indexSize
} else {
if ( foundIndex !== - 1 ) i -= i - foundIndex ;
foundIndex = - 1 ;
}
}
} else {
if ( byteOffset + valLength > arrLength ) byteOffset = arrLength - valLength ;
for ( i = byteOffset ; i >= 0 ; i -- ) {
var found = true ;
for ( var j = 0 ; j < valLength ; j ++ ) {
if ( read ( arr , i + j ) !== read ( val , j ) ) {
found = false ;
break
}
}
if ( found ) return i
}
}
return - 1
}
Buffer . prototype . includes = function includes ( val , byteOffset , encoding ) {
return this . indexOf ( val , byteOffset , encoding ) !== - 1
} ;
Buffer . prototype . indexOf = function indexOf ( val , byteOffset , encoding ) {
return bidirectionalIndexOf ( this , val , byteOffset , encoding , true )
} ;
Buffer . prototype . lastIndexOf = function lastIndexOf ( val , byteOffset , encoding ) {
return bidirectionalIndexOf ( this , val , byteOffset , encoding , false )
} ;
function hexWrite ( buf , string , offset , length ) {
offset = Number ( offset ) || 0 ;
var remaining = buf . length - offset ;
if ( ! length ) {
length = remaining ;
} else {
length = Number ( length ) ;
if ( length > remaining ) {
length = remaining ;
}
}
// must be an even number of digits
var strLen = string . length ;
if ( strLen % 2 !== 0 ) throw new TypeError ( 'Invalid hex string' )
if ( length > strLen / 2 ) {
length = strLen / 2 ;
}
for ( var i = 0 ; i < length ; ++ i ) {
var parsed = parseInt ( string . substr ( i * 2 , 2 ) , 16 ) ;
if ( isNaN ( parsed ) ) return i
buf [ offset + i ] = parsed ;
}
return i
}
function utf8Write ( buf , string , offset , length ) {
return blitBuffer ( utf8ToBytes ( string , buf . length - offset ) , buf , offset , length )
}
function asciiWrite ( buf , string , offset , length ) {
return blitBuffer ( asciiToBytes ( string ) , buf , offset , length )
}
function latin1Write ( buf , string , offset , length ) {
return asciiWrite ( buf , string , offset , length )
}
function base64Write ( buf , string , offset , length ) {
return blitBuffer ( base64ToBytes ( string ) , buf , offset , length )
}
function ucs2Write ( buf , string , offset , length ) {
return blitBuffer ( utf16leToBytes ( string , buf . length - offset ) , buf , offset , length )
}
Buffer . prototype . write = function write ( string , offset , length , encoding ) {
// Buffer#write(string)
if ( offset === undefined ) {
encoding = 'utf8' ;
length = this . length ;
offset = 0 ;
// Buffer#write(string, encoding)
} else if ( length === undefined && typeof offset === 'string' ) {
encoding = offset ;
length = this . length ;
offset = 0 ;
// Buffer#write(string, offset[, length][, encoding])
} else if ( isFinite ( offset ) ) {
offset = offset | 0 ;
if ( isFinite ( length ) ) {
length = length | 0 ;
if ( encoding === undefined ) encoding = 'utf8' ;
} else {
encoding = length ;
length = undefined ;
}
// legacy write(string, encoding, offset, length) - remove in v0.13
} else {
throw new Error (
'Buffer.write(string, encoding, offset[, length]) is no longer supported'
)
}
var remaining = this . length - offset ;
if ( length === undefined || length > remaining ) length = remaining ;
if ( ( string . length > 0 && ( length < 0 || offset < 0 ) ) || offset > this . length ) {
throw new RangeError ( 'Attempt to write outside buffer bounds' )
}
if ( ! encoding ) encoding = 'utf8' ;
var loweredCase = false ;
for ( ; ; ) {
switch ( encoding ) {
case 'hex' :
return hexWrite ( this , string , offset , length )
case 'utf8' :
case 'utf-8' :
return utf8Write ( this , string , offset , length )
case 'ascii' :
return asciiWrite ( this , string , offset , length )
case 'latin1' :
case 'binary' :
return latin1Write ( this , string , offset , length )
case 'base64' :
// Warning: maxLength not taken into account in base64Write
return base64Write ( this , string , offset , length )
case 'ucs2' :
case 'ucs-2' :
case 'utf16le' :
case 'utf-16le' :
return ucs2Write ( this , string , offset , length )
default :
if ( loweredCase ) throw new TypeError ( 'Unknown encoding: ' + encoding )
encoding = ( '' + encoding ) . toLowerCase ( ) ;
loweredCase = true ;
}
}
} ;
Buffer . prototype . toJSON = function toJSON ( ) {
return {
type : 'Buffer' ,
data : Array . prototype . slice . call ( this . _arr || this , 0 )
}
} ;
function base64Slice ( buf , start , end ) {
if ( start === 0 && end === buf . length ) {
return fromByteArray ( buf )
} else {
return fromByteArray ( buf . slice ( start , end ) )
}
}
function utf8Slice ( buf , start , end ) {
end = Math . min ( buf . length , end ) ;
var res = [ ] ;
var i = start ;
while ( i < end ) {
var firstByte = buf [ i ] ;
var codePoint = null ;
var bytesPerSequence = ( firstByte > 0xEF ) ? 4
: ( firstByte > 0xDF ) ? 3
: ( firstByte > 0xBF ) ? 2
: 1 ;
if ( i + bytesPerSequence <= end ) {
var secondByte , thirdByte , fourthByte , tempCodePoint ;
switch ( bytesPerSequence ) {
case 1 :
if ( firstByte < 0x80 ) {
codePoint = firstByte ;
}
break
case 2 :
secondByte = buf [ i + 1 ] ;
if ( ( secondByte & 0xC0 ) === 0x80 ) {
tempCodePoint = ( firstByte & 0x1F ) << 0x6 | ( secondByte & 0x3F ) ;
if ( tempCodePoint > 0x7F ) {
codePoint = tempCodePoint ;
}
}
break
case 3 :
secondByte = buf [ i + 1 ] ;
thirdByte = buf [ i + 2 ] ;
if ( ( secondByte & 0xC0 ) === 0x80 && ( thirdByte & 0xC0 ) === 0x80 ) {
tempCodePoint = ( firstByte & 0xF ) << 0xC | ( secondByte & 0x3F ) << 0x6 | ( thirdByte & 0x3F ) ;
if ( tempCodePoint > 0x7FF && ( tempCodePoint < 0xD800 || tempCodePoint > 0xDFFF ) ) {
codePoint = tempCodePoint ;
}
}
break
case 4 :
secondByte = buf [ i + 1 ] ;
thirdByte = buf [ i + 2 ] ;
fourthByte = buf [ i + 3 ] ;
if ( ( secondByte & 0xC0 ) === 0x80 && ( thirdByte & 0xC0 ) === 0x80 && ( fourthByte & 0xC0 ) === 0x80 ) {
tempCodePoint = ( firstByte & 0xF ) << 0x12 | ( secondByte & 0x3F ) << 0xC | ( thirdByte & 0x3F ) << 0x6 | ( fourthByte & 0x3F ) ;
if ( tempCodePoint > 0xFFFF && tempCodePoint < 0x110000 ) {
codePoint = tempCodePoint ;
}
}
}
}
if ( codePoint === null ) {
// we did not generate a valid codePoint so insert a
// replacement char (U+FFFD) and advance only 1 byte
codePoint = 0xFFFD ;
bytesPerSequence = 1 ;
} else if ( codePoint > 0xFFFF ) {
// encode to utf16 (surrogate pair dance)
codePoint -= 0x10000 ;
res . push ( codePoint >>> 10 & 0x3FF | 0xD800 ) ;
codePoint = 0xDC00 | codePoint & 0x3FF ;
}
res . push ( codePoint ) ;
i += bytesPerSequence ;
}
return decodeCodePointsArray ( res )
}
// Based on http://stackoverflow.com/a/22747272/680742, the browser with
// the lowest limit is Chrome, with 0x10000 args.
// We go 1 magnitude less, for safety
var MAX _ARGUMENTS _LENGTH = 0x1000 ;
function decodeCodePointsArray ( codePoints ) {
var len = codePoints . length ;
if ( len <= MAX _ARGUMENTS _LENGTH ) {
return String . fromCharCode . apply ( String , codePoints ) // avoid extra slice()
}
// Decode in chunks to avoid "call stack size exceeded".
var res = '' ;
var i = 0 ;
while ( i < len ) {
res += String . fromCharCode . apply (
String ,
codePoints . slice ( i , i += MAX _ARGUMENTS _LENGTH )
) ;
}
return res
}
function asciiSlice ( buf , start , end ) {
var ret = '' ;
end = Math . min ( buf . length , end ) ;
for ( var i = start ; i < end ; ++ i ) {
ret += String . fromCharCode ( buf [ i ] & 0x7F ) ;
}
return ret
}
function latin1Slice ( buf , start , end ) {
var ret = '' ;
end = Math . min ( buf . length , end ) ;
for ( var i = start ; i < end ; ++ i ) {
ret += String . fromCharCode ( buf [ i ] ) ;
}
return ret
}
function hexSlice ( buf , start , end ) {
var len = buf . length ;
if ( ! start || start < 0 ) start = 0 ;
if ( ! end || end < 0 || end > len ) end = len ;
var out = '' ;
for ( var i = start ; i < end ; ++ i ) {
out += toHex ( buf [ i ] ) ;
}
return out
}
function utf16leSlice ( buf , start , end ) {
var bytes = buf . slice ( start , end ) ;
var res = '' ;
for ( var i = 0 ; i < bytes . length ; i += 2 ) {
res += String . fromCharCode ( bytes [ i ] + bytes [ i + 1 ] * 256 ) ;
}
return res
}
Buffer . prototype . slice = function slice ( start , end ) {
var len = this . length ;
start = ~ ~ start ;
end = end === undefined ? len : ~ ~ end ;
if ( start < 0 ) {
start += len ;
if ( start < 0 ) start = 0 ;
} else if ( start > len ) {
start = len ;
}
if ( end < 0 ) {
end += len ;
if ( end < 0 ) end = 0 ;
} else if ( end > len ) {
end = len ;
}
if ( end < start ) end = start ;
var newBuf ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
newBuf = this . subarray ( start , end ) ;
newBuf . _ _proto _ _ = Buffer . prototype ;
} else {
var sliceLen = end - start ;
newBuf = new Buffer ( sliceLen , undefined ) ;
for ( var i = 0 ; i < sliceLen ; ++ i ) {
newBuf [ i ] = this [ i + start ] ;
}
}
return newBuf
} ;
/ *
* Need to make sure that buffer isn ' t trying to write out of bounds .
* /
function checkOffset ( offset , ext , length ) {
if ( ( offset % 1 ) !== 0 || offset < 0 ) throw new RangeError ( 'offset is not uint' )
if ( offset + ext > length ) throw new RangeError ( 'Trying to access beyond buffer length' )
}
Buffer . prototype . readUIntLE = function readUIntLE ( offset , byteLength , noAssert ) {
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) checkOffset ( offset , byteLength , this . length ) ;
var val = this [ offset ] ;
var mul = 1 ;
var i = 0 ;
while ( ++ i < byteLength && ( mul *= 0x100 ) ) {
val += this [ offset + i ] * mul ;
}
return val
} ;
Buffer . prototype . readUIntBE = function readUIntBE ( offset , byteLength , noAssert ) {
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) {
checkOffset ( offset , byteLength , this . length ) ;
}
var val = this [ offset + -- byteLength ] ;
var mul = 1 ;
while ( byteLength > 0 && ( mul *= 0x100 ) ) {
val += this [ offset + -- byteLength ] * mul ;
}
return val
} ;
Buffer . prototype . readUInt8 = function readUInt8 ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 1 , this . length ) ;
return this [ offset ]
} ;
Buffer . prototype . readUInt16LE = function readUInt16LE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 2 , this . length ) ;
return this [ offset ] | ( this [ offset + 1 ] << 8 )
} ;
Buffer . prototype . readUInt16BE = function readUInt16BE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 2 , this . length ) ;
return ( this [ offset ] << 8 ) | this [ offset + 1 ]
} ;
Buffer . prototype . readUInt32LE = function readUInt32LE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return ( ( this [ offset ] ) |
( this [ offset + 1 ] << 8 ) |
( this [ offset + 2 ] << 16 ) ) +
( this [ offset + 3 ] * 0x1000000 )
} ;
Buffer . prototype . readUInt32BE = function readUInt32BE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return ( this [ offset ] * 0x1000000 ) +
( ( this [ offset + 1 ] << 16 ) |
( this [ offset + 2 ] << 8 ) |
this [ offset + 3 ] )
} ;
Buffer . prototype . readIntLE = function readIntLE ( offset , byteLength , noAssert ) {
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) checkOffset ( offset , byteLength , this . length ) ;
var val = this [ offset ] ;
var mul = 1 ;
var i = 0 ;
while ( ++ i < byteLength && ( mul *= 0x100 ) ) {
val += this [ offset + i ] * mul ;
}
mul *= 0x80 ;
if ( val >= mul ) val -= Math . pow ( 2 , 8 * byteLength ) ;
return val
} ;
Buffer . prototype . readIntBE = function readIntBE ( offset , byteLength , noAssert ) {
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) checkOffset ( offset , byteLength , this . length ) ;
var i = byteLength ;
var mul = 1 ;
var val = this [ offset + -- i ] ;
while ( i > 0 && ( mul *= 0x100 ) ) {
val += this [ offset + -- i ] * mul ;
}
mul *= 0x80 ;
if ( val >= mul ) val -= Math . pow ( 2 , 8 * byteLength ) ;
return val
} ;
Buffer . prototype . readInt8 = function readInt8 ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 1 , this . length ) ;
if ( ! ( this [ offset ] & 0x80 ) ) return ( this [ offset ] )
return ( ( 0xff - this [ offset ] + 1 ) * - 1 )
} ;
Buffer . prototype . readInt16LE = function readInt16LE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 2 , this . length ) ;
var val = this [ offset ] | ( this [ offset + 1 ] << 8 ) ;
return ( val & 0x8000 ) ? val | 0xFFFF0000 : val
} ;
Buffer . prototype . readInt16BE = function readInt16BE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 2 , this . length ) ;
var val = this [ offset + 1 ] | ( this [ offset ] << 8 ) ;
return ( val & 0x8000 ) ? val | 0xFFFF0000 : val
} ;
Buffer . prototype . readInt32LE = function readInt32LE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return ( this [ offset ] ) |
( this [ offset + 1 ] << 8 ) |
( this [ offset + 2 ] << 16 ) |
( this [ offset + 3 ] << 24 )
} ;
Buffer . prototype . readInt32BE = function readInt32BE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return ( this [ offset ] << 24 ) |
( this [ offset + 1 ] << 16 ) |
( this [ offset + 2 ] << 8 ) |
( this [ offset + 3 ] )
} ;
Buffer . prototype . readFloatLE = function readFloatLE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return read ( this , offset , true , 23 , 4 )
} ;
Buffer . prototype . readFloatBE = function readFloatBE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 4 , this . length ) ;
return read ( this , offset , false , 23 , 4 )
} ;
Buffer . prototype . readDoubleLE = function readDoubleLE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 8 , this . length ) ;
return read ( this , offset , true , 52 , 8 )
} ;
Buffer . prototype . readDoubleBE = function readDoubleBE ( offset , noAssert ) {
if ( ! noAssert ) checkOffset ( offset , 8 , this . length ) ;
return read ( this , offset , false , 52 , 8 )
} ;
function checkInt ( buf , value , offset , ext , max , min ) {
if ( ! internalIsBuffer ( buf ) ) throw new TypeError ( '"buffer" argument must be a Buffer instance' )
if ( value > max || value < min ) throw new RangeError ( '"value" argument is out of bounds' )
if ( offset + ext > buf . length ) throw new RangeError ( 'Index out of range' )
}
Buffer . prototype . writeUIntLE = function writeUIntLE ( value , offset , byteLength , noAssert ) {
value = + value ;
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) {
var maxBytes = Math . pow ( 2 , 8 * byteLength ) - 1 ;
checkInt ( this , value , offset , byteLength , maxBytes , 0 ) ;
}
var mul = 1 ;
var i = 0 ;
this [ offset ] = value & 0xFF ;
while ( ++ i < byteLength && ( mul *= 0x100 ) ) {
this [ offset + i ] = ( value / mul ) & 0xFF ;
}
return offset + byteLength
} ;
Buffer . prototype . writeUIntBE = function writeUIntBE ( value , offset , byteLength , noAssert ) {
value = + value ;
offset = offset | 0 ;
byteLength = byteLength | 0 ;
if ( ! noAssert ) {
var maxBytes = Math . pow ( 2 , 8 * byteLength ) - 1 ;
checkInt ( this , value , offset , byteLength , maxBytes , 0 ) ;
}
var i = byteLength - 1 ;
var mul = 1 ;
this [ offset + i ] = value & 0xFF ;
while ( -- i >= 0 && ( mul *= 0x100 ) ) {
this [ offset + i ] = ( value / mul ) & 0xFF ;
}
return offset + byteLength
} ;
Buffer . prototype . writeUInt8 = function writeUInt8 ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 1 , 0xff , 0 ) ;
if ( ! Buffer . TYPED _ARRAY _SUPPORT ) value = Math . floor ( value ) ;
this [ offset ] = ( value & 0xff ) ;
return offset + 1
} ;
function objectWriteUInt16 ( buf , value , offset , littleEndian ) {
if ( value < 0 ) value = 0xffff + value + 1 ;
for ( var i = 0 , j = Math . min ( buf . length - offset , 2 ) ; i < j ; ++ i ) {
buf [ offset + i ] = ( value & ( 0xff << ( 8 * ( littleEndian ? i : 1 - i ) ) ) ) >>>
( littleEndian ? i : 1 - i ) * 8 ;
}
}
Buffer . prototype . writeUInt16LE = function writeUInt16LE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 2 , 0xffff , 0 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value & 0xff ) ;
this [ offset + 1 ] = ( value >>> 8 ) ;
} else {
objectWriteUInt16 ( this , value , offset , true ) ;
}
return offset + 2
} ;
Buffer . prototype . writeUInt16BE = function writeUInt16BE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 2 , 0xffff , 0 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value >>> 8 ) ;
this [ offset + 1 ] = ( value & 0xff ) ;
} else {
objectWriteUInt16 ( this , value , offset , false ) ;
}
return offset + 2
} ;
function objectWriteUInt32 ( buf , value , offset , littleEndian ) {
if ( value < 0 ) value = 0xffffffff + value + 1 ;
for ( var i = 0 , j = Math . min ( buf . length - offset , 4 ) ; i < j ; ++ i ) {
buf [ offset + i ] = ( value >>> ( littleEndian ? i : 3 - i ) * 8 ) & 0xff ;
}
}
Buffer . prototype . writeUInt32LE = function writeUInt32LE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 4 , 0xffffffff , 0 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset + 3 ] = ( value >>> 24 ) ;
this [ offset + 2 ] = ( value >>> 16 ) ;
this [ offset + 1 ] = ( value >>> 8 ) ;
this [ offset ] = ( value & 0xff ) ;
} else {
objectWriteUInt32 ( this , value , offset , true ) ;
}
return offset + 4
} ;
Buffer . prototype . writeUInt32BE = function writeUInt32BE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 4 , 0xffffffff , 0 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value >>> 24 ) ;
this [ offset + 1 ] = ( value >>> 16 ) ;
this [ offset + 2 ] = ( value >>> 8 ) ;
this [ offset + 3 ] = ( value & 0xff ) ;
} else {
objectWriteUInt32 ( this , value , offset , false ) ;
}
return offset + 4
} ;
Buffer . prototype . writeIntLE = function writeIntLE ( value , offset , byteLength , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) {
var limit = Math . pow ( 2 , 8 * byteLength - 1 ) ;
checkInt ( this , value , offset , byteLength , limit - 1 , - limit ) ;
}
var i = 0 ;
var mul = 1 ;
var sub = 0 ;
this [ offset ] = value & 0xFF ;
while ( ++ i < byteLength && ( mul *= 0x100 ) ) {
if ( value < 0 && sub === 0 && this [ offset + i - 1 ] !== 0 ) {
sub = 1 ;
}
this [ offset + i ] = ( ( value / mul ) >> 0 ) - sub & 0xFF ;
}
return offset + byteLength
} ;
Buffer . prototype . writeIntBE = function writeIntBE ( value , offset , byteLength , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) {
var limit = Math . pow ( 2 , 8 * byteLength - 1 ) ;
checkInt ( this , value , offset , byteLength , limit - 1 , - limit ) ;
}
var i = byteLength - 1 ;
var mul = 1 ;
var sub = 0 ;
this [ offset + i ] = value & 0xFF ;
while ( -- i >= 0 && ( mul *= 0x100 ) ) {
if ( value < 0 && sub === 0 && this [ offset + i + 1 ] !== 0 ) {
sub = 1 ;
}
this [ offset + i ] = ( ( value / mul ) >> 0 ) - sub & 0xFF ;
}
return offset + byteLength
} ;
Buffer . prototype . writeInt8 = function writeInt8 ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 1 , 0x7f , - 0x80 ) ;
if ( ! Buffer . TYPED _ARRAY _SUPPORT ) value = Math . floor ( value ) ;
if ( value < 0 ) value = 0xff + value + 1 ;
this [ offset ] = ( value & 0xff ) ;
return offset + 1
} ;
Buffer . prototype . writeInt16LE = function writeInt16LE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 2 , 0x7fff , - 0x8000 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value & 0xff ) ;
this [ offset + 1 ] = ( value >>> 8 ) ;
} else {
objectWriteUInt16 ( this , value , offset , true ) ;
}
return offset + 2
} ;
Buffer . prototype . writeInt16BE = function writeInt16BE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 2 , 0x7fff , - 0x8000 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value >>> 8 ) ;
this [ offset + 1 ] = ( value & 0xff ) ;
} else {
objectWriteUInt16 ( this , value , offset , false ) ;
}
return offset + 2
} ;
Buffer . prototype . writeInt32LE = function writeInt32LE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 4 , 0x7fffffff , - 0x80000000 ) ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value & 0xff ) ;
this [ offset + 1 ] = ( value >>> 8 ) ;
this [ offset + 2 ] = ( value >>> 16 ) ;
this [ offset + 3 ] = ( value >>> 24 ) ;
} else {
objectWriteUInt32 ( this , value , offset , true ) ;
}
return offset + 4
} ;
Buffer . prototype . writeInt32BE = function writeInt32BE ( value , offset , noAssert ) {
value = + value ;
offset = offset | 0 ;
if ( ! noAssert ) checkInt ( this , value , offset , 4 , 0x7fffffff , - 0x80000000 ) ;
if ( value < 0 ) value = 0xffffffff + value + 1 ;
if ( Buffer . TYPED _ARRAY _SUPPORT ) {
this [ offset ] = ( value >>> 24 ) ;
this [ offset + 1 ] = ( value >>> 16 ) ;
this [ offset + 2 ] = ( value >>> 8 ) ;
this [ offset + 3 ] = ( value & 0xff ) ;
} else {
objectWriteUInt32 ( this , value , offset , false ) ;
}
return offset + 4
} ;
function checkIEEE754 ( buf , value , offset , ext , max , min ) {
if ( offset + ext > buf . length ) throw new RangeError ( 'Index out of range' )
if ( offset < 0 ) throw new RangeError ( 'Index out of range' )
}
function writeFloat ( buf , value , offset , littleEndian , noAssert ) {
if ( ! noAssert ) {
checkIEEE754 ( buf , value , offset , 4 ) ;
}
write ( buf , value , offset , littleEndian , 23 , 4 ) ;
return offset + 4
}
Buffer . prototype . writeFloatLE = function writeFloatLE ( value , offset , noAssert ) {
return writeFloat ( this , value , offset , true , noAssert )
} ;
Buffer . prototype . writeFloatBE = function writeFloatBE ( value , offset , noAssert ) {
return writeFloat ( this , value , offset , false , noAssert )
} ;
function writeDouble ( buf , value , offset , littleEndian , noAssert ) {
if ( ! noAssert ) {
checkIEEE754 ( buf , value , offset , 8 ) ;
}
write ( buf , value , offset , littleEndian , 52 , 8 ) ;
return offset + 8
}
Buffer . prototype . writeDoubleLE = function writeDoubleLE ( value , offset , noAssert ) {
return writeDouble ( this , value , offset , true , noAssert )
} ;
Buffer . prototype . writeDoubleBE = function writeDoubleBE ( value , offset , noAssert ) {
return writeDouble ( this , value , offset , false , noAssert )
} ;
// copy(targetBuffer, targetStart=0, sourceStart=0, sourceEnd=buffer.length)
Buffer . prototype . copy = function copy ( target , targetStart , start , end ) {
if ( ! start ) start = 0 ;
if ( ! end && end !== 0 ) end = this . length ;
if ( targetStart >= target . length ) targetStart = target . length ;
if ( ! targetStart ) targetStart = 0 ;
if ( end > 0 && end < start ) end = start ;
// Copy 0 bytes; we're done
if ( end === start ) return 0
if ( target . length === 0 || this . length === 0 ) return 0
// Fatal error conditions
if ( targetStart < 0 ) {
throw new RangeError ( 'targetStart out of bounds' )
}
if ( start < 0 || start >= this . length ) throw new RangeError ( 'sourceStart out of bounds' )
if ( end < 0 ) throw new RangeError ( 'sourceEnd out of bounds' )
// Are we oob?
if ( end > this . length ) end = this . length ;
if ( target . length - targetStart < end - start ) {
end = target . length - targetStart + start ;
}
var len = end - start ;
var i ;
if ( this === target && start < targetStart && targetStart < end ) {
// descending copy from end
for ( i = len - 1 ; i >= 0 ; -- i ) {
target [ i + targetStart ] = this [ i + start ] ;
}
} else if ( len < 1000 || ! Buffer . TYPED _ARRAY _SUPPORT ) {
// ascending copy from start
for ( i = 0 ; i < len ; ++ i ) {
target [ i + targetStart ] = this [ i + start ] ;
}
} else {
Uint8Array . prototype . set . call (
target ,
this . subarray ( start , start + len ) ,
targetStart
) ;
}
return len
} ;
// Usage:
// buffer.fill(number[, offset[, end]])
// buffer.fill(buffer[, offset[, end]])
// buffer.fill(string[, offset[, end]][, encoding])
Buffer . prototype . fill = function fill ( val , start , end , encoding ) {
// Handle string cases:
if ( typeof val === 'string' ) {
if ( typeof start === 'string' ) {
encoding = start ;
start = 0 ;
end = this . length ;
} else if ( typeof end === 'string' ) {
encoding = end ;
end = this . length ;
}
if ( val . length === 1 ) {
var code = val . charCodeAt ( 0 ) ;
if ( code < 256 ) {
val = code ;
}
}
if ( encoding !== undefined && typeof encoding !== 'string' ) {
throw new TypeError ( 'encoding must be a string' )
}
if ( typeof encoding === 'string' && ! Buffer . isEncoding ( encoding ) ) {
throw new TypeError ( 'Unknown encoding: ' + encoding )
}
} else if ( typeof val === 'number' ) {
val = val & 255 ;
}
// Invalid ranges are not set to a default, so can range check early.
if ( start < 0 || this . length < start || this . length < end ) {
throw new RangeError ( 'Out of range index' )
}
if ( end <= start ) {
return this
}
start = start >>> 0 ;
end = end === undefined ? this . length : end >>> 0 ;
if ( ! val ) val = 0 ;
var i ;
if ( typeof val === 'number' ) {
for ( i = start ; i < end ; ++ i ) {
this [ i ] = val ;
}
} else {
var bytes = internalIsBuffer ( val )
? val
: utf8ToBytes ( new Buffer ( val , encoding ) . toString ( ) ) ;
var len = bytes . length ;
for ( i = 0 ; i < end - start ; ++ i ) {
this [ i + start ] = bytes [ i % len ] ;
}
}
return this
} ;
// HELPER FUNCTIONS
// ================
var INVALID _BASE64 _RE = /[^+\/0-9A-Za-z-_]/g ;
function base64clean ( str ) {
// Node strips out invalid characters like \n and \t from the string, base64-js does not
str = stringtrim ( str ) . replace ( INVALID _BASE64 _RE , '' ) ;
// Node converts strings with length < 2 to ''
if ( str . length < 2 ) return ''
// Node allows for non-padded base64 strings (missing trailing ===), base64-js does not
while ( str . length % 4 !== 0 ) {
str = str + '=' ;
}
return str
}
function stringtrim ( str ) {
if ( str . trim ) return str . trim ( )
return str . replace ( /^\s+|\s+$/g , '' )
}
function toHex ( n ) {
if ( n < 16 ) return '0' + n . toString ( 16 )
return n . toString ( 16 )
}
function utf8ToBytes ( string , units ) {
units = units || Infinity ;
var codePoint ;
var length = string . length ;
var leadSurrogate = null ;
var bytes = [ ] ;
for ( var i = 0 ; i < length ; ++ i ) {
codePoint = string . charCodeAt ( i ) ;
// is surrogate component
if ( codePoint > 0xD7FF && codePoint < 0xE000 ) {
// last char was a lead
if ( ! leadSurrogate ) {
// no lead yet
if ( codePoint > 0xDBFF ) {
// unexpected trail
if ( ( units -= 3 ) > - 1 ) bytes . push ( 0xEF , 0xBF , 0xBD ) ;
continue
} else if ( i + 1 === length ) {
// unpaired lead
if ( ( units -= 3 ) > - 1 ) bytes . push ( 0xEF , 0xBF , 0xBD ) ;
continue
}
// valid lead
leadSurrogate = codePoint ;
continue
}
// 2 leads in a row
if ( codePoint < 0xDC00 ) {
if ( ( units -= 3 ) > - 1 ) bytes . push ( 0xEF , 0xBF , 0xBD ) ;
leadSurrogate = codePoint ;
continue
}
// valid surrogate pair
codePoint = ( leadSurrogate - 0xD800 << 10 | codePoint - 0xDC00 ) + 0x10000 ;
} else if ( leadSurrogate ) {
// valid bmp char, but last char was a lead
if ( ( units -= 3 ) > - 1 ) bytes . push ( 0xEF , 0xBF , 0xBD ) ;
}
leadSurrogate = null ;
// encode utf8
if ( codePoint < 0x80 ) {
if ( ( units -= 1 ) < 0 ) break
bytes . push ( codePoint ) ;
} else if ( codePoint < 0x800 ) {
if ( ( units -= 2 ) < 0 ) break
bytes . push (
codePoint >> 0x6 | 0xC0 ,
codePoint & 0x3F | 0x80
) ;
} else if ( codePoint < 0x10000 ) {
if ( ( units -= 3 ) < 0 ) break
bytes . push (
codePoint >> 0xC | 0xE0 ,
codePoint >> 0x6 & 0x3F | 0x80 ,
codePoint & 0x3F | 0x80
) ;
} else if ( codePoint < 0x110000 ) {
if ( ( units -= 4 ) < 0 ) break
bytes . push (
codePoint >> 0x12 | 0xF0 ,
codePoint >> 0xC & 0x3F | 0x80 ,
codePoint >> 0x6 & 0x3F | 0x80 ,
codePoint & 0x3F | 0x80
) ;
} else {
throw new Error ( 'Invalid code point' )
}
}
return bytes
}
function asciiToBytes ( str ) {
var byteArray = [ ] ;
for ( var i = 0 ; i < str . length ; ++ i ) {
// Node's code seems to be doing this and not & 0x7F..
byteArray . push ( str . charCodeAt ( i ) & 0xFF ) ;
}
return byteArray
}
function utf16leToBytes ( str , units ) {
var c , hi , lo ;
var byteArray = [ ] ;
for ( var i = 0 ; i < str . length ; ++ i ) {
if ( ( units -= 2 ) < 0 ) break
c = str . charCodeAt ( i ) ;
hi = c >> 8 ;
lo = c % 256 ;
byteArray . push ( lo ) ;
byteArray . push ( hi ) ;
}
return byteArray
}
function base64ToBytes ( str ) {
return toByteArray ( base64clean ( str ) )
}
function blitBuffer ( src , dst , offset , length ) {
for ( var i = 0 ; i < length ; ++ i ) {
if ( ( i + offset >= dst . length ) || ( i >= src . length ) ) break
dst [ i + offset ] = src [ i ] ;
}
return i
}
function isnan ( val ) {
return val !== val // eslint-disable-line no-self-compare
}
// the following is from is-buffer, also by Feross Aboukhadijeh and with same lisence
// The _isBuffer check is for Safari 5-7 support, because it's missing
// Object.prototype.constructor. Remove this eventually
function isBuffer ( obj ) {
return obj != null && ( ! ! obj . _isBuffer || isFastBuffer ( obj ) || isSlowBuffer ( obj ) )
}
function isFastBuffer ( obj ) {
return ! ! obj . constructor && typeof obj . constructor . isBuffer === 'function' && obj . constructor . isBuffer ( obj )
}
// For Node v0.10 support. Remove this eventually.
function isSlowBuffer ( obj ) {
return typeof obj . readFloatLE === 'function' && typeof obj . slice === 'function' && isFastBuffer ( obj . slice ( 0 , 0 ) )
}
/ * *
* Create an Error with the specified message , config , error code , request and response .
*
* @ param { string } message The error message .
* @ param { string } [ code ] The error code ( for example , 'ECONNABORTED' ) .
* @ param { Object } [ config ] The config .
* @ param { Object } [ request ] The request .
* @ param { Object } [ response ] The response .
*
* @ returns { Error } The created error .
* /
function AxiosError ( message , code , config , request , response ) {
Error . call ( this ) ;
if ( Error . captureStackTrace ) {
Error . captureStackTrace ( this , this . constructor ) ;
} else {
this . stack = ( new Error ( ) ) . stack ;
}
this . message = message ;
this . name = 'AxiosError' ;
code && ( this . code = code ) ;
config && ( this . config = config ) ;
request && ( this . request = request ) ;
response && ( this . response = response ) ;
}
utils$1 . inherits ( AxiosError , Error , {
toJSON : function toJSON ( ) {
return {
// Standard
message : this . message ,
name : this . name ,
// Microsoft
description : this . description ,
number : this . number ,
// Mozilla
fileName : this . fileName ,
lineNumber : this . lineNumber ,
columnNumber : this . columnNumber ,
stack : this . stack ,
// Axios
config : utils$1 . toJSONObject ( this . config ) ,
code : this . code ,
status : this . response && this . response . status ? this . response . status : null
} ;
}
} ) ;
const prototype$1 = AxiosError . prototype ;
const descriptors = { } ;
[
'ERR_BAD_OPTION_VALUE' ,
'ERR_BAD_OPTION' ,
'ECONNABORTED' ,
'ETIMEDOUT' ,
'ERR_NETWORK' ,
'ERR_FR_TOO_MANY_REDIRECTS' ,
'ERR_DEPRECATED' ,
'ERR_BAD_RESPONSE' ,
'ERR_BAD_REQUEST' ,
'ERR_CANCELED' ,
'ERR_NOT_SUPPORT' ,
'ERR_INVALID_URL'
// eslint-disable-next-line func-names
] . forEach ( code => {
descriptors [ code ] = { value : code } ;
} ) ;
Object . defineProperties ( AxiosError , descriptors ) ;
Object . defineProperty ( prototype$1 , 'isAxiosError' , { value : true } ) ;
// eslint-disable-next-line func-names
AxiosError . from = ( error , code , config , request , response , customProps ) => {
const axiosError = Object . create ( prototype$1 ) ;
utils$1 . toFlatObject ( error , axiosError , function filter ( obj ) {
return obj !== Error . prototype ;
} , prop => {
return prop !== 'isAxiosError' ;
} ) ;
AxiosError . call ( axiosError , error . message , code , config , request , response ) ;
axiosError . cause = error ;
axiosError . name = error . name ;
customProps && Object . assign ( axiosError , customProps ) ;
return axiosError ;
} ;
// eslint-disable-next-line strict
var httpAdapter = null ;
/ * *
* Determines if the given thing is a array or js object .
*
* @ param { string } thing - The object or array to be visited .
*
* @ returns { boolean }
* /
function isVisitable ( thing ) {
return utils$1 . isPlainObject ( thing ) || utils$1 . isArray ( thing ) ;
}
/ * *
* It removes the brackets from the end of a string
*
* @ param { string } key - The key of the parameter .
*
* @ returns { string } the key without the brackets .
* /
function removeBrackets ( key ) {
return utils$1 . endsWith ( key , '[]' ) ? key . slice ( 0 , - 2 ) : key ;
}
/ * *
* It takes a path , a key , and a boolean , and returns a string
*
* @ param { string } path - The path to the current key .
* @ param { string } key - The key of the current object being iterated over .
* @ param { string } dots - If true , the key will be rendered with dots instead of brackets .
*
* @ returns { string } The path to the current key .
* /
function renderKey ( path , key , dots ) {
if ( ! path ) return key ;
return path . concat ( key ) . map ( function each ( token , i ) {
// eslint-disable-next-line no-param-reassign
token = removeBrackets ( token ) ;
return ! dots && i ? '[' + token + ']' : token ;
} ) . join ( dots ? '.' : '' ) ;
}
/ * *
* If the array is an array and none of its elements are visitable , then it ' s a flat array .
*
* @ param { Array < any > } arr - The array to check
*
* @ returns { boolean }
* /
function isFlatArray ( arr ) {
return utils$1 . isArray ( arr ) && ! arr . some ( isVisitable ) ;
}
const predicates = utils$1 . toFlatObject ( utils$1 , { } , null , function filter ( prop ) {
return /^is[A-Z]/ . test ( prop ) ;
} ) ;
/ * *
* Convert a data object to FormData
*
* @ param { Object } obj
* @ param { ? Object } [ formData ]
* @ param { ? Object } [ options ]
* @ param { Function } [ options . visitor ]
* @ param { Boolean } [ options . metaTokens = true ]
* @ param { Boolean } [ options . dots = false ]
* @ param { ? Boolean } [ options . indexes = false ]
*
* @ returns { Object }
* * /
/ * *
* It converts an object into a FormData object
*
* @ param { Object < any , any > } obj - The object to convert to form data .
* @ param { string } formData - The FormData object to append to .
* @ param { Object < string , any > } options
*
* @ returns
* /
function toFormData ( obj , formData , options ) {
if ( ! utils$1 . isObject ( obj ) ) {
throw new TypeError ( 'target must be an object' ) ;
}
// eslint-disable-next-line no-param-reassign
formData = formData || new ( FormData ) ( ) ;
// eslint-disable-next-line no-param-reassign
options = utils$1 . toFlatObject ( options , {
metaTokens : true ,
dots : false ,
indexes : false
} , false , function defined ( option , source ) {
// eslint-disable-next-line no-eq-null,eqeqeq
return ! utils$1 . isUndefined ( source [ option ] ) ;
} ) ;
const metaTokens = options . metaTokens ;
// eslint-disable-next-line no-use-before-define
const visitor = options . visitor || defaultVisitor ;
const dots = options . dots ;
const indexes = options . indexes ;
const _Blob = options . Blob || typeof Blob !== 'undefined' && Blob ;
const useBlob = _Blob && utils$1 . isSpecCompliantForm ( formData ) ;
if ( ! utils$1 . isFunction ( visitor ) ) {
throw new TypeError ( 'visitor must be a function' ) ;
}
function convertValue ( value ) {
if ( value === null ) return '' ;
if ( utils$1 . isDate ( value ) ) {
return value . toISOString ( ) ;
}
if ( ! useBlob && utils$1 . isBlob ( value ) ) {
throw new AxiosError ( 'Blob is not supported. Use a Buffer instead.' ) ;
}
if ( utils$1 . isArrayBuffer ( value ) || utils$1 . isTypedArray ( value ) ) {
return useBlob && typeof Blob === 'function' ? new Blob ( [ value ] ) : Buffer . from ( value ) ;
}
return value ;
}
/ * *
* Default visitor .
*
* @ param { * } value
* @ param { String | Number } key
* @ param { Array < String | Number > } path
* @ this { FormData }
*
* @ returns { boolean } return true to visit the each prop of the value recursively
* /
function defaultVisitor ( value , key , path ) {
let arr = value ;
if ( value && ! path && typeof value === 'object' ) {
if ( utils$1 . endsWith ( key , '{}' ) ) {
// eslint-disable-next-line no-param-reassign
key = metaTokens ? key : key . slice ( 0 , - 2 ) ;
// eslint-disable-next-line no-param-reassign
value = JSON . stringify ( value ) ;
} else if (
( utils$1 . isArray ( value ) && isFlatArray ( value ) ) ||
( ( utils$1 . isFileList ( value ) || utils$1 . endsWith ( key , '[]' ) ) && ( arr = utils$1 . toArray ( value ) )
) ) {
// eslint-disable-next-line no-param-reassign
key = removeBrackets ( key ) ;
arr . forEach ( function each ( el , index ) {
! ( utils$1 . isUndefined ( el ) || el === null ) && formData . append (
// eslint-disable-next-line no-nested-ternary
indexes === true ? renderKey ( [ key ] , index , dots ) : ( indexes === null ? key : key + '[]' ) ,
convertValue ( el )
) ;
} ) ;
return false ;
}
}
if ( isVisitable ( value ) ) {
return true ;
}
formData . append ( renderKey ( path , key , dots ) , convertValue ( value ) ) ;
return false ;
}
const stack = [ ] ;
const exposedHelpers = Object . assign ( predicates , {
defaultVisitor ,
convertValue ,
isVisitable
} ) ;
function build ( value , path ) {
if ( utils$1 . isUndefined ( value ) ) return ;
if ( stack . indexOf ( value ) !== - 1 ) {
throw Error ( 'Circular reference detected in ' + path . join ( '.' ) ) ;
}
stack . push ( value ) ;
utils$1 . forEach ( value , function each ( el , key ) {
const result = ! ( utils$1 . isUndefined ( el ) || el === null ) && visitor . call (
formData , el , utils$1 . isString ( key ) ? key . trim ( ) : key , path , exposedHelpers
) ;
if ( result === true ) {
build ( el , path ? path . concat ( key ) : [ key ] ) ;
}
} ) ;
stack . pop ( ) ;
}
if ( ! utils$1 . isObject ( obj ) ) {
throw new TypeError ( 'data must be an object' ) ;
}
build ( obj ) ;
return formData ;
}
/ * *
* It encodes a string by replacing all characters that are not in the unreserved set with
* their percent - encoded equivalents
*
* @ param { string } str - The string to encode .
*
* @ returns { string } The encoded string .
* /
function encode$2 ( str ) {
const charMap = {
'!' : '%21' ,
"'" : '%27' ,
'(' : '%28' ,
')' : '%29' ,
'~' : '%7E' ,
'%20' : '+' ,
'%00' : '\x00'
} ;
return encodeURIComponent ( str ) . replace ( /[!'()~]|%20|%00/g , function replacer ( match ) {
return charMap [ match ] ;
} ) ;
}
/ * *
* It takes a params object and converts it to a FormData object
*
* @ param { Object < string , any > } params - The parameters to be converted to a FormData object .
* @ param { Object < string , any > } options - The options object passed to the Axios constructor .
*
* @ returns { void }
* /
function AxiosURLSearchParams ( params , options ) {
this . _pairs = [ ] ;
params && toFormData ( params , this , options ) ;
}
const prototype = AxiosURLSearchParams . prototype ;
prototype . append = function append ( name , value ) {
this . _pairs . push ( [ name , value ] ) ;
} ;
prototype . toString = function toString ( encoder ) {
const _encode = encoder ? function ( value ) {
return encoder . call ( this , value , encode$2 ) ;
} : encode$2 ;
return this . _pairs . map ( function each ( pair ) {
return _encode ( pair [ 0 ] ) + '=' + _encode ( pair [ 1 ] ) ;
} , '' ) . join ( '&' ) ;
} ;
/ * *
* It replaces all instances of the characters ` : ` , ` $ ` , ` , ` , ` + ` , ` [ ` , and ` ] ` with their
* URI encoded counterparts
*
* @ param { string } val The value to be encoded .
*
* @ returns { string } The encoded value .
* /
function encode$1 ( val ) {
return encodeURIComponent ( val ) .
replace ( /%3A/gi , ':' ) .
replace ( /%24/g , '$' ) .
replace ( /%2C/gi , ',' ) .
replace ( /%20/g , '+' ) .
replace ( /%5B/gi , '[' ) .
replace ( /%5D/gi , ']' ) ;
}
/ * *
* Build a URL by appending params to the end
*
* @ param { string } url The base of the url ( e . g . , http : //www.google.com)
* @ param { object } [ params ] The params to be appended
* @ param { ? object } options
*
* @ returns { string } The formatted url
* /
function buildURL ( url , params , options ) {
/*eslint no-param-reassign:0*/
if ( ! params ) {
return url ;
}
const _encode = options && options . encode || encode$1 ;
const serializeFn = options && options . serialize ;
let serializedParams ;
if ( serializeFn ) {
serializedParams = serializeFn ( params , options ) ;
} else {
serializedParams = utils$1 . isURLSearchParams ( params ) ?
params . toString ( ) :
new AxiosURLSearchParams ( params , options ) . toString ( _encode ) ;
}
if ( serializedParams ) {
const hashmarkIndex = url . indexOf ( "#" ) ;
if ( hashmarkIndex !== - 1 ) {
url = url . slice ( 0 , hashmarkIndex ) ;
}
url += ( url . indexOf ( '?' ) === - 1 ? '?' : '&' ) + serializedParams ;
}
return url ;
}
class InterceptorManager {
constructor ( ) {
this . handlers = [ ] ;
}
/ * *
* Add a new interceptor to the stack
*
* @ param { Function } fulfilled The function to handle ` then ` for a ` Promise `
* @ param { Function } rejected The function to handle ` reject ` for a ` Promise `
*
* @ return { Number } An ID used to remove interceptor later
* /
use ( fulfilled , rejected , options ) {
this . handlers . push ( {
fulfilled ,
rejected ,
synchronous : options ? options . synchronous : false ,
runWhen : options ? options . runWhen : null
} ) ;
return this . handlers . length - 1 ;
}
/ * *
* Remove an interceptor from the stack
*
* @ param { Number } id The ID that was returned by ` use `
*
* @ returns { Boolean } ` true ` if the interceptor was removed , ` false ` otherwise
* /
eject ( id ) {
if ( this . handlers [ id ] ) {
this . handlers [ id ] = null ;
}
}
/ * *
* Clear all interceptors from the stack
*
* @ returns { void }
* /
clear ( ) {
if ( this . handlers ) {
this . handlers = [ ] ;
}
}
/ * *
* Iterate over all the registered interceptors
*
* This method is particularly useful for skipping over any
* interceptors that may have become ` null ` calling ` eject ` .
*
* @ param { Function } fn The function to call for each interceptor
*
* @ returns { void }
* /
forEach ( fn ) {
utils$1 . forEach ( this . handlers , function forEachHandler ( h ) {
if ( h !== null ) {
fn ( h ) ;
}
} ) ;
}
}
var InterceptorManager$1 = InterceptorManager ;
var transitionalDefaults = {
silentJSONParsing : true ,
forcedJSONParsing : true ,
clarifyTimeoutError : false
} ;
var URLSearchParams$1 = typeof URLSearchParams !== 'undefined' ? URLSearchParams : AxiosURLSearchParams ;
var FormData$1 = typeof FormData !== 'undefined' ? FormData : null ;
var Blob$1 = typeof Blob !== 'undefined' ? Blob : null ;
var platform$1 = {
isBrowser : true ,
classes : {
URLSearchParams : URLSearchParams$1 ,
FormData : FormData$1 ,
Blob : Blob$1
} ,
protocols : [ 'http' , 'https' , 'file' , 'blob' , 'url' , 'data' ]
} ;
const hasBrowserEnv = typeof window !== 'undefined' && typeof document !== 'undefined' ;
/ * *
* Determine if we ' re running in a standard browser environment
*
* This allows axios to run in a web worker , and react - native .
* Both environments support XMLHttpRequest , but not fully standard globals .
*
* web workers :
* typeof window - > undefined
* typeof document - > undefined
*
* react - native :
* navigator . product - > 'ReactNative'
* nativescript
* navigator . product - > 'NativeScript' or 'NS'
*
* @ returns { boolean }
* /
const hasStandardBrowserEnv = (
( product ) => {
return hasBrowserEnv && [ 'ReactNative' , 'NativeScript' , 'NS' ] . indexOf ( product ) < 0
} ) ( typeof navigator !== 'undefined' && navigator . product ) ;
/ * *
* Determine if we ' re running in a standard browser webWorker environment
*
* Although the ` isStandardBrowserEnv ` method indicates that
* ` allows axios to run in a web worker ` , the WebWorker will still be
* filtered out due to its judgment standard
* ` typeof window !== 'undefined' && typeof document !== 'undefined' ` .
* This leads to a problem when axios post ` FormData ` in webWorker
* /
const hasStandardBrowserWebWorkerEnv = ( ( ) => {
return (
typeof WorkerGlobalScope !== 'undefined' &&
// eslint-disable-next-line no-undef
self instanceof WorkerGlobalScope &&
typeof self . importScripts === 'function'
) ;
} ) ( ) ;
var utils = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
hasBrowserEnv : hasBrowserEnv ,
hasStandardBrowserEnv : hasStandardBrowserEnv ,
hasStandardBrowserWebWorkerEnv : hasStandardBrowserWebWorkerEnv
} ) ;
var platform = {
... utils ,
... platform$1
} ;
function toURLEncodedForm ( data , options ) {
return toFormData ( data , new platform . classes . URLSearchParams ( ) , Object . assign ( {
visitor : function ( value , key , path , helpers ) {
if ( platform . isNode && utils$1 . isBuffer ( value ) ) {
this . append ( key , value . toString ( 'base64' ) ) ;
return false ;
}
return helpers . defaultVisitor . apply ( this , arguments ) ;
}
} , options ) ) ;
}
/ * *
* It takes a string like ` foo[x][y][z] ` and returns an array like ` ['foo', 'x', 'y', 'z']
*
* @ param { string } name - The name of the property to get .
*
* @ returns An array of strings .
* /
function parsePropPath ( name ) {
// foo[x][y][z]
// foo.x.y.z
// foo-x-y-z
// foo x y z
return utils$1 . matchAll ( /\w+|\[(\w*)]/g , name ) . map ( match => {
return match [ 0 ] === '[]' ? '' : match [ 1 ] || match [ 0 ] ;
} ) ;
}
/ * *
* Convert an array to an object .
*
* @ param { Array < any > } arr - The array to convert to an object .
*
* @ returns An object with the same keys and values as the array .
* /
function arrayToObject ( arr ) {
const obj = { } ;
const keys = Object . keys ( arr ) ;
let i ;
const len = keys . length ;
let key ;
for ( i = 0 ; i < len ; i ++ ) {
key = keys [ i ] ;
obj [ key ] = arr [ key ] ;
}
return obj ;
}
/ * *
* It takes a FormData object and returns a JavaScript object
*
* @ param { string } formData The FormData object to convert to JSON .
*
* @ returns { Object < string , any > | null } The converted object .
* /
function formDataToJSON ( formData ) {
function buildPath ( path , value , target , index ) {
let name = path [ index ++ ] ;
if ( name === '__proto__' ) return true ;
const isNumericKey = Number . isFinite ( + name ) ;
const isLast = index >= path . length ;
name = ! name && utils$1 . isArray ( target ) ? target . length : name ;
if ( isLast ) {
if ( utils$1 . hasOwnProp ( target , name ) ) {
target [ name ] = [ target [ name ] , value ] ;
} else {
target [ name ] = value ;
}
return ! isNumericKey ;
}
if ( ! target [ name ] || ! utils$1 . isObject ( target [ name ] ) ) {
target [ name ] = [ ] ;
}
const result = buildPath ( path , value , target [ name ] , index ) ;
if ( result && utils$1 . isArray ( target [ name ] ) ) {
target [ name ] = arrayToObject ( target [ name ] ) ;
}
return ! isNumericKey ;
}
if ( utils$1 . isFormData ( formData ) && utils$1 . isFunction ( formData . entries ) ) {
const obj = { } ;
utils$1 . forEachEntry ( formData , ( name , value ) => {
buildPath ( parsePropPath ( name ) , value , obj , 0 ) ;
} ) ;
return obj ;
}
return null ;
}
/ * *
* It takes a string , tries to parse it , and if it fails , it returns the stringified version
* of the input
*
* @ param { any } rawValue - The value to be stringified .
* @ param { Function } parser - A function that parses a string into a JavaScript object .
* @ param { Function } encoder - A function that takes a value and returns a string .
*
* @ returns { string } A stringified version of the rawValue .
* /
function stringifySafely ( rawValue , parser , encoder ) {
if ( utils$1 . isString ( rawValue ) ) {
try {
( parser || JSON . parse ) ( rawValue ) ;
return utils$1 . trim ( rawValue ) ;
} catch ( e ) {
if ( e . name !== 'SyntaxError' ) {
throw e ;
}
}
}
return ( encoder || JSON . stringify ) ( rawValue ) ;
}
const defaults = {
transitional : transitionalDefaults ,
adapter : [ 'xhr' , 'http' ] ,
transformRequest : [ function transformRequest ( data , headers ) {
const contentType = headers . getContentType ( ) || '' ;
const hasJSONContentType = contentType . indexOf ( 'application/json' ) > - 1 ;
const isObjectPayload = utils$1 . isObject ( data ) ;
if ( isObjectPayload && utils$1 . isHTMLForm ( data ) ) {
data = new FormData ( data ) ;
}
const isFormData = utils$1 . isFormData ( data ) ;
if ( isFormData ) {
if ( ! hasJSONContentType ) {
return data ;
}
return hasJSONContentType ? JSON . stringify ( formDataToJSON ( data ) ) : data ;
}
if ( utils$1 . isArrayBuffer ( data ) ||
utils$1 . isBuffer ( data ) ||
utils$1 . isStream ( data ) ||
utils$1 . isFile ( data ) ||
utils$1 . isBlob ( data )
) {
return data ;
}
if ( utils$1 . isArrayBufferView ( data ) ) {
return data . buffer ;
}
if ( utils$1 . isURLSearchParams ( data ) ) {
headers . setContentType ( 'application/x-www-form-urlencoded;charset=utf-8' , false ) ;
return data . toString ( ) ;
}
let isFileList ;
if ( isObjectPayload ) {
if ( contentType . indexOf ( 'application/x-www-form-urlencoded' ) > - 1 ) {
return toURLEncodedForm ( data , this . formSerializer ) . toString ( ) ;
}
if ( ( isFileList = utils$1 . isFileList ( data ) ) || contentType . indexOf ( 'multipart/form-data' ) > - 1 ) {
const _FormData = this . env && this . env . FormData ;
return toFormData (
isFileList ? { 'files[]' : data } : data ,
_FormData && new _FormData ( ) ,
this . formSerializer
) ;
}
}
if ( isObjectPayload || hasJSONContentType ) {
headers . setContentType ( 'application/json' , false ) ;
return stringifySafely ( data ) ;
}
return data ;
} ] ,
transformResponse : [ function transformResponse ( data ) {
const transitional = this . transitional || defaults . transitional ;
const forcedJSONParsing = transitional && transitional . forcedJSONParsing ;
const JSONRequested = this . responseType === 'json' ;
if ( data && utils$1 . isString ( data ) && ( ( forcedJSONParsing && ! this . responseType ) || JSONRequested ) ) {
const silentJSONParsing = transitional && transitional . silentJSONParsing ;
const strictJSONParsing = ! silentJSONParsing && JSONRequested ;
try {
return JSON . parse ( data ) ;
} catch ( e ) {
if ( strictJSONParsing ) {
if ( e . name === 'SyntaxError' ) {
throw AxiosError . from ( e , AxiosError . ERR _BAD _RESPONSE , this , null , this . response ) ;
}
throw e ;
}
}
}
return data ;
} ] ,
/ * *
* A timeout in milliseconds to abort a request . If set to 0 ( default ) a
* timeout is not created .
* /
timeout : 0 ,
xsrfCookieName : 'XSRF-TOKEN' ,
xsrfHeaderName : 'X-XSRF-TOKEN' ,
maxContentLength : - 1 ,
maxBodyLength : - 1 ,
env : {
FormData : platform . classes . FormData ,
Blob : platform . classes . Blob
} ,
validateStatus : function validateStatus ( status ) {
return status >= 200 && status < 300 ;
} ,
headers : {
common : {
'Accept' : 'application/json, text/plain, */*' ,
'Content-Type' : undefined
}
}
} ;
utils$1 . forEach ( [ 'delete' , 'get' , 'head' , 'post' , 'put' , 'patch' ] , ( method ) => {
defaults . headers [ method ] = { } ;
} ) ;
var defaults$1 = defaults ;
// RawAxiosHeaders whose duplicates are ignored by node
// c.f. https://nodejs.org/api/http.html#http_message_headers
const ignoreDuplicateOf = utils$1 . toObjectSet ( [
'age' , 'authorization' , 'content-length' , 'content-type' , 'etag' ,
'expires' , 'from' , 'host' , 'if-modified-since' , 'if-unmodified-since' ,
'last-modified' , 'location' , 'max-forwards' , 'proxy-authorization' ,
'referer' , 'retry-after' , 'user-agent'
] ) ;
/ * *
* Parse headers into an object
*
* ` ` `
* Date : Wed , 27 Aug 2014 08 : 58 : 49 GMT
* Content - Type : application / json
* Connection : keep - alive
* Transfer - Encoding : chunked
* ` ` `
*
* @ param { String } rawHeaders Headers needing to be parsed
*
* @ returns { Object } Headers parsed into an object
* /
var parseHeaders = rawHeaders => {
const parsed = { } ;
let key ;
let val ;
let i ;
rawHeaders && rawHeaders . split ( '\n' ) . forEach ( function parser ( line ) {
i = line . indexOf ( ':' ) ;
key = line . substring ( 0 , i ) . trim ( ) . toLowerCase ( ) ;
val = line . substring ( i + 1 ) . trim ( ) ;
if ( ! key || ( parsed [ key ] && ignoreDuplicateOf [ key ] ) ) {
return ;
}
if ( key === 'set-cookie' ) {
if ( parsed [ key ] ) {
parsed [ key ] . push ( val ) ;
} else {
parsed [ key ] = [ val ] ;
}
} else {
parsed [ key ] = parsed [ key ] ? parsed [ key ] + ', ' + val : val ;
}
} ) ;
return parsed ;
} ;
const $internals = Symbol ( 'internals' ) ;
function normalizeHeader ( header ) {
return header && String ( header ) . trim ( ) . toLowerCase ( ) ;
}
function normalizeValue ( value ) {
if ( value === false || value == null ) {
return value ;
}
return utils$1 . isArray ( value ) ? value . map ( normalizeValue ) : String ( value ) ;
}
function parseTokens ( str ) {
const tokens = Object . create ( null ) ;
const tokensRE = /([^\s,;=]+)\s*(?:=\s*([^,;]+))?/g ;
let match ;
while ( ( match = tokensRE . exec ( str ) ) ) {
tokens [ match [ 1 ] ] = match [ 2 ] ;
}
return tokens ;
}
const isValidHeaderName = ( str ) => / ^ [ - _a - zA - Z0 - 9 ^ ` |~,!# $ %&'*+.]+ $ /.test(str.trim());
function matchHeaderValue ( context , value , header , filter , isHeaderNameFilter ) {
if ( utils$1 . isFunction ( filter ) ) {
return filter . call ( this , value , header ) ;
}
if ( isHeaderNameFilter ) {
value = header ;
}
if ( ! utils$1 . isString ( value ) ) return ;
if ( utils$1 . isString ( filter ) ) {
return value . indexOf ( filter ) !== - 1 ;
}
if ( utils$1 . isRegExp ( filter ) ) {
return filter . test ( value ) ;
}
}
function formatHeader ( header ) {
return header . trim ( )
. toLowerCase ( ) . replace ( /([a-z\d])(\w*)/g , ( w , char , str ) => {
return char . toUpperCase ( ) + str ;
} ) ;
}
function buildAccessors ( obj , header ) {
const accessorName = utils$1 . toCamelCase ( ' ' + header ) ;
[ 'get' , 'set' , 'has' ] . forEach ( methodName => {
Object . defineProperty ( obj , methodName + accessorName , {
value : function ( arg1 , arg2 , arg3 ) {
return this [ methodName ] . call ( this , header , arg1 , arg2 , arg3 ) ;
} ,
configurable : true
} ) ;
} ) ;
}
class AxiosHeaders {
constructor ( headers ) {
headers && this . set ( headers ) ;
}
set ( header , valueOrRewrite , rewrite ) {
const self = this ;
function setHeader ( _value , _header , _rewrite ) {
const lHeader = normalizeHeader ( _header ) ;
if ( ! lHeader ) {
throw new Error ( 'header name must be a non-empty string' ) ;
}
const key = utils$1 . findKey ( self , lHeader ) ;
if ( ! key || self [ key ] === undefined || _rewrite === true || ( _rewrite === undefined && self [ key ] !== false ) ) {
self [ key || _header ] = normalizeValue ( _value ) ;
}
}
const setHeaders = ( headers , _rewrite ) =>
utils$1 . forEach ( headers , ( _value , _header ) => setHeader ( _value , _header , _rewrite ) ) ;
if ( utils$1 . isPlainObject ( header ) || header instanceof this . constructor ) {
setHeaders ( header , valueOrRewrite ) ;
} else if ( utils$1 . isString ( header ) && ( header = header . trim ( ) ) && ! isValidHeaderName ( header ) ) {
setHeaders ( parseHeaders ( header ) , valueOrRewrite ) ;
} else {
header != null && setHeader ( valueOrRewrite , header , rewrite ) ;
}
return this ;
}
get ( header , parser ) {
header = normalizeHeader ( header ) ;
if ( header ) {
const key = utils$1 . findKey ( this , header ) ;
if ( key ) {
const value = this [ key ] ;
if ( ! parser ) {
return value ;
}
if ( parser === true ) {
return parseTokens ( value ) ;
}
if ( utils$1 . isFunction ( parser ) ) {
return parser . call ( this , value , key ) ;
}
if ( utils$1 . isRegExp ( parser ) ) {
return parser . exec ( value ) ;
}
throw new TypeError ( 'parser must be boolean|regexp|function' ) ;
}
}
}
has ( header , matcher ) {
header = normalizeHeader ( header ) ;
if ( header ) {
const key = utils$1 . findKey ( this , header ) ;
return ! ! ( key && this [ key ] !== undefined && ( ! matcher || matchHeaderValue ( this , this [ key ] , key , matcher ) ) ) ;
}
return false ;
}
delete ( header , matcher ) {
const self = this ;
let deleted = false ;
function deleteHeader ( _header ) {
_header = normalizeHeader ( _header ) ;
if ( _header ) {
const key = utils$1 . findKey ( self , _header ) ;
if ( key && ( ! matcher || matchHeaderValue ( self , self [ key ] , key , matcher ) ) ) {
delete self [ key ] ;
deleted = true ;
}
}
}
if ( utils$1 . isArray ( header ) ) {
header . forEach ( deleteHeader ) ;
} else {
deleteHeader ( header ) ;
}
return deleted ;
}
clear ( matcher ) {
const keys = Object . keys ( this ) ;
let i = keys . length ;
let deleted = false ;
while ( i -- ) {
const key = keys [ i ] ;
if ( ! matcher || matchHeaderValue ( this , this [ key ] , key , matcher , true ) ) {
delete this [ key ] ;
deleted = true ;
}
}
return deleted ;
}
normalize ( format ) {
const self = this ;
const headers = { } ;
utils$1 . forEach ( this , ( value , header ) => {
const key = utils$1 . findKey ( headers , header ) ;
if ( key ) {
self [ key ] = normalizeValue ( value ) ;
delete self [ header ] ;
return ;
}
const normalized = format ? formatHeader ( header ) : String ( header ) . trim ( ) ;
if ( normalized !== header ) {
delete self [ header ] ;
}
self [ normalized ] = normalizeValue ( value ) ;
headers [ normalized ] = true ;
} ) ;
return this ;
}
concat ( ... targets ) {
return this . constructor . concat ( this , ... targets ) ;
}
toJSON ( asStrings ) {
const obj = Object . create ( null ) ;
utils$1 . forEach ( this , ( value , header ) => {
value != null && value !== false && ( obj [ header ] = asStrings && utils$1 . isArray ( value ) ? value . join ( ', ' ) : value ) ;
} ) ;
return obj ;
}
[ Symbol . iterator ] ( ) {
return Object . entries ( this . toJSON ( ) ) [ Symbol . iterator ] ( ) ;
}
toString ( ) {
return Object . entries ( this . toJSON ( ) ) . map ( ( [ header , value ] ) => header + ': ' + value ) . join ( '\n' ) ;
}
get [ Symbol . toStringTag ] ( ) {
return 'AxiosHeaders' ;
}
static from ( thing ) {
return thing instanceof this ? thing : new this ( thing ) ;
}
static concat ( first , ... targets ) {
const computed = new this ( first ) ;
targets . forEach ( ( target ) => computed . set ( target ) ) ;
return computed ;
}
static accessor ( header ) {
const internals = this [ $internals ] = ( this [ $internals ] = {
accessors : { }
} ) ;
const accessors = internals . accessors ;
const prototype = this . prototype ;
function defineAccessor ( _header ) {
const lHeader = normalizeHeader ( _header ) ;
if ( ! accessors [ lHeader ] ) {
buildAccessors ( prototype , _header ) ;
accessors [ lHeader ] = true ;
}
}
utils$1 . isArray ( header ) ? header . forEach ( defineAccessor ) : defineAccessor ( header ) ;
return this ;
}
}
AxiosHeaders . accessor ( [ 'Content-Type' , 'Content-Length' , 'Accept' , 'Accept-Encoding' , 'User-Agent' , 'Authorization' ] ) ;
// reserved names hotfix
utils$1 . reduceDescriptors ( AxiosHeaders . prototype , ( { value } , key ) => {
let mapped = key [ 0 ] . toUpperCase ( ) + key . slice ( 1 ) ; // map `set` => `Set`
return {
get : ( ) => value ,
set ( headerValue ) {
this [ mapped ] = headerValue ;
}
}
} ) ;
utils$1 . freezeMethods ( AxiosHeaders ) ;
var AxiosHeaders$1 = AxiosHeaders ;
/ * *
* Transform the data for a request or a response
*
* @ param { Array | Function } fns A single function or Array of functions
* @ param { ? Object } response The response object
*
* @ returns { * } The resulting transformed data
* /
function transformData ( fns , response ) {
const config = this || defaults$1 ;
const context = response || config ;
const headers = AxiosHeaders$1 . from ( context . headers ) ;
let data = context . data ;
utils$1 . forEach ( fns , function transform ( fn ) {
data = fn . call ( config , data , headers . normalize ( ) , response ? response . status : undefined ) ;
} ) ;
headers . normalize ( ) ;
return data ;
}
function isCancel ( value ) {
return ! ! ( value && value . _ _CANCEL _ _ ) ;
}
/ * *
* A ` CanceledError ` is an object that is thrown when an operation is canceled .
*
* @ param { string = } message The message .
* @ param { Object = } config The config .
* @ param { Object = } request The request .
*
* @ returns { CanceledError } The created error .
* /
function CanceledError ( message , config , request ) {
// eslint-disable-next-line no-eq-null,eqeqeq
AxiosError . call ( this , message == null ? 'canceled' : message , AxiosError . ERR _CANCELED , config , request ) ;
this . name = 'CanceledError' ;
}
utils$1 . inherits ( CanceledError , AxiosError , {
_ _CANCEL _ _ : true
} ) ;
/ * *
* Resolve or reject a Promise based on response status .
*
* @ param { Function } resolve A function that resolves the promise .
* @ param { Function } reject A function that rejects the promise .
* @ param { object } response The response .
*
* @ returns { object } The response .
* /
function settle ( resolve , reject , response ) {
const validateStatus = response . config . validateStatus ;
if ( ! response . status || ! validateStatus || validateStatus ( response . status ) ) {
resolve ( response ) ;
} else {
reject ( new AxiosError (
'Request failed with status code ' + response . status ,
[ AxiosError . ERR _BAD _REQUEST , AxiosError . ERR _BAD _RESPONSE ] [ Math . floor ( response . status / 100 ) - 4 ] ,
response . config ,
response . request ,
response
) ) ;
}
}
var cookies = platform . hasStandardBrowserEnv ?
// Standard browser envs support document.cookie
{
write ( name , value , expires , path , domain , secure ) {
const cookie = [ name + '=' + encodeURIComponent ( value ) ] ;
utils$1 . isNumber ( expires ) && cookie . push ( 'expires=' + new Date ( expires ) . toGMTString ( ) ) ;
utils$1 . isString ( path ) && cookie . push ( 'path=' + path ) ;
utils$1 . isString ( domain ) && cookie . push ( 'domain=' + domain ) ;
secure === true && cookie . push ( 'secure' ) ;
document . cookie = cookie . join ( '; ' ) ;
} ,
read ( name ) {
const match = document . cookie . match ( new RegExp ( '(^|;\\s*)(' + name + ')=([^;]*)' ) ) ;
return ( match ? decodeURIComponent ( match [ 3 ] ) : null ) ;
} ,
remove ( name ) {
this . write ( name , '' , Date . now ( ) - 86400000 ) ;
}
}
:
// Non-standard browser env (web workers, react-native) lack needed support.
{
write ( ) { } ,
read ( ) {
return null ;
} ,
remove ( ) { }
} ;
/ * *
* Determines whether the specified URL is absolute
*
* @ param { string } url The URL to test
*
* @ returns { boolean } True if the specified URL is absolute , otherwise false
* /
function isAbsoluteURL ( url ) {
// A URL is considered absolute if it begins with "<scheme>://" or "//" (protocol-relative URL).
// RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed
// by any combination of letters, digits, plus, period, or hyphen.
return /^([a-z][a-z\d+\-.]*:)?\/\//i . test ( url ) ;
}
/ * *
* Creates a new URL by combining the specified URLs
*
* @ param { string } baseURL The base URL
* @ param { string } relativeURL The relative URL
*
* @ returns { string } The combined URL
* /
function combineURLs ( baseURL , relativeURL ) {
return relativeURL
? baseURL . replace ( /\/?\/$/ , '' ) + '/' + relativeURL . replace ( /^\/+/ , '' )
: baseURL ;
}
/ * *
* Creates a new URL by combining the baseURL with the requestedURL ,
* only when the requestedURL is not already an absolute URL .
* If the requestURL is absolute , this function returns the requestedURL untouched .
*
* @ param { string } baseURL The base URL
* @ param { string } requestedURL Absolute or relative URL to combine
*
* @ returns { string } The combined full path
* /
function buildFullPath ( baseURL , requestedURL ) {
if ( baseURL && ! isAbsoluteURL ( requestedURL ) ) {
return combineURLs ( baseURL , requestedURL ) ;
}
return requestedURL ;
}
var isURLSameOrigin = platform . hasStandardBrowserEnv ?
// Standard browser envs have full support of the APIs needed to test
// whether the request URL is of the same origin as current location.
( function standardBrowserEnv ( ) {
const msie = /(msie|trident)/i . test ( navigator . userAgent ) ;
const urlParsingNode = document . createElement ( 'a' ) ;
let originURL ;
/ * *
* Parse a URL to discover its components
*
* @ param { String } url The URL to be parsed
* @ returns { Object }
* /
function resolveURL ( url ) {
let href = url ;
if ( msie ) {
// IE needs attribute set twice to normalize properties
urlParsingNode . setAttribute ( 'href' , href ) ;
href = urlParsingNode . href ;
}
urlParsingNode . setAttribute ( 'href' , href ) ;
// urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils
return {
href : urlParsingNode . href ,
protocol : urlParsingNode . protocol ? urlParsingNode . protocol . replace ( /:$/ , '' ) : '' ,
host : urlParsingNode . host ,
search : urlParsingNode . search ? urlParsingNode . search . replace ( /^\?/ , '' ) : '' ,
hash : urlParsingNode . hash ? urlParsingNode . hash . replace ( /^#/ , '' ) : '' ,
hostname : urlParsingNode . hostname ,
port : urlParsingNode . port ,
pathname : ( urlParsingNode . pathname . charAt ( 0 ) === '/' ) ?
urlParsingNode . pathname :
'/' + urlParsingNode . pathname
} ;
}
originURL = resolveURL ( window . location . href ) ;
/ * *
* Determine if a URL shares the same origin as the current location
*
* @ param { String } requestURL The URL to test
* @ returns { boolean } True if URL shares the same origin , otherwise false
* /
return function isURLSameOrigin ( requestURL ) {
const parsed = ( utils$1 . isString ( requestURL ) ) ? resolveURL ( requestURL ) : requestURL ;
return ( parsed . protocol === originURL . protocol &&
parsed . host === originURL . host ) ;
} ;
} ) ( ) :
// Non standard browser envs (web workers, react-native) lack needed support.
( function nonStandardBrowserEnv ( ) {
return function isURLSameOrigin ( ) {
return true ;
} ;
} ) ( ) ;
function parseProtocol ( url ) {
const match = /^([-+\w]{1,25})(:?\/\/|:)/ . exec ( url ) ;
return match && match [ 1 ] || '' ;
}
/ * *
* Calculate data maxRate
* @ param { Number } [ samplesCount = 10 ]
* @ param { Number } [ min = 1000 ]
* @ returns { Function }
* /
function speedometer ( samplesCount , min ) {
samplesCount = samplesCount || 10 ;
const bytes = new Array ( samplesCount ) ;
const timestamps = new Array ( samplesCount ) ;
let head = 0 ;
let tail = 0 ;
let firstSampleTS ;
min = min !== undefined ? min : 1000 ;
return function push ( chunkLength ) {
const now = Date . now ( ) ;
const startedAt = timestamps [ tail ] ;
if ( ! firstSampleTS ) {
firstSampleTS = now ;
}
bytes [ head ] = chunkLength ;
timestamps [ head ] = now ;
let i = tail ;
let bytesCount = 0 ;
while ( i !== head ) {
bytesCount += bytes [ i ++ ] ;
i = i % samplesCount ;
}
head = ( head + 1 ) % samplesCount ;
if ( head === tail ) {
tail = ( tail + 1 ) % samplesCount ;
}
if ( now - firstSampleTS < min ) {
return ;
}
const passed = startedAt && now - startedAt ;
return passed ? Math . round ( bytesCount * 1000 / passed ) : undefined ;
} ;
}
function progressEventReducer ( listener , isDownloadStream ) {
let bytesNotified = 0 ;
const _speedometer = speedometer ( 50 , 250 ) ;
return e => {
const loaded = e . loaded ;
const total = e . lengthComputable ? e . total : undefined ;
const progressBytes = loaded - bytesNotified ;
const rate = _speedometer ( progressBytes ) ;
const inRange = loaded <= total ;
bytesNotified = loaded ;
const data = {
loaded ,
total ,
progress : total ? ( loaded / total ) : undefined ,
bytes : progressBytes ,
rate : rate ? rate : undefined ,
estimated : rate && total && inRange ? ( total - loaded ) / rate : undefined ,
event : e
} ;
data [ isDownloadStream ? 'download' : 'upload' ] = true ;
listener ( data ) ;
} ;
}
const isXHRAdapterSupported = typeof XMLHttpRequest !== 'undefined' ;
var xhrAdapter = isXHRAdapterSupported && function ( config ) {
return new Promise ( function dispatchXhrRequest ( resolve , reject ) {
let requestData = config . data ;
const requestHeaders = AxiosHeaders$1 . from ( config . headers ) . normalize ( ) ;
let { responseType , withXSRFToken } = config ;
let onCanceled ;
function done ( ) {
if ( config . cancelToken ) {
config . cancelToken . unsubscribe ( onCanceled ) ;
}
if ( config . signal ) {
config . signal . removeEventListener ( 'abort' , onCanceled ) ;
}
}
let contentType ;
if ( utils$1 . isFormData ( requestData ) ) {
if ( platform . hasStandardBrowserEnv || platform . hasStandardBrowserWebWorkerEnv ) {
requestHeaders . setContentType ( false ) ; // Let the browser set it
} else if ( ( contentType = requestHeaders . getContentType ( ) ) !== false ) {
// fix semicolon duplication issue for ReactNative FormData implementation
const [ type , ... tokens ] = contentType ? contentType . split ( ';' ) . map ( token => token . trim ( ) ) . filter ( Boolean ) : [ ] ;
requestHeaders . setContentType ( [ type || 'multipart/form-data' , ... tokens ] . join ( '; ' ) ) ;
}
}
let request = new XMLHttpRequest ( ) ;
// HTTP basic authentication
if ( config . auth ) {
const username = config . auth . username || '' ;
const password = config . auth . password ? unescape ( encodeURIComponent ( config . auth . password ) ) : '' ;
requestHeaders . set ( 'Authorization' , 'Basic ' + btoa ( username + ':' + password ) ) ;
}
const fullPath = buildFullPath ( config . baseURL , config . url ) ;
request . open ( config . method . toUpperCase ( ) , buildURL ( fullPath , config . params , config . paramsSerializer ) , true ) ;
// Set the request timeout in MS
request . timeout = config . timeout ;
function onloadend ( ) {
if ( ! request ) {
return ;
}
// Prepare the response
const responseHeaders = AxiosHeaders$1 . from (
'getAllResponseHeaders' in request && request . getAllResponseHeaders ( )
) ;
const responseData = ! responseType || responseType === 'text' || responseType === 'json' ?
request . responseText : request . response ;
const response = {
data : responseData ,
status : request . status ,
statusText : request . statusText ,
headers : responseHeaders ,
config ,
request
} ;
settle ( function _resolve ( value ) {
resolve ( value ) ;
done ( ) ;
} , function _reject ( err ) {
reject ( err ) ;
done ( ) ;
} , response ) ;
// Clean up request
request = null ;
}
if ( 'onloadend' in request ) {
// Use onloadend if available
request . onloadend = onloadend ;
} else {
// Listen for ready state to emulate onloadend
request . onreadystatechange = function handleLoad ( ) {
if ( ! request || request . readyState !== 4 ) {
return ;
}
// The request errored out and we didn't get a response, this will be
// handled by onerror instead
// With one exception: request that using file: protocol, most browsers
// will return status as 0 even though it's a successful request
if ( request . status === 0 && ! ( request . responseURL && request . responseURL . indexOf ( 'file:' ) === 0 ) ) {
return ;
}
// readystate handler is calling before onerror or ontimeout handlers,
// so we should call onloadend on the next 'tick'
setTimeout ( onloadend ) ;
} ;
}
// Handle browser request cancellation (as opposed to a manual cancellation)
request . onabort = function handleAbort ( ) {
if ( ! request ) {
return ;
}
reject ( new AxiosError ( 'Request aborted' , AxiosError . ECONNABORTED , config , request ) ) ;
// Clean up request
request = null ;
} ;
// Handle low level network errors
request . onerror = function handleError ( ) {
// Real errors are hidden from us by the browser
// onerror should only fire if it's a network error
reject ( new AxiosError ( 'Network Error' , AxiosError . ERR _NETWORK , config , request ) ) ;
// Clean up request
request = null ;
} ;
// Handle timeout
request . ontimeout = function handleTimeout ( ) {
let timeoutErrorMessage = config . timeout ? 'timeout of ' + config . timeout + 'ms exceeded' : 'timeout exceeded' ;
const transitional = config . transitional || transitionalDefaults ;
if ( config . timeoutErrorMessage ) {
timeoutErrorMessage = config . timeoutErrorMessage ;
}
reject ( new AxiosError (
timeoutErrorMessage ,
transitional . clarifyTimeoutError ? AxiosError . ETIMEDOUT : AxiosError . ECONNABORTED ,
config ,
request ) ) ;
// Clean up request
request = null ;
} ;
// Add xsrf header
// This is only done if running in a standard browser environment.
// Specifically not if we're in a web worker, or react-native.
if ( platform . hasStandardBrowserEnv ) {
withXSRFToken && utils$1 . isFunction ( withXSRFToken ) && ( withXSRFToken = withXSRFToken ( config ) ) ;
if ( withXSRFToken || ( withXSRFToken !== false && isURLSameOrigin ( fullPath ) ) ) {
// Add xsrf header
const xsrfValue = config . xsrfHeaderName && config . xsrfCookieName && cookies . read ( config . xsrfCookieName ) ;
if ( xsrfValue ) {
requestHeaders . set ( config . xsrfHeaderName , xsrfValue ) ;
}
}
}
// Remove Content-Type if data is undefined
requestData === undefined && requestHeaders . setContentType ( null ) ;
// Add headers to the request
if ( 'setRequestHeader' in request ) {
utils$1 . forEach ( requestHeaders . toJSON ( ) , function setRequestHeader ( val , key ) {
request . setRequestHeader ( key , val ) ;
} ) ;
}
// Add withCredentials to request if needed
if ( ! utils$1 . isUndefined ( config . withCredentials ) ) {
request . withCredentials = ! ! config . withCredentials ;
}
// Add responseType to request if needed
if ( responseType && responseType !== 'json' ) {
request . responseType = config . responseType ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// Handle progress if needed
if ( typeof config . onDownloadProgress === 'function' ) {
request . addEventListener ( 'progress' , progressEventReducer ( config . onDownloadProgress , true ) ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// Not all browsers support upload events
if ( typeof config . onUploadProgress === 'function' && request . upload ) {
request . upload . addEventListener ( 'progress' , progressEventReducer ( config . onUploadProgress ) ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( config . cancelToken || config . signal ) {
// Handle cancellation
// eslint-disable-next-line func-names
onCanceled = cancel => {
if ( ! request ) {
return ;
}
reject ( ! cancel || cancel . type ? new CanceledError ( null , config , request ) : cancel ) ;
request . abort ( ) ;
request = null ;
} ;
config . cancelToken && config . cancelToken . subscribe ( onCanceled ) ;
if ( config . signal ) {
config . signal . aborted ? onCanceled ( ) : config . signal . addEventListener ( 'abort' , onCanceled ) ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const protocol = parseProtocol ( fullPath ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( protocol && platform . protocols . indexOf ( protocol ) === - 1 ) {
reject ( new AxiosError ( 'Unsupported protocol ' + protocol + ':' , AxiosError . ERR _BAD _REQUEST , config ) ) ;
return ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// Send the request
request . send ( requestData || null ) ;
} ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const knownAdapters = {
http : httpAdapter ,
xhr : xhrAdapter
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
utils$1 . forEach ( knownAdapters , ( fn , value ) => {
if ( fn ) {
try {
Object . defineProperty ( fn , 'name' , { value } ) ;
} catch ( e ) {
// eslint-disable-next-line no-empty
}
Object . defineProperty ( fn , 'adapterName' , { value } ) ;
}
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const renderReason = ( reason ) => ` - ${ reason } ` ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const isResolvedHandle = ( adapter ) => utils$1 . isFunction ( adapter ) || adapter === null || adapter === false ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var adapters = {
getAdapter : ( adapters ) => {
adapters = utils$1 . isArray ( adapters ) ? adapters : [ adapters ] ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const { length } = adapters ;
let nameOrAdapter ;
let adapter ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const rejectedReasons = { } ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
for ( let i = 0 ; i < length ; i ++ ) {
nameOrAdapter = adapters [ i ] ;
let id ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
adapter = nameOrAdapter ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( ! isResolvedHandle ( nameOrAdapter ) ) {
adapter = knownAdapters [ ( id = String ( nameOrAdapter ) ) . toLowerCase ( ) ] ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( adapter === undefined ) {
throw new AxiosError ( ` Unknown adapter ' ${ id } ' ` ) ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( adapter ) {
break ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
rejectedReasons [ id || '#' + i ] = adapter ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( ! adapter ) {
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const reasons = Object . entries ( rejectedReasons )
. map ( ( [ id , state ] ) => ` adapter ${ id } ` +
( state === false ? 'is not supported by the environment' : 'is not available in the build' )
) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
let s = length ?
( reasons . length > 1 ? 'since :\n' + reasons . map ( renderReason ) . join ( '\n' ) : ' ' + renderReason ( reasons [ 0 ] ) ) :
'as no adapter specified' ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
throw new AxiosError (
` There is no suitable adapter to dispatch the request ` + s ,
'ERR_NOT_SUPPORT'
) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return adapter ;
} ,
adapters : knownAdapters
} ;
2023-07-09 04:05:21 -06:00
/ * *
2024-01-23 11:06:49 -07:00
* Throws a ` CanceledError ` if cancellation has been requested .
*
* @ param { Object } config The config that is to be used for the request
*
* @ returns { void }
2023-07-09 04:05:21 -06:00
* /
function throwIfCancellationRequested ( config ) {
if ( config . cancelToken ) {
config . cancelToken . throwIfRequested ( ) ;
}
if ( config . signal && config . signal . aborted ) {
2024-01-23 11:06:49 -07:00
throw new CanceledError ( null , config ) ;
2023-07-09 04:05:21 -06:00
}
}
/ * *
* Dispatch a request to the server using the configured adapter .
*
* @ param { object } config The config that is to be used for the request
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ returns { Promise } The Promise to be fulfilled
* /
2024-01-23 11:06:49 -07:00
function dispatchRequest ( config ) {
2023-07-09 04:05:21 -06:00
throwIfCancellationRequested ( config ) ;
2024-01-23 11:06:49 -07:00
config . headers = AxiosHeaders$1 . from ( config . headers ) ;
2023-07-09 04:05:21 -06:00
// Transform request data
config . data = transformData . call (
config ,
config . transformRequest
) ;
2024-01-23 11:06:49 -07:00
if ( [ 'post' , 'put' , 'patch' ] . indexOf ( config . method ) !== - 1 ) {
config . headers . setContentType ( 'application/x-www-form-urlencoded' , false ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const adapter = adapters . getAdapter ( config . adapter || defaults$1 . adapter ) ;
2023-07-09 04:05:21 -06:00
return adapter ( config ) . then ( function onAdapterResolution ( response ) {
throwIfCancellationRequested ( config ) ;
// Transform response data
response . data = transformData . call (
config ,
2024-01-23 11:06:49 -07:00
config . transformResponse ,
response
2023-07-09 04:05:21 -06:00
) ;
2024-01-23 11:06:49 -07:00
response . headers = AxiosHeaders$1 . from ( response . headers ) ;
2023-07-09 04:05:21 -06:00
return response ;
} , function onAdapterRejection ( reason ) {
if ( ! isCancel ( reason ) ) {
throwIfCancellationRequested ( config ) ;
// Transform response data
if ( reason && reason . response ) {
reason . response . data = transformData . call (
config ,
2024-01-23 11:06:49 -07:00
config . transformResponse ,
reason . response
2023-07-09 04:05:21 -06:00
) ;
2024-01-23 11:06:49 -07:00
reason . response . headers = AxiosHeaders$1 . from ( reason . response . headers ) ;
2023-07-09 04:05:21 -06:00
}
}
return Promise . reject ( reason ) ;
} ) ;
2024-01-23 11:06:49 -07:00
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const headersToObject = ( thing ) => thing instanceof AxiosHeaders$1 ? thing . toJSON ( ) : thing ;
2023-07-09 04:05:21 -06:00
/ * *
* Config - specific merge - function which creates a new config - object
* by merging two configuration objects together .
*
* @ param { Object } config1
* @ param { Object } config2
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ returns { Object } New object resulting from merging config2 to config1
* /
2024-01-23 11:06:49 -07:00
function mergeConfig ( config1 , config2 ) {
2023-07-09 04:05:21 -06:00
// eslint-disable-next-line no-param-reassign
config2 = config2 || { } ;
2024-01-23 11:06:49 -07:00
const config = { } ;
function getMergedValue ( target , source , caseless ) {
if ( utils$1 . isPlainObject ( target ) && utils$1 . isPlainObject ( source ) ) {
return utils$1 . merge . call ( { caseless } , target , source ) ;
} else if ( utils$1 . isPlainObject ( source ) ) {
return utils$1 . merge ( { } , source ) ;
} else if ( utils$1 . isArray ( source ) ) {
2023-07-09 04:05:21 -06:00
return source . slice ( ) ;
}
return source ;
}
// eslint-disable-next-line consistent-return
2024-01-23 11:06:49 -07:00
function mergeDeepProperties ( a , b , caseless ) {
if ( ! utils$1 . isUndefined ( b ) ) {
return getMergedValue ( a , b , caseless ) ;
} else if ( ! utils$1 . isUndefined ( a ) ) {
return getMergedValue ( undefined , a , caseless ) ;
2023-07-09 04:05:21 -06:00
}
}
// eslint-disable-next-line consistent-return
2024-01-23 11:06:49 -07:00
function valueFromConfig2 ( a , b ) {
if ( ! utils$1 . isUndefined ( b ) ) {
return getMergedValue ( undefined , b ) ;
2023-07-09 04:05:21 -06:00
}
}
// eslint-disable-next-line consistent-return
2024-01-23 11:06:49 -07:00
function defaultToConfig2 ( a , b ) {
if ( ! utils$1 . isUndefined ( b ) ) {
return getMergedValue ( undefined , b ) ;
} else if ( ! utils$1 . isUndefined ( a ) ) {
return getMergedValue ( undefined , a ) ;
2023-07-09 04:05:21 -06:00
}
}
// eslint-disable-next-line consistent-return
2024-01-23 11:06:49 -07:00
function mergeDirectKeys ( a , b , prop ) {
2023-07-09 04:05:21 -06:00
if ( prop in config2 ) {
2024-01-23 11:06:49 -07:00
return getMergedValue ( a , b ) ;
2023-07-09 04:05:21 -06:00
} else if ( prop in config1 ) {
2024-01-23 11:06:49 -07:00
return getMergedValue ( undefined , a ) ;
}
}
const mergeMap = {
url : valueFromConfig2 ,
method : valueFromConfig2 ,
data : valueFromConfig2 ,
baseURL : defaultToConfig2 ,
transformRequest : defaultToConfig2 ,
transformResponse : defaultToConfig2 ,
paramsSerializer : defaultToConfig2 ,
timeout : defaultToConfig2 ,
timeoutMessage : defaultToConfig2 ,
withCredentials : defaultToConfig2 ,
withXSRFToken : defaultToConfig2 ,
adapter : defaultToConfig2 ,
responseType : defaultToConfig2 ,
xsrfCookieName : defaultToConfig2 ,
xsrfHeaderName : defaultToConfig2 ,
onUploadProgress : defaultToConfig2 ,
onDownloadProgress : defaultToConfig2 ,
decompress : defaultToConfig2 ,
maxContentLength : defaultToConfig2 ,
maxBodyLength : defaultToConfig2 ,
beforeRedirect : defaultToConfig2 ,
transport : defaultToConfig2 ,
httpAgent : defaultToConfig2 ,
httpsAgent : defaultToConfig2 ,
cancelToken : defaultToConfig2 ,
socketPath : defaultToConfig2 ,
responseEncoding : defaultToConfig2 ,
validateStatus : mergeDirectKeys ,
headers : ( a , b ) => mergeDeepProperties ( headersToObject ( a ) , headersToObject ( b ) , true )
2023-07-09 04:05:21 -06:00
} ;
2024-01-23 11:06:49 -07:00
utils$1 . forEach ( Object . keys ( Object . assign ( { } , config1 , config2 ) ) , function computeConfigValue ( prop ) {
const merge = mergeMap [ prop ] || mergeDeepProperties ;
const configValue = merge ( config1 [ prop ] , config2 [ prop ] , prop ) ;
( utils$1 . isUndefined ( configValue ) && merge !== mergeDirectKeys ) || ( config [ prop ] = configValue ) ;
2023-07-09 04:05:21 -06:00
} ) ;
return config ;
}
2024-01-23 11:06:49 -07:00
const VERSION = "1.6.5" ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const validators$1 = { } ;
2023-07-09 04:05:21 -06:00
// eslint-disable-next-line func-names
2024-01-23 11:06:49 -07:00
[ 'object' , 'boolean' , 'number' , 'function' , 'string' , 'symbol' ] . forEach ( ( type , i ) => {
2023-07-09 04:05:21 -06:00
validators$1 [ type ] = function validator ( thing ) {
return typeof thing === type || 'a' + ( i < 1 ? 'n ' : ' ' ) + type ;
} ;
} ) ;
2024-01-23 11:06:49 -07:00
const deprecatedWarnings = { } ;
2023-07-09 04:05:21 -06:00
/ * *
* Transitional option validator
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ param { function | boolean ? } validator - set to false if the transitional option has been removed
* @ param { string ? } version - deprecated version / removed since version
* @ param { string ? } message - some message with additional info
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ returns { function }
* /
validators$1 . transitional = function transitional ( validator , version , message ) {
function formatMessage ( opt , desc ) {
return '[Axios v' + VERSION + '] Transitional option \'' + opt + '\'' + desc + ( message ? '. ' + message : '' ) ;
}
// eslint-disable-next-line func-names
2024-01-23 11:06:49 -07:00
return ( value , opt , opts ) => {
2023-07-09 04:05:21 -06:00
if ( validator === false ) {
2024-01-23 11:06:49 -07:00
throw new AxiosError (
formatMessage ( opt , ' has been removed' + ( version ? ' in ' + version : '' ) ) ,
AxiosError . ERR _DEPRECATED
) ;
2023-07-09 04:05:21 -06:00
}
if ( version && ! deprecatedWarnings [ opt ] ) {
deprecatedWarnings [ opt ] = true ;
// eslint-disable-next-line no-console
console . warn (
formatMessage (
opt ,
' has been deprecated since v' + version + ' and will be removed in the near future'
)
) ;
}
return validator ? validator ( value , opt , opts ) : true ;
} ;
} ;
/ * *
* Assert object ' s properties type
2024-01-23 11:06:49 -07:00
*
2023-07-09 04:05:21 -06:00
* @ param { object } options
* @ param { object } schema
* @ param { boolean ? } allowUnknown
2024-01-23 11:06:49 -07:00
*
* @ returns { object }
2023-07-09 04:05:21 -06:00
* /
function assertOptions ( options , schema , allowUnknown ) {
if ( typeof options !== 'object' ) {
2024-01-23 11:06:49 -07:00
throw new AxiosError ( 'options must be an object' , AxiosError . ERR _BAD _OPTION _VALUE ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
const keys = Object . keys ( options ) ;
let i = keys . length ;
2023-07-09 04:05:21 -06:00
while ( i -- > 0 ) {
2024-01-23 11:06:49 -07:00
const opt = keys [ i ] ;
const validator = schema [ opt ] ;
2023-07-09 04:05:21 -06:00
if ( validator ) {
2024-01-23 11:06:49 -07:00
const value = options [ opt ] ;
const result = value === undefined || validator ( value , opt , options ) ;
2023-07-09 04:05:21 -06:00
if ( result !== true ) {
2024-01-23 11:06:49 -07:00
throw new AxiosError ( 'option ' + opt + ' must be ' + result , AxiosError . ERR _BAD _OPTION _VALUE ) ;
2023-07-09 04:05:21 -06:00
}
continue ;
}
if ( allowUnknown !== true ) {
2024-01-23 11:06:49 -07:00
throw new AxiosError ( 'Unknown option ' + opt , AxiosError . ERR _BAD _OPTION ) ;
2023-07-09 04:05:21 -06:00
}
}
}
2024-01-23 11:06:49 -07:00
var validator = {
assertOptions ,
2023-07-09 04:05:21 -06:00
validators : validators$1
} ;
2024-01-23 11:06:49 -07:00
const validators = validator . validators ;
2023-07-09 04:05:21 -06:00
/ * *
* Create a new instance of Axios
*
* @ param { Object } instanceConfig The default config for the instance
*
2024-01-23 11:06:49 -07:00
* @ return { Axios } A new instance of Axios
2023-07-09 04:05:21 -06:00
* /
2024-01-23 11:06:49 -07:00
class Axios {
constructor ( instanceConfig ) {
this . defaults = instanceConfig ;
this . interceptors = {
request : new InterceptorManager$1 ( ) ,
response : new InterceptorManager$1 ( )
} ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
/ * *
* Dispatch a request
*
* @ param { String | Object } configOrUrl The config specific for this request ( merged with this . defaults )
* @ param { ? Object } config
*
* @ returns { Promise } The Promise to be fulfilled
* /
request ( configOrUrl , config ) {
/*eslint no-param-reassign:0*/
// Allow for axios('example/url'[, config]) a la fetch API
if ( typeof configOrUrl === 'string' ) {
config = config || { } ;
config . url = configOrUrl ;
} else {
config = configOrUrl || { } ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
config = mergeConfig ( this . defaults , config ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const { transitional , paramsSerializer , headers } = config ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( transitional !== undefined ) {
validator . assertOptions ( transitional , {
silentJSONParsing : validators . transitional ( validators . boolean ) ,
forcedJSONParsing : validators . transitional ( validators . boolean ) ,
clarifyTimeoutError : validators . transitional ( validators . boolean )
} , false ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( paramsSerializer != null ) {
if ( utils$1 . isFunction ( paramsSerializer ) ) {
config . paramsSerializer = {
serialize : paramsSerializer
} ;
} else {
validator . assertOptions ( paramsSerializer , {
encode : validators . function ,
serialize : validators . function
} , true ) ;
}
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
// Set config.method
config . method = ( config . method || this . defaults . method || 'get' ) . toLowerCase ( ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// Flatten headers
let contextHeaders = headers && utils$1 . merge (
headers . common ,
headers [ config . method ]
) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
headers && utils$1 . forEach (
[ 'delete' , 'get' , 'head' , 'post' , 'put' , 'patch' , 'common' ] ,
( method ) => {
delete headers [ method ] ;
}
) ;
config . headers = AxiosHeaders$1 . concat ( contextHeaders , headers ) ;
// filter out skipped interceptors
const requestInterceptorChain = [ ] ;
let synchronousRequestInterceptors = true ;
this . interceptors . request . forEach ( function unshiftRequestInterceptors ( interceptor ) {
if ( typeof interceptor . runWhen === 'function' && interceptor . runWhen ( config ) === false ) {
return ;
}
synchronousRequestInterceptors = synchronousRequestInterceptors && interceptor . synchronous ;
requestInterceptorChain . unshift ( interceptor . fulfilled , interceptor . rejected ) ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const responseInterceptorChain = [ ] ;
this . interceptors . response . forEach ( function pushResponseInterceptors ( interceptor ) {
responseInterceptorChain . push ( interceptor . fulfilled , interceptor . rejected ) ;
} ) ;
let promise ;
let i = 0 ;
let len ;
if ( ! synchronousRequestInterceptors ) {
const chain = [ dispatchRequest . bind ( this ) , undefined ] ;
chain . unshift . apply ( chain , requestInterceptorChain ) ;
chain . push . apply ( chain , responseInterceptorChain ) ;
len = chain . length ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
promise = Promise . resolve ( config ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
while ( i < len ) {
promise = promise . then ( chain [ i ++ ] , chain [ i ++ ] ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return promise ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
len = requestInterceptorChain . length ;
let newConfig = config ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
i = 0 ;
while ( i < len ) {
const onFulfilled = requestInterceptorChain [ i ++ ] ;
const onRejected = requestInterceptorChain [ i ++ ] ;
try {
newConfig = onFulfilled ( newConfig ) ;
} catch ( error ) {
onRejected . call ( this , error ) ;
break ;
}
}
2023-07-09 04:05:21 -06:00
try {
2024-01-23 11:06:49 -07:00
promise = dispatchRequest . call ( this , newConfig ) ;
2023-07-09 04:05:21 -06:00
} catch ( error ) {
2024-01-23 11:06:49 -07:00
return Promise . reject ( error ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
i = 0 ;
len = responseInterceptorChain . length ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
while ( i < len ) {
promise = promise . then ( responseInterceptorChain [ i ++ ] , responseInterceptorChain [ i ++ ] ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return promise ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
getUri ( config ) {
config = mergeConfig ( this . defaults , config ) ;
const fullPath = buildFullPath ( config . baseURL , config . url ) ;
return buildURL ( fullPath , config . params , config . paramsSerializer ) ;
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
}
2023-07-09 04:05:21 -06:00
// Provide aliases for supported request methods
utils$1 . forEach ( [ 'delete' , 'get' , 'head' , 'options' ] , function forEachMethodNoData ( method ) {
/*eslint func-names:0*/
2024-01-23 11:06:49 -07:00
Axios . prototype [ method ] = function ( url , config ) {
return this . request ( mergeConfig ( config || { } , {
method ,
url ,
2023-07-09 04:05:21 -06:00
data : ( config || { } ) . data
} ) ) ;
} ;
} ) ;
utils$1 . forEach ( [ 'post' , 'put' , 'patch' ] , function forEachMethodWithData ( method ) {
/*eslint func-names:0*/
2024-01-23 11:06:49 -07:00
function generateHTTPMethod ( isForm ) {
return function httpMethod ( url , data , config ) {
return this . request ( mergeConfig ( config || { } , {
method ,
headers : isForm ? {
'Content-Type' : 'multipart/form-data'
} : { } ,
url ,
data
} ) ) ;
} ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
Axios . prototype [ method ] = generateHTTPMethod ( ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
Axios . prototype [ method + 'Form' ] = generateHTTPMethod ( true ) ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var Axios$1 = Axios ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* A ` CancelToken ` is an object that can be used to request cancellation of an operation .
*
* @ param { Function } executor The executor function .
*
* @ returns { CancelToken }
* /
class CancelToken {
constructor ( executor ) {
if ( typeof executor !== 'function' ) {
throw new TypeError ( 'executor must be a function.' ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
let resolvePromise ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
this . promise = new Promise ( function promiseExecutor ( resolve ) {
resolvePromise = resolve ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
const token = this ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// eslint-disable-next-line func-names
this . promise . then ( cancel => {
if ( ! token . _listeners ) return ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
let i = token . _listeners . length ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
while ( i -- > 0 ) {
token . _listeners [ i ] ( cancel ) ;
}
token . _listeners = null ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// eslint-disable-next-line func-names
this . promise . then = onfulfilled => {
let _resolve ;
// eslint-disable-next-line func-names
const promise = new Promise ( resolve => {
token . subscribe ( resolve ) ;
_resolve = resolve ;
} ) . then ( onfulfilled ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
promise . cancel = function reject ( ) {
token . unsubscribe ( _resolve ) ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
return promise ;
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
executor ( function cancel ( message , config , request ) {
if ( token . reason ) {
// Cancellation has already been requested
return ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
token . reason = new CanceledError ( message , config , request ) ;
resolvePromise ( token . reason ) ;
} ) ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Throws a ` CanceledError ` if cancellation has been requested .
* /
throwIfRequested ( ) {
if ( this . reason ) {
throw this . reason ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Subscribe to the cancel signal
* /
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
subscribe ( listener ) {
if ( this . reason ) {
listener ( this . reason ) ;
return ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
if ( this . _listeners ) {
this . _listeners . push ( listener ) ;
} else {
this . _listeners = [ listener ] ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Unsubscribe from the cancel signal
* /
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
unsubscribe ( listener ) {
if ( ! this . _listeners ) {
return ;
}
const index = this . _listeners . indexOf ( listener ) ;
if ( index !== - 1 ) {
this . _listeners . splice ( index , 1 ) ;
}
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Returns an object that contains a new ` CancelToken ` and a function that , when called ,
* cancels the ` CancelToken ` .
* /
static source ( ) {
let cancel ;
const token = new CancelToken ( function executor ( c ) {
cancel = c ;
} ) ;
return {
token ,
cancel
} ;
}
2023-07-09 04:05:21 -06:00
}
2024-01-23 11:06:49 -07:00
var CancelToken$1 = CancelToken ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Syntactic sugar for invoking a function and expanding an array for arguments .
*
* Common use case would be to use ` Function.prototype.apply ` .
*
* ` ` ` js
* function f ( x , y , z ) { }
* var args = [ 1 , 2 , 3 ] ;
* f . apply ( null , args ) ;
* ` ` `
*
* With ` spread ` this example can be re - written .
*
* ` ` ` js
* spread ( function ( x , y , z ) { } ) ( [ 1 , 2 , 3 ] ) ;
* ` ` `
*
* @ param { Function } callback
*
* @ returns { Function }
* /
function spread ( callback ) {
return function wrap ( arr ) {
return callback . apply ( null , arr ) ;
} ;
}
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
/ * *
* Determines whether the payload is an error thrown by Axios
*
* @ param { * } payload The value to test
*
* @ returns { boolean } True if the payload is an error thrown by Axios , otherwise false
* /
function isAxiosError ( payload ) {
return utils$1 . isObject ( payload ) && ( payload . isAxiosError === true ) ;
}
const HttpStatusCode = {
Continue : 100 ,
SwitchingProtocols : 101 ,
Processing : 102 ,
EarlyHints : 103 ,
Ok : 200 ,
Created : 201 ,
Accepted : 202 ,
NonAuthoritativeInformation : 203 ,
NoContent : 204 ,
ResetContent : 205 ,
PartialContent : 206 ,
MultiStatus : 207 ,
AlreadyReported : 208 ,
ImUsed : 226 ,
MultipleChoices : 300 ,
MovedPermanently : 301 ,
Found : 302 ,
SeeOther : 303 ,
NotModified : 304 ,
UseProxy : 305 ,
Unused : 306 ,
TemporaryRedirect : 307 ,
PermanentRedirect : 308 ,
BadRequest : 400 ,
Unauthorized : 401 ,
PaymentRequired : 402 ,
Forbidden : 403 ,
NotFound : 404 ,
MethodNotAllowed : 405 ,
NotAcceptable : 406 ,
ProxyAuthenticationRequired : 407 ,
RequestTimeout : 408 ,
Conflict : 409 ,
Gone : 410 ,
LengthRequired : 411 ,
PreconditionFailed : 412 ,
PayloadTooLarge : 413 ,
UriTooLong : 414 ,
UnsupportedMediaType : 415 ,
RangeNotSatisfiable : 416 ,
ExpectationFailed : 417 ,
ImATeapot : 418 ,
MisdirectedRequest : 421 ,
UnprocessableEntity : 422 ,
Locked : 423 ,
FailedDependency : 424 ,
TooEarly : 425 ,
UpgradeRequired : 426 ,
PreconditionRequired : 428 ,
TooManyRequests : 429 ,
RequestHeaderFieldsTooLarge : 431 ,
UnavailableForLegalReasons : 451 ,
InternalServerError : 500 ,
NotImplemented : 501 ,
BadGateway : 502 ,
ServiceUnavailable : 503 ,
GatewayTimeout : 504 ,
HttpVersionNotSupported : 505 ,
VariantAlsoNegotiates : 506 ,
InsufficientStorage : 507 ,
LoopDetected : 508 ,
NotExtended : 510 ,
NetworkAuthenticationRequired : 511 ,
} ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
Object . entries ( HttpStatusCode ) . forEach ( ( [ key , value ] ) => {
HttpStatusCode [ value ] = key ;
} ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
var HttpStatusCode$1 = HttpStatusCode ;
2023-07-09 04:05:21 -06:00
/ * *
* Create an instance of Axios
*
* @ param { Object } defaultConfig The default config for the instance
2024-01-23 11:06:49 -07:00
*
* @ returns { Axios } A new instance of Axios
2023-07-09 04:05:21 -06:00
* /
function createInstance ( defaultConfig ) {
2024-01-23 11:06:49 -07:00
const context = new Axios$1 ( defaultConfig ) ;
const instance = bind ( Axios$1 . prototype . request , context ) ;
2023-07-09 04:05:21 -06:00
// Copy axios.prototype to instance
2024-01-23 11:06:49 -07:00
utils$1 . extend ( instance , Axios$1 . prototype , context , { allOwnKeys : true } ) ;
2023-07-09 04:05:21 -06:00
// Copy context to instance
2024-01-23 11:06:49 -07:00
utils$1 . extend ( instance , context , null , { allOwnKeys : true } ) ;
2023-07-09 04:05:21 -06:00
// Factory for creating new instances
instance . create = function create ( instanceConfig ) {
return createInstance ( mergeConfig ( defaultConfig , instanceConfig ) ) ;
} ;
return instance ;
}
// Create the default instance to be exported
2024-01-23 11:06:49 -07:00
const axios = createInstance ( defaults$1 ) ;
2023-07-09 04:05:21 -06:00
// Expose Axios class to allow class inheritance
2024-01-23 11:06:49 -07:00
axios . Axios = Axios$1 ;
2023-07-09 04:05:21 -06:00
// Expose Cancel & CancelToken
2024-01-23 11:06:49 -07:00
axios . CanceledError = CanceledError ;
axios . CancelToken = CancelToken$1 ;
axios . isCancel = isCancel ;
axios . VERSION = VERSION ;
axios . toFormData = toFormData ;
// Expose AxiosError class
axios . AxiosError = AxiosError ;
// alias for CanceledError for backward compatibility
axios . Cancel = axios . CanceledError ;
2023-07-09 04:05:21 -06:00
// Expose all/spread
2024-01-23 11:06:49 -07:00
axios . all = function all ( promises ) {
2023-07-09 04:05:21 -06:00
return Promise . all ( promises ) ;
} ;
2024-01-23 11:06:49 -07:00
axios . spread = spread ;
2023-07-09 04:05:21 -06:00
// Expose isAxiosError
2024-01-23 11:06:49 -07:00
axios . isAxiosError = isAxiosError ;
// Expose mergeConfig
axios . mergeConfig = mergeConfig ;
axios . AxiosHeaders = AxiosHeaders$1 ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
axios . formToJSON = thing => formDataToJSON ( utils$1 . isHTMLForm ( thing ) ? new FormData ( thing ) : thing ) ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
axios . getAdapter = adapters . getAdapter ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
axios . HttpStatusCode = HttpStatusCode$1 ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
axios . default = axios ;
2023-07-09 04:05:21 -06:00
2024-01-23 11:06:49 -07:00
// this module should only have a default export
var axios$1 = axios ;
2023-07-09 04:05:21 -06:00
var _nodeResolve _empty = { } ;
var _nodeResolve _empty$1 = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
default : _nodeResolve _empty
} ) ;
var require$$2 = /*@__PURE__*/ getAugmentedNamespace ( _nodeResolve _empty$1 ) ;
// hkp-client - A HKP client implementation in javascript
// Copyright (C) 2015 Tankred Hase
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 3.0 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
/ * *
* This class implements a client for the OpenPGP HTTP Keyserver Protocol ( HKP )
* in order to lookup and upload keys on standard public key servers .
* /
class HKP {
/ * *
* Initialize the HKP client and configure it with the key server url and fetch function .
* @ param { String } [ keyServerBaseUrl ] - The HKP key server base url including
* the protocol to use , e . g . 'https://pgp.mit.edu' ; defaults to
* openpgp . config . keyserver ( https : //keyserver.ubuntu.com)
* @ param { Object } [ config ] - Full configuration , defaults to openpgp . config
* /
constructor ( keyServerBaseUrl = 'https://keyserver.ubuntu.com' ) {
this . _baseUrl = keyServerBaseUrl ;
this . _fetch = typeof globalThis . fetch === 'function' ? globalThis . fetch : require$$2 ;
}
/ * *
* Search for a public key on the key server either by key ID or part of the user ID .
* @ param { String } options . keyId The long public key ID .
* @ param { String } options . query This can be any part of the key user ID such as name
* or email address .
* @ returns { String } The ascii armored public key .
* @ async
* /
lookup ( options ) {
let uri = this . _baseUrl + '/pks/lookup?op=get&options=mr&search=' ;
const fetch = this . _fetch ;
if ( options . keyId ) {
uri += '0x' + encodeURIComponent ( options . keyId ) ;
} else if ( options . query ) {
uri += encodeURIComponent ( options . query ) ;
} else {
throw new Error ( 'You must provide a query parameter!' ) ;
}
return fetch ( uri ) . then ( function ( response ) {
if ( response . status === 200 ) {
return response . text ( ) ;
}
} ) . then ( function ( publicKeyArmored ) {
if ( ! publicKeyArmored || publicKeyArmored . indexOf ( '-----END PGP PUBLIC KEY BLOCK-----' ) < 0 ) {
return ;
}
return publicKeyArmored . trim ( ) ;
} ) ;
}
/ * *
* Upload a public key to the server .
* @ param { String } publicKeyArmored - An ascii armored public key to be uploaded .
* @ returns { Promise }
* @ async
* /
upload ( publicKeyArmored ) {
const uri = this . _baseUrl + '/pks/add' ;
const fetch = this . _fetch ;
return fetch ( uri , {
method : 'post' ,
headers : {
'Content-Type' : 'application/x-www-form-urlencoded; charset=UTF-8'
} ,
body : 'keytext=' + encodeURIComponent ( publicKeyArmored )
} ) ;
}
}
var hkp = HKP ;
var HKP$1 = /*@__PURE__*/ getDefaultExportFromCjs ( hkp ) ;
var _polyfillNode _crypto = { } ;
var _polyfillNode _crypto$1 = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
default : _polyfillNode _crypto
} ) ;
var require$$1 = /*@__PURE__*/ getAugmentedNamespace ( _polyfillNode _crypto$1 ) ;
// wkd-client - A WKD client implementation in javascript
// Copyright (C) 2018 Wiktor Kwapisiewicz
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 3.0 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
/ * *
* This class implements a client for the Web Key Directory ( WKD ) protocol
* in order to lookup keys on designated servers .
* @ see https : //datatracker.ietf.org/doc/draft-koch-openpgp-webkey-service/
* /
class WKD {
/ * *
* Initialize the WKD client
* /
constructor ( ) {
this . _fetch = typeof globalThis . fetch === 'function' ? globalThis . fetch : require$$2 ;
const { subtle } = globalThis . crypto || require$$1 . webcrypto || new ( require$$2 . Crypto ) ( ) ;
this . _subtle = subtle ;
}
/ * *
* Search for a public key using Web Key Directory protocol .
* @ param { String } options . email User ' s email .
* @ returns { Uint8Array } The public key .
* @ async
* /
async lookup ( options ) {
const fetch = this . _fetch ;
if ( ! options . email ) {
throw new Error ( 'You must provide an email parameter!' ) ;
}
if ( typeof options . email !== 'string' || ! options . email . includes ( '@' ) ) {
throw new Error ( 'Invalid e-mail address.' ) ;
}
const [ localPart , domain ] = options . email . split ( '@' ) ;
const localPartEncoded = new TextEncoder ( ) . encode ( localPart . toLowerCase ( ) ) ;
const localPartHashed = new Uint8Array ( await this . _subtle . digest ( 'SHA-1' , localPartEncoded ) ) ;
const localPartBase32 = encodeZBase32 ( localPartHashed ) ;
const localPartEscaped = encodeURIComponent ( localPart ) ;
const urlAdvanced = ` https://openpgpkey. ${ domain } /.well-known/openpgpkey/ ${ domain } /hu/ ${ localPartBase32 } ?l= ${ localPartEscaped } ` ;
const urlDirect = ` https:// ${ domain } /.well-known/openpgpkey/hu/ ${ localPartBase32 } ?l= ${ localPartEscaped } ` ;
let response ;
try {
response = await fetch ( urlAdvanced ) ;
if ( response . status !== 200 ) {
throw new Error ( 'Advanced WKD lookup failed: ' + response . statusText ) ;
}
} catch ( err ) {
response = await fetch ( urlDirect ) ;
if ( response . status !== 200 ) {
throw new Error ( 'Direct WKD lookup failed: ' + response . statusText ) ;
}
}
return new Uint8Array ( await response . arrayBuffer ( ) ) ;
}
}
/ * *
* Encode input buffer using Z - Base32 encoding .
* See : https : //tools.ietf.org/html/rfc6189#section-5.1.6
*
* @ param { Uint8Array } data - The binary data to encode
* @ returns { String } Binary data encoded using Z - Base32 .
* /
function encodeZBase32 ( data ) {
if ( data . length === 0 ) {
return "" ;
}
const ALPHABET = "ybndrfg8ejkmcpqxot1uwisza345h769" ;
const SHIFT = 5 ;
const MASK = 31 ;
let buffer = data [ 0 ] ;
let index = 1 ;
let bitsLeft = 8 ;
let result = '' ;
while ( bitsLeft > 0 || index < data . length ) {
if ( bitsLeft < SHIFT ) {
if ( index < data . length ) {
buffer <<= 8 ;
buffer |= data [ index ++ ] & 0xff ;
bitsLeft += 8 ;
} else {
const pad = SHIFT - bitsLeft ;
buffer <<= pad ;
bitsLeft += pad ;
}
}
bitsLeft -= SHIFT ;
result += ALPHABET [ MASK & ( buffer >> bitsLeft ) ] ;
}
return result ;
}
var wkd = WKD ;
var WKD$1 = /*@__PURE__*/ getDefaultExportFromCjs ( wkd ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* Functions related to OpenPGP Profiles
* @ module openpgp
* /
/ * *
* Fetch a public key using keyservers
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } identifier - Fingerprint or email address
* @ param { string } [ keyserverDomain ] - Domain of the keyserver
* @ returns { Promise < Profile > } The profile from the fetched OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key1 = doip . keys . fetchHKP ( 'alice@domain.tld' ) ;
* const key2 = doip . keys . fetchHKP ( '123abc123abc' ) ;
2024-02-01 09:06:40 -07:00
* const key3 = doip . keys . fetchHKP ( '123abc123abc' , 'pgpkeys.eu' ) ;
2023-07-09 04:05:21 -06:00
* /
2024-02-01 09:06:40 -07:00
async function fetchHKP ( identifier , keyserverDomain = 'keys.openpgp.org' ) {
const keyserverBaseUrl = ` https:// ${ keyserverDomain ? ? 'keys.openpgp.org' } ` ;
2023-07-09 04:05:21 -06:00
const hkp = new HKP$1 ( keyserverBaseUrl ) ;
const lookupOpts = {
query : identifier
} ;
const publicKeyArmored = await hkp
. lookup ( lookupOpts )
. catch ( ( error ) => {
throw new Error ( ` Key does not exist or could not be fetched ( ${ error } ) ` )
} ) ;
if ( ! publicKeyArmored ) {
throw new Error ( 'Key does not exist or could not be fetched' )
}
2024-01-23 11:06:49 -07:00
const publicKey = await openpgp$2 . readKey ( {
2023-07-09 04:05:21 -06:00
armoredKey : publicKeyArmored
} )
. catch ( ( error ) => {
throw new Error ( ` Key could not be read ( ${ error } ) ` )
} ) ;
const profile = await parsePublicKey ( publicKey ) ;
profile . publicKey . fetch . method = PublicKeyFetchMethod . HKP ;
profile . publicKey . fetch . query = identifier ;
return profile
}
/ * *
* Fetch a public key using Web Key Directory
* @ function
* @ param { string } identifier - Identifier of format ' username @ domain . tld `
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile from the fetched OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key = doip . keys . fetchWKD ( 'alice@domain.tld' ) ;
* /
async function fetchWKD ( identifier ) {
const wkd = new WKD$1 ( ) ;
const lookupOpts = {
email : identifier
} ;
const publicKeyBinary = await wkd
. lookup ( lookupOpts )
. catch ( ( /** @type {Error} */ error ) => {
throw new Error ( ` Key does not exist or could not be fetched ( ${ error } ) ` )
} ) ;
if ( ! publicKeyBinary ) {
throw new Error ( 'Key does not exist or could not be fetched' )
}
2024-01-23 11:06:49 -07:00
const publicKey = await openpgp$2 . readKey ( {
2023-07-09 04:05:21 -06:00
binaryKey : publicKeyBinary
} )
. catch ( ( error ) => {
throw new Error ( ` Key could not be read ( ${ error } ) ` )
} ) ;
const profile = await parsePublicKey ( publicKey ) ;
profile . publicKey . fetch . method = PublicKeyFetchMethod . WKD ;
profile . publicKey . fetch . query = identifier ;
return profile
}
/ * *
* Fetch a public key from Keybase
* @ function
2024-02-01 09:06:40 -07:00
* @ param { string } username - Keybase username
* @ param { string } fingerprint - Fingerprint of key
* @ returns { Promise < Profile > } The profile from the fetched OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key = doip . keys . fetchKeybase ( 'alice' , '123abc123abc' ) ;
* /
async function fetchKeybase ( username , fingerprint ) {
const keyLink = ` https://keybase.io/ ${ username } /pgp_keys.asc?fingerprint= ${ fingerprint } ` ;
let rawKeyContent ;
try {
rawKeyContent = await axios$1 . get (
keyLink ,
{
responseType : 'text'
}
)
. then ( ( /** @type {import('axios').AxiosResponse} */ response ) => {
if ( response . status === 200 ) {
return response
}
} )
. then ( ( /** @type {import('axios').AxiosResponse} */ response ) => response . data ) ;
} catch ( e ) {
throw new Error ( ` Error fetching Keybase key: ${ e . message } ` )
}
2024-01-23 11:06:49 -07:00
const publicKey = await openpgp$2 . readKey ( {
2023-07-09 04:05:21 -06:00
armoredKey : rawKeyContent
} )
. catch ( ( error ) => {
throw new Error ( ` Key does not exist or could not be fetched ( ${ error } ) ` )
} ) ;
const profile = await parsePublicKey ( publicKey ) ;
profile . publicKey . fetch . method = PublicKeyFetchMethod . HTTP ;
profile . publicKey . fetch . query = null ;
profile . publicKey . fetch . resolvedUrl = keyLink ;
return profile
}
/ * *
2024-02-01 09:06:40 -07:00
* Get a public key from armored public key text data
2023-07-09 04:05:21 -06:00
* @ function
* @ param { string } rawKeyContent - Plaintext ASCII - formatted public key data
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile from the armored public key
2023-07-09 04:05:21 -06:00
* @ example
* const plainkey = ` -----BEGIN PGP PUBLIC KEY BLOCK-----
*
* mQINBF0mIsIBEADacleiyiV + z6FIunvLWrO6ZETxGNVpqM + WbBQKdW1BVrJBBolg
* [ ... ]
* = 6 lib
* -- -- - END PGP PUBLIC KEY BLOCK -- -- - `
* const key = doip . keys . fetchPlaintext ( plainkey ) ;
* /
async function fetchPlaintext ( rawKeyContent ) {
2024-01-23 11:06:49 -07:00
const publicKey = await openpgp$2 . readKey ( {
2023-07-09 04:05:21 -06:00
armoredKey : rawKeyContent
} )
. catch ( ( error ) => {
throw new Error ( ` Key could not be read ( ${ error } ) ` )
} ) ;
const profile = await parsePublicKey ( publicKey ) ;
return profile
}
/ * *
* Fetch a public key using an URI
* @ function
* @ param { string } uri - URI that defines the location of the key
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile from the fetched OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key1 = doip . keys . fetchURI ( 'hkp:alice@domain.tld' ) ;
* const key2 = doip . keys . fetchURI ( 'hkp:123abc123abc' ) ;
* const key3 = doip . keys . fetchURI ( 'wkd:alice@domain.tld' ) ;
* /
async function fetchURI ( uri ) {
if ( ! validUrlExports . isUri ( uri ) ) {
throw new Error ( 'Invalid URI' )
}
const re = /([a-zA-Z0-9]*):([a-zA-Z0-9@._=+-]*)(?::([a-zA-Z0-9@._=+-]*))?/ ;
const match = uri . match ( re ) ;
if ( ! match [ 1 ] ) {
throw new Error ( 'Invalid URI' )
}
switch ( match [ 1 ] ) {
case 'hkp' :
return await fetchHKP (
match [ 3 ] ? match [ 3 ] : match [ 2 ] ,
match [ 3 ] ? match [ 2 ] : null
)
case 'wkd' :
return await fetchWKD ( match [ 2 ] )
case 'kb' :
return await fetchKeybase ( match [ 2 ] , match . length >= 4 ? match [ 3 ] : null )
default :
throw new Error ( 'Invalid URI protocol' )
}
}
/ * *
* Fetch a public key
*
* This function will attempt to detect the identifier and fetch the key
* accordingly . If the identifier is an email address , it will first try and
* fetch the key using WKD and then HKP . Otherwise , it will try HKP only .
*
* This function will also try and parse the input as a plaintext key
* @ function
* @ param { string } identifier - URI that defines the location of the key
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile from the fetched OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key1 = doip . keys . fetch ( 'alice@domain.tld' ) ;
* const key2 = doip . keys . fetch ( '123abc123abc' ) ;
* /
async function fetch$1 ( identifier ) {
const re = /([a-zA-Z0-9@._=+-]*)(?::([a-zA-Z0-9@._=+-]*))?/ ;
const match = identifier . match ( re ) ;
let profile = null ;
// Attempt plaintext
try {
profile = await fetchPlaintext ( identifier ) ;
} catch ( e ) { }
// Attempt WKD
if ( ! profile && identifier . includes ( '@' ) ) {
try {
profile = await fetchWKD ( match [ 1 ] ) ;
} catch ( e ) { }
}
// Attempt HKP
if ( ! profile ) {
profile = await fetchHKP (
match [ 2 ] ? match [ 2 ] : match [ 1 ] ,
match [ 2 ] ? match [ 1 ] : null
) ;
}
if ( ! profile ) {
throw new Error ( 'Key does not exist or could not be fetched' )
}
return profile
}
/ * *
2023-07-13 02:41:31 -06:00
* Process a public key to get a profile
2023-07-09 04:05:21 -06:00
* @ function
2023-07-13 02:41:31 -06:00
* @ param { PublicKey } publicKey - The public key to parse
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile from the processed OpenPGP key
2023-07-09 04:05:21 -06:00
* @ example
* const key = doip . keys . fetchURI ( 'hkp:alice@domain.tld' ) ;
2023-07-13 02:41:31 -06:00
* const profile = doip . keys . parsePublicKey ( key ) ;
* profile . personas [ 0 ] . claims . forEach ( claim => {
2023-07-09 04:05:21 -06:00
* console . log ( claim . uri ) ;
* } ) ;
* /
async function parsePublicKey ( publicKey ) {
2024-01-23 11:06:49 -07:00
if ( ! ( publicKey && ( publicKey instanceof openpgp$2 . PublicKey ) ) ) {
2023-07-09 04:05:21 -06:00
throw new Error ( 'Invalid public key' )
}
const fingerprint = publicKey . getFingerprint ( ) ;
const primaryUser = await publicKey . getPrimaryUser ( ) ;
const users = publicKey . users ;
const personas = [ ] ;
users . forEach ( ( user , i ) => {
2023-09-18 09:46:54 -06:00
if ( ! user . userID ) return
2023-07-09 04:05:21 -06:00
const pe = new Persona ( user . userID . name , [ ] ) ;
pe . setIdentifier ( user . userID . userID ) ;
pe . setDescription ( user . userID . comment ) ;
pe . setEmailAddress ( user . userID . email ) ;
if ( 'selfCertifications' in user && user . selfCertifications . length > 0 ) {
const selfCertification = user . selfCertifications . sort ( ( e1 , e2 ) => e2 . created . getTime ( ) - e1 . created . getTime ( ) ) [ 0 ] ;
if ( selfCertification . revoked ) {
pe . revoke ( ) ;
}
const notations = selfCertification . rawNotations ;
pe . claims = notations
. filter (
( { name , humanReadable } ) =>
humanReadable && ( name === 'proof@ariadne.id' || name === 'proof@metacode.biz' )
)
. map (
( { value } ) =>
new Claim ( new TextDecoder ( ) . decode ( value ) , ` openpgp4fpr: ${ fingerprint } ` )
) ;
}
personas . push ( pe ) ;
} ) ;
2023-07-13 02:41:31 -06:00
const profile = new Profile ( ProfileType . OPENPGP , ` openpgp4fpr: ${ fingerprint } ` , personas ) ;
profile . primaryPersonaIndex = primaryUser . index ;
profile . publicKey . keyType = PublicKeyType . OPENPGP ;
profile . publicKey . fingerprint = fingerprint ;
profile . publicKey . encoding = PublicKeyEncoding . ARMORED _PGP ;
profile . publicKey . encodedKey = publicKey . armor ( ) ;
profile . publicKey . key = publicKey ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
return profile
2023-07-09 04:05:21 -06:00
}
var openpgp = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
fetch : fetch$1 ,
fetchHKP : fetchHKP ,
fetchKeybase : fetchKeybase ,
fetchPlaintext : fetchPlaintext ,
fetchURI : fetchURI ,
2023-07-13 02:41:31 -06:00
fetchWKD : fetchWKD ,
parsePublicKey : parsePublicKey
2023-07-09 04:05:21 -06:00
} ) ;
var crypto$1 = crypto ;
const isCryptoKey = ( key ) => key instanceof CryptoKey ;
const digest = async ( algorithm , data ) => {
const subtleDigest = ` SHA- ${ algorithm . slice ( - 3 ) } ` ;
return new Uint8Array ( await crypto$1 . subtle . digest ( subtleDigest , data ) ) ;
} ;
const encoder = new TextEncoder ( ) ;
const decoder = new TextDecoder ( ) ;
function concat ( ... buffers ) {
const size = buffers . reduce ( ( acc , { length } ) => acc + length , 0 ) ;
const buf = new Uint8Array ( size ) ;
let i = 0 ;
buffers . forEach ( ( buffer ) => {
buf . set ( buffer , i ) ;
i += buffer . length ;
} ) ;
return buf ;
}
const encodeBase64 = ( input ) => {
let unencoded = input ;
if ( typeof unencoded === 'string' ) {
unencoded = encoder . encode ( unencoded ) ;
}
const CHUNK _SIZE = 0x8000 ;
const arr = [ ] ;
for ( let i = 0 ; i < unencoded . length ; i += CHUNK _SIZE ) {
arr . push ( String . fromCharCode . apply ( null , unencoded . subarray ( i , i + CHUNK _SIZE ) ) ) ;
}
return btoa ( arr . join ( '' ) ) ;
} ;
const encode = ( input ) => {
return encodeBase64 ( input ) . replace ( /=/g , '' ) . replace ( /\+/g , '-' ) . replace ( /\//g , '_' ) ;
} ;
const decodeBase64 = ( encoded ) => {
const binary = atob ( encoded ) ;
const bytes = new Uint8Array ( binary . length ) ;
for ( let i = 0 ; i < binary . length ; i ++ ) {
bytes [ i ] = binary . charCodeAt ( i ) ;
}
return bytes ;
} ;
const decode$1 = ( input ) => {
let encoded = input ;
if ( encoded instanceof Uint8Array ) {
encoded = decoder . decode ( encoded ) ;
}
encoded = encoded . replace ( /-/g , '+' ) . replace ( /_/g , '/' ) . replace ( /\s/g , '' ) ;
try {
return decodeBase64 ( encoded ) ;
}
catch ( _a ) {
throw new TypeError ( 'The input to be decoded is not correctly encoded.' ) ;
}
} ;
class JOSEError extends Error {
static get code ( ) {
return 'ERR_JOSE_GENERIC' ;
}
constructor ( message ) {
var _a ;
super ( message ) ;
this . code = 'ERR_JOSE_GENERIC' ;
this . name = this . constructor . name ;
( _a = Error . captureStackTrace ) === null || _a === void 0 ? void 0 : _a . call ( Error , this , this . constructor ) ;
}
}
class JOSEAlgNotAllowed extends JOSEError {
constructor ( ) {
super ( ... arguments ) ;
this . code = 'ERR_JOSE_ALG_NOT_ALLOWED' ;
}
static get code ( ) {
return 'ERR_JOSE_ALG_NOT_ALLOWED' ;
}
}
class JOSENotSupported extends JOSEError {
constructor ( ) {
super ( ... arguments ) ;
this . code = 'ERR_JOSE_NOT_SUPPORTED' ;
}
static get code ( ) {
return 'ERR_JOSE_NOT_SUPPORTED' ;
}
}
class JWSInvalid extends JOSEError {
constructor ( ) {
super ( ... arguments ) ;
this . code = 'ERR_JWS_INVALID' ;
}
static get code ( ) {
return 'ERR_JWS_INVALID' ;
}
}
class JWKInvalid extends JOSEError {
constructor ( ) {
super ( ... arguments ) ;
this . code = 'ERR_JWK_INVALID' ;
}
static get code ( ) {
return 'ERR_JWK_INVALID' ;
}
}
class JWSSignatureVerificationFailed extends JOSEError {
constructor ( ) {
super ( ... arguments ) ;
this . code = 'ERR_JWS_SIGNATURE_VERIFICATION_FAILED' ;
this . message = 'signature verification failed' ;
}
static get code ( ) {
return 'ERR_JWS_SIGNATURE_VERIFICATION_FAILED' ;
}
}
function unusable ( name , prop = 'algorithm.name' ) {
return new TypeError ( ` CryptoKey does not support this operation, its ${ prop } must be ${ name } ` ) ;
}
function isAlgorithm ( algorithm , name ) {
return algorithm . name === name ;
}
function getHashLength ( hash ) {
return parseInt ( hash . name . slice ( 4 ) , 10 ) ;
}
function getNamedCurve ( alg ) {
switch ( alg ) {
case 'ES256' :
return 'P-256' ;
case 'ES384' :
return 'P-384' ;
case 'ES512' :
return 'P-521' ;
default :
throw new Error ( 'unreachable' ) ;
}
}
function checkUsage ( key , usages ) {
if ( usages . length && ! usages . some ( ( expected ) => key . usages . includes ( expected ) ) ) {
let msg = 'CryptoKey does not support this operation, its usages must include ' ;
if ( usages . length > 2 ) {
const last = usages . pop ( ) ;
msg += ` one of ${ usages . join ( ', ' ) } , or ${ last } . ` ;
}
else if ( usages . length === 2 ) {
msg += ` one of ${ usages [ 0 ] } or ${ usages [ 1 ] } . ` ;
}
else {
msg += ` ${ usages [ 0 ] } . ` ;
}
throw new TypeError ( msg ) ;
}
}
function checkSigCryptoKey ( key , alg , ... usages ) {
switch ( alg ) {
case 'HS256' :
case 'HS384' :
case 'HS512' : {
if ( ! isAlgorithm ( key . algorithm , 'HMAC' ) )
throw unusable ( 'HMAC' ) ;
const expected = parseInt ( alg . slice ( 2 ) , 10 ) ;
const actual = getHashLength ( key . algorithm . hash ) ;
if ( actual !== expected )
throw unusable ( ` SHA- ${ expected } ` , 'algorithm.hash' ) ;
break ;
}
case 'RS256' :
case 'RS384' :
case 'RS512' : {
if ( ! isAlgorithm ( key . algorithm , 'RSASSA-PKCS1-v1_5' ) )
throw unusable ( 'RSASSA-PKCS1-v1_5' ) ;
const expected = parseInt ( alg . slice ( 2 ) , 10 ) ;
const actual = getHashLength ( key . algorithm . hash ) ;
if ( actual !== expected )
throw unusable ( ` SHA- ${ expected } ` , 'algorithm.hash' ) ;
break ;
}
case 'PS256' :
case 'PS384' :
case 'PS512' : {
if ( ! isAlgorithm ( key . algorithm , 'RSA-PSS' ) )
throw unusable ( 'RSA-PSS' ) ;
const expected = parseInt ( alg . slice ( 2 ) , 10 ) ;
const actual = getHashLength ( key . algorithm . hash ) ;
if ( actual !== expected )
throw unusable ( ` SHA- ${ expected } ` , 'algorithm.hash' ) ;
break ;
}
case 'EdDSA' : {
if ( key . algorithm . name !== 'Ed25519' && key . algorithm . name !== 'Ed448' ) {
throw unusable ( 'Ed25519 or Ed448' ) ;
}
break ;
}
case 'ES256' :
case 'ES384' :
case 'ES512' : {
if ( ! isAlgorithm ( key . algorithm , 'ECDSA' ) )
throw unusable ( 'ECDSA' ) ;
const expected = getNamedCurve ( alg ) ;
const actual = key . algorithm . namedCurve ;
if ( actual !== expected )
throw unusable ( expected , 'algorithm.namedCurve' ) ;
break ;
}
default :
throw new TypeError ( 'CryptoKey does not support this operation' ) ;
}
checkUsage ( key , usages ) ;
}
function message ( msg , actual , ... types ) {
if ( types . length > 2 ) {
const last = types . pop ( ) ;
msg += ` one of type ${ types . join ( ', ' ) } , or ${ last } . ` ;
}
else if ( types . length === 2 ) {
msg += ` one of type ${ types [ 0 ] } or ${ types [ 1 ] } . ` ;
}
else {
msg += ` of type ${ types [ 0 ] } . ` ;
}
if ( actual == null ) {
msg += ` Received ${ actual } ` ;
}
else if ( typeof actual === 'function' && actual . name ) {
msg += ` Received function ${ actual . name } ` ;
}
else if ( typeof actual === 'object' && actual != null ) {
if ( actual . constructor && actual . constructor . name ) {
msg += ` Received an instance of ${ actual . constructor . name } ` ;
}
}
return msg ;
}
var invalidKeyInput = ( actual , ... types ) => {
return message ( 'Key must be ' , actual , ... types ) ;
} ;
function withAlg ( alg , actual , ... types ) {
return message ( ` Key for the ${ alg } algorithm must be ` , actual , ... types ) ;
}
var isKeyLike = ( key ) => {
return isCryptoKey ( key ) ;
} ;
const types = [ 'CryptoKey' ] ;
const isDisjoint = ( ... headers ) => {
const sources = headers . filter ( Boolean ) ;
if ( sources . length === 0 || sources . length === 1 ) {
return true ;
}
let acc ;
for ( const header of sources ) {
const parameters = Object . keys ( header ) ;
if ( ! acc || acc . size === 0 ) {
acc = new Set ( parameters ) ;
continue ;
}
for ( const parameter of parameters ) {
if ( acc . has ( parameter ) ) {
return false ;
}
acc . add ( parameter ) ;
}
}
return true ;
} ;
function isObjectLike ( value ) {
return typeof value === 'object' && value !== null ;
}
function isObject ( input ) {
if ( ! isObjectLike ( input ) || Object . prototype . toString . call ( input ) !== '[object Object]' ) {
return false ;
}
if ( Object . getPrototypeOf ( input ) === null ) {
return true ;
}
let proto = input ;
while ( Object . getPrototypeOf ( proto ) !== null ) {
proto = Object . getPrototypeOf ( proto ) ;
}
return Object . getPrototypeOf ( input ) === proto ;
}
var checkKeyLength = ( alg , key ) => {
if ( alg . startsWith ( 'RS' ) || alg . startsWith ( 'PS' ) ) {
const { modulusLength } = key . algorithm ;
if ( typeof modulusLength !== 'number' || modulusLength < 2048 ) {
throw new TypeError ( ` ${ alg } requires key modulusLength to be 2048 bits or larger ` ) ;
}
}
} ;
function subtleMapping ( jwk ) {
let algorithm ;
let keyUsages ;
switch ( jwk . kty ) {
case 'oct' : {
switch ( jwk . alg ) {
case 'HS256' :
case 'HS384' :
case 'HS512' :
algorithm = { name : 'HMAC' , hash : ` SHA- ${ jwk . alg . slice ( - 3 ) } ` } ;
keyUsages = [ 'sign' , 'verify' ] ;
break ;
case 'A128CBC-HS256' :
case 'A192CBC-HS384' :
case 'A256CBC-HS512' :
throw new JOSENotSupported ( ` ${ jwk . alg } keys cannot be imported as CryptoKey instances ` ) ;
case 'A128GCM' :
case 'A192GCM' :
case 'A256GCM' :
case 'A128GCMKW' :
case 'A192GCMKW' :
case 'A256GCMKW' :
algorithm = { name : 'AES-GCM' } ;
keyUsages = [ 'encrypt' , 'decrypt' ] ;
break ;
case 'A128KW' :
case 'A192KW' :
case 'A256KW' :
algorithm = { name : 'AES-KW' } ;
keyUsages = [ 'wrapKey' , 'unwrapKey' ] ;
break ;
case 'PBES2-HS256+A128KW' :
case 'PBES2-HS384+A192KW' :
case 'PBES2-HS512+A256KW' :
algorithm = { name : 'PBKDF2' } ;
keyUsages = [ 'deriveBits' ] ;
break ;
default :
throw new JOSENotSupported ( 'Invalid or unsupported JWK "alg" (Algorithm) Parameter value' ) ;
}
break ;
}
case 'RSA' : {
switch ( jwk . alg ) {
case 'PS256' :
case 'PS384' :
case 'PS512' :
algorithm = { name : 'RSA-PSS' , hash : ` SHA- ${ jwk . alg . slice ( - 3 ) } ` } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'RS256' :
case 'RS384' :
case 'RS512' :
algorithm = { name : 'RSASSA-PKCS1-v1_5' , hash : ` SHA- ${ jwk . alg . slice ( - 3 ) } ` } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'RSA-OAEP' :
case 'RSA-OAEP-256' :
case 'RSA-OAEP-384' :
case 'RSA-OAEP-512' :
algorithm = {
name : 'RSA-OAEP' ,
hash : ` SHA- ${ parseInt ( jwk . alg . slice ( - 3 ) , 10 ) || 1 } ` ,
} ;
keyUsages = jwk . d ? [ 'decrypt' , 'unwrapKey' ] : [ 'encrypt' , 'wrapKey' ] ;
break ;
default :
throw new JOSENotSupported ( 'Invalid or unsupported JWK "alg" (Algorithm) Parameter value' ) ;
}
break ;
}
case 'EC' : {
switch ( jwk . alg ) {
case 'ES256' :
algorithm = { name : 'ECDSA' , namedCurve : 'P-256' } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'ES384' :
algorithm = { name : 'ECDSA' , namedCurve : 'P-384' } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'ES512' :
algorithm = { name : 'ECDSA' , namedCurve : 'P-521' } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'ECDH-ES' :
case 'ECDH-ES+A128KW' :
case 'ECDH-ES+A192KW' :
case 'ECDH-ES+A256KW' :
algorithm = { name : 'ECDH' , namedCurve : jwk . crv } ;
keyUsages = jwk . d ? [ 'deriveBits' ] : [ ] ;
break ;
default :
throw new JOSENotSupported ( 'Invalid or unsupported JWK "alg" (Algorithm) Parameter value' ) ;
}
break ;
}
case 'OKP' : {
switch ( jwk . alg ) {
case 'EdDSA' :
algorithm = { name : jwk . crv } ;
keyUsages = jwk . d ? [ 'sign' ] : [ 'verify' ] ;
break ;
case 'ECDH-ES' :
case 'ECDH-ES+A128KW' :
case 'ECDH-ES+A192KW' :
case 'ECDH-ES+A256KW' :
algorithm = { name : jwk . crv } ;
keyUsages = jwk . d ? [ 'deriveBits' ] : [ ] ;
break ;
default :
throw new JOSENotSupported ( 'Invalid or unsupported JWK "alg" (Algorithm) Parameter value' ) ;
}
break ;
}
default :
throw new JOSENotSupported ( 'Invalid or unsupported JWK "kty" (Key Type) Parameter value' ) ;
}
return { algorithm , keyUsages } ;
}
2023-07-13 02:41:31 -06:00
const parse$2 = async ( jwk ) => {
2023-07-09 04:05:21 -06:00
var _a , _b ;
if ( ! jwk . alg ) {
throw new TypeError ( '"alg" argument is required when "jwk.alg" is not present' ) ;
}
const { algorithm , keyUsages } = subtleMapping ( jwk ) ;
const rest = [
algorithm ,
( _a = jwk . ext ) !== null && _a !== void 0 ? _a : false ,
( _b = jwk . key _ops ) !== null && _b !== void 0 ? _b : keyUsages ,
] ;
if ( algorithm . name === 'PBKDF2' ) {
return crypto$1 . subtle . importKey ( 'raw' , decode$1 ( jwk . k ) , ... rest ) ;
}
const keyData = { ... jwk } ;
delete keyData . alg ;
delete keyData . use ;
return crypto$1 . subtle . importKey ( 'jwk' , keyData , ... rest ) ;
} ;
2023-07-13 02:41:31 -06:00
var asKeyObject = parse$2 ;
2023-07-09 04:05:21 -06:00
async function importJWK ( jwk , alg , octAsKeyObject ) {
var _a ;
if ( ! isObject ( jwk ) ) {
throw new TypeError ( 'JWK must be an object' ) ;
}
alg || ( alg = jwk . alg ) ;
switch ( jwk . kty ) {
case 'oct' :
if ( typeof jwk . k !== 'string' || ! jwk . k ) {
throw new TypeError ( 'missing "k" (Key Value) Parameter value' ) ;
}
octAsKeyObject !== null && octAsKeyObject !== void 0 ? octAsKeyObject : ( octAsKeyObject = jwk . ext !== true ) ;
if ( octAsKeyObject ) {
return asKeyObject ( { ... jwk , alg , ext : ( _a = jwk . ext ) !== null && _a !== void 0 ? _a : false } ) ;
}
return decode$1 ( jwk . k ) ;
case 'RSA' :
if ( jwk . oth !== undefined ) {
throw new JOSENotSupported ( 'RSA JWK "oth" (Other Primes Info) Parameter value is not supported' ) ;
}
case 'EC' :
case 'OKP' :
return asKeyObject ( { ... jwk , alg } ) ;
default :
throw new JOSENotSupported ( 'Unsupported "kty" (Key Type) Parameter value' ) ;
}
}
const symmetricTypeCheck = ( alg , key ) => {
if ( key instanceof Uint8Array )
return ;
if ( ! isKeyLike ( key ) ) {
throw new TypeError ( withAlg ( alg , key , ... types , 'Uint8Array' ) ) ;
}
if ( key . type !== 'secret' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for symmetric algorithms must be of type "secret" ` ) ;
}
} ;
const asymmetricTypeCheck = ( alg , key , usage ) => {
if ( ! isKeyLike ( key ) ) {
throw new TypeError ( withAlg ( alg , key , ... types ) ) ;
}
if ( key . type === 'secret' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for asymmetric algorithms must not be of type "secret" ` ) ;
}
if ( usage === 'sign' && key . type === 'public' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for asymmetric algorithm signing must be of type "private" ` ) ;
}
if ( usage === 'decrypt' && key . type === 'public' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for asymmetric algorithm decryption must be of type "private" ` ) ;
}
if ( key . algorithm && usage === 'verify' && key . type === 'private' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for asymmetric algorithm verifying must be of type "public" ` ) ;
}
if ( key . algorithm && usage === 'encrypt' && key . type === 'private' ) {
throw new TypeError ( ` ${ types . join ( ' or ' ) } instances for asymmetric algorithm encryption must be of type "public" ` ) ;
}
} ;
const checkKeyType = ( alg , key , usage ) => {
const symmetric = alg . startsWith ( 'HS' ) ||
alg === 'dir' ||
alg . startsWith ( 'PBES2' ) ||
/^A\d{3}(?:GCM)?KW$/ . test ( alg ) ;
if ( symmetric ) {
symmetricTypeCheck ( alg , key ) ;
}
else {
asymmetricTypeCheck ( alg , key , usage ) ;
}
} ;
function validateCrit ( Err , recognizedDefault , recognizedOption , protectedHeader , joseHeader ) {
if ( joseHeader . crit !== undefined && protectedHeader . crit === undefined ) {
throw new Err ( '"crit" (Critical) Header Parameter MUST be integrity protected' ) ;
}
if ( ! protectedHeader || protectedHeader . crit === undefined ) {
return new Set ( ) ;
}
if ( ! Array . isArray ( protectedHeader . crit ) ||
protectedHeader . crit . length === 0 ||
protectedHeader . crit . some ( ( input ) => typeof input !== 'string' || input . length === 0 ) ) {
throw new Err ( '"crit" (Critical) Header Parameter MUST be an array of non-empty strings when present' ) ;
}
let recognized ;
if ( recognizedOption !== undefined ) {
recognized = new Map ( [ ... Object . entries ( recognizedOption ) , ... recognizedDefault . entries ( ) ] ) ;
}
else {
recognized = recognizedDefault ;
}
for ( const parameter of protectedHeader . crit ) {
if ( ! recognized . has ( parameter ) ) {
throw new JOSENotSupported ( ` Extension Header Parameter " ${ parameter } " is not recognized ` ) ;
}
if ( joseHeader [ parameter ] === undefined ) {
throw new Err ( ` Extension Header Parameter " ${ parameter } " is missing ` ) ;
}
else if ( recognized . get ( parameter ) && protectedHeader [ parameter ] === undefined ) {
throw new Err ( ` Extension Header Parameter " ${ parameter } " MUST be integrity protected ` ) ;
}
}
return new Set ( protectedHeader . crit ) ;
}
const validateAlgorithms = ( option , algorithms ) => {
if ( algorithms !== undefined &&
( ! Array . isArray ( algorithms ) || algorithms . some ( ( s ) => typeof s !== 'string' ) ) ) {
throw new TypeError ( ` " ${ option } " option must be an array of strings ` ) ;
}
if ( ! algorithms ) {
return undefined ;
}
return new Set ( algorithms ) ;
} ;
function subtleDsa ( alg , algorithm ) {
const hash = ` SHA- ${ alg . slice ( - 3 ) } ` ;
switch ( alg ) {
case 'HS256' :
case 'HS384' :
case 'HS512' :
return { hash , name : 'HMAC' } ;
case 'PS256' :
case 'PS384' :
case 'PS512' :
return { hash , name : 'RSA-PSS' , saltLength : alg . slice ( - 3 ) >> 3 } ;
case 'RS256' :
case 'RS384' :
case 'RS512' :
return { hash , name : 'RSASSA-PKCS1-v1_5' } ;
case 'ES256' :
case 'ES384' :
case 'ES512' :
return { hash , name : 'ECDSA' , namedCurve : algorithm . namedCurve } ;
case 'EdDSA' :
return { name : algorithm . name } ;
default :
throw new JOSENotSupported ( ` alg ${ alg } is not supported either by JOSE or your javascript runtime ` ) ;
}
}
function getCryptoKey ( alg , key , usage ) {
if ( isCryptoKey ( key ) ) {
checkSigCryptoKey ( key , alg , usage ) ;
return key ;
}
if ( key instanceof Uint8Array ) {
if ( ! alg . startsWith ( 'HS' ) ) {
throw new TypeError ( invalidKeyInput ( key , ... types ) ) ;
}
return crypto$1 . subtle . importKey ( 'raw' , key , { hash : ` SHA- ${ alg . slice ( - 3 ) } ` , name : 'HMAC' } , false , [ usage ] ) ;
}
throw new TypeError ( invalidKeyInput ( key , ... types , 'Uint8Array' ) ) ;
}
const verify = async ( alg , key , signature , data ) => {
const cryptoKey = await getCryptoKey ( alg , key , 'verify' ) ;
checkKeyLength ( alg , cryptoKey ) ;
const algorithm = subtleDsa ( alg , cryptoKey . algorithm ) ;
try {
return await crypto$1 . subtle . verify ( algorithm , cryptoKey , signature , data ) ;
}
catch ( _a ) {
return false ;
}
} ;
async function flattenedVerify ( jws , key , options ) {
var _a ;
if ( ! isObject ( jws ) ) {
throw new JWSInvalid ( 'Flattened JWS must be an object' ) ;
}
if ( jws . protected === undefined && jws . header === undefined ) {
throw new JWSInvalid ( 'Flattened JWS must have either of the "protected" or "header" members' ) ;
}
if ( jws . protected !== undefined && typeof jws . protected !== 'string' ) {
throw new JWSInvalid ( 'JWS Protected Header incorrect type' ) ;
}
if ( jws . payload === undefined ) {
throw new JWSInvalid ( 'JWS Payload missing' ) ;
}
if ( typeof jws . signature !== 'string' ) {
throw new JWSInvalid ( 'JWS Signature missing or incorrect type' ) ;
}
if ( jws . header !== undefined && ! isObject ( jws . header ) ) {
throw new JWSInvalid ( 'JWS Unprotected Header incorrect type' ) ;
}
let parsedProt = { } ;
if ( jws . protected ) {
try {
const protectedHeader = decode$1 ( jws . protected ) ;
parsedProt = JSON . parse ( decoder . decode ( protectedHeader ) ) ;
}
catch ( _b ) {
throw new JWSInvalid ( 'JWS Protected Header is invalid' ) ;
}
}
if ( ! isDisjoint ( parsedProt , jws . header ) ) {
throw new JWSInvalid ( 'JWS Protected and JWS Unprotected Header Parameter names must be disjoint' ) ;
}
const joseHeader = {
... parsedProt ,
... jws . header ,
} ;
const extensions = validateCrit ( JWSInvalid , new Map ( [ [ 'b64' , true ] ] ) , options === null || options === void 0 ? void 0 : options . crit , parsedProt , joseHeader ) ;
let b64 = true ;
if ( extensions . has ( 'b64' ) ) {
b64 = parsedProt . b64 ;
if ( typeof b64 !== 'boolean' ) {
throw new JWSInvalid ( 'The "b64" (base64url-encode payload) Header Parameter must be a boolean' ) ;
}
}
const { alg } = joseHeader ;
if ( typeof alg !== 'string' || ! alg ) {
throw new JWSInvalid ( 'JWS "alg" (Algorithm) Header Parameter missing or invalid' ) ;
}
const algorithms = options && validateAlgorithms ( 'algorithms' , options . algorithms ) ;
if ( algorithms && ! algorithms . has ( alg ) ) {
throw new JOSEAlgNotAllowed ( '"alg" (Algorithm) Header Parameter not allowed' ) ;
}
if ( b64 ) {
if ( typeof jws . payload !== 'string' ) {
throw new JWSInvalid ( 'JWS Payload must be a string' ) ;
}
}
else if ( typeof jws . payload !== 'string' && ! ( jws . payload instanceof Uint8Array ) ) {
throw new JWSInvalid ( 'JWS Payload must be a string or an Uint8Array instance' ) ;
}
let resolvedKey = false ;
if ( typeof key === 'function' ) {
key = await key ( parsedProt , jws ) ;
resolvedKey = true ;
}
checkKeyType ( alg , key , 'verify' ) ;
const data = concat ( encoder . encode ( ( _a = jws . protected ) !== null && _a !== void 0 ? _a : '' ) , encoder . encode ( '.' ) , typeof jws . payload === 'string' ? encoder . encode ( jws . payload ) : jws . payload ) ;
2024-01-23 11:06:49 -07:00
let signature ;
try {
signature = decode$1 ( jws . signature ) ;
}
catch ( _c ) {
throw new JWSInvalid ( 'Failed to base64url decode the signature' ) ;
}
2023-07-09 04:05:21 -06:00
const verified = await verify ( alg , key , signature , data ) ;
if ( ! verified ) {
throw new JWSSignatureVerificationFailed ( ) ;
}
let payload ;
if ( b64 ) {
2024-01-23 11:06:49 -07:00
try {
payload = decode$1 ( jws . payload ) ;
}
catch ( _d ) {
throw new JWSInvalid ( 'Failed to base64url decode the payload' ) ;
}
2023-07-09 04:05:21 -06:00
}
else if ( typeof jws . payload === 'string' ) {
payload = encoder . encode ( jws . payload ) ;
}
else {
payload = jws . payload ;
}
const result = { payload } ;
if ( jws . protected !== undefined ) {
result . protectedHeader = parsedProt ;
}
if ( jws . header !== undefined ) {
result . unprotectedHeader = jws . header ;
}
if ( resolvedKey ) {
return { ... result , key } ;
}
return result ;
}
async function compactVerify ( jws , key , options ) {
if ( jws instanceof Uint8Array ) {
jws = decoder . decode ( jws ) ;
}
if ( typeof jws !== 'string' ) {
throw new JWSInvalid ( 'Compact JWS must be a string or Uint8Array' ) ;
}
const { 0 : protectedHeader , 1 : payload , 2 : signature , length } = jws . split ( '.' ) ;
if ( length !== 3 ) {
throw new JWSInvalid ( 'Invalid Compact JWS' ) ;
}
const verified = await flattenedVerify ( { payload , protected : protectedHeader , signature } , key , options ) ;
const result = { payload : verified . payload , protectedHeader : verified . protectedHeader } ;
if ( typeof key === 'function' ) {
return { ... result , key : verified . key } ;
}
return result ;
}
const check = ( value , description ) => {
if ( typeof value !== 'string' || ! value ) {
throw new JWKInvalid ( ` ${ description } missing or invalid ` ) ;
}
} ;
async function calculateJwkThumbprint ( jwk , digestAlgorithm ) {
if ( ! isObject ( jwk ) ) {
throw new TypeError ( 'JWK must be an object' ) ;
}
digestAlgorithm !== null && digestAlgorithm !== void 0 ? digestAlgorithm : ( digestAlgorithm = 'sha256' ) ;
if ( digestAlgorithm !== 'sha256' &&
digestAlgorithm !== 'sha384' &&
digestAlgorithm !== 'sha512' ) {
throw new TypeError ( 'digestAlgorithm must one of "sha256", "sha384", or "sha512"' ) ;
}
let components ;
switch ( jwk . kty ) {
case 'EC' :
check ( jwk . crv , '"crv" (Curve) Parameter' ) ;
check ( jwk . x , '"x" (X Coordinate) Parameter' ) ;
check ( jwk . y , '"y" (Y Coordinate) Parameter' ) ;
components = { crv : jwk . crv , kty : jwk . kty , x : jwk . x , y : jwk . y } ;
break ;
case 'OKP' :
check ( jwk . crv , '"crv" (Subtype of Key Pair) Parameter' ) ;
check ( jwk . x , '"x" (Public Key) Parameter' ) ;
components = { crv : jwk . crv , kty : jwk . kty , x : jwk . x } ;
break ;
case 'RSA' :
check ( jwk . e , '"e" (Exponent) Parameter' ) ;
check ( jwk . n , '"n" (Modulus) Parameter' ) ;
components = { e : jwk . e , kty : jwk . kty , n : jwk . n } ;
break ;
case 'oct' :
check ( jwk . k , '"k" (Key Value) Parameter' ) ;
components = { k : jwk . k , kty : jwk . kty } ;
break ;
default :
throw new JOSENotSupported ( '"kty" (Key Type) Parameter missing or unsupported' ) ;
}
const data = encoder . encode ( JSON . stringify ( components ) ) ;
return encode ( await digest ( digestAlgorithm , data ) ) ;
}
const decode = decode$1 ;
function decodeProtectedHeader ( token ) {
let protectedB64u ;
if ( typeof token === 'string' ) {
const parts = token . split ( '.' ) ;
if ( parts . length === 3 || parts . length === 5 ) {
[ protectedB64u ] = parts ;
}
}
else if ( typeof token === 'object' && token ) {
if ( 'protected' in token ) {
protectedB64u = token . protected ;
}
else {
throw new TypeError ( 'Token does not contain a Protected Header' ) ;
}
}
try {
if ( typeof protectedB64u !== 'string' || ! protectedB64u ) {
throw new Error ( ) ;
}
const result = JSON . parse ( decoder . decode ( decode ( protectedB64u ) ) ) ;
if ( ! isObject ( result ) ) {
throw new Error ( ) ;
}
return result ;
}
catch ( _a ) {
throw new TypeError ( 'Invalid Token or Protected Header formatting' ) ;
}
}
/* eslint-disable @typescript-eslint/strict-boolean-expressions */
2023-07-13 02:41:31 -06:00
function parse$1 ( string , encoding , opts ) {
2023-07-09 04:05:21 -06:00
var _opts$out ;
if ( opts === void 0 ) {
opts = { } ;
}
// Build the character lookup table:
if ( ! encoding . codes ) {
encoding . codes = { } ;
for ( var i = 0 ; i < encoding . chars . length ; ++ i ) {
encoding . codes [ encoding . chars [ i ] ] = i ;
}
} // The string must have a whole number of bytes:
if ( ! opts . loose && string . length * encoding . bits & 7 ) {
throw new SyntaxError ( 'Invalid padding' ) ;
} // Count the padding bytes:
var end = string . length ;
while ( string [ end - 1 ] === '=' ) {
-- end ; // If we get a whole number of bytes, there is too much padding:
if ( ! opts . loose && ! ( ( string . length - end ) * encoding . bits & 7 ) ) {
throw new SyntaxError ( 'Invalid padding' ) ;
}
} // Allocate the output:
var out = new ( ( _opts$out = opts . out ) != null ? _opts$out : Uint8Array ) ( end * encoding . bits / 8 | 0 ) ; // Parse the data:
var bits = 0 ; // Number of bits currently in the buffer
var buffer = 0 ; // Bits waiting to be written out, MSB first
var written = 0 ; // Next byte to write
for ( var _i = 0 ; _i < end ; ++ _i ) {
// Read one character from the string:
var value = encoding . codes [ string [ _i ] ] ;
if ( value === undefined ) {
throw new SyntaxError ( 'Invalid character ' + string [ _i ] ) ;
} // Append the bits to the buffer:
buffer = buffer << encoding . bits | value ;
bits += encoding . bits ; // Write out some bits if the buffer has a byte's worth:
if ( bits >= 8 ) {
bits -= 8 ;
out [ written ++ ] = 0xff & buffer >> bits ;
}
} // Verify that we have received just enough bits:
if ( bits >= encoding . bits || 0xff & buffer << 8 - bits ) {
throw new SyntaxError ( 'Unexpected end of data' ) ;
}
return out ;
}
function stringify ( data , encoding , opts ) {
if ( opts === void 0 ) {
opts = { } ;
}
var _opts = opts ,
_opts$pad = _opts . pad ,
pad = _opts$pad === void 0 ? true : _opts$pad ;
var mask = ( 1 << encoding . bits ) - 1 ;
var out = '' ;
var bits = 0 ; // Number of bits currently in the buffer
var buffer = 0 ; // Bits waiting to be written out, MSB first
for ( var i = 0 ; i < data . length ; ++ i ) {
// Slurp data into the buffer:
buffer = buffer << 8 | 0xff & data [ i ] ;
bits += 8 ; // Write out as much as we can:
while ( bits > encoding . bits ) {
bits -= encoding . bits ;
out += encoding . chars [ mask & buffer >> bits ] ;
}
} // Partial character:
if ( bits ) {
out += encoding . chars [ mask & buffer << encoding . bits - bits ] ;
} // Add padding characters until we hit a byte boundary:
if ( pad ) {
while ( out . length * encoding . bits & 7 ) {
out += '=' ;
}
}
return out ;
}
var base32Encoding = {
chars : 'ABCDEFGHIJKLMNOPQRSTUVWXYZ234567' ,
bits : 5
} ;
var base64UrlEncoding = {
chars : 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_' ,
bits : 6
} ;
2024-01-23 11:06:49 -07:00
var base32 = {
2023-07-13 02:41:31 -06:00
parse : function parse$1$1 ( string , opts ) {
2023-07-09 04:05:21 -06:00
if ( opts === void 0 ) {
opts = { } ;
}
2023-07-13 02:41:31 -06:00
return parse$1 ( opts . loose ? string . toUpperCase ( ) . replace ( /0/g , 'O' ) . replace ( /1/g , 'L' ) . replace ( /8/g , 'B' ) : string , base32Encoding , opts ) ;
2023-07-09 04:05:21 -06:00
} ,
stringify : function stringify$1 ( data , opts ) {
return stringify ( data , base32Encoding , opts ) ;
}
} ;
2024-01-23 11:06:49 -07:00
var base64url = {
2023-07-13 02:41:31 -06:00
parse : function parse$1$1 ( string , opts ) {
return parse$1 ( string , base64UrlEncoding , opts ) ;
2023-07-09 04:05:21 -06:00
} ,
stringify : function stringify$1 ( data , opts ) {
return stringify ( data , base64UrlEncoding , opts ) ;
}
} ;
/ *
Copyright 2023 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
const SupportedCryptoAlg = [ 'EdDSA' , 'ES256' , 'ES256K' , 'ES384' , 'ES512' ] ;
/ * *
* Functions related to Ariadne Signature Profiles
* @ module asp
* /
/ * *
* Fetch a public key using Web Key Directory
* @ function
* @ param { string } uri - ASPE URI
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The fetched profile
2023-07-09 04:05:21 -06:00
* @ example
2024-02-01 09:06:40 -07:00
* const key = await doip . aspe . fetchASPE ( 'aspe:domain.example:1234567890' ) ;
2023-07-09 04:05:21 -06:00
* /
async function fetchASPE ( uri ) {
const re = /aspe:(.*):(.*)/ ;
if ( ! re . test ( uri ) ) {
throw new Error ( 'Invalid ASPE URI' )
}
const matches = uri . match ( re ) ;
const domainPart = matches [ 1 ] ;
const localPart = matches [ 2 ] . toUpperCase ( ) ;
const profileUrl = ` https:// ${ domainPart } /.well-known/aspe/id/ ${ localPart } ` ;
let profileJws ;
try {
profileJws = await axios$1 . get (
profileUrl ,
{
responseType : 'text'
}
)
. then ( ( /** @type {import('axios').AxiosResponse} */ response ) => {
if ( response . status === 200 ) {
return response
}
} )
. then ( ( /** @type {import('axios').AxiosResponse} */ response ) => response . data ) ;
} catch ( e ) {
throw new Error ( ` Error fetching Keybase key: ${ e . message } ` )
}
2023-07-13 02:41:31 -06:00
const profile = await parseProfileJws ( profileJws , uri ) ;
profile . publicKey . fetch . method = PublicKeyFetchMethod . ASPE ;
profile . publicKey . fetch . query = uri ;
profile . publicKey . fetch . resolvedUrl = profileUrl ;
return profile
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Parse a JWS and extract the profile it contains
2023-07-09 04:05:21 -06:00
* @ function
* @ param { string } profileJws - Compact - Serialized profile JWS
2024-02-01 09:06:40 -07:00
* @ param { string } uri - The ASPE URI associated with the profile
* @ returns { Promise < Profile > } The extracted profile
2023-07-09 04:05:21 -06:00
* @ example
2024-02-01 09:06:40 -07:00
* const key = await doip . aspe . parseProfileJws ( '...' , 'aspe:domain.example:123' ) ;
2023-07-09 04:05:21 -06:00
* /
async function parseProfileJws ( profileJws , uri ) {
const matches = uri . match ( /aspe:(.*):(.*)/ ) ;
const localPart = matches [ 2 ] . toUpperCase ( ) ;
// Decode the headers
const protectedHeader = decodeProtectedHeader ( profileJws ) ;
// Extract the JWK
if ( ! SupportedCryptoAlg . includes ( protectedHeader . alg ) ) {
throw new Error ( 'Invalid profile JWS: wrong key algorithm' )
}
if ( ! protectedHeader . kid ) {
throw new Error ( 'Invalid profile JWS: missing key identifier' )
}
if ( ! protectedHeader . jwk ) {
throw new Error ( 'Invalid profile JWS: missing key' )
}
const publicKey = await importJWK ( protectedHeader . jwk , protectedHeader . alg ) ;
// Compute and verify the fingerprint
const fp = await computeJwkFingerprint ( protectedHeader . jwk ) ;
if ( fp !== protectedHeader . kid ) {
throw new Error ( 'Invalid profile JWS: wrong key' )
}
if ( localPart && fp !== localPart ) {
throw new Error ( 'Invalid profile JWS: wrong key' )
}
// Decode the payload
const { payload } = await compactVerify ( profileJws , publicKey ) ;
const payloadJson = JSON . parse ( new TextDecoder ( ) . decode ( payload ) ) ;
// Verify the payload
if ( ! ( Object . prototype . hasOwnProperty . call ( payloadJson , 'http://ariadne.id/type' ) && payloadJson [ 'http://ariadne.id/type' ] === 'profile' ) ) {
throw new Error ( 'Invalid profile JWS: JWS is not a profile' )
}
if ( ! ( Object . prototype . hasOwnProperty . call ( payloadJson , 'http://ariadne.id/version' ) && payloadJson [ 'http://ariadne.id/version' ] === 0 ) ) {
throw new Error ( 'Invalid profile JWS: profile version not supported' )
}
// Extract data from the payload
/** @type {string} */
const profileName = payloadJson [ 'http://ariadne.id/name' ] ;
/** @type {string} */
const profileDescription = payloadJson [ 'http://ariadne.id/description' ] ;
2023-10-05 03:14:38 -06:00
/** @type {string} */
const profileThemeColor = payloadJson [ 'http://ariadne.id/color' ] ;
2024-02-01 09:06:40 -07:00
/** @type {Array<string>} */
2023-07-09 04:05:21 -06:00
const profileClaims = payloadJson [ 'http://ariadne.id/claims' ] ;
const profileClaimsParsed = profileClaims . map ( x => new Claim ( x , uri ) ) ;
const pe = new Persona ( profileName , profileClaimsParsed ) ;
if ( profileDescription ) {
pe . setDescription ( profileDescription ) ;
}
2023-10-05 03:14:38 -06:00
if ( profileThemeColor && /^#([0-9A-F]{3}){1,2}$/i . test ( profileThemeColor ) ) {
pe . themeColor = profileThemeColor ;
}
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
const profile = new Profile ( ProfileType . ASP , uri , [ pe ] ) ;
profile . publicKey . fingerprint = fp ;
profile . publicKey . encoding = PublicKeyEncoding . JWK ;
profile . publicKey . encodedKey = JSON . stringify ( protectedHeader . jwk ) ;
profile . publicKey . key = protectedHeader . jwk ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
switch ( protectedHeader . alg ) {
case 'ES256' :
profile . publicKey . keyType = PublicKeyType . ES256 ;
break
case 'EdDSA' :
profile . publicKey . keyType = PublicKeyType . EDDSA ;
break
default :
profile . publicKey . keyType = PublicKeyType . UNKNOWN ;
break
}
return profile
2023-07-09 04:05:21 -06:00
}
/ * *
2024-02-01 09:06:40 -07:00
* Compute the fingerprint for { @ link https : //github.com/panva/jose/blob/main/docs/interfaces/types.JWK.md JWK} keys
2023-07-09 04:05:21 -06:00
* @ function
2024-02-01 09:06:40 -07:00
* @ param { import ( 'jose' ) . JWK } key - The JWK public key for which to compute the fingerprint
* @ returns { Promise < string > } The computed fingerprint
2023-07-09 04:05:21 -06:00
* /
async function computeJwkFingerprint ( key ) {
const thumbprint = await calculateJwkThumbprint ( key , 'sha512' ) ;
const fingerprintBytes = base64url . parse ( thumbprint , { loose : true } ) . slice ( 0 , 16 ) ;
const fingerprint = base32 . stringify ( fingerprintBytes , { pad : false } ) ;
return fingerprint
}
var asp = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
computeJwkFingerprint : computeJwkFingerprint ,
fetchASPE : fetchASPE ,
parseProfileJws : parseProfileJws
} ) ;
/ *
Copyright 2021 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
/ * *
* @ module signatures
* /
/ * *
2023-07-13 02:41:31 -06:00
* Extract the profile from a signature and fetch the associated key
* @ param { string } signature - The plaintext signature to parse
2024-02-01 09:06:40 -07:00
* @ returns { Promise < Profile > } The profile obtained from the signature
2023-07-09 04:05:21 -06:00
* /
2023-07-13 02:41:31 -06:00
async function parse ( signature ) {
2024-02-01 09:06:40 -07:00
/** @type {CleartextMessage} */
2023-07-09 04:05:21 -06:00
let sigData ;
// Read the signature
try {
2024-01-23 11:06:49 -07:00
sigData = await openpgp$2 . readCleartextMessage ( {
2023-07-09 04:05:21 -06:00
cleartextMessage : signature
} ) ;
} catch ( e ) {
throw new Error ( ` Signature could not be read ( ${ e . message } ) ` )
}
// @ts-ignore
const issuerKeyID = sigData . signature . packets [ 0 ] . issuerKeyID . toHex ( ) ;
// @ts-ignore
const signersUserID = sigData . signature . packets [ 0 ] . signersUserID ;
const preferredKeyServer =
// @ts-ignore
sigData . signature . packets [ 0 ] . preferredKeyServer ||
'https://keys.openpgp.org/' ;
const text = sigData . getText ( ) ;
const sigKeys = [ ] ;
2023-07-13 02:41:31 -06:00
const claims = [ ] ;
2023-07-09 04:05:21 -06:00
text . split ( '\n' ) . forEach ( ( line , i ) => {
const match = line . match ( /^([a-zA-Z0-9]*)=(.*)$/i ) ;
if ( ! match ) {
return
}
switch ( match [ 1 ] . toLowerCase ( ) ) {
case 'key' :
sigKeys . push ( match [ 2 ] ) ;
break
case 'proof' :
2023-07-13 02:41:31 -06:00
claims . push ( new Claim ( match [ 2 ] ) ) ;
2023-07-09 04:05:21 -06:00
break
}
} ) ;
2023-07-13 02:41:31 -06:00
const obtainedKey = {
query : null ,
data : null ,
method : null
} ;
// Try key identifier found in the signature
2023-07-09 04:05:21 -06:00
if ( sigKeys . length > 0 ) {
try {
2023-07-13 02:41:31 -06:00
obtainedKey . query = sigKeys [ 0 ] ;
2024-02-01 09:06:40 -07:00
/** @type {PublicKey} */
2023-07-13 02:41:31 -06:00
obtainedKey . data = ( await fetchURI ( obtainedKey . query ) ) . publicKey . key ;
obtainedKey . method = obtainedKey . query . split ( ':' ) [ 0 ] ;
2023-07-09 04:05:21 -06:00
} catch ( e ) { }
}
// Try WKD
2023-07-13 02:41:31 -06:00
if ( ! obtainedKey . data && signersUserID ) {
2023-07-09 04:05:21 -06:00
try {
2023-07-13 02:41:31 -06:00
obtainedKey . query = signersUserID ;
obtainedKey . data = ( await fetchURI ( ` wkd: ${ signersUserID } ` ) ) . publicKey . key ;
obtainedKey . method = 'wkd' ;
2023-07-09 04:05:21 -06:00
} catch ( e ) { }
}
// Try HKP
2023-07-13 02:41:31 -06:00
if ( ! obtainedKey . data ) {
2023-07-09 04:05:21 -06:00
try {
const match = preferredKeyServer . match ( /^(.*:\/\/)?([^/]*)(?:\/)?$/i ) ;
2023-07-13 02:41:31 -06:00
obtainedKey . query = issuerKeyID || signersUserID ;
obtainedKey . data = ( await fetchURI ( ` hkp: ${ match [ 2 ] } : ${ obtainedKey . query } ` ) ) . publicKey . key ;
obtainedKey . method = 'hkp' ;
2023-07-09 04:05:21 -06:00
} catch ( e ) {
throw new Error ( 'Public key not found' )
}
}
2023-07-13 02:41:31 -06:00
const primaryUserData = await obtainedKey . data . getPrimaryUser ( ) ;
const fingerprint = obtainedKey . data . getFingerprint ( ) ;
2023-07-09 04:05:21 -06:00
// Verify the signature
2024-01-23 11:06:49 -07:00
const verificationResult = await openpgp$2 . verify ( {
2023-07-09 04:05:21 -06:00
// @ts-ignore
message : sigData ,
2023-07-13 02:41:31 -06:00
verificationKeys : obtainedKey . data
2023-07-09 04:05:21 -06:00
} ) ;
const { verified } = verificationResult . signatures [ 0 ] ;
try {
await verified ;
} catch ( e ) {
throw new Error ( ` Signature could not be verified ( ${ e . message } ) ` )
}
2023-07-13 02:41:31 -06:00
// Build the persona
const persona = new Persona ( primaryUserData . user . userID . name , [ ] ) ;
persona . setIdentifier ( primaryUserData . user . userID . userID ) ;
persona . setDescription ( primaryUserData . user . userID . comment || null ) ;
persona . setEmailAddress ( primaryUserData . user . userID . email || null ) ;
persona . claims = claims
. map (
( { value } ) =>
new Claim ( new TextDecoder ( ) . decode ( value ) , ` openpgp4fpr: ${ fingerprint } ` )
) ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
const profile = new Profile ( ProfileType . OPENPGP , ` openpgp4fpr: ${ fingerprint } ` , [ persona ] ) ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
profile . publicKey . keyType = PublicKeyType . OPENPGP ;
profile . publicKey . encoding = PublicKeyEncoding . ARMORED _PGP ;
profile . publicKey . encodedKey = obtainedKey . data . armor ( ) ;
profile . publicKey . key = obtainedKey . data ;
profile . publicKey . fetch . method = obtainedKey . method ;
profile . publicKey . fetch . query = obtainedKey . query ;
2023-07-09 04:05:21 -06:00
2023-07-13 02:41:31 -06:00
return profile
2023-07-09 04:05:21 -06:00
}
var signatures = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
2023-07-13 02:41:31 -06:00
parse : parse
2023-07-09 04:05:21 -06:00
} ) ;
2023-10-09 08:28:23 -06:00
/ *
Copyright 2023 Yarmo Mackenbach
Licensed under the Apache License , Version 2.0 ( the "License" ) ;
you may not use this file except in compliance with the License .
You may obtain a copy of the License at
http : //www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing , software
distributed under the License is distributed on an "AS IS" BASIS ,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND , either express or implied .
See the License for the specific language governing permissions and
limitations under the License .
* /
const profile = {
$schema : 'https://json-schema.org/draft/2020-12/schema' ,
$id : 'https://spec.keyoxide.org/2/profile.schema.json' ,
title : 'Profile' ,
description : 'Keyoxide profile with personas' ,
type : 'object' ,
properties : {
profileVersion : {
description : 'The version of the profile' ,
type : 'integer'
} ,
profileType : {
description : 'The type of the profile [openpgp, asp]' ,
type : 'string'
} ,
identifier : {
description : 'Identifier of the profile (email, fingerprint, URI)' ,
type : 'string'
} ,
personas : {
description : 'The personas inside the profile' ,
type : 'array' ,
items : {
$ref : 'https://spec.keyoxide.org/2/persona.schema.json'
} ,
minItems : 1 ,
uniqueItems : true
} ,
primaryPersonaIndex : {
description : 'The index of the primary persona' ,
type : 'integer'
} ,
publicKey : {
description : 'The cryptographic key associated with the profile' ,
type : 'object' ,
properties : {
keyType : {
description : 'The type of cryptographic key [eddsa, es256, openpgp, none]' ,
type : 'string'
} ,
encoding : {
description : 'The encoding of the cryptographic key [pem, jwk, armored_pgp, none]' ,
type : 'string'
} ,
encodedKey : {
description : 'The encoded cryptographic key (PEM, stringified JWK, ...)' ,
type : [ 'string' , 'null' ]
} ,
fetch : {
description : 'Details on how to fetch the public key' ,
type : 'object' ,
properties : {
method : {
description : 'The method to fetch the key [aspe, hkp, wkd, http, none]' ,
type : 'string'
} ,
query : {
description : 'The query to fetch the key' ,
type : [ 'string' , 'null' ]
} ,
resolvedUrl : {
description : 'The URL the method eventually resolved to' ,
type : [ 'string' , 'null' ]
}
}
}
} ,
required : [
'keyType' ,
'fetch'
]
} ,
verifiers : {
description : 'A list of links to verifiers' ,
type : 'array' ,
items : {
type : 'object' ,
properties : {
name : {
description : 'Name of the verifier site' ,
type : 'string'
} ,
url : {
description : 'URL to the profile page on the verifier site' ,
type : 'string'
}
}
} ,
uniqueItems : true
}
} ,
required : [
'profileVersion' ,
'profileType' ,
'identifier' ,
'personas' ,
'primaryPersonaIndex' ,
'publicKey' ,
'verifiers'
] ,
additionalProperties : false
} ;
const persona = {
$schema : 'https://json-schema.org/draft/2020-12/schema' ,
$id : 'https://spec.keyoxide.org/2/persona.schema.json' ,
title : 'Profile' ,
description : 'Keyoxide persona with identity claims' ,
type : 'object' ,
properties : {
identifier : {
description : 'Identifier of the persona' ,
type : [ 'string' , 'null' ]
} ,
name : {
description : 'Name of the persona' ,
type : 'string'
} ,
email : {
description : 'Email address of the persona' ,
type : [ 'string' , 'null' ]
} ,
description : {
description : 'Description of the persona' ,
type : [ 'string' , 'null' ]
} ,
avatarUrl : {
description : 'URL to an avatar image' ,
type : [ 'string' , 'null' ]
} ,
themeColor : {
description : 'Profile page theme color' ,
type : [ 'string' , 'null' ]
} ,
isRevoked : {
type : 'boolean'
} ,
claims : {
description : 'A list of identity claims' ,
type : 'array' ,
items : {
$ref : 'https://spec.keyoxide.org/2/claim.schema.json'
} ,
uniqueItems : true
}
} ,
required : [
'name' ,
'claims'
] ,
additionalProperties : false
} ;
const claim = {
$schema : 'https://json-schema.org/draft/2020-12/schema' ,
$id : 'https://spec.keyoxide.org/2/claim.schema.json' ,
title : 'Identity claim' ,
description : 'Verifiable online identity claim' ,
type : 'object' ,
properties : {
claimVersion : {
description : 'The version of the claim' ,
type : 'integer'
} ,
uri : {
description : 'The claim URI' ,
type : 'string'
} ,
proofs : {
description : 'The proofs that would verify the claim' ,
type : 'array' ,
items : {
type : 'string'
} ,
minItems : 1 ,
uniqueItems : true
} ,
matches : {
description : 'Service providers matched to the claim' ,
type : 'array' ,
items : {
$ref : 'https://spec.keyoxide.org/2/serviceprovider.schema.json'
} ,
uniqueItems : true
} ,
status : {
type : 'integer' ,
description : 'Claim status code'
} ,
display : {
type : 'object' ,
properties : {
profileName : {
type : 'string' ,
description : 'Account name to display in the user interface'
} ,
profileUrl : {
type : [ 'string' , 'null' ] ,
description : 'Profile URL to link to in the user interface'
} ,
proofUrl : {
type : [ 'string' , 'null' ] ,
description : 'Proof URL to link to in the user interface'
} ,
serviceProviderName : {
type : [ 'string' , 'null' ] ,
description : 'Name of the service provider to display in the user interface'
} ,
serviceProviderId : {
type : [ 'string' , 'null' ] ,
description : 'Id of the service provider'
}
}
}
} ,
required : [
'claimVersion' ,
'uri' ,
'proofs' ,
'status' ,
'display'
] ,
additionalProperties : false
} ;
const serviceprovider = {
$schema : 'https://json-schema.org/draft/2020-12/schema' ,
$id : 'https://spec.keyoxide.org/2/serviceprovider.schema.json' ,
title : 'Service provider' ,
description : 'A service provider that can be matched to identity claims' ,
type : 'object' ,
properties : {
about : {
description : 'Details about the service provider' ,
type : 'object' ,
properties : {
name : {
description : 'Full name of the service provider' ,
type : 'string'
} ,
id : {
description : 'Identifier of the service provider (no whitespace or symbols, lowercase)' ,
type : 'string'
} ,
homepage : {
description : 'URL to the homepage of the service provider' ,
type : [ 'string' , 'null' ]
}
}
} ,
profile : {
description : 'What the profile would look like if the match is correct' ,
type : 'object' ,
properties : {
display : {
description : 'Profile name to be displayed' ,
type : 'string'
} ,
uri : {
description : 'URI or URL for public access to the profile' ,
type : 'string'
} ,
qr : {
description : 'URI or URL associated with the profile usually served as a QR code' ,
type : [ 'string' , 'null' ]
}
}
} ,
claim : {
description : 'Details from the claim matching process' ,
type : 'object' ,
properties : {
uriRegularExpression : {
description : 'Regular expression used to parse the URI' ,
type : 'string'
} ,
uriIsAmbiguous : {
description : 'Whether this match automatically excludes other matches' ,
type : 'boolean'
}
}
} ,
proof : {
description : 'Information for the proof verification process' ,
type : 'object' ,
properties : {
request : {
description : 'Details to request the potential proof' ,
type : 'object' ,
properties : {
uri : {
description : 'Location of the proof' ,
type : [ 'string' , 'null' ]
} ,
accessRestriction : {
description : 'Type of access restriction [none, nocors, granted, server]' ,
type : 'string'
} ,
fetcher : {
description : 'Name of the fetcher to use' ,
type : 'string'
} ,
data : {
description : 'Data needed by the fetcher or proxy to request the proof' ,
type : 'object' ,
additionalProperties : true
}
}
} ,
response : {
description : 'Details about the expected response' ,
type : 'object' ,
properties : {
format : {
description : 'Expected format of the proof [text, json]' ,
type : 'string'
}
}
} ,
target : {
description : 'Details about the target located in the response' ,
type : 'array' ,
items : {
type : 'object' ,
properties : {
format : {
description : 'How is the proof formatted [uri, fingerprint]' ,
type : 'string'
} ,
encoding : {
description : 'How is the proof encoded [plain, html, xml]' ,
type : 'string'
} ,
relation : {
description : 'How are the response and the target related [contains, equals]' ,
type : 'string'
} ,
path : {
description : 'Path to the target location if the response is JSON' ,
type : 'array' ,
items : {
type : 'string'
}
}
}
}
}
}
}
} ,
required : [
'about' ,
'profile' ,
'claim' ,
'proof'
] ,
additionalProperties : false
} ;
var schemas = /*#__PURE__*/ Object . freeze ( {
_ _proto _ _ : null ,
claim : claim ,
persona : persona ,
profile : profile ,
serviceprovider : serviceprovider
} ) ;
2023-07-09 04:05:21 -06:00
exports . fetcher = fetcher _ _namespace ;
exports . Claim = Claim ;
exports . Persona = Persona ;
exports . Profile = Profile ;
exports . ServiceProvider = ServiceProvider ;
exports . ServiceProviderDefinitions = index ;
exports . asp = asp ;
2024-01-23 11:06:49 -07:00
exports . defaults = defaults$2 ;
2023-07-09 04:05:21 -06:00
exports . enums = enums ;
exports . openpgp = openpgp ;
exports . proofs = proofs ;
2023-10-09 08:28:23 -06:00
exports . schemas = schemas ;
2023-07-09 04:05:21 -06:00
exports . signatures = signatures ;
2024-01-23 11:06:49 -07:00
exports . utils = utils$2 ;
2023-07-09 04:05:21 -06:00
exports . verifications = verifications ;
return exports ;
2023-07-08 00:36:57 -06:00
2023-09-18 09:46:54 -06:00
} ) ( { } , openpgp , doipFetchers ) ;