diff options
author | Minteck <contact@minteck.org> | 2022-04-09 16:39:03 +0200 |
---|---|---|
committer | Minteck <contact@minteck.org> | 2022-04-09 16:40:02 +0200 |
commit | 0f8967b9113d698cdeb2d05ca85d2d9a80461c24 (patch) | |
tree | 00664ddd9c55a2c33631fd1bd33e556cea9c67e5 | |
parent | dac03ac82bc0f8044a4b339c27b5390e4dcecf2f (diff) | |
download | voicer-0f8967b9113d698cdeb2d05ca85d2d9a80461c24.tar.gz voicer-0f8967b9113d698cdeb2d05ca85d2d9a80461c24.tar.bz2 voicer-0f8967b9113d698cdeb2d05ca85d2d9a80461c24.zip |
299 files changed, 26223 insertions, 0 deletions
diff --git a/.DS_Store b/.DS_Store Binary files differnew file mode 100644 index 0000000..818cd75 --- /dev/null +++ b/.DS_Store diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..70353fb --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +weatherkey +wolframkey +model +venv
\ No newline at end of file diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..b58b603 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,5 @@ +# Default ignored files +/shelf/ +/workspace.xml +# Editor-based HTTP Client requests +/httpRequests/ diff --git a/.idea/Voicer.iml b/.idea/Voicer.iml new file mode 100644 index 0000000..57d91a9 --- /dev/null +++ b/.idea/Voicer.iml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<module type="WEB_MODULE" version="4"> + <component name="NewModuleRootManager"> + <content url="file://$MODULE_DIR$"> + <excludeFolder url="file://$MODULE_DIR$/temp" /> + <excludeFolder url="file://$MODULE_DIR$/.tmp" /> + <excludeFolder url="file://$MODULE_DIR$/tmp" /> + </content> + <orderEntry type="jdk" jdkName="Python 3.10 (Voicer)" jdkType="Python SDK" /> + <orderEntry type="sourceFolder" forTests="false" /> + </component> +</module>
\ No newline at end of file diff --git a/.idea/dictionaries/scoots.xml b/.idea/dictionaries/scoots.xml new file mode 100644 index 0000000..50bf2d2 --- /dev/null +++ b/.idea/dictionaries/scoots.xml @@ -0,0 +1,3 @@ +<component name="ProjectDictionaryState"> + <dictionary name="scoots" /> +</component>
\ No newline at end of file diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..b54be25 --- /dev/null +++ b/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,14 @@ +<component name="InspectionProjectProfileManager"> + <profile version="1.0"> + <option name="myName" value="Project Default" /> + <inspection_tool class="PyPackageRequirementsInspection" enabled="true" level="WARNING" enabled_by_default="true"> + <option name="ignoredPackages"> + <value> + <list size="1"> + <item index="0" class="java.lang.String" itemvalue="googletrans" /> + </list> + </value> + </option> + </inspection_tool> + </profile> +</component>
\ No newline at end of file diff --git a/.idea/jsLibraryMappings.xml b/.idea/jsLibraryMappings.xml new file mode 100644 index 0000000..d23208f --- /dev/null +++ b/.idea/jsLibraryMappings.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="JavaScriptLibraryMappings"> + <includedPredefinedLibrary name="Node.js Core" /> + </component> +</project>
\ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..e17c105 --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,4 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="ProjectRootManager" version="2" project-jdk-name="Python 3.10 (Voicer)" project-jdk-type="Python SDK" /> +</project>
\ No newline at end of file diff --git a/.idea/modules.xml b/.idea/modules.xml new file mode 100644 index 0000000..4691d2b --- /dev/null +++ b/.idea/modules.xml @@ -0,0 +1,8 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="ProjectModuleManager"> + <modules> + <module fileurl="file://$PROJECT_DIR$/.idea/Voicer.iml" filepath="$PROJECT_DIR$/.idea/Voicer.iml" /> + </modules> + </component> +</project>
\ No newline at end of file diff --git a/actions.json b/actions.json new file mode 100644 index 0000000..51a6359 --- /dev/null +++ b/actions.json @@ -0,0 +1,73 @@ +[ + { + "triggers": [ + ["blague"], + ["fais", "rire"], + ["fait", "rire"], + ["fais", "rires"], + ["fait", "rires"], + ["vanne", "raconte"], + ["vanne", "dit"], + ["vanne", "dis"], + ["gag", "raconte"], + ["gag", "dit"], + ["gag", "dis"] + ], + "action": "joke" + }, + { + "triggers": [ + ["quelle", "heure"], + ["quel", "heure"], + ["temps", "est", "il"] + ], + "action": "time" + }, + { + "triggers": [ + ["quel", "jour"], + ["quelle", "jour"], + ["jour", "est", "il"] + ], + "action": "date" + }, + { + "triggers": [ + ["temps", "fait", "il"], + ["fait", "beau"], + ["pleut"], + ["dehors"] + ], + "action": "weather" + }, + { + "triggers": [ + ["où", "suis", "je"], + ["où", "sommes", "nous"], + ["où", "est", "on"], + ["où", "es", "on"], + ["où", "tu", "es"], + ["où", "tu", "est"], + ["ou", "suis", "je"], + ["ou", "suis-je"], + ["ou", "es-tu"], + ["ou", "est-tu"], + ["ou", "est-on"], + ["ou", "sommes-nous"], + ["où", "suis-je"], + ["où", "es-tu"], + ["où", "est-tu"], + ["où", "est-on"], + ["où", "sommes-nous"], + ["ou", "sommes", "nous"], + ["ou", "est", "on"], + ["ou", "es", "on"], + ["ou", "tu", "es"], + ["ou", "tu", "est"], + ["position", "notre"], + ["position", "ma"], + ["position", "ta"] + ], + "action": "location" + } +]
\ No newline at end of file diff --git a/actions/_default.py b/actions/_default.py new file mode 100644 index 0000000..bf66d19 --- /dev/null +++ b/actions/_default.py @@ -0,0 +1,15 @@ +import random + + +# noinspection PyUnresolvedReferences +def _action__default(_input): + fallbacks = [ + "Désolé, je ne comprends pas", + "Je ne peux pas vous aider en ce moment", + "Je ne comprends pas", + "Excusez moi, mais je ne comprends pas", + "Je ne pense pas être en mesure de vous aider", + "Je ne parviens pas à vous aider en ce moment", + ] + + say(random.choice(fallbacks)) diff --git a/actions/date.py b/actions/date.py new file mode 100644 index 0000000..aa91f1c --- /dev/null +++ b/actions/date.py @@ -0,0 +1,9 @@ +from datetime import datetime + + +# noinspection PyUnresolvedReferences +def _action_date(_input): + now = datetime.now() + time = now.strftime("%A %e %B %Y") + say(f"Nous sommes le {time}") + return diff --git a/actions/joke.py b/actions/joke.py new file mode 100644 index 0000000..1d2a75e --- /dev/null +++ b/actions/joke.py @@ -0,0 +1,112 @@ +import random + + +# noinspection PyUnresolvedReferences +def _action_joke(_input): + jokes = [ + "Quelle mamie fait peur aux voleurs ? Mamie Traillette.", + "J'ai une blague sur les magasins. Mais elle a pas supermarché...", + "Pourquoi est-ce c'est difficile de conduire dans le Nord ? Parce que les voitures arrêtent pas de caler.", + "Deux lions discutent. T’as une belle crinière. Arrête, tu vas me faire rugir.", + "Pourquoi est-ce qu'on dit que les bretons sont tous frères et sœurs ? Parce qu’ils n’ont Quimper.", + "Pourquoi est-ce qu'on met tous les crocos en prison ? Parce que les crocos dealent.", + "Comment fait-on pour allumer un barbecue breton ? On utilise des breizh.", + "Pourquoi dit-on que les poissons travaillent illégalement ? Parce qu’ils n’ont pas de fish de paie.", + "Quel est le bar préféré des espagnols ? Le Bar-celone", + "Pourquoi est-ce que les mexicains mangent-ils aux toilettes ? Parce qu’ils aiment manger épicé.", + "Que faisaient les dinosaures quand ils n'arrivaient pas à se décider ? Des tirageosaures", + "Qu'est-ce qu'un tennisman adore faire ? Rendre des services", + "Pourquoi est-ce que les vêtements sont toujours fatigués quand ils sortent de la machine ? Parce qu’ils sont léssivés.", + "Pourquoi est-ce que les livres ont-ils toujours chaud ? Parce qu’ils ont une couverture", + "Où est-ce que les super héros vont-ils faire leurs courses ? Au supermarché", + "Que se passe-t-il quand 2 poissons s'énervent ? Le thon monte", + "Quel fruit est assez fort pour couper des arbres ? Le ci-tron", + "Quel est le jambon que tout le monde déteste ? Le sale ami", + "Que fait un cendrier devant un ascenseur ? Il veut des cendres", + "Que dit une imprimante dans l'eau ? J’ai papier", + "Un chameau dit à un dromadaire : Comment ça va ? Bien, je bosse, et toi ? Je bosse, je bosse.", + "Quel est l'aliment le plus hilarant ? Le riz", + "C’est une jolie petite antenne de TV qui est tombée amoureuse d’un paratonnerre... Elle lui dit : Dis, tu y crois toi, au coup de foudre ?", + "Quel est le sport préféré des insectes ? Le criquet", + "Deux souris voient passer une chauve-souris. Regarde, un ange !", + "Les girafes n'existent pas... C’est un cou monté", + "Pourquoi est ce que Hulk a un beau jardin ? Parce qu’il a la main verte", + "C'est deux fous qui marchent dans la rue. Le premier demande au second : je peux me mettre au milieu ?", + "Qu'est-ce qu'un mort qui coupe du fromage ? Un fend-tome", + "Comment est-ce que les abeilles communiquent entre elles ? Par e-miel", + "Quel est l'arbre préféré des chômeurs ? Le bouleau", + "Que dit-on d'une fleur qui a eu zéro à son contrôle ? Qu’elle s’est plantée", + "Comment appelle-t-on un jeudi vraiment nul ? Une trajeudi", + "Que fait un employé de chez Sephora à sa pause clope ? Il parfumer", + "Qu'est-ce qu'une frite enceinte ? Une patate sautée", + "Qu'est ce qu'une lampe moche ? Un LEDron", + "Deux canards discutent : Coin coin. C’est dingue, j’allais dire la même chose !", + "Est-ce qu'une poule peut parler anglais ? Yes chicken", + "Qui vit dans les tavernes ? Les hommes de bières", + "Quelle est la danse préférée des chats ? Le cha cha cha", + "Qu'est ce qu'une carotte dans une flaque d'eau ? Un bonhomme de neige en été", + "Pourquoi est-ce que les bières sont toujours stressées ? Parce qu’elles ont la pression", + "Quelle princesse a les lèvres gercées ? Labello bois dormant", + "Pourquoi est ce que les poissons n'ont plus de maison ? Parce qu’on les a des truites", + "Pourquoi est ce que le lapin est bleu ? Parce qu’on lapin", + "Pourquoi est ce que Potter est triste ? Parce que personne Harry à sa blague", + "Comment appelle-t-on un combat entre un petit pois et une carotte ? Un bon duel", + "Pourquoi est-ce que les éoliennes n'ont pas de copain ? Parce qu’elles se prennent toujours des vents", + "Où irait Voldemort s'il décidait de jouer de la trompette ? À Jazzkaban", + "D'où viennent les gens les plus dangereux ? D’Angers", + "Qu'est ce qu'un cadeau qui s'en va ? Une surprise party", + "Quelle est la fée que les enfants détestent ? La fée C", + "Qu'est-ce qui est blanc puni dans un coin ? Un vilain frigo", + "Quel poisson n'a pas de certificat de naissance ? Le poisson pané", + "Quel est le médecin qui nous fait tous craquer ? L’ostéo", + "Deux puces sortent du cinéma : L’une dit à l’autre : on rentre à pieds ou on prend un chien ?", + "Deux chiens se promènent. T’as vu ? Un réverbère tout neuf ! Ça s’arrose !", + "Quel est le super héros qui a tout le temps peur ? Le super-sticieux", + "Pourquoi est-ce que les chercheurs ont-ils des trous de mémoire ? Parce qu’ils se creusent la tête", + "Comment les musiciens choisissent-ils leur parquet ? Ils choisissent un parquet Fa Si La Si Ré", + "Quel est le musicien préféré des maladies ? Bach-terie", + "Quel est le réseau préféré des pêcheurs ? Truiteur", + "C'est l'histoire d'un poil. Avant il était bien, et maintenant il est pubien.", + "Que fait un geek quand il a peur ? Il url.", + "Quel est le carburant le plus détendu ? Le kérozen", + "Quel est le fast food préféré de Flash ? Quick", + "C’est 2 grains de sable qui arrivent à la plage : Putain c’est blindé aujourd’hui…", + "Qu'est-ce qui est vert et qui se déplace sous l'eau ? Un chou marin", + "Quel est le pays le plus cool du monde ? Le Yééémen", + "Que fait une vache quand elle ferme les yeux ? Du lait concentré", + "Quel est le super héros qui donne le plus vite l'heure ? Speed heure man", + "Pourquoi est-ce que les anges sont sourds ? Parce que Jésus Christ", + "Quel est le fruit préféré des profs d'histoire ? Les dates", + "Quelle est la déesse du wifi ? La déesse L", + "Qu'est-ce qui est pire que le vent ? Un vampire", + "Quelle est l'arme préféré des vegans ? Le lance roquette", + "Un homme entre dans un restaurant : Bonjour, est-ce que vous servez des nouilles ? Bien sûr, ici on sert tout le monde monsieur.", + "Quelle est la femme du hamster ? L’amsterdam", + "Dans quel pays ne bronze-t-on pas du nez ? Au Népal", + "Deux femmes discutent : Tu fumes après l’amour ? Je sais pas, j’ai jamais regardé.", + "Que fait une théière devant un ascenseur ? Elle veut mon thé", + "Pourquoi est-ce que Winnie l'Ourson veut absolument se marier ? Pour partir en lune de miel", + "Que dit une mère à son fils geek quand le dîner est servi ? Alt Tab !", + "Quelle est la meilleure heure pour écouter de la musique ? Deezer !", + "Que fait un geek quand il descend du métro ? Il libère la RAM", + "Quel est l'animal le plus connecté ? Le porc USB", + "Où vont les biscottes pour danser ? En biscothèque", + "Quel est le style musical préféré des médecins ? Le blouse", + "Comment appelle-t-on un chat qui va dans l'espace ? Un chatellite", + "Que fait un jardinier quand il ment ? Il raconte des salades", + "Où est-ce que l'homme invisible part en vacances ? Chez ses transparents", + "Pourquoi est-ce que Napoléon n'a pas voulu acheter de maison ? Parce qu’il avait déjà un Bonaparte", + "Que dit Frodon devant sa maison ? C’est là que j’hobbit", + "Quels sont les fruits qu'on trouve dans toutes les maisons ? Des coings et des mûres", + "Pourquoi un chasseur emmène-t-il son fusil aux toilettes ? Pour tirer la chasse", + "Quel est le crustacé le plus léger de la mer ? La palourde", + "Pourquoi est-ce que la Saint Valentin est davantage fêtée dans le Nord ? Parce que ça se fête en famille", + "Que dit un informaticien quand il s'ennuie ? Je me fichier", + "Avec quelle monnaie les marins payent-ils ? Avec des sous marins", + "Que dit un italien pour dire au revoir ? Pasta la vista", + "Où va Messi quand il se blesse ? À la pharmessi", + "Que demande un footballeur à son coiffeur ? La coupe du monde s’il vous plaît", + "Que dit un chihuahua japonais pour dire bonjour ? Konichihuahua", + ] + + say(random.choice(jokes)) diff --git a/actions/location.py b/actions/location.py new file mode 100644 index 0000000..4eee869 --- /dev/null +++ b/actions/location.py @@ -0,0 +1,22 @@ +import urllib +from urllib.request import urlopen, Request +import ssl +import json + + +# noinspection PyUnresolvedReferences +def _action_location(_input): + try: + ctx = ssl.create_default_context() + ctx.check_hostname = False + ctx.verify_mode = ssl.CERT_NONE + + ip = urlopen(Request("https://ip.me", headers={"User-Agent": "curl/0.0.0"}), context=ctx).read().decode("utf-8")\ + .strip() + location = json.loads(urlopen(Request("https://ipinfo.io/" + ip + "/json", headers={"User-Agent": "curl/0.0.0"}), + context=ctx).read().decode("utf-8").strip()) + say(f"Vous êtes à {location['city']}, {location['region']}") + except urllib.error.URLError: + say("Désolé, je ne parviens pas à accéder à Internet en ce moment. Vérifiez que votre appareil dispose d'une" + "connexion Internet stable et réessayez.") + return diff --git a/actions/time.py b/actions/time.py new file mode 100644 index 0000000..a894270 --- /dev/null +++ b/actions/time.py @@ -0,0 +1,9 @@ +from datetime import datetime + + +# noinspection PyUnresolvedReferences +def _action_time(_input): + now = datetime.now() + time = now.strftime("%Hh%M") + say(f"Il est {time}") + return diff --git a/actions/weather.py b/actions/weather.py new file mode 100644 index 0000000..c652d77 --- /dev/null +++ b/actions/weather.py @@ -0,0 +1,70 @@ +import urllib +from urllib.request import urlopen, Request +from urllib.parse import quote +import ssl +from datetime import datetime +import json + + +key = open("./weatherkey", "r").read().strip() +codes = json.loads(open("./weatherconditions.json", "r").read().strip()) + + +def temp(t): + return str(t).replace(".", ",").replace(",0", "") + + +def direction(t): + if t == "N": + return "du nord" + elif t == "S": + return "du sud" + elif t == "W": + return "de l'ouest" + elif t == "E": + return "de l'est" + elif t == "SE": + return "du sud-est" + elif t == "NE": + return "du nord-est" + elif t == "SW": + return "du sud-ouest" + elif t == "NW": + return "du nord-ouest" + + +def localizedcode(sel, day): + now = datetime.now() + time = int(now.strftime("%H")) + + for code in codes: + if code['code'] == sel: + if day == "1": + return code['languages'][8]['day_text'] + else: + return code['languages'][8]['night_text'] + + +# noinspection PyUnresolvedReferences +def _action_weather(_input): + try: + ctx = ssl.create_default_context() + ctx.check_hostname = False + ctx.verify_mode = ssl.CERT_NONE + + ip = urlopen(Request("https://ip.me", headers={"User-Agent": "curl/0.0.0"}), context=ctx).read().decode("utf-8")\ + .strip() + location = json.loads(urlopen(Request("https://ipinfo.io/" + ip + "/json", headers={"User-Agent": "curl/0.0.0"}), + context=ctx).read().decode("utf-8").strip()) + weather = json.loads(urlopen(Request(f"https://api.weatherapi.com/v1/current.json?key={key}&q=" + f"{quote(location['city'])}", headers={"User-Agent": "curl/0.0.0"}), + context=ctx).read().decode("utf-8").strip()) + say(f"Actuellement, à {weather['location']['name']}, il fait {temp(weather['current']['temp_c'])} degrés," + f"ressenti {temp(weather['current']['feelslike_c'])} degrés, avec un temps" + f"{localizedcode(weather['current']['condition']['code'], weather['current']['is_day'])}. Le vent souffle à" + f"{temp(weather['current']['wind_kph'])} kilomètre heure, en direction" + f"{direction(weather['current']['wind_dir'])}") + except urllib.error.URLError: + say("Désolé, je ne parviens pas à accéder à Internet en ce moment. Vérifiez que votre appareil dispose d'une" + "connexion Internet stable et réessayez.") + return diff --git a/actions/wolfram.py b/actions/wolfram.py new file mode 100644 index 0000000..97e9c70 --- /dev/null +++ b/actions/wolfram.py @@ -0,0 +1,10 @@ +import os +import base64 + + +# noinspection PyUnresolvedReferences +def _action_wolfram(_input): + result = subprocess.run('node wolfram.js \"' + base64.b64encode(_input.encode("utf-8")).decode('utf-8') + '\"', + shell=True, check=True, capture_output=True).stdout.decode('utf-8').strip() + say(result) + return @@ -0,0 +1,181 @@ +#!/usr/bin/env python3 + +import argparse +import os +import queue +import sounddevice as sd +import vosk +import sys +import json +import subprocess +import locale + +subprocess.run("afplay sounds/load.wav", shell=True, check=True) + + +def say(message="Une erreur s'est produite"): + subprocess.run("say -v Audrey \"" + message.replace("'", "").replace('"', "\\\"").replace("`", "\\`") + .replace("$", "\\$").replace("{", "\\{").replace("}", "\\}") + "\"", shell=True, check=True) + + +def runaction(action="_default",input=""): + try: + locals()["_action_" + action](input) + except: + globals()["_action_" + action](input) + + +q = queue.Queue() +actions = json.loads(open("actions.json", "r").read()) +prefixes = json.loads(open("prefixes.json", "r").read()) +locale.setlocale(locale.LC_TIME, "fr_FR") +locale.setlocale(locale.LC_ALL, "fr_FR") + +for action in actions: + exec(open("./actions/" + action["action"] + ".py").read()) + +exec(open("./actions/_default.py").read()) +exec(open("./actions/wolfram.py").read()) + + +def int_or_str(text): + """Helper function for argument parsing.""" + try: + return int(text) + except ValueError: + return text + + +def callback(indata, frames, time, status): + """This is called (from a separate thread) for each audio block.""" + if status: + print(status, file=sys.stderr) + q.put(bytes(indata)) + + +parser = argparse.ArgumentParser(add_help=False) +parser.add_argument( + '-l', '--list-devices', action='store_true', + help='show list of audio devices and exit') +args, remaining = parser.parse_known_args() +if args.list_devices: + print(sd.query_devices()) + parser.exit(0) +parser = argparse.ArgumentParser( + description=__doc__, + formatter_class=argparse.RawDescriptionHelpFormatter, + parents=[parser]) +parser.add_argument( + '-f', '--filename', type=str, metavar='FILENAME', + help='audio file to store recording to') +parser.add_argument( + '-m', '--model', type=str, metavar='MODEL_PATH', + help='Path to the model') +parser.add_argument( + '-d', '--device', type=int_or_str, + help='input device (numeric ID or substring)') +parser.add_argument( + '-r', '--samplerate', type=int, help='sampling rate') +args = parser.parse_args(remaining) + +try: + if args.model is None: + args.model = "model" + if not os.path.exists(args.model): + print("Please download a model for your language from https://alphacephei.com/vosk/models") + print("and unpack as 'model' in the current folder.") + parser.exit(0) + if args.samplerate is None: + device_info = sd.query_devices(args.device, 'input') + # soundfile expects an int, sounddevice provides a float: + args.samplerate = int(device_info['default_samplerate']) + + model = vosk.Model(args.model) + + if args.filename: + dump_fn = open(args.filename, "wb") + else: + dump_fn = None + + with sd.RawInputStream(samplerate=args.samplerate, blocksize=8000, device=args.device, dtype='int16', + channels=1, callback=callback): + print('#' * 80) + print('Press Ctrl+C to stop the recording') + print('#' * 80) + + subprocess.run("afplay sounds/ready.wav", shell=True, check=True) + + rec = vosk.KaldiRecognizer(model, args.samplerate) + listening = False + while True: + data = q.get() + if rec.AcceptWaveform(data): + text = json.loads(rec.Result())["text"] + otext = text + process = False + used_prefix = None + for prefix in prefixes: + if text.strip().startswith(prefix): + used_prefix = prefix + process = True + if process: + text = text[len(used_prefix):].strip() + if len(text) > 2: + subprocess.run("afplay sounds/stop.wav", shell=True, check=True) + sys.stdout.write("\033[K") + print(" >>> " + text) + words = text.split(" ") + + sact = None + for action in actions: + for trigger in action["triggers"]: + score = 0 + + for tw in trigger: + if tw in words: + score += 1 + + if score >= len(trigger): + sact = action + + if sact is not None: + try: + runaction(sact["action"], text) + except Exception as e: + print(e) + say("Une erreur s'est produite, réessayez à nouveau dans quelques instants.") + else: + try: + runaction("wolfram", text) + except Exception as e: + print(e) + runaction("_default", text) + else: + if len(text) > 0: + print(" xxx " + text) + listening = False + else: + text = json.loads(rec.PartialResult())["partial"] + process = False + for prefix in prefixes: + if text.strip().startswith(prefix): + used_prefix = prefix + process = True + if process: + sys.stdout.write("\033[K") + if not listening: + listening = True + print("> " + text[len(used_prefix):].strip(), end='\r') + else: + if len(text.strip()) > 0: + sys.stdout.write("\033[K") + print("(" + text + ")", end='\r') + else: + sys.stdout.write("\033[K") + print("...", end='\r') + if dump_fn is not None: + dump_fn.write(data) + +except KeyboardInterrupt: + print('\nDone') + parser.exit(0) diff --git a/node_modules/.package-lock.json b/node_modules/.package-lock.json new file mode 100644 index 0000000..f13ee5e --- /dev/null +++ b/node_modules/.package-lock.json @@ -0,0 +1,402 @@ +{ + "name": "voicer", + "version": "1.0.0", + "lockfileVersion": 2, + "requires": true, + "packages": { + "node_modules/@sindresorhus/is": { + "version": "0.14.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", + "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==", + "engines": { + "node": ">=6" + } + }, + "node_modules/@szmarczak/http-timer": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", + "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", + "dependencies": { + "defer-to-connect": "^1.0.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/axios": { + "version": "0.26.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.26.1.tgz", + "integrity": "sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==", + "dependencies": { + "follow-redirects": "^1.14.8" + } + }, + "node_modules/cacheable-request": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", + "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", + "dependencies": { + "clone-response": "^1.0.2", + "get-stream": "^5.1.0", + "http-cache-semantics": "^4.0.0", + "keyv": "^3.0.0", + "lowercase-keys": "^2.0.0", + "normalize-url": "^4.1.0", + "responselike": "^1.0.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/cacheable-request/node_modules/get-stream": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz", + "integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==", + "dependencies": { + "pump": "^3.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cacheable-request/node_modules/lowercase-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", + "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==", + "engines": { + "node": ">=8" + } + }, + "node_modules/clone-response": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", + "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "dependencies": { + "mimic-response": "^1.0.0" + } + }, + "node_modules/configstore": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-4.0.0.tgz", + "integrity": "sha512-CmquAXFBocrzaSM8mtGPMM/HiWmyIpr4CcJl/rgY2uCObZ/S7cKU0silxslqJejl+t/T9HS8E0PUNQD81JGUEQ==", + "dependencies": { + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/crypto-random-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", + "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", + "engines": { + "node": ">=4" + } + }, + "node_modules/decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", + "dependencies": { + "mimic-response": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/defer-to-connect": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", + "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==" + }, + "node_modules/dot-prop": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.1.tgz", + "integrity": "sha512-l0p4+mIuJIua0mhxGoh4a+iNL9bmeK5DvnSVQa6T0OhrVmaEa1XScX5Etc673FePCJOArq/4Pa2cLGODUWTPOQ==", + "dependencies": { + "is-obj": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/follow-redirects": { + "version": "1.14.9", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.9.tgz", + "integrity": "sha512-MQDfihBQYMcyy5dhRDJUHcw7lb2Pv/TuE6xP1vyraLukNDHKbDxDNaOE3NbCAdKQApno+GPRyo1YAp89yCjK4w==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/get-stream": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", + "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", + "dependencies": { + "pump": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/got": { + "version": "9.6.0", + "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", + "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", + "dependencies": { + "@sindresorhus/is": "^0.14.0", + "@szmarczak/http-timer": "^1.1.2", + "cacheable-request": "^6.0.0", + "decompress-response": "^3.3.0", + "duplexer3": "^0.1.4", + "get-stream": "^4.1.0", + "lowercase-keys": "^1.0.1", + "mimic-response": "^1.0.1", + "p-cancelable": "^1.0.0", + "to-readable-stream": "^1.0.0", + "url-parse-lax": "^3.0.0" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.10", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==" + }, + "node_modules/http-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==" + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/is-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", + "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/json-buffer": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", + "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" + }, + "node_modules/keyv": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", + "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", + "dependencies": { + "json-buffer": "3.0.0" + } + }, + "node_modules/lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/make-dir": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "dependencies": { + "pify": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==", + "engines": { + "node": ">=4" + } + }, + "node_modules/normalize-url": { + "version": "4.5.1", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", + "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==", + "engines": { + "node": ">=8" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/p-cancelable": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", + "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", + "engines": { + "node": ">=6" + } + }, + "node_modules/pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "engines": { + "node": ">=4" + } + }, + "node_modules/prepend-http": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", + "engines": { + "node": ">=4" + } + }, + "node_modules/proxy-check": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/proxy-check/-/proxy-check-1.0.8.tgz", + "integrity": "sha512-gooLamKpgl6wi3tJuVpDC7KL3+xSwstUIatyrknMSLaznc+n/cpEiO2HwIAcU30VLExafchmzTpFOgHr8of0wA==" + }, + "node_modules/pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/responselike": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", + "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "dependencies": { + "lowercase-keys": "^1.0.0" + } + }, + "node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==" + }, + "node_modules/to-readable-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", + "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==", + "engines": { + "node": ">=6" + } + }, + "node_modules/translatte": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/translatte/-/translatte-3.0.1.tgz", + "integrity": "sha512-OP41nm4dS1ctRmDDXfgJGK7tAtq2yJe0QCOaRBQjBM+kS4ak4dhWrbL8Mf8p7TFzWJAdV+TLZ1oiYEW3gpWGJg==", + "dependencies": { + "configstore": "4.0.0", + "got": "9.6.0", + "proxy-check": "1.0.8", + "tunnel": "0.0.6" + } + }, + "node_modules/tunnel": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz", + "integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==", + "engines": { + "node": ">=0.6.11 <=0.7.0 || >=0.7.3" + } + }, + "node_modules/unique-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", + "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "dependencies": { + "crypto-random-string": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/url-parse-lax": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", + "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "dependencies": { + "prepend-http": "^2.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" + }, + "node_modules/write-file-atomic": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", + "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", + "dependencies": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + } + }, + "node_modules/xdg-basedir": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", + "integrity": "sha1-SWsswQnsqNus/i3HK2A8F8WHCtQ=", + "engines": { + "node": ">=4" + } + } + } +} diff --git a/node_modules/@sindresorhus/is/dist/index.d.ts b/node_modules/@sindresorhus/is/dist/index.d.ts new file mode 100644 index 0000000..e94d30b --- /dev/null +++ b/node_modules/@sindresorhus/is/dist/index.d.ts @@ -0,0 +1,132 @@ +/// <reference types="node" /> +/// <reference lib="es2016" /> +/// <reference lib="es2017.sharedmemory" /> +/// <reference lib="esnext.asynciterable" /> +/// <reference lib="dom" /> +declare type TypedArray = Int8Array | Uint8Array | Uint8ClampedArray | Int16Array | Uint16Array | Int32Array | Uint32Array | Float32Array | Float64Array; +declare type Primitive = null | undefined | string | number | boolean | Symbol; +export interface ArrayLike { + length: number; +} +export interface Class<T = unknown> { + new (...args: any[]): T; +} +declare type DomElement = object & { + nodeType: 1; + nodeName: string; +}; +declare type NodeStream = object & { + pipe: Function; +}; +export declare const enum TypeName { + null = "null", + boolean = "boolean", + undefined = "undefined", + string = "string", + number = "number", + symbol = "symbol", + Function = "Function", + GeneratorFunction = "GeneratorFunction", + AsyncFunction = "AsyncFunction", + Observable = "Observable", + Array = "Array", + Buffer = "Buffer", + Object = "Object", + RegExp = "RegExp", + Date = "Date", + Error = "Error", + Map = "Map", + Set = "Set", + WeakMap = "WeakMap", + WeakSet = "WeakSet", + Int8Array = "Int8Array", + Uint8Array = "Uint8Array", + Uint8ClampedArray = "Uint8ClampedArray", + Int16Array = "Int16Array", + Uint16Array = "Uint16Array", + Int32Array = "Int32Array", + Uint32Array = "Uint32Array", + Float32Array = "Float32Array", + Float64Array = "Float64Array", + ArrayBuffer = "ArrayBuffer", + SharedArrayBuffer = "SharedArrayBuffer", + DataView = "DataView", + Promise = "Promise", + URL = "URL" +} +declare function is(value: unknown): TypeName; +declare namespace is { + const undefined: (value: unknown) => value is undefined; + const string: (value: unknown) => value is string; + const number: (value: unknown) => value is number; + const function_: (value: unknown) => value is Function; + const null_: (value: unknown) => value is null; + const class_: (value: unknown) => value is Class<unknown>; + const boolean: (value: unknown) => value is boolean; + const symbol: (value: unknown) => value is Symbol; + const numericString: (value: unknown) => boolean; + const array: (arg: any) => arg is any[]; + const buffer: (input: unknown) => input is Buffer; + const nullOrUndefined: (value: unknown) => value is null | undefined; + const object: (value: unknown) => value is object; + const iterable: (value: unknown) => value is IterableIterator<unknown>; + const asyncIterable: (value: unknown) => value is AsyncIterableIterator<unknown>; + const generator: (value: unknown) => value is Generator; + const nativePromise: (value: unknown) => value is Promise<unknown>; + const promise: (value: unknown) => value is Promise<unknown>; + const generatorFunction: (value: unknown) => value is GeneratorFunction; + const asyncFunction: (value: unknown) => value is Function; + const boundFunction: (value: unknown) => value is Function; + const regExp: (value: unknown) => value is RegExp; + const date: (value: unknown) => value is Date; + const error: (value: unknown) => value is Error; + const map: (value: unknown) => value is Map<unknown, unknown>; + const set: (value: unknown) => value is Set<unknown>; + const weakMap: (value: unknown) => value is WeakMap<object, unknown>; + const weakSet: (value: unknown) => value is WeakSet<object>; + const int8Array: (value: unknown) => value is Int8Array; + const uint8Array: (value: unknown) => value is Uint8Array; + const uint8ClampedArray: (value: unknown) => value is Uint8ClampedArray; + const int16Array: (value: unknown) => value is Int16Array; + const uint16Array: (value: unknown) => value is Uint16Array; + const int32Array: (value: unknown) => value is Int32Array; + const uint32Array: (value: unknown) => value is Uint32Array; + const float32Array: (value: unknown) => value is Float32Array; + const float64Array: (value: unknown) => value is Float64Array; + const arrayBuffer: (value: unknown) => value is ArrayBuffer; + const sharedArrayBuffer: (value: unknown) => value is SharedArrayBuffer; + const dataView: (value: unknown) => value is DataView; + const directInstanceOf: <T>(instance: unknown, klass: Class<T>) => instance is T; + const urlInstance: (value: unknown) => value is URL; + const urlString: (value: unknown) => boolean; + const truthy: (value: unknown) => boolean; + const falsy: (value: unknown) => boolean; + const nan: (value: unknown) => boolean; + const primitive: (value: unknown) => value is Primitive; + const integer: (value: unknown) => value is number; + const safeInteger: (value: unknown) => value is number; + const plainObject: (value: unknown) => boolean; + const typedArray: (value: unknown) => value is TypedArray; + const arrayLike: (value: unknown) => value is ArrayLike; + const inRange: (value: number, range: number | number[]) => boolean; + const domElement: (value: unknown) => value is DomElement; + const observable: (value: unknown) => boolean; + const nodeStream: (value: unknown) => value is NodeStream; + const infinite: (value: unknown) => boolean; + const even: (value: number) => boolean; + const odd: (value: number) => boolean; + const emptyArray: (value: unknown) => boolean; + const nonEmptyArray: (value: unknown) => boolean; + const emptyString: (value: unknown) => boolean; + const nonEmptyString: (value: unknown) => boolean; + const emptyStringOrWhitespace: (value: unknown) => boolean; + const emptyObject: (value: unknown) => boolean; + const nonEmptyObject: (value: unknown) => boolean; + const emptySet: (value: unknown) => boolean; + const nonEmptySet: (value: unknown) => boolean; + const emptyMap: (value: unknown) => boolean; + const nonEmptyMap: (value: unknown) => boolean; + const any: (predicate: unknown, ...values: unknown[]) => boolean; + const all: (predicate: unknown, ...values: unknown[]) => boolean; +} +export default is; diff --git a/node_modules/@sindresorhus/is/dist/index.js b/node_modules/@sindresorhus/is/dist/index.js new file mode 100644 index 0000000..3cbafae --- /dev/null +++ b/node_modules/@sindresorhus/is/dist/index.js @@ -0,0 +1,245 @@ +"use strict"; +/// <reference lib="es2016"/> +/// <reference lib="es2017.sharedmemory"/> +/// <reference lib="esnext.asynciterable"/> +/// <reference lib="dom"/> +Object.defineProperty(exports, "__esModule", { value: true }); +// TODO: Use the `URL` global when targeting Node.js 10 +// tslint:disable-next-line +const URLGlobal = typeof URL === 'undefined' ? require('url').URL : URL; +const toString = Object.prototype.toString; +const isOfType = (type) => (value) => typeof value === type; +const isBuffer = (input) => !is.nullOrUndefined(input) && !is.nullOrUndefined(input.constructor) && is.function_(input.constructor.isBuffer) && input.constructor.isBuffer(input); +const getObjectType = (value) => { + const objectName = toString.call(value).slice(8, -1); + if (objectName) { + return objectName; + } + return null; +}; +const isObjectOfType = (type) => (value) => getObjectType(value) === type; +function is(value) { + switch (value) { + case null: + return "null" /* null */; + case true: + case false: + return "boolean" /* boolean */; + default: + } + switch (typeof value) { + case 'undefined': + return "undefined" /* undefined */; + case 'string': + return "string" /* string */; + case 'number': + return "number" /* number */; + case 'symbol': + return "symbol" /* symbol */; + default: + } + if (is.function_(value)) { + return "Function" /* Function */; + } + if (is.observable(value)) { + return "Observable" /* Observable */; + } + if (Array.isArray(value)) { + return "Array" /* Array */; + } + if (isBuffer(value)) { + return "Buffer" /* Buffer */; + } + const tagType = getObjectType(value); + if (tagType) { + return tagType; + } + if (value instanceof String || value instanceof Boolean || value instanceof Number) { + throw new TypeError('Please don\'t use object wrappers for primitive types'); + } + return "Object" /* Object */; +} +(function (is) { + // tslint:disable-next-line:strict-type-predicates + const isObject = (value) => typeof value === 'object'; + // tslint:disable:variable-name + is.undefined = isOfType('undefined'); + is.string = isOfType('string'); + is.number = isOfType('number'); + is.function_ = isOfType('function'); + // tslint:disable-next-line:strict-type-predicates + is.null_ = (value) => value === null; + is.class_ = (value) => is.function_(value) && value.toString().startsWith('class '); + is.boolean = (value) => value === true || value === false; + is.symbol = isOfType('symbol'); + // tslint:enable:variable-name + is.numericString = (value) => is.string(value) && value.length > 0 && !Number.isNaN(Number(value)); + is.array = Array.isArray; + is.buffer = isBuffer; + is.nullOrUndefined = (value) => is.null_(value) || is.undefined(value); + is.object = (value) => !is.nullOrUndefined(value) && (is.function_(value) || isObject(value)); + is.iterable = (value) => !is.nullOrUndefined(value) && is.function_(value[Symbol.iterator]); + is.asyncIterable = (value) => !is.nullOrUndefined(value) && is.function_(value[Symbol.asyncIterator]); + is.generator = (value) => is.iterable(value) && is.function_(value.next) && is.function_(value.throw); + is.nativePromise = (value) => isObjectOfType("Promise" /* Promise */)(value); + const hasPromiseAPI = (value) => !is.null_(value) && + isObject(value) && + is.function_(value.then) && + is.function_(value.catch); + is.promise = (value) => is.nativePromise(value) || hasPromiseAPI(value); + is.generatorFunction = isObjectOfType("GeneratorFunction" /* GeneratorFunction */); + is.asyncFunction = isObjectOfType("AsyncFunction" /* AsyncFunction */); + is.boundFunction = (value) => is.function_(value) && !value.hasOwnProperty('prototype'); + is.regExp = isObjectOfType("RegExp" /* RegExp */); + is.date = isObjectOfType("Date" /* Date */); + is.error = isObjectOfType("Error" /* Error */); + is.map = (value) => isObjectOfType("Map" /* Map */)(value); + is.set = (value) => isObjectOfType("Set" /* Set */)(value); + is.weakMap = (value) => isObjectOfType("WeakMap" /* WeakMap */)(value); + is.weakSet = (value) => isObjectOfType("WeakSet" /* WeakSet */)(value); + is.int8Array = isObjectOfType("Int8Array" /* Int8Array */); + is.uint8Array = isObjectOfType("Uint8Array" /* Uint8Array */); + is.uint8ClampedArray = isObjectOfType("Uint8ClampedArray" /* Uint8ClampedArray */); + is.int16Array = isObjectOfType("Int16Array" /* Int16Array */); + is.uint16Array = isObjectOfType("Uint16Array" /* Uint16Array */); + is.int32Array = isObjectOfType("Int32Array" /* Int32Array */); + is.uint32Array = isObjectOfType("Uint32Array" /* Uint32Array */); + is.float32Array = isObjectOfType("Float32Array" /* Float32Array */); + is.float64Array = isObjectOfType("Float64Array" /* Float64Array */); + is.arrayBuffer = isObjectOfType("ArrayBuffer" /* ArrayBuffer */); + is.sharedArrayBuffer = isObjectOfType("SharedArrayBuffer" /* SharedArrayBuffer */); + is.dataView = isObjectOfType("DataView" /* DataView */); + is.directInstanceOf = (instance, klass) => Object.getPrototypeOf(instance) === klass.prototype; + is.urlInstance = (value) => isObjectOfType("URL" /* URL */)(value); + is.urlString = (value) => { + if (!is.string(value)) { + return false; + } + try { + new URLGlobal(value); // tslint:disable-line no-unused-expression + return true; + } + catch (_a) { + return false; + } + }; + is.truthy = (value) => Boolean(value); + is.falsy = (value) => !value; + is.nan = (value) => Number.isNaN(value); + const primitiveTypes = new Set([ + 'undefined', + 'string', + 'number', + 'boolean', + 'symbol' + ]); + is.primitive = (value) => is.null_(value) || primitiveTypes.has(typeof value); + is.integer = (value) => Number.isInteger(value); + is.safeInteger = (value) => Number.isSafeInteger(value); + is.plainObject = (value) => { + // From: https://github.com/sindresorhus/is-plain-obj/blob/master/index.js + let prototype; + return getObjectType(value) === "Object" /* Object */ && + (prototype = Object.getPrototypeOf(value), prototype === null || // tslint:disable-line:ban-comma-operator + prototype === Object.getPrototypeOf({})); + }; + const typedArrayTypes = new Set([ + "Int8Array" /* Int8Array */, + "Uint8Array" /* Uint8Array */, + "Uint8ClampedArray" /* Uint8ClampedArray */, + "Int16Array" /* Int16Array */, + "Uint16Array" /* Uint16Array */, + "Int32Array" /* Int32Array */, + "Uint32Array" /* Uint32Array */, + "Float32Array" /* Float32Array */, + "Float64Array" /* Float64Array */ + ]); + is.typedArray = (value) => { + const objectType = getObjectType(value); + if (objectType === null) { + return false; + } + return typedArrayTypes.has(objectType); + }; + const isValidLength = (value) => is.safeInteger(value) && value > -1; + is.arrayLike = (value) => !is.nullOrUndefined(value) && !is.function_(value) && isValidLength(value.length); + is.inRange = (value, range) => { + if (is.number(range)) { + return value >= Math.min(0, range) && value <= Math.max(range, 0); + } + if (is.array(range) && range.length === 2) { + return value >= Math.min(...range) && value <= Math.max(...range); + } + throw new TypeError(`Invalid range: ${JSON.stringify(range)}`); + }; + const NODE_TYPE_ELEMENT = 1; + const DOM_PROPERTIES_TO_CHECK = [ + 'innerHTML', + 'ownerDocument', + 'style', + 'attributes', + 'nodeValue' + ]; + is.domElement = (value) => is.object(value) && value.nodeType === NODE_TYPE_ELEMENT && is.string(value.nodeName) && + !is.plainObject(value) && DOM_PROPERTIES_TO_CHECK.every(property => property in value); + is.observable = (value) => { + if (!value) { + return false; + } + if (value[Symbol.observable] && value === value[Symbol.observable]()) { + return true; + } + if (value['@@observable'] && value === value['@@observable']()) { + return true; + } + return false; + }; + is.nodeStream = (value) => !is.nullOrUndefined(value) && isObject(value) && is.function_(value.pipe) && !is.observable(value); + is.infinite = (value) => value === Infinity || value === -Infinity; + const isAbsoluteMod2 = (rem) => (value) => is.integer(value) && Math.abs(value % 2) === rem; + is.even = isAbsoluteMod2(0); + is.odd = isAbsoluteMod2(1); + const isWhiteSpaceString = (value) => is.string(value) && /\S/.test(value) === false; + is.emptyArray = (value) => is.array(value) && value.length === 0; + is.nonEmptyArray = (value) => is.array(value) && value.length > 0; + is.emptyString = (value) => is.string(value) && value.length === 0; + is.nonEmptyString = (value) => is.string(value) && value.length > 0; + is.emptyStringOrWhitespace = (value) => is.emptyString(value) || isWhiteSpaceString(value); + is.emptyObject = (value) => is.object(value) && !is.map(value) && !is.set(value) && Object.keys(value).length === 0; + is.nonEmptyObject = (value) => is.object(value) && !is.map(value) && !is.set(value) && Object.keys(value).length > 0; + is.emptySet = (value) => is.set(value) && value.size === 0; + is.nonEmptySet = (value) => is.set(value) && value.size > 0; + is.emptyMap = (value) => is.map(value) && value.size === 0; + is.nonEmptyMap = (value) => is.map(value) && value.size > 0; + const predicateOnArray = (method, predicate, values) => { + if (is.function_(predicate) === false) { + throw new TypeError(`Invalid predicate: ${JSON.stringify(predicate)}`); + } + if (values.length === 0) { + throw new TypeError('Invalid number of values'); + } + return method.call(values, predicate); + }; + // tslint:disable variable-name + is.any = (predicate, ...values) => predicateOnArray(Array.prototype.some, predicate, values); + is.all = (predicate, ...values) => predicateOnArray(Array.prototype.every, predicate, values); + // tslint:enable variable-name +})(is || (is = {})); +// Some few keywords are reserved, but we'll populate them for Node.js users +// See https://github.com/Microsoft/TypeScript/issues/2536 +Object.defineProperties(is, { + class: { + value: is.class_ + }, + function: { + value: is.function_ + }, + null: { + value: is.null_ + } +}); +exports.default = is; +// For CommonJS default export support +module.exports = is; +module.exports.default = is; +//# sourceMappingURL=index.js.map
\ No newline at end of file diff --git a/node_modules/@sindresorhus/is/dist/index.js.map b/node_modules/@sindresorhus/is/dist/index.js.map new file mode 100644 index 0000000..cd827fc --- /dev/null +++ b/node_modules/@sindresorhus/is/dist/index.js.map @@ -0,0 +1 @@ +{"version":3,"file":"index.js","sourceRoot":"","sources":["../source/index.ts"],"names":[],"mappings":";AAAA,6BAA6B;AAC7B,0CAA0C;AAC1C,2CAA2C;AAC3C,0BAA0B;;AAE1B,uDAAuD;AACvD,2BAA2B;AAC3B,MAAM,SAAS,GAAG,OAAO,GAAG,KAAK,WAAW,CAAC,CAAC,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC;AAqDxE,MAAM,QAAQ,GAAG,MAAM,CAAC,SAAS,CAAC,QAAQ,CAAC;AAC3C,MAAM,QAAQ,GAAG,CAAI,IAAY,EAAE,EAAE,CAAC,CAAC,KAAc,EAAc,EAAE,CAAC,OAAO,KAAK,KAAK,IAAI,CAAC;AAC5F,MAAM,QAAQ,GAAG,CAAC,KAAc,EAAmB,EAAE,CAAC,CAAC,EAAE,CAAC,eAAe,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,eAAe,CAAE,KAAgB,CAAC,WAAW,CAAC,IAAI,EAAE,CAAC,SAAS,CAAE,KAAgB,CAAC,WAAW,CAAC,QAAQ,CAAC,IAAK,KAAgB,CAAC,WAAW,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;AAEhP,MAAM,aAAa,GAAG,CAAC,KAAc,EAAmB,EAAE;IACzD,MAAM,UAAU,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;IAErD,IAAI,UAAU,EAAE;QACf,OAAO,UAAsB,CAAC;KAC9B;IAED,OAAO,IAAI,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,cAAc,GAAG,CAAI,IAAc,EAAE,EAAE,CAAC,CAAC,KAAc,EAAc,EAAE,CAAC,aAAa,CAAC,KAAK,CAAC,KAAK,IAAI,CAAC;AAE5G,SAAS,EAAE,CAAC,KAAc;IACzB,QAAQ,KAAK,EAAE;QACd,KAAK,IAAI;YACR,yBAAqB;QACtB,KAAK,IAAI,CAAC;QACV,KAAK,KAAK;YACT,+BAAwB;QACzB,QAAQ;KACR;IAED,QAAQ,OAAO,KAAK,EAAE;QACrB,KAAK,WAAW;YACf,mCAA0B;QAC3B,KAAK,QAAQ;YACZ,6BAAuB;QACxB,KAAK,QAAQ;YACZ,6BAAuB;QACxB,KAAK,QAAQ;YACZ,6BAAuB;QACxB,QAAQ;KACR;IAED,IAAI,EAAE,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE;QACxB,iCAAyB;KACzB;IAED,IAAI,EAAE,CAAC,UAAU,CAAC,KAAK,CAAC,EAAE;QACzB,qCAA2B;KAC3B;IAED,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE;QACzB,2BAAsB;KACtB;IAED,IAAI,QAAQ,CAAC,KAAK,CAAC,EAAE;QACpB,6BAAuB;KACvB;IAED,MAAM,OAAO,GAAG,aAAa,CAAC,KAAK,CAAC,CAAC;IACrC,IAAI,OAAO,EAAE;QACZ,OAAO,OAAO,CAAC;KACf;IAED,IAAI,KAAK,YAAY,MAAM,IAAI,KAAK,YAAY,OAAO,IAAI,KAAK,YAAY,MAAM,EAAE;QACnF,MAAM,IAAI,SAAS,CAAC,uDAAuD,CAAC,CAAC;KAC7E;IAED,6BAAuB;AACxB,CAAC;AAED,WAAU,EAAE;IACX,kDAAkD;IAClD,MAAM,QAAQ,GAAG,CAAC,KAAc,EAAmB,EAAE,CAAC,OAAO,KAAK,KAAK,QAAQ,CAAC;IAEhF,+BAA+B;IAClB,YAAS,GAAG,QAAQ,CAAY,WAAW,CAAC,CAAC;IAC7C,SAAM,GAAG,QAAQ,CAAS,QAAQ,CAAC,CAAC;IACpC,SAAM,GAAG,QAAQ,CAAS,QAAQ,CAAC,CAAC;IACpC,YAAS,GAAG,QAAQ,CAAW,UAAU,CAAC,CAAC;IACxD,kDAAkD;IACrC,QAAK,GAAG,CAAC,KAAc,EAAiB,EAAE,CAAC,KAAK,KAAK,IAAI,CAAC;IAC1D,SAAM,GAAG,CAAC,KAAc,EAAkB,EAAE,CAAC,GAAA,SAAS,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC;IACvG,UAAO,GAAG,CAAC,KAAc,EAAoB,EAAE,CAAC,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,KAAK,CAAC;IAClF,SAAM,GAAG,QAAQ,CAAS,QAAQ,CAAC,CAAC;IACjD,8BAA8B;IAEjB,gBAAa,GAAG,CAAC,KAAc,EAAW,EAAE,CACxD,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAEtD,QAAK,GAAG,KAAK,CAAC,OAAO,CAAC;IACtB,SAAM,GAAG,QAAQ,CAAC;IAElB,kBAAe,GAAG,CAAC,KAAc,EAA6B,EAAE,CAAC,GAAA,KAAK,CAAC,KAAK,CAAC,IAAI,GAAA,SAAS,CAAC,KAAK,CAAC,CAAC;IAClG,SAAM,GAAG,CAAC,KAAc,EAAmB,EAAE,CAAC,CAAC,GAAA,eAAe,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,SAAS,CAAC,KAAK,CAAC,IAAI,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;IAC/G,WAAQ,GAAG,CAAC,KAAc,EAAsC,EAAE,CAAC,CAAC,GAAA,eAAe,CAAC,KAAK,CAAC,IAAI,GAAA,SAAS,CAAE,KAAmC,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC;IAC/J,gBAAa,GAAG,CAAC,KAAc,EAA2C,EAAE,CAAC,CAAC,GAAA,eAAe,CAAC,KAAK,CAAC,IAAI,GAAA,SAAS,CAAE,KAAwC,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,CAAC;IACnL,YAAS,GAAG,CAAC,KAAc,EAAsB,EAAE,CAAC,GAAA,QAAQ,CAAC,KAAK,CAAC,IAAI,GAAA,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,GAAA,SAAS,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAEvH,gBAAa,GAAG,CAAC,KAAc,EAA6B,EAAE,CAC1E,cAAc,yBAAoC,CAAC,KAAK,CAAC,CAAC;IAE3D,MAAM,aAAa,GAAG,CAAC,KAAc,EAA6B,EAAE,CACnE,CAAC,GAAA,KAAK,CAAC,KAAK,CAAC;QACb,QAAQ,CAAC,KAAK,CAAY;QAC1B,GAAA,SAAS,CAAE,KAA0B,CAAC,IAAI,CAAC;QAC3C,GAAA,SAAS,CAAE,KAA0B,CAAC,KAAK,CAAC,CAAC;IAEjC,UAAO,GAAG,CAAC,KAAc,EAA6B,EAAE,CAAC,GAAA,aAAa,CAAC,KAAK,CAAC,IAAI,aAAa,CAAC,KAAK,CAAC,CAAC;IAEtG,oBAAiB,GAAG,cAAc,6CAA+C,CAAC;IAClF,gBAAa,GAAG,cAAc,qCAAkC,CAAC;IACjE,gBAAa,GAAG,CAAC,KAAc,EAAqB,EAAE,CAAC,GAAA,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,WAAW,CAAC,CAAC;IAE9G,SAAM,GAAG,cAAc,uBAAyB,CAAC;IACjD,OAAI,GAAG,cAAc,mBAAqB,CAAC;IAC3C,QAAK,GAAG,cAAc,qBAAuB,CAAC;IAC9C,MAAG,GAAG,CAAC,KAAc,EAAkC,EAAE,CAAC,cAAc,iBAAqC,CAAC,KAAK,CAAC,CAAC;IACrH,MAAG,GAAG,CAAC,KAAc,EAAyB,EAAE,CAAC,cAAc,iBAA4B,CAAC,KAAK,CAAC,CAAC;IACnG,UAAO,GAAG,CAAC,KAAc,EAAqC,EAAE,CAAC,cAAc,yBAA4C,CAAC,KAAK,CAAC,CAAC;IACnI,UAAO,GAAG,CAAC,KAAc,EAA4B,EAAE,CAAC,cAAc,yBAAmC,CAAC,KAAK,CAAC,CAAC;IAEjH,YAAS,GAAG,cAAc,6BAA+B,CAAC;IAC1D,aAAU,GAAG,cAAc,+BAAiC,CAAC;IAC7D,oBAAiB,GAAG,cAAc,6CAA+C,CAAC;IAClF,aAAU,GAAG,cAAc,+BAAiC,CAAC;IAC7D,cAAW,GAAG,cAAc,iCAAmC,CAAC;IAChE,aAAU,GAAG,cAAc,+BAAiC,CAAC;IAC7D,cAAW,GAAG,cAAc,iCAAmC,CAAC;IAChE,eAAY,GAAG,cAAc,mCAAqC,CAAC;IACnE,eAAY,GAAG,cAAc,mCAAqC,CAAC;IAEnE,cAAW,GAAG,cAAc,iCAAmC,CAAC;IAChE,oBAAiB,GAAG,cAAc,6CAA+C,CAAC;IAClF,WAAQ,GAAG,cAAc,2BAA6B,CAAC;IAEvD,mBAAgB,GAAG,CAAI,QAAiB,EAAE,KAAe,EAAiB,EAAE,CAAC,MAAM,CAAC,cAAc,CAAC,QAAQ,CAAC,KAAK,KAAK,CAAC,SAAS,CAAC;IACjI,cAAW,GAAG,CAAC,KAAc,EAAgB,EAAE,CAAC,cAAc,iBAAmB,CAAC,KAAK,CAAC,CAAC;IAEzF,YAAS,GAAG,CAAC,KAAc,EAAE,EAAE;QAC3C,IAAI,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,EAAE;YACnB,OAAO,KAAK,CAAC;SACb;QAED,IAAI;YACH,IAAI,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,2CAA2C;YACjE,OAAO,IAAI,CAAC;SACZ;QAAC,WAAM;YACP,OAAO,KAAK,CAAC;SACb;IACF,CAAC,CAAC;IAEW,SAAM,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;IAC5C,QAAK,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,CAAC,KAAK,CAAC;IAEnC,MAAG,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,KAAe,CAAC,CAAC;IAErE,MAAM,cAAc,GAAG,IAAI,GAAG,CAAC;QAC9B,WAAW;QACX,QAAQ;QACR,QAAQ;QACR,SAAS;QACT,QAAQ;KACR,CAAC,CAAC;IAEU,YAAS,GAAG,CAAC,KAAc,EAAsB,EAAE,CAAC,GAAA,KAAK,CAAC,KAAK,CAAC,IAAI,cAAc,CAAC,GAAG,CAAC,OAAO,KAAK,CAAC,CAAC;IAErG,UAAO,GAAG,CAAC,KAAc,EAAmB,EAAE,CAAC,MAAM,CAAC,SAAS,CAAC,KAAe,CAAC,CAAC;IACjF,cAAW,GAAG,CAAC,KAAc,EAAmB,EAAE,CAAC,MAAM,CAAC,aAAa,CAAC,KAAe,CAAC,CAAC;IAEzF,cAAW,GAAG,CAAC,KAAc,EAAE,EAAE;QAC7C,0EAA0E;QAC1E,IAAI,SAAS,CAAC;QAEd,OAAO,aAAa,CAAC,KAAK,CAAC,0BAAoB;YAC9C,CAAC,SAAS,GAAG,MAAM,CAAC,cAAc,CAAC,KAAK,CAAC,EAAE,SAAS,KAAK,IAAI,IAAI,yCAAyC;gBACzG,SAAS,KAAK,MAAM,CAAC,cAAc,CAAC,EAAE,CAAC,CAAC,CAAC;IAC5C,CAAC,CAAC;IAEF,MAAM,eAAe,GAAG,IAAI,GAAG,CAAC;;;;;;;;;;KAU/B,CAAC,CAAC;IACU,aAAU,GAAG,CAAC,KAAc,EAAuB,EAAE;QACjE,MAAM,UAAU,GAAG,aAAa,CAAC,KAAK,CAAC,CAAC;QAExC,IAAI,UAAU,KAAK,IAAI,EAAE;YACxB,OAAO,KAAK,CAAC;SACb;QAED,OAAO,eAAe,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;IACxC,CAAC,CAAC;IAEF,MAAM,aAAa,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,WAAW,CAAC,KAAK,CAAC,IAAI,KAAK,GAAG,CAAC,CAAC,CAAC;IAC9D,YAAS,GAAG,CAAC,KAAc,EAAsB,EAAE,CAAC,CAAC,GAAA,eAAe,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,SAAS,CAAC,KAAK,CAAC,IAAI,aAAa,CAAE,KAAmB,CAAC,MAAM,CAAC,CAAC;IAE/I,UAAO,GAAG,CAAC,KAAa,EAAE,KAAwB,EAAE,EAAE;QAClE,IAAI,GAAA,MAAM,CAAC,KAAK,CAAC,EAAE;YAClB,OAAO,KAAK,IAAI,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,CAAC,IAAI,KAAK,IAAI,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC;SAClE;QAED,IAAI,GAAA,KAAK,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE;YACvC,OAAO,KAAK,IAAI,IAAI,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC,IAAI,KAAK,IAAI,IAAI,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC;SAClE;QAED,MAAM,IAAI,SAAS,CAAC,kBAAkB,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;IAChE,CAAC,CAAC;IAEF,MAAM,iBAAiB,GAAG,CAAC,CAAC;IAC5B,MAAM,uBAAuB,GAAG;QAC/B,WAAW;QACX,eAAe;QACf,OAAO;QACP,YAAY;QACZ,WAAW;KACX,CAAC;IAEW,aAAU,GAAG,CAAC,KAAc,EAAuB,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAK,KAAoB,CAAC,QAAQ,KAAK,iBAAiB,IAAI,GAAA,MAAM,CAAE,KAAoB,CAAC,QAAQ,CAAC;QACjL,CAAC,GAAA,WAAW,CAAC,KAAK,CAAC,IAAI,uBAAuB,CAAC,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC,QAAQ,IAAK,KAAoB,CAAC,CAAC;IAExF,aAAU,GAAG,CAAC,KAAc,EAAE,EAAE;QAC5C,IAAI,CAAC,KAAK,EAAE;YACX,OAAO,KAAK,CAAC;SACb;QAED,IAAK,KAAa,CAAC,MAAM,CAAC,UAAU,CAAC,IAAI,KAAK,KAAM,KAAa,CAAC,MAAM,CAAC,UAAU,CAAC,EAAE,EAAE;YACvF,OAAO,IAAI,CAAC;SACZ;QAED,IAAK,KAAa,CAAC,cAAc,CAAC,IAAI,KAAK,KAAM,KAAa,CAAC,cAAc,CAAC,EAAE,EAAE;YACjF,OAAO,IAAI,CAAC;SACZ;QAED,OAAO,KAAK,CAAC;IACd,CAAC,CAAC;IAEW,aAAU,GAAG,CAAC,KAAc,EAAuB,EAAE,CAAC,CAAC,GAAA,eAAe,CAAC,KAAK,CAAC,IAAI,QAAQ,CAAC,KAAK,CAAY,IAAI,GAAA,SAAS,CAAE,KAAoB,CAAC,IAAI,CAAC,IAAI,CAAC,GAAA,UAAU,CAAC,KAAK,CAAC,CAAC;IAE3K,WAAQ,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,CAAC,QAAQ,CAAC;IAEtF,MAAM,cAAc,GAAG,CAAC,GAAW,EAAE,EAAE,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,GAAA,OAAO,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,GAAG,CAAC,KAAK,GAAG,CAAC,CAAC,KAAK,GAAG,CAAC;IAC5F,OAAI,GAAG,cAAc,CAAC,CAAC,CAAC,CAAC;IACzB,MAAG,GAAG,cAAc,CAAC,CAAC,CAAC,CAAC;IAErC,MAAM,kBAAkB,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,KAAK,CAAC;IAE9E,aAAU,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,KAAK,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,CAAC;IACpE,gBAAa,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,KAAK,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;IAErE,cAAW,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,CAAC;IACtE,iBAAc,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;IACvE,0BAAuB,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,WAAW,CAAC,KAAK,CAAC,IAAI,kBAAkB,CAAC,KAAK,CAAC,CAAC;IAE9F,cAAW,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,CAAC;IACjH,iBAAc,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,GAAG,CAAC,CAAC;IAElH,WAAQ,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,KAAK,CAAC,CAAC;IAC9D,cAAW,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,GAAG,CAAC,CAAC;IAE/D,WAAQ,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,KAAK,CAAC,CAAC;IAC9D,cAAW,GAAG,CAAC,KAAc,EAAE,EAAE,CAAC,GAAA,GAAG,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,GAAG,CAAC,CAAC;IAG5E,MAAM,gBAAgB,GAAG,CAAC,MAAmB,EAAE,SAAkB,EAAE,MAAiB,EAAE,EAAE;QACvF,IAAI,GAAA,SAAS,CAAC,SAAS,CAAC,KAAK,KAAK,EAAE;YACnC,MAAM,IAAI,SAAS,CAAC,sBAAsB,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,EAAE,CAAC,CAAC;SACvE;QAED,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE;YACxB,MAAM,IAAI,SAAS,CAAC,0BAA0B,CAAC,CAAC;SAChD;QAED,OAAO,MAAM,CAAC,IAAI,CAAC,MAAM,EAAE,SAAgB,CAAC,CAAC;IAC9C,CAAC,CAAC;IAEF,+BAA+B;IAClB,MAAG,GAAG,CAAC,SAAkB,EAAE,GAAG,MAAiB,EAAE,EAAE,CAAC,gBAAgB,CAAC,KAAK,CAAC,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,MAAM,CAAC,CAAC;IAC9G,MAAG,GAAG,CAAC,SAAkB,EAAE,GAAG,MAAiB,EAAE,EAAE,CAAC,gBAAgB,CAAC,KAAK,CAAC,SAAS,CAAC,KAAK,EAAE,SAAS,EAAE,MAAM,CAAC,CAAC;IAC5H,8BAA8B;AAC/B,CAAC,EAvNS,EAAE,KAAF,EAAE,QAuNX;AAED,4EAA4E;AAC5E,0DAA0D;AAC1D,MAAM,CAAC,gBAAgB,CAAC,EAAE,EAAE;IAC3B,KAAK,EAAE;QACN,KAAK,EAAE,EAAE,CAAC,MAAM;KAChB;IACD,QAAQ,EAAE;QACT,KAAK,EAAE,EAAE,CAAC,SAAS;KACnB;IACD,IAAI,EAAE;QACL,KAAK,EAAE,EAAE,CAAC,KAAK;KACf;CACD,CAAC,CAAC;AAEH,kBAAe,EAAE,CAAC;AAElB,sCAAsC;AACtC,MAAM,CAAC,OAAO,GAAG,EAAE,CAAC;AACpB,MAAM,CAAC,OAAO,CAAC,OAAO,GAAG,EAAE,CAAC"}
\ No newline at end of file diff --git a/node_modules/@sindresorhus/is/license b/node_modules/@sindresorhus/is/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/@sindresorhus/is/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/@sindresorhus/is/package.json b/node_modules/@sindresorhus/is/package.json new file mode 100644 index 0000000..bf0d9fe --- /dev/null +++ b/node_modules/@sindresorhus/is/package.json @@ -0,0 +1,63 @@ +{ + "name": "@sindresorhus/is", + "version": "0.14.0", + "description": "Type check values: `is.string('🦄') //=> true`", + "license": "MIT", + "repository": "sindresorhus/is", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "main": "dist/index.js", + "engines": { + "node": ">=6" + }, + "scripts": { + "lint": "tslint --format stylish --project .", + "build": "del dist && tsc", + "test": "npm run lint && npm run build && ava dist/tests", + "prepublish": "npm run build && del dist/tests" + }, + "files": [ + "dist" + ], + "keywords": [ + "type", + "types", + "is", + "check", + "checking", + "validate", + "validation", + "utility", + "util", + "typeof", + "instanceof", + "object", + "assert", + "assertion", + "test", + "kind", + "primitive", + "verify", + "compare" + ], + "devDependencies": { + "@sindresorhus/tsconfig": "^0.1.0", + "@types/jsdom": "^11.12.0", + "@types/node": "^10.12.10", + "@types/tempy": "^0.2.0", + "@types/zen-observable": "^0.8.0", + "ava": "^0.25.0", + "del-cli": "^1.1.0", + "jsdom": "^11.6.2", + "rxjs": "^6.3.3", + "tempy": "^0.2.1", + "tslint": "^5.9.1", + "tslint-xo": "^0.10.0", + "typescript": "^3.2.1", + "zen-observable": "^0.8.8" + }, + "types": "dist/index.d.ts" +} diff --git a/node_modules/@sindresorhus/is/readme.md b/node_modules/@sindresorhus/is/readme.md new file mode 100644 index 0000000..97c023b --- /dev/null +++ b/node_modules/@sindresorhus/is/readme.md @@ -0,0 +1,451 @@ +# is [![Build Status](https://travis-ci.org/sindresorhus/is.svg?branch=master)](https://travis-ci.org/sindresorhus/is) + +> Type check values: `is.string('🦄') //=> true` + +<img src="header.gif" width="182" align="right"> + + +## Install + +``` +$ npm install @sindresorhus/is +``` + + +## Usage + +```js +const is = require('@sindresorhus/is'); + +is('🦄'); +//=> 'string' + +is(new Map()); +//=> 'Map' + +is.number(6); +//=> true +``` + +When using `is` together with TypeScript, [type guards](http://www.typescriptlang.org/docs/handbook/advanced-types.html#type-guards-and-differentiating-types) are being used to infer the correct type inside if-else statements. + +```ts +import is from '@sindresorhus/is'; + +const padLeft = (value: string, padding: string | number) => { + if (is.number(padding)) { + // `padding` is typed as `number` + return Array(padding + 1).join(' ') + value; + } + + if (is.string(padding)) { + // `padding` is typed as `string` + return padding + value; + } + + throw new TypeError(`Expected 'padding' to be of type 'string' or 'number', got '${is(padding)}'.`); +} + +padLeft('🦄', 3); +//=> ' 🦄' + +padLeft('🦄', '🌈'); +//=> '🌈🦄' +``` + + +## API + +### is(value) + +Returns the type of `value`. + +Primitives are lowercase and object types are camelcase. + +Example: + +- `'undefined'` +- `'null'` +- `'string'` +- `'symbol'` +- `'Array'` +- `'Function'` +- `'Object'` + +Note: It will throw an error if you try to feed it object-wrapped primitives, as that's a bad practice. For example `new String('foo')`. + +### is.{method} + +All the below methods accept a value and returns a boolean for whether the value is of the desired type. + +#### Primitives + +##### .undefined(value) +##### .null(value) +##### .string(value) +##### .number(value) +##### .boolean(value) +##### .symbol(value) + +#### Built-in types + +##### .array(value) +##### .function(value) +##### .buffer(value) +##### .object(value) + +Keep in mind that [functions are objects too](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions). + +##### .numericString(value) + +Returns `true` for a string that represents a number. For example, `'42'` and `'-8'`. + +Note: `'NaN'` returns `false`, but `'Infinity'` and `'-Infinity'` return `true`. + +##### .regExp(value) +##### .date(value) +##### .error(value) +##### .nativePromise(value) +##### .promise(value) + +Returns `true` for any object with a `.then()` and `.catch()` method. Prefer this one over `.nativePromise()` as you usually want to allow userland promise implementations too. + +##### .generator(value) + +Returns `true` for any object that implements its own `.next()` and `.throw()` methods and has a function definition for `Symbol.iterator`. + +##### .generatorFunction(value) + +##### .asyncFunction(value) + +Returns `true` for any `async` function that can be called with the `await` operator. + +```js +is.asyncFunction(async () => {}); +// => true + +is.asyncFunction(() => {}); +// => false +``` + +##### .boundFunction(value) + +Returns `true` for any `bound` function. + +```js +is.boundFunction(() => {}); +// => true + +is.boundFunction(function () {}.bind(null)); +// => true + +is.boundFunction(function () {}); +// => false +``` + +##### .map(value) +##### .set(value) +##### .weakMap(value) +##### .weakSet(value) + +#### Typed arrays + +##### .int8Array(value) +##### .uint8Array(value) +##### .uint8ClampedArray(value) +##### .int16Array(value) +##### .uint16Array(value) +##### .int32Array(value) +##### .uint32Array(value) +##### .float32Array(value) +##### .float64Array(value) + +#### Structured data + +##### .arrayBuffer(value) +##### .sharedArrayBuffer(value) +##### .dataView(value) + +#### Emptiness + +##### .emptyString(value) + +Returns `true` if the value is a `string` and the `.length` is 0. + +##### .nonEmptyString(value) + +Returns `true` if the value is a `string` and the `.length` is more than 0. + +##### .emptyStringOrWhitespace(value) + +Returns `true` if `is.emptyString(value)` or if it's a `string` that is all whitespace. + +##### .emptyArray(value) + +Returns `true` if the value is an `Array` and the `.length` is 0. + +##### .nonEmptyArray(value) + +Returns `true` if the value is an `Array` and the `.length` is more than 0. + +##### .emptyObject(value) + +Returns `true` if the value is an `Object` and `Object.keys(value).length` is 0. + +Please note that `Object.keys` returns only own enumerable properties. Hence something like this can happen: + +```js +const object1 = {}; + +Object.defineProperty(object1, 'property1', { + value: 42, + writable: true, + enumerable: false, + configurable: true +}); + +is.emptyObject(object1); +// => true +``` + +##### .nonEmptyObject(value) + +Returns `true` if the value is an `Object` and `Object.keys(value).length` is more than 0. + +##### .emptySet(value) + +Returns `true` if the value is a `Set` and the `.size` is 0. + +##### .nonEmptySet(Value) + +Returns `true` if the value is a `Set` and the `.size` is more than 0. + +##### .emptyMap(value) + +Returns `true` if the value is a `Map` and the `.size` is 0. + +##### .nonEmptyMap(value) + +Returns `true` if the value is a `Map` and the `.size` is more than 0. + +#### Miscellaneous + +##### .directInstanceOf(value, class) + +Returns `true` if `value` is a direct instance of `class`. + +```js +is.directInstanceOf(new Error(), Error); +//=> true + +class UnicornError extends Error {} + +is.directInstanceOf(new UnicornError(), Error); +//=> false +``` + +##### .urlInstance(value) + +Returns `true` if `value` is an instance of the [`URL` class](https://developer.mozilla.org/en-US/docs/Web/API/URL). + +```js +const url = new URL('https://example.com'); + +is.urlInstance(url); +//=> true +``` + +### .url(value) + +Returns `true` if `value` is a URL string. + +Note: this only does basic checking using the [`URL` class](https://developer.mozilla.org/en-US/docs/Web/API/URL) constructor. + +```js +const url = 'https://example.com'; + +is.url(url); +//=> true + +is.url(new URL(url)); +//=> false +``` + +##### .truthy(value) + +Returns `true` for all values that evaluate to true in a boolean context: + +```js +is.truthy('🦄'); +//=> true + +is.truthy(undefined); +//=> false +``` + +##### .falsy(value) + +Returns `true` if `value` is one of: `false`, `0`, `''`, `null`, `undefined`, `NaN`. + +##### .nan(value) +##### .nullOrUndefined(value) +##### .primitive(value) + +JavaScript primitives are as follows: `null`, `undefined`, `string`, `number`, `boolean`, `symbol`. + +##### .integer(value) + +##### .safeInteger(value) + +Returns `true` if `value` is a [safe integer](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/isSafeInteger). + +##### .plainObject(value) + +An object is plain if it's created by either `{}`, `new Object()`, or `Object.create(null)`. + +##### .iterable(value) +##### .asyncIterable(value) +##### .class(value) + +Returns `true` for instances created by a class. + +##### .typedArray(value) + +##### .arrayLike(value) + +A `value` is array-like if it is not a function and has a `value.length` that is a safe integer greater than or equal to 0. + +```js +is.arrayLike(document.forms); +//=> true + +function foo() { + is.arrayLike(arguments); + //=> true +} +foo(); +``` + +##### .inRange(value, range) + +Check if `value` (number) is in the given `range`. The range is an array of two values, lower bound and upper bound, in no specific order. + +```js +is.inRange(3, [0, 5]); +is.inRange(3, [5, 0]); +is.inRange(0, [-2, 2]); +``` + +##### .inRange(value, upperBound) + +Check if `value` (number) is in the range of `0` to `upperBound`. + +```js +is.inRange(3, 10); +``` + +##### .domElement(value) + +Returns `true` if `value` is a DOM Element. + +##### .nodeStream(value) + +Returns `true` if `value` is a Node.js [stream](https://nodejs.org/api/stream.html). + +```js +const fs = require('fs'); + +is.nodeStream(fs.createReadStream('unicorn.png')); +//=> true +``` + +##### .observable(value) + +Returns `true` if `value` is an `Observable`. + +```js +const {Observable} = require('rxjs'); + +is.observable(new Observable()); +//=> true +``` + +##### .infinite(value) + +Check if `value` is `Infinity` or `-Infinity`. + +##### .even(value) + +Returns `true` if `value` is an even integer. + +##### .odd(value) + +Returns `true` if `value` is an odd integer. + +##### .any(predicate, ...values) + +Returns `true` if **any** of the input `values` returns true in the `predicate`: + +```js +is.any(is.string, {}, true, '🦄'); +//=> true + +is.any(is.boolean, 'unicorns', [], new Map()); +//=> false +``` + +##### .all(predicate, ...values) + +Returns `true` if **all** of the input `values` returns true in the `predicate`: + +```js +is.all(is.object, {}, new Map(), new Set()); +//=> true + +is.all(is.string, '🦄', [], 'unicorns'); +//=> false +``` + + +## FAQ + +### Why yet another type checking module? + +There are hundreds of type checking modules on npm, unfortunately, I couldn't find any that fit my needs: + +- Includes both type methods and ability to get the type +- Types of primitives returned as lowercase and object types as camelcase +- Covers all built-ins +- Unsurprising behavior +- Well-maintained +- Comprehensive test suite + +For the ones I found, pick 3 of these. + +The most common mistakes I noticed in these modules was using `instanceof` for type checking, forgetting that functions are objects, and omitting `symbol` as a primitive. + + +## Related + +- [ow](https://github.com/sindresorhus/ow) - Function argument validation for humans +- [is-stream](https://github.com/sindresorhus/is-stream) - Check if something is a Node.js stream +- [is-observable](https://github.com/sindresorhus/is-observable) - Check if a value is an Observable +- [file-type](https://github.com/sindresorhus/file-type) - Detect the file type of a Buffer/Uint8Array +- [is-ip](https://github.com/sindresorhus/is-ip) - Check if a string is an IP address +- [is-array-sorted](https://github.com/sindresorhus/is-array-sorted) - Check if an Array is sorted +- [is-error-constructor](https://github.com/sindresorhus/is-error-constructor) - Check if a value is an error constructor +- [is-empty-iterable](https://github.com/sindresorhus/is-empty-iterable) - Check if an Iterable is empty +- [is-blob](https://github.com/sindresorhus/is-blob) - Check if a value is a Blob - File-like object of immutable, raw data +- [has-emoji](https://github.com/sindresorhus/has-emoji) - Check whether a string has any emoji + + +## Created by + +- [Sindre Sorhus](https://github.com/sindresorhus) +- [Giora Guttsait](https://github.com/gioragutt) +- [Brandon Smith](https://github.com/brandon93s) + + +## License + +MIT diff --git a/node_modules/@szmarczak/http-timer/LICENSE b/node_modules/@szmarczak/http-timer/LICENSE new file mode 100755 index 0000000..15ad2e8 --- /dev/null +++ b/node_modules/@szmarczak/http-timer/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2018 Szymon Marczak + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/node_modules/@szmarczak/http-timer/README.md b/node_modules/@szmarczak/http-timer/README.md new file mode 100755 index 0000000..13279ed --- /dev/null +++ b/node_modules/@szmarczak/http-timer/README.md @@ -0,0 +1,70 @@ +# http-timer +> Timings for HTTP requests + +[![Build Status](https://travis-ci.org/szmarczak/http-timer.svg?branch=master)](https://travis-ci.org/szmarczak/http-timer) +[![Coverage Status](https://coveralls.io/repos/github/szmarczak/http-timer/badge.svg?branch=master)](https://coveralls.io/github/szmarczak/http-timer?branch=master) +[![install size](https://packagephobia.now.sh/badge?p=@szmarczak/http-timer)](https://packagephobia.now.sh/result?p=@szmarczak/http-timer) + +Inspired by the [`request` package](https://github.com/request/request). + +## Usage +```js +'use strict'; +const https = require('https'); +const timer = require('@szmarczak/http-timer'); + +const request = https.get('https://httpbin.org/anything'); +const timings = timer(request); + +request.on('response', response => { + response.on('data', () => {}); // Consume the data somehow + response.on('end', () => { + console.log(timings); + }); +}); + +// { start: 1535708511443, +// socket: 1535708511444, +// lookup: 1535708511444, +// connect: 1535708511582, +// upload: 1535708511887, +// response: 1535708512037, +// end: 1535708512040, +// phases: +// { wait: 1, +// dns: 0, +// tcp: 138, +// request: 305, +// firstByte: 150, +// download: 3, +// total: 597 } } +``` + +## API + +### timer(request) + +Returns: `Object` + +- `start` - Time when the request started. +- `socket` - Time when a socket was assigned to the request. +- `lookup` - Time when the DNS lookup finished. +- `connect` - Time when the socket successfully connected. +- `upload` - Time when the request finished uploading. +- `response` - Time when the request fired the `response` event. +- `end` - Time when the response fired the `end` event. +- `error` - Time when the request fired the `error` event. +- `phases` + - `wait` - `timings.socket - timings.start` + - `dns` - `timings.lookup - timings.socket` + - `tcp` - `timings.connect - timings.lookup` + - `request` - `timings.upload - timings.connect` + - `firstByte` - `timings.response - timings.upload` + - `download` - `timings.end - timings.response` + - `total` - `timings.end - timings.start` or `timings.error - timings.start` + +**Note**: The time is a `number` representing the milliseconds elapsed since the UNIX epoch. + +## License + +MIT diff --git a/node_modules/@szmarczak/http-timer/package.json b/node_modules/@szmarczak/http-timer/package.json new file mode 100755 index 0000000..9346648 --- /dev/null +++ b/node_modules/@szmarczak/http-timer/package.json @@ -0,0 +1,47 @@ +{ + "name": "@szmarczak/http-timer", + "version": "1.1.2", + "description": "Timings for HTTP requests", + "main": "source", + "engines": { + "node": ">=6" + }, + "scripts": { + "test": "xo && nyc ava", + "coveralls": "nyc report --reporter=text-lcov | coveralls" + }, + "files": [ + "source" + ], + "keywords": [ + "http", + "https", + "timer", + "timings" + ], + "repository": { + "type": "git", + "url": "git+https://github.com/szmarczak/http-timer.git" + }, + "author": "Szymon Marczak", + "license": "MIT", + "bugs": { + "url": "https://github.com/szmarczak/http-timer/issues" + }, + "homepage": "https://github.com/szmarczak/http-timer#readme", + "xo": { + "rules": { + "unicorn/filename-case": "camelCase" + } + }, + "devDependencies": { + "ava": "^0.25.0", + "coveralls": "^3.0.2", + "p-event": "^2.1.0", + "nyc": "^12.0.2", + "xo": "^0.22.0" + }, + "dependencies": { + "defer-to-connect": "^1.0.1" + } +} diff --git a/node_modules/@szmarczak/http-timer/source/index.js b/node_modules/@szmarczak/http-timer/source/index.js new file mode 100755 index 0000000..e294580 --- /dev/null +++ b/node_modules/@szmarczak/http-timer/source/index.js @@ -0,0 +1,99 @@ +'use strict'; +const deferToConnect = require('defer-to-connect'); + +module.exports = request => { + const timings = { + start: Date.now(), + socket: null, + lookup: null, + connect: null, + upload: null, + response: null, + end: null, + error: null, + phases: { + wait: null, + dns: null, + tcp: null, + request: null, + firstByte: null, + download: null, + total: null + } + }; + + const handleError = origin => { + const emit = origin.emit.bind(origin); + origin.emit = (event, ...args) => { + // Catches the `error` event + if (event === 'error') { + timings.error = Date.now(); + timings.phases.total = timings.error - timings.start; + + origin.emit = emit; + } + + // Saves the original behavior + return emit(event, ...args); + }; + }; + + let uploadFinished = false; + const onUpload = () => { + timings.upload = Date.now(); + timings.phases.request = timings.upload - timings.connect; + }; + + handleError(request); + + request.once('socket', socket => { + timings.socket = Date.now(); + timings.phases.wait = timings.socket - timings.start; + + const lookupListener = () => { + timings.lookup = Date.now(); + timings.phases.dns = timings.lookup - timings.socket; + }; + + socket.once('lookup', lookupListener); + + deferToConnect(socket, () => { + timings.connect = Date.now(); + + if (timings.lookup === null) { + socket.removeListener('lookup', lookupListener); + timings.lookup = timings.connect; + timings.phases.dns = timings.lookup - timings.socket; + } + + timings.phases.tcp = timings.connect - timings.lookup; + + if (uploadFinished && !timings.upload) { + onUpload(); + } + }); + }); + + request.once('finish', () => { + uploadFinished = true; + + if (timings.connect) { + onUpload(); + } + }); + + request.once('response', response => { + timings.response = Date.now(); + timings.phases.firstByte = timings.response - timings.upload; + + handleError(response); + + response.once('end', () => { + timings.end = Date.now(); + timings.phases.download = timings.end - timings.response; + timings.phases.total = timings.end - timings.start; + }); + }); + + return timings; +}; diff --git a/node_modules/axios/CHANGELOG.md b/node_modules/axios/CHANGELOG.md new file mode 100644 index 0000000..d1204ff --- /dev/null +++ b/node_modules/axios/CHANGELOG.md @@ -0,0 +1,906 @@ +# Changelog + +### 0.26.1 (March 9, 2022) + +Fixes and Functionality: +- Refactored project file structure to avoid circular imports ([##4220](https://github.com/axios/axios/pull/#4220)) + +### 0.26.0 (February 13, 2022) + +Fixes and Functionality: +- Fixed The timeoutErrorMessage property in config not work with Node.js ([#3581](https://github.com/axios/axios/pull/3581)) +- Added errors to be displayed when the query parsing process itself fails ([#3961](https://github.com/axios/axios/pull/3961)) +- Fix/remove url required ([#4426](https://github.com/axios/axios/pull/4426)) +- Update follow-redirects dependency due to Vurnerbility ([#4462](https://github.com/axios/axios/pull/4462)) +- Bump karma from 6.3.11 to 6.3.14 ([#4461](https://github.com/axios/axios/pull/4461)) +- Bump follow-redirects from 1.14.7 to 1.14.8 ([#4473](https://github.com/axios/axios/pull/4473)) + +### 0.25.0 (January 18, 2022) + +Breaking changes: +- Fixing maxBodyLength enforcement ([#3786](https://github.com/axios/axios/pull/3786)) +- Don't rely on strict mode behaviour for arguments ([#3470](https://github.com/axios/axios/pull/3470)) +- Adding error handling when missing url ([#3791](https://github.com/axios/axios/pull/3791)) +- Update isAbsoluteURL.js removing escaping of non-special characters ([#3809](https://github.com/axios/axios/pull/3809)) +- Use native Array.isArray() in utils.js ([#3836](https://github.com/axios/axios/pull/3836)) +- Adding error handling inside stream end callback ([#3967](https://github.com/axios/axios/pull/3967)) + +Fixes and Functionality: +- Added aborted even handler ([#3916](https://github.com/axios/axios/pull/3916)) +- Header types expanded allowing `boolean` and `number` types ([#4144](https://github.com/axios/axios/pull/4144)) +- Fix cancel signature allowing cancel message to be `undefined` ([#3153](https://github.com/axios/axios/pull/3153)) +- Updated type checks to be formulated better ([#3342](https://github.com/axios/axios/pull/3342)) +- Avoid unnecessary buffer allocations ([#3321](https://github.com/axios/axios/pull/3321)) +- Adding a socket handler to keep TCP connection live when processing long living requests ([#3422](https://github.com/axios/axios/pull/3422)) +- Added toFormData helper function ([#3757](https://github.com/axios/axios/pull/3757)) +- Adding responseEncoding prop type in AxiosRequestConfig ([#3918](https://github.com/axios/axios/pull/3918)) + +Internal and Tests: +- Adding axios-test-instance to ecosystem ([#3786](https://github.com/axios/axios/pull/3786)) +- Optimize the logic of isAxiosError ([#3546](https://github.com/axios/axios/pull/3546)) +- Add tests and documentation to display how multiple inceptors work ([#3564](https://github.com/axios/axios/pull/3564)) +- Updating follow-redirects to version 1.14.7 ([#4379](https://github.com/axios/axios/pull/4379)) + + +Documentation: +- Fixing changelog to show corrext pull request ([#4219](https://github.com/axios/axios/pull/4219)) +- Update upgrade guide for https proxy setting ([#3604](https://github.com/axios/axios/pull/3604)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Rijk van Zanten](https://github.com/rijkvanzanten) +- [Kohta Ito](https://github.com/koh110) +- [Brandon Faulkner](https://github.com/bfaulk96) +- [Stefano Magni](https://github.com/NoriSte) +- [enofan](https://github.com/fanguangyi) +- [Andrey Pechkurov](https://github.com/puzpuzpuz) +- [Doowonee](https://github.com/doowonee) +- [Emil Broman](https://github.com/emilbroman-eqt) +- [Remco Haszing](https://github.com/remcohaszing) +- [Black-Hole](https://github.com/BlackHole1) +- [Wolfram Kriesing](https://github.com/wolframkriesing) +- [Andrew Ovens](https://github.com/repl-andrew-ovens) +- [Paulo Renato](https://github.com/PauloRSF) +- [Ben Carp](https://github.com/carpben) +- [Hirotaka Tagawa](https://github.com/wafuwafu13) +- [狼族小狈](https://github.com/lzxb) +- [C. Lewis](https://github.com/ctjlewis) +- [Felipe Carvalho](https://github.com/FCarvalhoVII) +- [Daniel](https://github.com/djs113) +- [Gustavo Sales](https://github.com/gussalesdev) + +### 0.24.0 (October 25, 2021) + +Breaking changes: +- Revert: change type of AxiosResponse to any, please read lengthy discussion here: ([#4141](https://github.com/axios/axios/issues/4141)) pull request: ([#4186](https://github.com/axios/axios/pull/4186)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Rodry](https://github.com/ImRodry) +- [Remco Haszing](https://github.com/remcohaszing) +- [Isaiah Thomason](https://github.com/ITenthusiasm) + +### 0.23.0 (October 12, 2021) + +Breaking changes: +- Distinguish request and response data types ([#4116](https://github.com/axios/axios/pull/4116)) +- Change never type to unknown ([#4142](https://github.com/axios/axios/pull/4142)) +- Fixed TransitionalOptions typings ([#4147](https://github.com/axios/axios/pull/4147)) + +Fixes and Functionality: +- Adding globalObject: 'this' to webpack config ([#3176](https://github.com/axios/axios/pull/3176)) +- Adding insecureHTTPParser type to AxiosRequestConfig ([#4066](https://github.com/axios/axios/pull/4066)) +- Fix missing semicolon in typings ([#4115](https://github.com/axios/axios/pull/4115)) +- Fix response headers types ([#4136](https://github.com/axios/axios/pull/4136)) + +Internal and Tests: +- Improve timeout error when timeout is browser default ([#3209](https://github.com/axios/axios/pull/3209)) +- Fix node version on CI ([#4069](https://github.com/axios/axios/pull/4069)) +- Added testing to TypeScript portion of project ([#4140](https://github.com/axios/axios/pull/4140)) + +Documentation: +- Rename Angular to AngularJS ([#4114](https://github.com/axios/axios/pull/4114)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Evan-Finkelstein](https://github.com/Evan-Finkelstein) +- [Paweł Szymański](https://github.com/Jezorko) +- [Dobes Vandermeer](https://github.com/dobesv) +- [Claas Augner](https://github.com/caugner) +- [Remco Haszing](https://github.com/remcohaszing) +- [Evgeniy](https://github.com/egmen) +- [Dmitriy Mozgovoy](https://github.com/DigitalBrainJS) + +### 0.22.0 (October 01, 2021) + +Fixes and Functionality: +- Caseless header comparing in HTTP adapter ([#2880](https://github.com/axios/axios/pull/2880)) +- Avoid package.json import fixing issues and warnings related to this ([#4041](https://github.com/axios/axios/pull/4041)), ([#4065](https://github.com/axios/axios/pull/4065)) +- Fixed cancelToken leakage and added AbortController support ([#3305](https://github.com/axios/axios/pull/3305)) +- Updating CI to run on release branches +- Bump follow redirects version +- Fixed default transitional config for custom Axios instance; ([#4052](https://github.com/axios/axios/pull/4052)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Matt R. Wilson](https://github.com/mastermatt) +- [Xianming Zhong](https://github.com/chinesedfan) +- [Dmitriy Mozgovoy](https://github.com/DigitalBrainJS) + +### 0.21.4 (September 6, 2021) + +Fixes and Functionality: +- Fixing JSON transform when data is stringified. Providing backward compatability and complying to the JSON RFC standard ([#4020](https://github.com/axios/axios/pull/4020)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Guillaume Fortaine](https://github.com/gfortaine) +- [Yusuke Kawasaki](https://github.com/kawanet) +- [Dmitriy Mozgovoy](https://github.com/DigitalBrainJS) + +### 0.21.3 (September 4, 2021) + +Fixes and Functionality: +- Fixing response interceptor not being called when request interceptor is attached ([#4013](https://github.com/axios/axios/pull/4013)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Julian Hollmann](https://github.com/nerdbeere) + +### 0.21.2 (September 4, 2021) + +Fixes and Functionality: + +- Updating axios requests to be delayed by pre-emptive promise creation ([#2702](https://github.com/axios/axios/pull/2702)) +- Adding "synchronous" and "runWhen" options to interceptors api ([#2702](https://github.com/axios/axios/pull/2702)) +- Updating of transformResponse ([#3377](https://github.com/axios/axios/pull/3377)) +- Adding ability to omit User-Agent header ([#3703](https://github.com/axios/axios/pull/3703)) +- Adding multiple JSON improvements ([#3688](https://github.com/axios/axios/pull/3688), [#3763](https://github.com/axios/axios/pull/3763)) +- Fixing quadratic runtime and extra memory usage when setting a maxContentLength ([#3738](https://github.com/axios/axios/pull/3738)) +- Adding parseInt to config.timeout ([#3781](https://github.com/axios/axios/pull/3781)) +- Adding custom return type support to interceptor ([#3783](https://github.com/axios/axios/pull/3783)) +- Adding security fix for ReDoS vulnerability ([#3980](https://github.com/axios/axios/pull/3980)) + +Internal and Tests: + +- Updating build dev dependancies ([#3401](https://github.com/axios/axios/pull/3401)) +- Fixing builds running on Travis CI ([#3538](https://github.com/axios/axios/pull/3538)) +- Updating follow rediect version ([#3694](https://github.com/axios/axios/pull/3694), [#3771](https://github.com/axios/axios/pull/3771)) +- Updating karma sauce launcher to fix failing sauce tests ([#3712](https://github.com/axios/axios/pull/3712), [#3717](https://github.com/axios/axios/pull/3717)) +- Updating content-type header for application/json to not contain charset field, according do RFC 8259 ([#2154](https://github.com/axios/axios/pull/2154)) +- Fixing tests by bumping karma-sauce-launcher version ([#3813](https://github.com/axios/axios/pull/3813)) +- Changing testing process from Travis CI to GitHub Actions ([#3938](https://github.com/axios/axios/pull/3938)) + +Documentation: + +- Updating documentation around the use of `AUTH_TOKEN` with multiple domain endpoints ([#3539](https://github.com/axios/axios/pull/3539)) +- Remove duplication of item in changelog ([#3523](https://github.com/axios/axios/pull/3523)) +- Fixing gramatical errors ([#2642](https://github.com/axios/axios/pull/2642)) +- Fixing spelling error ([#3567](https://github.com/axios/axios/pull/3567)) +- Moving gitpod metion ([#2637](https://github.com/axios/axios/pull/2637)) +- Adding new axios documentation website link ([#3681](https://github.com/axios/axios/pull/3681), [#3707](https://github.com/axios/axios/pull/3707)) +- Updating documentation around dispatching requests ([#3772](https://github.com/axios/axios/pull/3772)) +- Adding documentation for the type guard isAxiosError ([#3767](https://github.com/axios/axios/pull/3767)) +- Adding explanation of cancel token ([#3803](https://github.com/axios/axios/pull/3803)) +- Updating CI status badge ([#3953](https://github.com/axios/axios/pull/3953)) +- Fixing errors with JSON documentation ([#3936](https://github.com/axios/axios/pull/3936)) +- Fixing README typo under Request Config ([#3825](https://github.com/axios/axios/pull/3825)) +- Adding axios-multi-api to the ecosystem file ([#3817](https://github.com/axios/axios/pull/3817)) +- Adding SECURITY.md to properly disclose security vulnerabilities ([#3981](https://github.com/axios/axios/pull/3981)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- [Jay](mailto:jasonsaayman@gmail.com) +- [Sasha Korotkov](https://github.com/SashaKoro) +- [Daniel Lopretto](https://github.com/timemachine3030) +- [Mike Bishop](https://github.com/MikeBishop) +- [Dmitriy Mozgovoy](https://github.com/DigitalBrainJS) +- [Mark](https://github.com/bimbiltu) +- [Philipe Gouveia Paixão](https://github.com/piiih) +- [hippo](https://github.com/hippo2cat) +- [ready-research](https://github.com/ready-research) +- [Xianming Zhong](https://github.com/chinesedfan) +- [Christopher Chrapka](https://github.com/OJezu) +- [Brian Anglin](https://github.com/anglinb) +- [Kohta Ito](https://github.com/koh110) +- [Ali Clark](https://github.com/aliclark) +- [caikan](https://github.com/caikan) +- [Elina Gorshkova](https://github.com/elinagorshkova) +- [Ryota Ikezawa](https://github.com/paveg) +- [Nisar Hassan Naqvi](https://github.com/nisarhassan12) +- [Jake](https://github.com/codemaster138) +- [TagawaHirotaka](https://github.com/wafuwafu13) +- [Johannes Jarbratt](https://github.com/johachi) +- [Mo Sattler](https://github.com/MoSattler) +- [Sam Carlton](https://github.com/ThatGuySam) +- [Matt Czapliński](https://github.com/MattCCC) +- [Ziding Zhang](https://github.com/zidingz) + +### 0.21.1 (December 21, 2020) + +Fixes and Functionality: + +- Hotfix: Prevent SSRF ([#3410](https://github.com/axios/axios/pull/3410)) +- Protocol not parsed when setting proxy config from env vars ([#3070](https://github.com/axios/axios/pull/3070)) +- Updating axios in types to be lower case ([#2797](https://github.com/axios/axios/pull/2797)) +- Adding a type guard for `AxiosError` ([#2949](https://github.com/axios/axios/pull/2949)) + +Internal and Tests: + +- Remove the skipping of the `socket` http test ([#3364](https://github.com/axios/axios/pull/3364)) +- Use different socket for Win32 test ([#3375](https://github.com/axios/axios/pull/3375)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- Daniel Lopretto <timemachine3030@users.noreply.github.com> +- Jason Kwok <JasonHK@users.noreply.github.com> +- Jay <jasonsaayman@gmail.com> +- Jonathan Foster <jonathan@jonathanfoster.io> +- Remco Haszing <remcohaszing@gmail.com> +- Xianming Zhong <chinesedfan@qq.com> + +### 0.21.0 (October 23, 2020) + +Fixes and Functionality: + +- Fixing requestHeaders.Authorization ([#3287](https://github.com/axios/axios/pull/3287)) +- Fixing node types ([#3237](https://github.com/axios/axios/pull/3237)) +- Fixing axios.delete ignores config.data ([#3282](https://github.com/axios/axios/pull/3282)) +- Revert "Fixing overwrite Blob/File type as Content-Type in browser. (#1773)" ([#3289](https://github.com/axios/axios/pull/3289)) +- Fixing an issue that type 'null' and 'undefined' is not assignable to validateStatus when typescript strict option is enabled ([#3200](https://github.com/axios/axios/pull/3200)) + +Internal and Tests: + +- Lock travis to not use node v15 ([#3361](https://github.com/axios/axios/pull/3361)) + +Documentation: + +- Fixing simple typo, existant -> existent ([#3252](https://github.com/axios/axios/pull/3252)) +- Fixing typos ([#3309](https://github.com/axios/axios/pull/3309)) + +Huge thanks to everyone who contributed to this release via code (authors listed below) or via reviews and triaging on GitHub: + +- Allan Cruz <57270969+Allanbcruz@users.noreply.github.com> +- George Cheng <Gerhut@GMail.com> +- Jay <jasonsaayman@gmail.com> +- Kevin Kirsche <Kev.Kirsche+GitHub@gmail.com> +- Remco Haszing <remcohaszing@gmail.com> +- Taemin Shin <cprayer13@gmail.com> +- Tim Gates <tim.gates@iress.com> +- Xianming Zhong <chinesedfan@qq.com> + +### 0.20.0 (August 20, 2020) + +Release of 0.20.0-pre as a full release with no other changes. + +### 0.20.0-pre (July 15, 2020) + +Fixes and Functionality: + +- Fixing response with utf-8 BOM can not parse to json ([#2419](https://github.com/axios/axios/pull/2419)) + - fix: remove byte order marker (UTF-8 BOM) when transform response + - fix: remove BOM only utf-8 + - test: utf-8 BOM + - fix: incorrect param name +- Refactor mergeConfig without utils.deepMerge ([#2844](https://github.com/axios/axios/pull/2844)) + - Adding failing test + - Fixing #2587 default custom config persisting + - Adding Concat keys and filter duplicates + - Fixed value from CPE + - update for review feedbacks + - no deepMerge + - only merge between plain objects + - fix rename + - always merge config by mergeConfig + - extract function mergeDeepProperties + - refactor mergeConfig with all keys, and add special logic for validateStatus + - add test for resetting headers + - add lots of tests and fix a bug + - should not inherit `data` + - use simple toString +- Fixing overwrite Blob/File type as Content-Type in browser. ([#1773](https://github.com/axios/axios/pull/1773)) +- Fixing an issue that type 'null' is not assignable to validateStatus ([#2773](https://github.com/axios/axios/pull/2773)) +- Fixing special char encoding ([#1671](https://github.com/axios/axios/pull/1671)) + - removing @ character from replacement list since it is a reserved character + - Updating buildURL test to not include the @ character + - Removing console logs +- Fixing password encoding with special characters in basic authentication ([#1492](https://github.com/axios/axios/pull/1492)) + - Fixing password encoding with special characters in basic authentication + - Adding test to check if password with non-Latin1 characters pass +- Fixing 'Network Error' in react native android ([#1487](https://github.com/axios/axios/pull/1487)) + There is a bug in react native Android platform when using get method. It will trigger a 'Network Error' when passing the requestData which is an empty string to request.send function. So if the requestData is an empty string we can set it to null as well to fix the bug. +- Fixing Cookie Helper with Async Components ([#1105](https://github.com/axios/axios/pull/1105)) ([#1107](https://github.com/axios/axios/pull/1107)) +- Fixing 'progressEvent' type ([#2851](https://github.com/axios/axios/pull/2851)) + - Fix 'progressEvent' type + - Update axios.ts +- Fixing getting local files (file://) failed ([#2470](https://github.com/axios/axios/pull/2470)) + - fix issue #2416, #2396 + - fix Eslint warn + - Modify judgment conditions + - add unit test + - update unit test + - update unit test +- Allow PURGE method in typings ([#2191](https://github.com/axios/axios/pull/2191)) +- Adding option to disable automatic decompression ([#2661](https://github.com/axios/axios/pull/2661)) + - Adding ability to disable auto decompression + - Updating decompress documentation in README + - Fixing test\unit\adapters\http.js lint errors + - Adding test for disabling auto decompression + - Removing changes that fixed lint errors in tests + - Removing formatting change to unit test +- Add independent `maxBodyLength` option ([#2781](https://github.com/axios/axios/pull/2781)) + - Add independent option to set the maximum size of the request body + - Remove maxBodyLength check + - Update README + - Assert for error code and message +- Adding responseEncoding to mergeConfig ([#1745](https://github.com/axios/axios/pull/1745)) +- Compatible with follow-redirect aborts the request ([#2689](https://github.com/axios/axios/pull/2689)) + - Compatible with follow-redirect aborts the request + - Use the error code +- Fix merging of params ([#2656](https://github.com/axios/axios/pull/2656)) + - Name function to avoid ESLint func-names warning + - Switch params config to merge list and update tests + - Restore testing of both false and null + - Restore test cases for keys without defaults + - Include test for non-object values that aren't false-y. +- Revert `finally` as `then` ([#2683](https://github.com/axios/axios/pull/2683)) + +Internal and Tests: + +- Fix stale bot config ([#3049](https://github.com/axios/axios/pull/3049)) + - fix stale bot config + - fix multiple lines +- Add days and change name to work ([#3035](https://github.com/axios/axios/pull/3035)) +- Update close-issues.yml ([#3031](https://github.com/axios/axios/pull/3031)) + - Update close-issues.yml + Update close message to read better 😄 + - Fix use of quotations + Use single quotes as per other .yml files + - Remove user name form message +- Add GitHub actions to close stale issues/prs ([#3029](https://github.com/axios/axios/pull/3029)) + - prepare stale actions + - update messages + - Add exempt labels and lighten up comments +- Add GitHub actions to close invalid issues ([#3022](https://github.com/axios/axios/pull/3022)) + - add close actions + - fix with checkout + - update issue templates + - add reminder + - update close message +- Add test with Node.js 12 ([#2860](https://github.com/axios/axios/pull/2860)) + - test with Node.js 12 + - test with latest +- Adding console log on sandbox server startup ([#2210](https://github.com/axios/axios/pull/2210)) + - Adding console log on sandbox server startup + - Update server.js + Add server error handling + - Update server.js + Better error message, remove retry. +- Adding tests for method `options` type definitions ([#1996](https://github.com/axios/axios/pull/1996)) + Update tests. +- Add test for redirecting with too large response ([#2695](https://github.com/axios/axios/pull/2695)) +- Fixing unit test failure in Windows OS ([#2601](https://github.com/axios/axios/pull/2601)) +- Fixing issue for HEAD method and gzipped response ([#2666](https://github.com/axios/axios/pull/2666)) +- Fix tests in browsers ([#2748](https://github.com/axios/axios/pull/2748)) +- chore: add `jsdelivr` and `unpkg` support ([#2443](https://github.com/axios/axios/pull/2443)) + +Documentation: + +- Adding support for URLSearchParams in node ([#1900](https://github.com/axios/axios/pull/1900)) + - Adding support for URLSearchParams in node + - Remove un-needed code + - Update utils.js + - Make changes as suggested +- Adding table of content (preview) ([#3050](https://github.com/axios/axios/pull/3050)) + - add toc (preview) + - remove toc in toc + Signed-off-by: Moni <usmoni@gmail.com> + - fix sublinks + - fix indentation + - remove redundant table links + - update caps and indent + - remove axios +- Replace 'blacklist' with 'blocklist' ([#3006](https://github.com/axios/axios/pull/3006)) +- docs(): Detailed config options environment. ([#2088](https://github.com/axios/axios/pull/2088)) + - docs(): Detailed config options environment. + - Update README.md +- Include axios-data-unpacker in ECOSYSTEM.md ([#2080](https://github.com/axios/axios/pull/2080)) +- Allow opening examples in Gitpod ([#1958](https://github.com/axios/axios/pull/1958)) +- Remove axios.all() and axios.spread() from Readme.md ([#2727](https://github.com/axios/axios/pull/2727)) + - remove axios.all(), axios.spread() + - replace example + - axios.all() -> Promise.all() + - axios.spread(function (acct, perms)) -> function (acct, perms) + - add deprecated mark +- Update README.md ([#2887](https://github.com/axios/axios/pull/2887)) + Small change to the data attribute doc of the config. A request body can also be set for DELETE methods but this wasn't mentioned in the documentation (it only mentioned POST, PUT and PATCH). Took my some 10-20 minutes until I realized that I don't need to manipulate the request body with transformRequest in the case of DELETE. +- Include swagger-taxos-codegen in ECOSYSTEM.md ([#2162](https://github.com/axios/axios/pull/2162)) +- Add CDNJS version badge in README.md ([#878](https://github.com/axios/axios/pull/878)) + This badge will show the version on CDNJS! +- Documentation update to clear up ambiguity in code examples ([#2928](https://github.com/axios/axios/pull/2928)) + - Made an adjustment to the documentation to clear up any ambiguity around the use of "fs". This should help clear up that the code examples with "fs" cannot be used on the client side. +- Update README.md about validateStatus ([#2912](https://github.com/axios/axios/pull/2912)) + Rewrote the comment from "Reject only if the status code is greater than or equal to 500" to "Resolve only if the status code is less than 500" +- Updating documentation for usage form-data ([#2805](https://github.com/axios/axios/pull/2805)) + Closes #2049 +- Fixing CHANGELOG.md issue link ([#2784](https://github.com/axios/axios/pull/2784)) +- Include axios-hooks in ECOSYSTEM.md ([#2003](https://github.com/axios/axios/pull/2003)) +- Added Response header access instructions ([#1901](https://github.com/axios/axios/pull/1901)) + - Added Response header access instructions + - Added note about using bracket notation +- Add `onUploadProgress` and `onDownloadProgress` are browser only ([#2763](https://github.com/axios/axios/pull/2763)) + Saw in #928 and #1966 that `onUploadProgress` and `onDownloadProgress` only work in the browser and was missing that from the README. +- Update ' sign to ` in proxy spec ([#2778](https://github.com/axios/axios/pull/2778)) +- Adding jsDelivr link in README ([#1110](https://github.com/axios/axios/pull/1110)) + - Adding jsDelivr link + - Add SRI + - Remove SRI + +Huge thanks to everyone who contributed to this release via code (authors listed +below) or via reviews and triaging on GitHub: + +- Alan Wang <wp_scut@163.com> +- Alexandru Ungureanu <khakcarot@gmail.com> +- Anubhav Srivastava <anubhav.srivastava00@gmail.com> +- Benny Neugebauer <bn@bennyn.de> +- Cr <631807682@qq.com> +- David <cygnidavid@gmail.com> +- David Ko <david.ko@pvtmethod.com> +- David Tanner <david.tanner@lifeomic.com> +- Emily Morehouse <emilyemorehouse@gmail.com> +- Felipe Martins <felipewmartins@gmail.com> +- Fonger <5862369+Fonger@users.noreply.github.com> +- Frostack <soulburn007@gmail.com> +- George Cheng <Gerhut@GMail.com> +- grumblerchester <grumblerchester@users.noreply.github.com> +- Gustavo López <gualopezb@gmail.com> +- hexaez <45806662+hexaez@users.noreply.github.com> +- huangzuizui <huangzuizui@gmail.com> +- Ian Wijma <ian@wij.ma> +- Jay <jasonsaayman@gmail.com> +- jeffjing <zgayjjf@qq.com> +- jennynju <46782518+jennynju@users.noreply.github.com> +- Jimmy Liao <52391190+jimmy-liao-gogoro@users.noreply.github.com> +- Jonathan Sharpe <j.r.sharpe@gmail.com> +- JounQin <admin@1stg.me> +- Justin Beckwith <justin.beckwith@gmail.com> +- Kamil Posiadała <3dcreator.pl@gmail.com> +- Lukas Drgon <lukas.drgon@gmail.com> +- marcinx <mail@marcinx.com> +- Martti Laine <martti@codeclown.net> +- Michał Zarach <michal.m.zarach@gmail.com> +- Moni <usmoni@gmail.com> +- Motonori Iwata <121048+iwata@users.noreply.github.com> +- Nikita Galkin <nikita@galk.in> +- Petr Mares <petr@mares.tw> +- Philippe Recto <precto1285@gmal.com> +- Remco Haszing <remcohaszing@gmail.com> +- rockcs1992 <chengshi1219@gmail.com> +- Ryan Bown <rbown@niftee.com.au> +- Samina Fu <sufuf3@gmail.com> +- Simone Busoli <simone.busoli@gmail.com> +- Spencer von der Ohe <s.vonderohe40@gmail.com> +- Sven Efftinge <sven.efftinge@typefox.io> +- Taegyeoung Oh <otk1090@naver.com> +- Taemin Shin <cprayer13@gmail.com> +- Thibault Ehrhart <1208424+ehrhart@users.noreply.github.com> +- Xianming Zhong <chinesedfan@qq.com> +- Yasu Flores <carlosyasu91@gmail.com> +- Zac Delventhal <delventhalz@gmail.com> + +### 0.19.2 (Jan 20, 2020) + +- Remove unnecessary XSS check ([#2679](https://github.com/axios/axios/pull/2679)) (see ([#2646](https://github.com/axios/axios/issues/2646)) for discussion) + +### 0.19.1 (Jan 7, 2020) + +Fixes and Functionality: + +- Fixing invalid agent issue ([#1904](https://github.com/axios/axios/pull/1904)) +- Fix ignore set withCredentials false ([#2582](https://github.com/axios/axios/pull/2582)) +- Delete useless default to hash ([#2458](https://github.com/axios/axios/pull/2458)) +- Fix HTTP/HTTPs agents passing to follow-redirect ([#1904](https://github.com/axios/axios/pull/1904)) +- Fix ignore set withCredentials false ([#2582](https://github.com/axios/axios/pull/2582)) +- Fix CI build failure ([#2570](https://github.com/axios/axios/pull/2570)) +- Remove dependency on is-buffer from package.json ([#1816](https://github.com/axios/axios/pull/1816)) +- Adding options typings ([#2341](https://github.com/axios/axios/pull/2341)) +- Adding Typescript HTTP method definition for LINK and UNLINK. ([#2444](https://github.com/axios/axios/pull/2444)) +- Update dist with newest changes, fixes Custom Attributes issue +- Change syntax to see if build passes ([#2488](https://github.com/axios/axios/pull/2488)) +- Update Webpack + deps, remove now unnecessary polyfills ([#2410](https://github.com/axios/axios/pull/2410)) +- Fix to prevent XSS, throw an error when the URL contains a JS script ([#2464](https://github.com/axios/axios/pull/2464)) +- Add custom timeout error copy in config ([#2275](https://github.com/axios/axios/pull/2275)) +- Add error toJSON example ([#2466](https://github.com/axios/axios/pull/2466)) +- Fixing Vulnerability A Fortify Scan finds a critical Cross-Site Scrip… ([#2451](https://github.com/axios/axios/pull/2451)) +- Fixing subdomain handling on no_proxy ([#2442](https://github.com/axios/axios/pull/2442)) +- Make redirection from HTTP to HTTPS work ([#2426](https://github.com/axios/axios/pull/2426)) and ([#2547](https://github.com/axios/axios/pull/2547)) +- Add toJSON property to AxiosError type ([#2427](https://github.com/axios/axios/pull/2427)) +- Fixing socket hang up error on node side for slow response. ([#1752](https://github.com/axios/axios/pull/1752)) +- Alternative syntax to send data into the body ([#2317](https://github.com/axios/axios/pull/2317)) +- Fixing custom config options ([#2207](https://github.com/axios/axios/pull/2207)) +- Fixing set `config.method` after mergeConfig for Axios.prototype.request ([#2383](https://github.com/axios/axios/pull/2383)) +- Axios create url bug ([#2290](https://github.com/axios/axios/pull/2290)) +- Do not modify config.url when using a relative baseURL (resolves [#1628](https://github.com/axios/axios/issues/1098)) ([#2391](https://github.com/axios/axios/pull/2391)) + +Internal: + +- Revert "Update Webpack + deps, remove now unnecessary polyfills" ([#2479](https://github.com/axios/axios/pull/2479)) +- Order of if/else blocks is causing unit tests mocking XHR. ([#2201](https://github.com/axios/axios/pull/2201)) +- Add license badge ([#2446](https://github.com/axios/axios/pull/2446)) +- Fix travis CI build [#2386](https://github.com/axios/axios/pull/2386) +- Fix cancellation error on build master. #2290 #2207 ([#2407](https://github.com/axios/axios/pull/2407)) + +Documentation: + +- Fixing typo in CHANGELOG.md: s/Functionallity/Functionality ([#2639](https://github.com/axios/axios/pull/2639)) +- Fix badge, use master branch ([#2538](https://github.com/axios/axios/pull/2538)) +- Fix typo in changelog [#2193](https://github.com/axios/axios/pull/2193) +- Document fix ([#2514](https://github.com/axios/axios/pull/2514)) +- Update docs with no_proxy change, issue #2484 ([#2513](https://github.com/axios/axios/pull/2513)) +- Fixing missing words in docs template ([#2259](https://github.com/axios/axios/pull/2259)) +- 🐛Fix request finally documentation in README ([#2189](https://github.com/axios/axios/pull/2189)) +- updating spelling and adding link to docs ([#2212](https://github.com/axios/axios/pull/2212)) +- docs: minor tweak ([#2404](https://github.com/axios/axios/pull/2404)) +- Update response interceptor docs ([#2399](https://github.com/axios/axios/pull/2399)) +- Update README.md ([#2504](https://github.com/axios/axios/pull/2504)) +- Fix word 'sintaxe' to 'syntax' in README.md ([#2432](https://github.com/axios/axios/pull/2432)) +- updating README: notes on CommonJS autocomplete ([#2256](https://github.com/axios/axios/pull/2256)) +- Fix grammar in README.md ([#2271](https://github.com/axios/axios/pull/2271)) +- Doc fixes, minor examples cleanup ([#2198](https://github.com/axios/axios/pull/2198)) + +### 0.19.0 (May 30, 2019) + +Fixes and Functionality: + +- Added support for no_proxy env variable ([#1693](https://github.com/axios/axios/pull/1693/files)) - Chance Dickson +- Unzip response body only for statuses != 204 ([#1129](https://github.com/axios/axios/pull/1129)) - drawski +- Destroy stream on exceeding maxContentLength (fixes [#1098](https://github.com/axios/axios/issues/1098)) ([#1485](https://github.com/axios/axios/pull/1485)) - Gadzhi Gadzhiev +- Makes Axios error generic to use AxiosResponse ([#1738](https://github.com/axios/axios/pull/1738)) - Suman Lama +- Fixing Mocha tests by locking follow-redirects version to 1.5.10 ([#1993](https://github.com/axios/axios/pull/1993)) - grumblerchester +- Allow uppercase methods in typings. ([#1781](https://github.com/axios/axios/pull/1781)) - Ken Powers +- Fixing building url with hash mark ([#1771](https://github.com/axios/axios/pull/1771)) - Anatoly Ryabov +- This commit fix building url with hash map (fragment identifier) when parameters are present: they must not be added after `#`, because client cut everything after `#` +- Preserve HTTP method when following redirect ([#1758](https://github.com/axios/axios/pull/1758)) - Rikki Gibson +- Add `getUri` signature to TypeScript definition. ([#1736](https://github.com/axios/axios/pull/1736)) - Alexander Trauzzi +- Adding isAxiosError flag to errors thrown by axios ([#1419](https://github.com/axios/axios/pull/1419)) - Ayush Gupta + +Internal: + +- Fixing .eslintrc without extension ([#1789](https://github.com/axios/axios/pull/1789)) - Manoel +- Fix failing SauceLabs tests by updating configuration - Emily Morehouse +- Add issue templates - Emily Morehouse + +Documentation: + +- Consistent coding style in README ([#1787](https://github.com/axios/axios/pull/1787)) - Ali Servet Donmez +- Add information about auth parameter to README ([#2166](https://github.com/axios/axios/pull/2166)) - xlaguna +- Add DELETE to list of methods that allow data as a config option ([#2169](https://github.com/axios/axios/pull/2169)) - Daniela Borges Matos de Carvalho +- Update ECOSYSTEM.md - Add Axios Endpoints ([#2176](https://github.com/axios/axios/pull/2176)) - Renan +- Add r2curl in ECOSYSTEM ([#2141](https://github.com/axios/axios/pull/2141)) - 유용우 / CX +- Update README.md - Add instructions for installing with yarn ([#2036](https://github.com/axios/axios/pull/2036)) - Victor Hermes +- Fixing spacing for README.md ([#2066](https://github.com/axios/axios/pull/2066)) - Josh McCarty +- Update README.md. - Change `.then` to `.finally` in example code ([#2090](https://github.com/axios/axios/pull/2090)) - Omar Cai +- Clarify what values responseType can have in Node ([#2121](https://github.com/axios/axios/pull/2121)) - Tyler Breisacher +- docs(ECOSYSTEM): add axios-api-versioning ([#2020](https://github.com/axios/axios/pull/2020)) - Weffe +- It seems that `responseType: 'blob'` doesn't actually work in Node (when I tried using it, response.data was a string, not a Blob, since Node doesn't have Blobs), so this clarifies that this option should only be used in the browser +- Update README.md. - Add Querystring library note ([#1896](https://github.com/axios/axios/pull/1896)) - Dmitriy Eroshenko +- Add react-hooks-axios to Libraries section of ECOSYSTEM.md ([#1925](https://github.com/axios/axios/pull/1925)) - Cody Chan +- Clarify in README that default timeout is 0 (no timeout) ([#1750](https://github.com/axios/axios/pull/1750)) - Ben Standefer + +### 0.19.0-beta.1 (Aug 9, 2018) + +**NOTE:** This is a beta version of this release. There may be functionality that is broken in +certain browsers, though we suspect that builds are hanging and not erroring. See +https://saucelabs.com/u/axios for the most up-to-date information. + +New Functionality: + +- Add getUri method ([#1712](https://github.com/axios/axios/issues/1712)) +- Add support for no_proxy env variable ([#1693](https://github.com/axios/axios/issues/1693)) +- Add toJSON to decorated Axios errors to facilitate serialization ([#1625](https://github.com/axios/axios/issues/1625)) +- Add second then on axios call ([#1623](https://github.com/axios/axios/issues/1623)) +- Typings: allow custom return types +- Add option to specify character set in responses (with http adapter) + +Fixes: + +- Fix Keep defaults local to instance ([#385](https://github.com/axios/axios/issues/385)) +- Correctly catch exception in http test ([#1475](https://github.com/axios/axios/issues/1475)) +- Fix accept header normalization ([#1698](https://github.com/axios/axios/issues/1698)) +- Fix http adapter to allow HTTPS connections via HTTP ([#959](https://github.com/axios/axios/issues/959)) +- Fix Removes usage of deprecated Buffer constructor. ([#1555](https://github.com/axios/axios/issues/1555), [#1622](https://github.com/axios/axios/issues/1622)) +- Fix defaults to use httpAdapter if available ([#1285](https://github.com/axios/axios/issues/1285)) + - Fixing defaults to use httpAdapter if available + - Use a safer, cross-platform method to detect the Node environment +- Fix Reject promise if request is cancelled by the browser ([#537](https://github.com/axios/axios/issues/537)) +- [Typescript] Fix missing type parameters on delete/head methods +- [NS]: Send `false` flag isStandardBrowserEnv for Nativescript +- Fix missing type parameters on delete/head +- Fix Default method for an instance always overwritten by get +- Fix type error when socketPath option in AxiosRequestConfig +- Capture errors on request data streams +- Decorate resolve and reject to clear timeout in all cases + +Huge thanks to everyone who contributed to this release via code (authors listed +below) or via reviews and triaging on GitHub: + +- Andrew Scott <ascott18@gmail.com> +- Anthony Gauthier <antho325@hotmail.com> +- arpit <arpit2438735@gmail.com> +- ascott18 +- Benedikt Rötsch <axe312ger@users.noreply.github.com> +- Chance Dickson <me@chancedickson.com> +- Dave Stewart <info@davestewart.co.uk> +- Deric Cain <deric.cain@gmail.com> +- Guillaume Briday <guillaumebriday@gmail.com> +- Jacob Wejendorp <jacob@wejendorp.dk> +- Jim Lynch <mrdotjim@gmail.com> +- johntron +- Justin Beckwith <beckwith@google.com> +- Justin Beckwith <justin.beckwith@gmail.com> +- Khaled Garbaya <khaledgarbaya@gmail.com> +- Lim Jing Rong <jjingrong@users.noreply.github.com> +- Mark van den Broek <mvdnbrk@gmail.com> +- Martti Laine <martti@codeclown.net> +- mattridley +- mattridley <matt.r@joinblink.com> +- Nicolas Del Valle <nicolas.delvalle@gmail.com> +- Nilegfx +- pbarbiero +- Rikki Gibson <rikkigibson@gmail.com> +- Sako Hartounian <sakohartounian@yahoo.com> +- Shane Fitzpatrick <fitzpasd@gmail.com> +- Stephan Schneider <stephanschndr@gmail.com> +- Steven <steven@ceriously.com> +- Tim Garthwaite <tim.garthwaite@jibo.com> +- Tim Johns <timjohns@yahoo.com> +- Yutaro Miyazaki <yutaro@studio-rubbish.com> + +### 0.18.0 (Feb 19, 2018) + +- Adding support for UNIX Sockets when running with Node.js ([#1070](https://github.com/axios/axios/pull/1070)) +- Fixing typings ([#1177](https://github.com/axios/axios/pull/1177)): + - AxiosRequestConfig.proxy: allows type false + - AxiosProxyConfig: added auth field +- Adding function signature in AxiosInstance interface so AxiosInstance can be invoked ([#1192](https://github.com/axios/axios/pull/1192), [#1254](https://github.com/axios/axios/pull/1254)) +- Allowing maxContentLength to pass through to redirected calls as maxBodyLength in follow-redirects config ([#1287](https://github.com/axios/axios/pull/1287)) +- Fixing configuration when using an instance - method can now be set ([#1342](https://github.com/axios/axios/pull/1342)) + +### 0.17.1 (Nov 11, 2017) + +- Fixing issue with web workers ([#1160](https://github.com/axios/axios/pull/1160)) +- Allowing overriding transport ([#1080](https://github.com/axios/axios/pull/1080)) +- Updating TypeScript typings ([#1165](https://github.com/axios/axios/pull/1165), [#1125](https://github.com/axios/axios/pull/1125), [#1131](https://github.com/axios/axios/pull/1131)) + +### 0.17.0 (Oct 21, 2017) + +- **BREAKING** Fixing issue with `baseURL` and interceptors ([#950](https://github.com/axios/axios/pull/950)) +- **BREAKING** Improving handing of duplicate headers ([#874](https://github.com/axios/axios/pull/874)) +- Adding support for disabling proxies ([#691](https://github.com/axios/axios/pull/691)) +- Updating TypeScript typings with generic type parameters ([#1061](https://github.com/axios/axios/pull/1061)) + +### 0.16.2 (Jun 3, 2017) + +- Fixing issue with including `buffer` in bundle ([#887](https://github.com/axios/axios/pull/887)) +- Including underlying request in errors ([#830](https://github.com/axios/axios/pull/830)) +- Convert `method` to lowercase ([#930](https://github.com/axios/axios/pull/930)) + +### 0.16.1 (Apr 8, 2017) + +- Improving HTTP adapter to return last request in case of redirects ([#828](https://github.com/axios/axios/pull/828)) +- Updating `follow-redirects` dependency ([#829](https://github.com/axios/axios/pull/829)) +- Adding support for passing `Buffer` in node ([#773](https://github.com/axios/axios/pull/773)) + +### 0.16.0 (Mar 31, 2017) + +- **BREAKING** Removing `Promise` from axios typings in favor of built-in type declarations ([#480](https://github.com/axios/axios/issues/480)) +- Adding `options` shortcut method ([#461](https://github.com/axios/axios/pull/461)) +- Fixing issue with using `responseType: 'json'` in browsers incompatible with XHR Level 2 ([#654](https://github.com/axios/axios/pull/654)) +- Improving React Native detection ([#731](https://github.com/axios/axios/pull/731)) +- Fixing `combineURLs` to support empty `relativeURL` ([#581](https://github.com/axios/axios/pull/581)) +- Removing `PROTECTION_PREFIX` support ([#561](https://github.com/axios/axios/pull/561)) + +### 0.15.3 (Nov 27, 2016) + +- Fixing issue with custom instances and global defaults ([#443](https://github.com/axios/axios/issues/443)) +- Renaming `axios.d.ts` to `index.d.ts` ([#519](https://github.com/axios/axios/issues/519)) +- Adding `get`, `head`, and `delete` to `defaults.headers` ([#509](https://github.com/axios/axios/issues/509)) +- Fixing issue with `btoa` and IE ([#507](https://github.com/axios/axios/issues/507)) +- Adding support for proxy authentication ([#483](https://github.com/axios/axios/pull/483)) +- Improving HTTP adapter to use `http` protocol by default ([#493](https://github.com/axios/axios/pull/493)) +- Fixing proxy issues ([#491](https://github.com/axios/axios/pull/491)) + +### 0.15.2 (Oct 17, 2016) + +- Fixing issue with calling `cancel` after response has been received ([#482](https://github.com/axios/axios/issues/482)) + +### 0.15.1 (Oct 14, 2016) + +- Fixing issue with UMD ([#485](https://github.com/axios/axios/issues/485)) + +### 0.15.0 (Oct 10, 2016) + +- Adding cancellation support ([#452](https://github.com/axios/axios/pull/452)) +- Moving default adapter to global defaults ([#437](https://github.com/axios/axios/pull/437)) +- Fixing issue with `file` URI scheme ([#440](https://github.com/axios/axios/pull/440)) +- Fixing issue with `params` objects that have no prototype ([#445](https://github.com/axios/axios/pull/445)) + +### 0.14.0 (Aug 27, 2016) + +- **BREAKING** Updating TypeScript definitions ([#419](https://github.com/axios/axios/pull/419)) +- **BREAKING** Replacing `agent` option with `httpAgent` and `httpsAgent` ([#387](https://github.com/axios/axios/pull/387)) +- **BREAKING** Splitting `progress` event handlers into `onUploadProgress` and `onDownloadProgress` ([#423](https://github.com/axios/axios/pull/423)) +- Adding support for `http_proxy` and `https_proxy` environment variables ([#366](https://github.com/axios/axios/pull/366)) +- Fixing issue with `auth` config option and `Authorization` header ([#397](https://github.com/axios/axios/pull/397)) +- Don't set XSRF header if `xsrfCookieName` is `null` ([#406](https://github.com/axios/axios/pull/406)) + +### 0.13.1 (Jul 16, 2016) + +- Fixing issue with response data not being transformed on error ([#378](https://github.com/axios/axios/issues/378)) + +### 0.13.0 (Jul 13, 2016) + +- **BREAKING** Improved error handling ([#345](https://github.com/axios/axios/pull/345)) +- **BREAKING** Response transformer now invoked in dispatcher not adapter ([10eb238](https://github.com/axios/axios/commit/10eb23865101f9347570552c04e9d6211376e25e)) +- **BREAKING** Request adapters now return a `Promise` ([157efd5](https://github.com/axios/axios/commit/157efd5615890301824e3121cc6c9d2f9b21f94a)) +- Fixing issue with `withCredentials` not being overwritten ([#343](https://github.com/axios/axios/issues/343)) +- Fixing regression with request transformer being called before request interceptor ([#352](https://github.com/axios/axios/issues/352)) +- Fixing custom instance defaults ([#341](https://github.com/axios/axios/issues/341)) +- Fixing instances created from `axios.create` to have same API as default axios ([#217](https://github.com/axios/axios/issues/217)) + +### 0.12.0 (May 31, 2016) + +- Adding support for `URLSearchParams` ([#317](https://github.com/axios/axios/pull/317)) +- Adding `maxRedirects` option ([#307](https://github.com/axios/axios/pull/307)) + +### 0.11.1 (May 17, 2016) + +- Fixing IE CORS support ([#313](https://github.com/axios/axios/pull/313)) +- Fixing detection of `FormData` ([#325](https://github.com/axios/axios/pull/325)) +- Adding `Axios` class to exports ([#321](https://github.com/axios/axios/pull/321)) + +### 0.11.0 (Apr 26, 2016) + +- Adding support for Stream with HTTP adapter ([#296](https://github.com/axios/axios/pull/296)) +- Adding support for custom HTTP status code error ranges ([#308](https://github.com/axios/axios/pull/308)) +- Fixing issue with ArrayBuffer ([#299](https://github.com/axios/axios/pull/299)) + +### 0.10.0 (Apr 20, 2016) + +- Fixing issue with some requests sending `undefined` instead of `null` ([#250](https://github.com/axios/axios/pull/250)) +- Fixing basic auth for HTTP adapter ([#252](https://github.com/axios/axios/pull/252)) +- Fixing request timeout for XHR adapter ([#227](https://github.com/axios/axios/pull/227)) +- Fixing IE8 support by using `onreadystatechange` instead of `onload` ([#249](https://github.com/axios/axios/pull/249)) +- Fixing IE9 cross domain requests ([#251](https://github.com/axios/axios/pull/251)) +- Adding `maxContentLength` option ([#275](https://github.com/axios/axios/pull/275)) +- Fixing XHR support for WebWorker environment ([#279](https://github.com/axios/axios/pull/279)) +- Adding request instance to response ([#200](https://github.com/axios/axios/pull/200)) + +### 0.9.1 (Jan 24, 2016) + +- Improving handling of request timeout in node ([#124](https://github.com/axios/axios/issues/124)) +- Fixing network errors not rejecting ([#205](https://github.com/axios/axios/pull/205)) +- Fixing issue with IE rejecting on HTTP 204 ([#201](https://github.com/axios/axios/issues/201)) +- Fixing host/port when following redirects ([#198](https://github.com/axios/axios/pull/198)) + +### 0.9.0 (Jan 18, 2016) + +- Adding support for custom adapters +- Fixing Content-Type header being removed when data is false ([#195](https://github.com/axios/axios/pull/195)) +- Improving XDomainRequest implementation ([#185](https://github.com/axios/axios/pull/185)) +- Improving config merging and order of precedence ([#183](https://github.com/axios/axios/pull/183)) +- Fixing XDomainRequest support for only <= IE9 ([#182](https://github.com/axios/axios/pull/182)) + +### 0.8.1 (Dec 14, 2015) + +- Adding support for passing XSRF token for cross domain requests when using `withCredentials` ([#168](https://github.com/axios/axios/pull/168)) +- Fixing error with format of basic auth header ([#178](https://github.com/axios/axios/pull/173)) +- Fixing error with JSON payloads throwing `InvalidStateError` in some cases ([#174](https://github.com/axios/axios/pull/174)) + +### 0.8.0 (Dec 11, 2015) + +- Adding support for creating instances of axios ([#123](https://github.com/axios/axios/pull/123)) +- Fixing http adapter to use `Buffer` instead of `String` in case of `responseType === 'arraybuffer'` ([#128](https://github.com/axios/axios/pull/128)) +- Adding support for using custom parameter serializer with `paramsSerializer` option ([#121](https://github.com/axios/axios/pull/121)) +- Fixing issue in IE8 caused by `forEach` on `arguments` ([#127](https://github.com/axios/axios/pull/127)) +- Adding support for following redirects in node ([#146](https://github.com/axios/axios/pull/146)) +- Adding support for transparent decompression if `content-encoding` is set ([#149](https://github.com/axios/axios/pull/149)) +- Adding support for transparent XDomainRequest to handle cross domain requests in IE9 ([#140](https://github.com/axios/axios/pull/140)) +- Adding support for HTTP basic auth via Authorization header ([#167](https://github.com/axios/axios/pull/167)) +- Adding support for baseURL option ([#160](https://github.com/axios/axios/pull/160)) + +### 0.7.0 (Sep 29, 2015) + +- Fixing issue with minified bundle in IE8 ([#87](https://github.com/axios/axios/pull/87)) +- Adding support for passing agent in node ([#102](https://github.com/axios/axios/pull/102)) +- Adding support for returning result from `axios.spread` for chaining ([#106](https://github.com/axios/axios/pull/106)) +- Fixing typescript definition ([#105](https://github.com/axios/axios/pull/105)) +- Fixing default timeout config for node ([#112](https://github.com/axios/axios/pull/112)) +- Adding support for use in web workers, and react-native ([#70](https://github.com/axios/axios/issue/70)), ([#98](https://github.com/axios/axios/pull/98)) +- Adding support for fetch like API `axios(url[, config])` ([#116](https://github.com/axios/axios/issues/116)) + +### 0.6.0 (Sep 21, 2015) + +- Removing deprecated success/error aliases +- Fixing issue with array params not being properly encoded ([#49](https://github.com/axios/axios/pull/49)) +- Fixing issue with User-Agent getting overridden ([#69](https://github.com/axios/axios/issues/69)) +- Adding support for timeout config ([#56](https://github.com/axios/axios/issues/56)) +- Removing es6-promise dependency +- Fixing issue preventing `length` to be used as a parameter ([#91](https://github.com/axios/axios/pull/91)) +- Fixing issue with IE8 ([#85](https://github.com/axios/axios/pull/85)) +- Converting build to UMD + +### 0.5.4 (Apr 08, 2015) + +- Fixing issue with FormData not being sent ([#53](https://github.com/axios/axios/issues/53)) + +### 0.5.3 (Apr 07, 2015) + +- Using JSON.parse unconditionally when transforming response string ([#55](https://github.com/axios/axios/issues/55)) + +### 0.5.2 (Mar 13, 2015) + +- Adding support for `statusText` in response ([#46](https://github.com/axios/axios/issues/46)) + +### 0.5.1 (Mar 10, 2015) + +- Fixing issue using strict mode ([#45](https://github.com/axios/axios/issues/45)) +- Fixing issue with standalone build ([#47](https://github.com/axios/axios/issues/47)) + +### 0.5.0 (Jan 23, 2015) + +- Adding support for intercepetors ([#14](https://github.com/axios/axios/issues/14)) +- Updating es6-promise dependency + +### 0.4.2 (Dec 10, 2014) + +- Fixing issue with `Content-Type` when using `FormData` ([#22](https://github.com/axios/axios/issues/22)) +- Adding support for TypeScript ([#25](https://github.com/axios/axios/issues/25)) +- Fixing issue with standalone build ([#29](https://github.com/axios/axios/issues/29)) +- Fixing issue with verbs needing to be capitalized in some browsers ([#30](https://github.com/axios/axios/issues/30)) + +### 0.4.1 (Oct 15, 2014) + +- Adding error handling to request for node.js ([#18](https://github.com/axios/axios/issues/18)) + +### 0.4.0 (Oct 03, 2014) + +- Adding support for `ArrayBuffer` and `ArrayBufferView` ([#10](https://github.com/axios/axios/issues/10)) +- Adding support for utf-8 for node.js ([#13](https://github.com/axios/axios/issues/13)) +- Adding support for SSL for node.js ([#12](https://github.com/axios/axios/issues/12)) +- Fixing incorrect `Content-Type` header ([#9](https://github.com/axios/axios/issues/9)) +- Adding standalone build without bundled es6-promise ([#11](https://github.com/axios/axios/issues/11)) +- Deprecating `success`/`error` in favor of `then`/`catch` + +### 0.3.1 (Sep 16, 2014) + +- Fixing missing post body when using node.js ([#3](https://github.com/axios/axios/issues/3)) + +### 0.3.0 (Sep 16, 2014) + +- Fixing `success` and `error` to properly receive response data as individual arguments ([#8](https://github.com/axios/axios/issues/8)) +- Updating `then` and `catch` to receive response data as a single object ([#6](https://github.com/axios/axios/issues/6)) +- Fixing issue with `all` not working ([#7](https://github.com/axios/axios/issues/7)) + +### 0.2.2 (Sep 14, 2014) + +- Fixing bundling with browserify ([#4](https://github.com/axios/axios/issues/4)) + +### 0.2.1 (Sep 12, 2014) + +- Fixing build problem causing ridiculous file sizes + +### 0.2.0 (Sep 12, 2014) + +- Adding support for `all` and `spread` +- Adding support for node.js ([#1](https://github.com/axios/axios/issues/1)) + +### 0.1.0 (Aug 29, 2014) + +- Initial release diff --git a/node_modules/axios/LICENSE b/node_modules/axios/LICENSE new file mode 100644 index 0000000..d36c80e --- /dev/null +++ b/node_modules/axios/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2014-present Matt Zabriskie + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/axios/README.md b/node_modules/axios/README.md new file mode 100755 index 0000000..d5ba7f9 --- /dev/null +++ b/node_modules/axios/README.md @@ -0,0 +1,909 @@ +# axios + +[![npm version](https://img.shields.io/npm/v/axios.svg?style=flat-square)](https://www.npmjs.org/package/axios) +[![CDNJS](https://img.shields.io/cdnjs/v/axios.svg?style=flat-square)](https://cdnjs.com/libraries/axios) +![Build status](https://github.com/axios/axios/actions/workflows/ci.yml/badge.svg) +[![Gitpod Ready-to-Code](https://img.shields.io/badge/Gitpod-Ready--to--Code-blue?logo=gitpod)](https://gitpod.io/#https://github.com/axios/axios) +[![code coverage](https://img.shields.io/coveralls/mzabriskie/axios.svg?style=flat-square)](https://coveralls.io/r/mzabriskie/axios) +[![install size](https://packagephobia.now.sh/badge?p=axios)](https://packagephobia.now.sh/result?p=axios) +[![npm downloads](https://img.shields.io/npm/dm/axios.svg?style=flat-square)](http://npm-stat.com/charts.html?package=axios) +[![gitter chat](https://img.shields.io/gitter/room/mzabriskie/axios.svg?style=flat-square)](https://gitter.im/mzabriskie/axios) +[![code helpers](https://www.codetriage.com/axios/axios/badges/users.svg)](https://www.codetriage.com/axios/axios) +[![Known Vulnerabilities](https://snyk.io/test/npm/axios/badge.svg)](https://snyk.io/test/npm/axios) + +Promise based HTTP client for the browser and node.js + +> New axios docs website: [click here](https://axios-http.com/) + +## Table of Contents + + - [Features](#features) + - [Browser Support](#browser-support) + - [Installing](#installing) + - [Example](#example) + - [Axios API](#axios-api) + - [Request method aliases](#request-method-aliases) + - [Concurrency (Deprecated)](#concurrency-deprecated) + - [Creating an instance](#creating-an-instance) + - [Instance methods](#instance-methods) + - [Request Config](#request-config) + - [Response Schema](#response-schema) + - [Config Defaults](#config-defaults) + - [Global axios defaults](#global-axios-defaults) + - [Custom instance defaults](#custom-instance-defaults) + - [Config order of precedence](#config-order-of-precedence) + - [Interceptors](#interceptors) + - [Multiple Interceptors](#multiple-interceptors) + - [Handling Errors](#handling-errors) + - [Cancellation](#cancellation) + - [Using application/x-www-form-urlencoded format](#using-applicationx-www-form-urlencoded-format) + - [Browser](#browser) + - [Node.js](#nodejs) + - [Query string](#query-string) + - [Form data](#form-data) + - [Semver](#semver) + - [Promises](#promises) + - [TypeScript](#typescript) + - [Resources](#resources) + - [Credits](#credits) + - [License](#license) + +## Features + +- Make [XMLHttpRequests](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest) from the browser +- Make [http](http://nodejs.org/api/http.html) requests from node.js +- Supports the [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) API +- Intercept request and response +- Transform request and response data +- Cancel requests +- Automatic transforms for JSON data +- Client side support for protecting against [XSRF](http://en.wikipedia.org/wiki/Cross-site_request_forgery) + +## Browser Support + +![Chrome](https://raw.github.com/alrra/browser-logos/master/src/chrome/chrome_48x48.png) | ![Firefox](https://raw.github.com/alrra/browser-logos/master/src/firefox/firefox_48x48.png) | ![Safari](https://raw.github.com/alrra/browser-logos/master/src/safari/safari_48x48.png) | ![Opera](https://raw.github.com/alrra/browser-logos/master/src/opera/opera_48x48.png) | ![Edge](https://raw.github.com/alrra/browser-logos/master/src/edge/edge_48x48.png) | ![IE](https://raw.github.com/alrra/browser-logos/master/src/archive/internet-explorer_9-11/internet-explorer_9-11_48x48.png) | +--- | --- | --- | --- | --- | --- | +Latest ✔ | Latest ✔ | Latest ✔ | Latest ✔ | Latest ✔ | 11 ✔ | + +[![Browser Matrix](https://saucelabs.com/open_sauce/build_matrix/axios.svg)](https://saucelabs.com/u/axios) + +## Installing + +Using npm: + +```bash +$ npm install axios +``` + +Using bower: + +```bash +$ bower install axios +``` + +Using yarn: + +```bash +$ yarn add axios +``` + +Using jsDelivr CDN: + +```html +<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script> +``` + +Using unpkg CDN: + +```html +<script src="https://unpkg.com/axios/dist/axios.min.js"></script> +``` + +## Example + +### note: CommonJS usage +In order to gain the TypeScript typings (for intellisense / autocomplete) while using CommonJS imports with `require()` use the following approach: + +```js +const axios = require('axios').default; + +// axios.<method> will now provide autocomplete and parameter typings +``` + +Performing a `GET` request + +```js +const axios = require('axios'); + +// Make a request for a user with a given ID +axios.get('/user?ID=12345') + .then(function (response) { + // handle success + console.log(response); + }) + .catch(function (error) { + // handle error + console.log(error); + }) + .then(function () { + // always executed + }); + +// Optionally the request above could also be done as +axios.get('/user', { + params: { + ID: 12345 + } + }) + .then(function (response) { + console.log(response); + }) + .catch(function (error) { + console.log(error); + }) + .then(function () { + // always executed + }); + +// Want to use async/await? Add the `async` keyword to your outer function/method. +async function getUser() { + try { + const response = await axios.get('/user?ID=12345'); + console.log(response); + } catch (error) { + console.error(error); + } +} +``` + +> **NOTE:** `async/await` is part of ECMAScript 2017 and is not supported in Internet +> Explorer and older browsers, so use with caution. + +Performing a `POST` request + +```js +axios.post('/user', { + firstName: 'Fred', + lastName: 'Flintstone' + }) + .then(function (response) { + console.log(response); + }) + .catch(function (error) { + console.log(error); + }); +``` + +Performing multiple concurrent requests + +```js +function getUserAccount() { + return axios.get('/user/12345'); +} + +function getUserPermissions() { + return axios.get('/user/12345/permissions'); +} + +Promise.all([getUserAccount(), getUserPermissions()]) + .then(function (results) { + const acct = results[0]; + const perm = results[1]; + }); +``` + +## axios API + +Requests can be made by passing the relevant config to `axios`. + +##### axios(config) + +```js +// Send a POST request +axios({ + method: 'post', + url: '/user/12345', + data: { + firstName: 'Fred', + lastName: 'Flintstone' + } +}); +``` + +```js +// GET request for remote image in node.js +axios({ + method: 'get', + url: 'http://bit.ly/2mTM3nY', + responseType: 'stream' +}) + .then(function (response) { + response.data.pipe(fs.createWriteStream('ada_lovelace.jpg')) + }); +``` + +##### axios(url[, config]) + +```js +// Send a GET request (default method) +axios('/user/12345'); +``` + +### Request method aliases + +For convenience aliases have been provided for all supported request methods. + +##### axios.request(config) +##### axios.get(url[, config]) +##### axios.delete(url[, config]) +##### axios.head(url[, config]) +##### axios.options(url[, config]) +##### axios.post(url[, data[, config]]) +##### axios.put(url[, data[, config]]) +##### axios.patch(url[, data[, config]]) + +###### NOTE +When using the alias methods `url`, `method`, and `data` properties don't need to be specified in config. + +### Concurrency (Deprecated) +Please use `Promise.all` to replace the below functions. + +Helper functions for dealing with concurrent requests. + +axios.all(iterable) +axios.spread(callback) + +### Creating an instance + +You can create a new instance of axios with a custom config. + +##### axios.create([config]) + +```js +const instance = axios.create({ + baseURL: 'https://some-domain.com/api/', + timeout: 1000, + headers: {'X-Custom-Header': 'foobar'} +}); +``` + +### Instance methods + +The available instance methods are listed below. The specified config will be merged with the instance config. + +##### axios#request(config) +##### axios#get(url[, config]) +##### axios#delete(url[, config]) +##### axios#head(url[, config]) +##### axios#options(url[, config]) +##### axios#post(url[, data[, config]]) +##### axios#put(url[, data[, config]]) +##### axios#patch(url[, data[, config]]) +##### axios#getUri([config]) + +## Request Config + +These are the available config options for making requests. Only the `url` is required. Requests will default to `GET` if `method` is not specified. + +```js +{ + // `url` is the server URL that will be used for the request + url: '/user', + + // `method` is the request method to be used when making the request + method: 'get', // default + + // `baseURL` will be prepended to `url` unless `url` is absolute. + // It can be convenient to set `baseURL` for an instance of axios to pass relative URLs + // to methods of that instance. + baseURL: 'https://some-domain.com/api/', + + // `transformRequest` allows changes to the request data before it is sent to the server + // This is only applicable for request methods 'PUT', 'POST', 'PATCH' and 'DELETE' + // The last function in the array must return a string or an instance of Buffer, ArrayBuffer, + // FormData or Stream + // You may modify the headers object. + transformRequest: [function (data, headers) { + // Do whatever you want to transform the data + + return data; + }], + + // `transformResponse` allows changes to the response data to be made before + // it is passed to then/catch + transformResponse: [function (data) { + // Do whatever you want to transform the data + + return data; + }], + + // `headers` are custom headers to be sent + headers: {'X-Requested-With': 'XMLHttpRequest'}, + + // `params` are the URL parameters to be sent with the request + // Must be a plain object or a URLSearchParams object + params: { + ID: 12345 + }, + + // `paramsSerializer` is an optional function in charge of serializing `params` + // (e.g. https://www.npmjs.com/package/qs, http://api.jquery.com/jquery.param/) + paramsSerializer: function (params) { + return Qs.stringify(params, {arrayFormat: 'brackets'}) + }, + + // `data` is the data to be sent as the request body + // Only applicable for request methods 'PUT', 'POST', 'DELETE , and 'PATCH' + // When no `transformRequest` is set, must be of one of the following types: + // - string, plain object, ArrayBuffer, ArrayBufferView, URLSearchParams + // - Browser only: FormData, File, Blob + // - Node only: Stream, Buffer + data: { + firstName: 'Fred' + }, + + // syntax alternative to send data into the body + // method post + // only the value is sent, not the key + data: 'Country=Brasil&City=Belo Horizonte', + + // `timeout` specifies the number of milliseconds before the request times out. + // If the request takes longer than `timeout`, the request will be aborted. + timeout: 1000, // default is `0` (no timeout) + + // `withCredentials` indicates whether or not cross-site Access-Control requests + // should be made using credentials + withCredentials: false, // default + + // `adapter` allows custom handling of requests which makes testing easier. + // Return a promise and supply a valid response (see lib/adapters/README.md). + adapter: function (config) { + /* ... */ + }, + + // `auth` indicates that HTTP Basic auth should be used, and supplies credentials. + // This will set an `Authorization` header, overwriting any existing + // `Authorization` custom headers you have set using `headers`. + // Please note that only HTTP Basic auth is configurable through this parameter. + // For Bearer tokens and such, use `Authorization` custom headers instead. + auth: { + username: 'janedoe', + password: 's00pers3cret' + }, + + // `responseType` indicates the type of data that the server will respond with + // options are: 'arraybuffer', 'document', 'json', 'text', 'stream' + // browser only: 'blob' + responseType: 'json', // default + + // `responseEncoding` indicates encoding to use for decoding responses (Node.js only) + // Note: Ignored for `responseType` of 'stream' or client-side requests + responseEncoding: 'utf8', // default + + // `xsrfCookieName` is the name of the cookie to use as a value for xsrf token + xsrfCookieName: 'XSRF-TOKEN', // default + + // `xsrfHeaderName` is the name of the http header that carries the xsrf token value + xsrfHeaderName: 'X-XSRF-TOKEN', // default + + // `onUploadProgress` allows handling of progress events for uploads + // browser only + onUploadProgress: function (progressEvent) { + // Do whatever you want with the native progress event + }, + + // `onDownloadProgress` allows handling of progress events for downloads + // browser only + onDownloadProgress: function (progressEvent) { + // Do whatever you want with the native progress event + }, + + // `maxContentLength` defines the max size of the http response content in bytes allowed in node.js + maxContentLength: 2000, + + // `maxBodyLength` (Node only option) defines the max size of the http request content in bytes allowed + maxBodyLength: 2000, + + // `validateStatus` defines whether to resolve or reject the promise for a given + // HTTP response status code. If `validateStatus` returns `true` (or is set to `null` + // or `undefined`), the promise will be resolved; otherwise, the promise will be + // rejected. + validateStatus: function (status) { + return status >= 200 && status < 300; // default + }, + + // `maxRedirects` defines the maximum number of redirects to follow in node.js. + // If set to 0, no redirects will be followed. + maxRedirects: 5, // default + + // `socketPath` defines a UNIX Socket to be used in node.js. + // e.g. '/var/run/docker.sock' to send requests to the docker daemon. + // Only either `socketPath` or `proxy` can be specified. + // If both are specified, `socketPath` is used. + socketPath: null, // default + + // `httpAgent` and `httpsAgent` define a custom agent to be used when performing http + // and https requests, respectively, in node.js. This allows options to be added like + // `keepAlive` that are not enabled by default. + httpAgent: new http.Agent({ keepAlive: true }), + httpsAgent: new https.Agent({ keepAlive: true }), + + // `proxy` defines the hostname, port, and protocol of the proxy server. + // You can also define your proxy using the conventional `http_proxy` and + // `https_proxy` environment variables. If you are using environment variables + // for your proxy configuration, you can also define a `no_proxy` environment + // variable as a comma-separated list of domains that should not be proxied. + // Use `false` to disable proxies, ignoring environment variables. + // `auth` indicates that HTTP Basic auth should be used to connect to the proxy, and + // supplies credentials. + // This will set an `Proxy-Authorization` header, overwriting any existing + // `Proxy-Authorization` custom headers you have set using `headers`. + // If the proxy server uses HTTPS, then you must set the protocol to `https`. + proxy: { + protocol: 'https', + host: '127.0.0.1', + port: 9000, + auth: { + username: 'mikeymike', + password: 'rapunz3l' + } + }, + + // `cancelToken` specifies a cancel token that can be used to cancel the request + // (see Cancellation section below for details) + cancelToken: new CancelToken(function (cancel) { + }), + + // an alternative way to cancel Axios requests using AbortController + signal: new AbortController().signal, + + // `decompress` indicates whether or not the response body should be decompressed + // automatically. If set to `true` will also remove the 'content-encoding' header + // from the responses objects of all decompressed responses + // - Node only (XHR cannot turn off decompression) + decompress: true // default + + // `insecureHTTPParser` boolean. + // Indicates where to use an insecure HTTP parser that accepts invalid HTTP headers. + // This may allow interoperability with non-conformant HTTP implementations. + // Using the insecure parser should be avoided. + // see options https://nodejs.org/dist/latest-v12.x/docs/api/http.html#http_http_request_url_options_callback + // see also https://nodejs.org/en/blog/vulnerability/february-2020-security-releases/#strict-http-header-parsing-none + insecureHTTPParser: undefined // default + + // transitional options for backward compatibility that may be removed in the newer versions + transitional: { + // silent JSON parsing mode + // `true` - ignore JSON parsing errors and set response.data to null if parsing failed (old behaviour) + // `false` - throw SyntaxError if JSON parsing failed (Note: responseType must be set to 'json') + silentJSONParsing: true, // default value for the current Axios version + + // try to parse the response string as JSON even if `responseType` is not 'json' + forcedJSONParsing: true, + + // throw ETIMEDOUT error instead of generic ECONNABORTED on request timeouts + clarifyTimeoutError: false, + } +} +``` + +## Response Schema + +The response for a request contains the following information. + +```js +{ + // `data` is the response that was provided by the server + data: {}, + + // `status` is the HTTP status code from the server response + status: 200, + + // `statusText` is the HTTP status message from the server response + statusText: 'OK', + + // `headers` the HTTP headers that the server responded with + // All header names are lower cased and can be accessed using the bracket notation. + // Example: `response.headers['content-type']` + headers: {}, + + // `config` is the config that was provided to `axios` for the request + config: {}, + + // `request` is the request that generated this response + // It is the last ClientRequest instance in node.js (in redirects) + // and an XMLHttpRequest instance in the browser + request: {} +} +``` + +When using `then`, you will receive the response as follows: + +```js +axios.get('/user/12345') + .then(function (response) { + console.log(response.data); + console.log(response.status); + console.log(response.statusText); + console.log(response.headers); + console.log(response.config); + }); +``` + +When using `catch`, or passing a [rejection callback](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/then) as second parameter of `then`, the response will be available through the `error` object as explained in the [Handling Errors](#handling-errors) section. + +## Config Defaults + +You can specify config defaults that will be applied to every request. + +### Global axios defaults + +```js +axios.defaults.baseURL = 'https://api.example.com'; + +// Important: If axios is used with multiple domains, the AUTH_TOKEN will be sent to all of them. +// See below for an example using Custom instance defaults instead. +axios.defaults.headers.common['Authorization'] = AUTH_TOKEN; + +axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded'; +``` + +### Custom instance defaults + +```js +// Set config defaults when creating the instance +const instance = axios.create({ + baseURL: 'https://api.example.com' +}); + +// Alter defaults after instance has been created +instance.defaults.headers.common['Authorization'] = AUTH_TOKEN; +``` + +### Config order of precedence + +Config will be merged with an order of precedence. The order is library defaults found in [lib/defaults.js](https://github.com/axios/axios/blob/master/lib/defaults.js#L28), then `defaults` property of the instance, and finally `config` argument for the request. The latter will take precedence over the former. Here's an example. + +```js +// Create an instance using the config defaults provided by the library +// At this point the timeout config value is `0` as is the default for the library +const instance = axios.create(); + +// Override timeout default for the library +// Now all requests using this instance will wait 2.5 seconds before timing out +instance.defaults.timeout = 2500; + +// Override timeout for this request as it's known to take a long time +instance.get('/longRequest', { + timeout: 5000 +}); +``` + +## Interceptors + +You can intercept requests or responses before they are handled by `then` or `catch`. + +```js +// Add a request interceptor +axios.interceptors.request.use(function (config) { + // Do something before request is sent + return config; + }, function (error) { + // Do something with request error + return Promise.reject(error); + }); + +// Add a response interceptor +axios.interceptors.response.use(function (response) { + // Any status code that lie within the range of 2xx cause this function to trigger + // Do something with response data + return response; + }, function (error) { + // Any status codes that falls outside the range of 2xx cause this function to trigger + // Do something with response error + return Promise.reject(error); + }); +``` + +If you need to remove an interceptor later you can. + +```js +const myInterceptor = axios.interceptors.request.use(function () {/*...*/}); +axios.interceptors.request.eject(myInterceptor); +``` + +You can add interceptors to a custom instance of axios. + +```js +const instance = axios.create(); +instance.interceptors.request.use(function () {/*...*/}); +``` + +When you add request interceptors, they are presumed to be asynchronous by default. This can cause a delay +in the execution of your axios request when the main thread is blocked (a promise is created under the hood for +the interceptor and your request gets put on the bottom of the call stack). If your request interceptors are synchronous you can add a flag +to the options object that will tell axios to run the code synchronously and avoid any delays in request execution. + +```js +axios.interceptors.request.use(function (config) { + config.headers.test = 'I am only a header!'; + return config; +}, null, { synchronous: true }); +``` + +If you want to execute a particular interceptor based on a runtime check, +you can add a `runWhen` function to the options object. The interceptor will not be executed **if and only if** the return +of `runWhen` is `false`. The function will be called with the config +object (don't forget that you can bind your own arguments to it as well.) This can be handy when you have an +asynchronous request interceptor that only needs to run at certain times. + +```js +function onGetCall(config) { + return config.method === 'get'; +} +axios.interceptors.request.use(function (config) { + config.headers.test = 'special get headers'; + return config; +}, null, { runWhen: onGetCall }); +``` + +### Multiple Interceptors + +Given you add multiple response interceptors +and when the response was fulfilled +- then each interceptor is executed +- then they are executed in the order they were added +- then only the last interceptor's result is returned +- then every interceptor receives the result of it's predecessor +- and when the fulfillment-interceptor throws + - then the following fulfillment-interceptor is not called + - then the following rejection-interceptor is called + - once caught, another following fulfill-interceptor is called again (just like in a promise chain). + +Read [the interceptor tests](./test/specs/interceptors.spec.js) for seeing all this in code. + +## Handling Errors + +```js +axios.get('/user/12345') + .catch(function (error) { + if (error.response) { + // The request was made and the server responded with a status code + // that falls out of the range of 2xx + console.log(error.response.data); + console.log(error.response.status); + console.log(error.response.headers); + } else if (error.request) { + // The request was made but no response was received + // `error.request` is an instance of XMLHttpRequest in the browser and an instance of + // http.ClientRequest in node.js + console.log(error.request); + } else { + // Something happened in setting up the request that triggered an Error + console.log('Error', error.message); + } + console.log(error.config); + }); +``` + +Using the `validateStatus` config option, you can define HTTP code(s) that should throw an error. + +```js +axios.get('/user/12345', { + validateStatus: function (status) { + return status < 500; // Resolve only if the status code is less than 500 + } +}) +``` + +Using `toJSON` you get an object with more information about the HTTP error. + +```js +axios.get('/user/12345') + .catch(function (error) { + console.log(error.toJSON()); + }); +``` + +## Cancellation + +You can cancel a request using a *cancel token*. + +> The axios cancel token API is based on the withdrawn [cancelable promises proposal](https://github.com/tc39/proposal-cancelable-promises). + +You can create a cancel token using the `CancelToken.source` factory as shown below: + +```js +const CancelToken = axios.CancelToken; +const source = CancelToken.source(); + +axios.get('/user/12345', { + cancelToken: source.token +}).catch(function (thrown) { + if (axios.isCancel(thrown)) { + console.log('Request canceled', thrown.message); + } else { + // handle error + } +}); + +axios.post('/user/12345', { + name: 'new name' +}, { + cancelToken: source.token +}) + +// cancel the request (the message parameter is optional) +source.cancel('Operation canceled by the user.'); +``` + +You can also create a cancel token by passing an executor function to the `CancelToken` constructor: + +```js +const CancelToken = axios.CancelToken; +let cancel; + +axios.get('/user/12345', { + cancelToken: new CancelToken(function executor(c) { + // An executor function receives a cancel function as a parameter + cancel = c; + }) +}); + +// cancel the request +cancel(); +``` + +Axios supports AbortController to abort requests in [`fetch API`](https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API#aborting_a_fetch) way: +```js +const controller = new AbortController(); + +axios.get('/foo/bar', { + signal: controller.signal +}).then(function(response) { + //... +}); +// cancel the request +controller.abort() +``` + +> Note: you can cancel several requests with the same cancel token/abort controller. +> If a cancellation token is already cancelled at the moment of starting an Axios request, then the request is cancelled immediately, without any attempts to make real request. + +## Using application/x-www-form-urlencoded format + +By default, axios serializes JavaScript objects to `JSON`. To send data in the `application/x-www-form-urlencoded` format instead, you can use one of the following options. + +### Browser + +In a browser, you can use the [`URLSearchParams`](https://developer.mozilla.org/en-US/docs/Web/API/URLSearchParams) API as follows: + +```js +const params = new URLSearchParams(); +params.append('param1', 'value1'); +params.append('param2', 'value2'); +axios.post('/foo', params); +``` + +> Note that `URLSearchParams` is not supported by all browsers (see [caniuse.com](http://www.caniuse.com/#feat=urlsearchparams)), but there is a [polyfill](https://github.com/WebReflection/url-search-params) available (make sure to polyfill the global environment). + +Alternatively, you can encode data using the [`qs`](https://github.com/ljharb/qs) library: + +```js +const qs = require('qs'); +axios.post('/foo', qs.stringify({ 'bar': 123 })); +``` + +Or in another way (ES6), + +```js +import qs from 'qs'; +const data = { 'bar': 123 }; +const options = { + method: 'POST', + headers: { 'content-type': 'application/x-www-form-urlencoded' }, + data: qs.stringify(data), + url, +}; +axios(options); +``` + +### Node.js + +#### Query string + +In node.js, you can use the [`querystring`](https://nodejs.org/api/querystring.html) module as follows: + +```js +const querystring = require('querystring'); +axios.post('http://something.com/', querystring.stringify({ foo: 'bar' })); +``` + +or ['URLSearchParams'](https://nodejs.org/api/url.html#url_class_urlsearchparams) from ['url module'](https://nodejs.org/api/url.html) as follows: + +```js +const url = require('url'); +const params = new url.URLSearchParams({ foo: 'bar' }); +axios.post('http://something.com/', params.toString()); +``` + +You can also use the [`qs`](https://github.com/ljharb/qs) library. + +###### NOTE +The `qs` library is preferable if you need to stringify nested objects, as the `querystring` method has known issues with that use case (https://github.com/nodejs/node-v0.x-archive/issues/1665). + +#### Form data + +In node.js, you can use the [`form-data`](https://github.com/form-data/form-data) library as follows: + +```js +const FormData = require('form-data'); + +const form = new FormData(); +form.append('my_field', 'my value'); +form.append('my_buffer', new Buffer(10)); +form.append('my_file', fs.createReadStream('/foo/bar.jpg')); + +axios.post('https://example.com', form, { headers: form.getHeaders() }) +``` + +Alternatively, use an interceptor: + +```js +axios.interceptors.request.use(config => { + if (config.data instanceof FormData) { + Object.assign(config.headers, config.data.getHeaders()); + } + return config; +}); +``` + +## Semver + +Until axios reaches a `1.0` release, breaking changes will be released with a new minor version. For example `0.5.1`, and `0.5.4` will have the same API, but `0.6.0` will have breaking changes. + +## Promises + +axios depends on a native ES6 Promise implementation to be [supported](http://caniuse.com/promises). +If your environment doesn't support ES6 Promises, you can [polyfill](https://github.com/jakearchibald/es6-promise). + +## TypeScript + +axios includes [TypeScript](http://typescriptlang.org) definitions and a type guard for axios errors. + +```typescript +let user: User = null; +try { + const { data } = await axios.get('/user?ID=12345'); + user = data.userDetails; +} catch (error) { + if (axios.isAxiosError(error)) { + handleAxiosError(error); + } else { + handleUnexpectedError(error); + } +} +``` + +## Online one-click setup + +You can use Gitpod an online IDE(which is free for Open Source) for contributing or running the examples online. + +[![Open in Gitpod](https://gitpod.io/button/open-in-gitpod.svg)](https://gitpod.io/#https://github.com/axios/axios/blob/master/examples/server.js) + + +## Resources + +* [Changelog](https://github.com/axios/axios/blob/master/CHANGELOG.md) +* [Upgrade Guide](https://github.com/axios/axios/blob/master/UPGRADE_GUIDE.md) +* [Ecosystem](https://github.com/axios/axios/blob/master/ECOSYSTEM.md) +* [Contributing Guide](https://github.com/axios/axios/blob/master/CONTRIBUTING.md) +* [Code of Conduct](https://github.com/axios/axios/blob/master/CODE_OF_CONDUCT.md) + +## Credits + +axios is heavily inspired by the [$http service](https://docs.angularjs.org/api/ng/service/$http) provided in [AngularJS](https://angularjs.org/). Ultimately axios is an effort to provide a standalone `$http`-like service for use outside of AngularJS. + +## License + +[MIT](LICENSE) diff --git a/node_modules/axios/SECURITY.md b/node_modules/axios/SECURITY.md new file mode 100644 index 0000000..353df9a --- /dev/null +++ b/node_modules/axios/SECURITY.md @@ -0,0 +1,5 @@ +# Security Policy + +## Reporting a Vulnerability + +Please report security issues to jasonsaayman@gmail.com diff --git a/node_modules/axios/UPGRADE_GUIDE.md b/node_modules/axios/UPGRADE_GUIDE.md new file mode 100644 index 0000000..fdcff1a --- /dev/null +++ b/node_modules/axios/UPGRADE_GUIDE.md @@ -0,0 +1,168 @@ +# Upgrade Guide + +### 0.18.x -> 0.19.0 + +#### HTTPS Proxies + +Routing through an https proxy now requires setting the `protocol` attribute of the proxy configuration to `https` + +### 0.15.x -> 0.16.0 + +#### `Promise` Type Declarations + +The `Promise` type declarations have been removed from the axios typings in favor of the built-in type declarations. If you use axios in a TypeScript project that targets `ES5`, please make sure to include the `es2015.promise` lib. Please see [this post](https://blog.mariusschulz.com/2016/11/25/typescript-2-0-built-in-type-declarations) for details. + +### 0.13.x -> 0.14.0 + +#### TypeScript Definitions + +The axios TypeScript definitions have been updated to match the axios API and use the ES2015 module syntax. + +Please use the following `import` statement to import axios in TypeScript: + +```typescript +import axios from 'axios'; + +axios.get('/foo') + .then(response => console.log(response)) + .catch(error => console.log(error)); +``` + +#### `agent` Config Option + +The `agent` config option has been replaced with two new options: `httpAgent` and `httpsAgent`. Please use them instead. + +```js +{ + // Define a custom agent for HTTP + httpAgent: new http.Agent({ keepAlive: true }), + // Define a custom agent for HTTPS + httpsAgent: new https.Agent({ keepAlive: true }) +} +``` + +#### `progress` Config Option + +The `progress` config option has been replaced with the `onUploadProgress` and `onDownloadProgress` options. + +```js +{ + // Define a handler for upload progress events + onUploadProgress: function (progressEvent) { + // ... + }, + + // Define a handler for download progress events + onDownloadProgress: function (progressEvent) { + // ... + } +} +``` + +### 0.12.x -> 0.13.0 + +The `0.13.0` release contains several changes to custom adapters and error handling. + +#### Error Handling + +Previous to this release an error could either be a server response with bad status code or an actual `Error`. With this release Promise will always reject with an `Error`. In the case that a response was received, the `Error` will also include the response. + +```js +axios.get('/user/12345') + .catch((error) => { + console.log(error.message); + console.log(error.code); // Not always specified + console.log(error.config); // The config that was used to make the request + console.log(error.response); // Only available if response was received from the server + }); +``` + +#### Request Adapters + +This release changes a few things about how request adapters work. Please take note if you are using your own custom adapter. + +1. Response transformer is now called outside of adapter. +2. Request adapter returns a `Promise`. + +This means that you no longer need to invoke `transformData` on response data. You will also no longer receive `resolve` and `reject` as arguments in your adapter. + +Previous code: + +```js +function myAdapter(resolve, reject, config) { + var response = { + data: transformData( + responseData, + responseHeaders, + config.transformResponse + ), + status: request.status, + statusText: request.statusText, + headers: responseHeaders + }; + settle(resolve, reject, response); +} +``` + +New code: + +```js +function myAdapter(config) { + return new Promise(function (resolve, reject) { + var response = { + data: responseData, + status: request.status, + statusText: request.statusText, + headers: responseHeaders + }; + settle(resolve, reject, response); + }); +} +``` + +See the related commits for more details: +- [Response transformers](https://github.com/axios/axios/commit/10eb23865101f9347570552c04e9d6211376e25e) +- [Request adapter Promise](https://github.com/axios/axios/commit/157efd5615890301824e3121cc6c9d2f9b21f94a) + +### 0.5.x -> 0.6.0 + +The `0.6.0` release contains mostly bug fixes, but there are a couple things to be aware of when upgrading. + +#### ES6 Promise Polyfill + +Up until the `0.6.0` release ES6 `Promise` was being polyfilled using [es6-promise](https://github.com/jakearchibald/es6-promise). With this release, the polyfill has been removed, and you will need to supply it yourself if your environment needs it. + +```js +require('es6-promise').polyfill(); +var axios = require('axios'); +``` + +This will polyfill the global environment, and only needs to be done once. + +#### `axios.success`/`axios.error` + +The `success`, and `error` aliases were deprecated in [0.4.0](https://github.com/axios/axios/blob/master/CHANGELOG.md#040-oct-03-2014). As of this release they have been removed entirely. Instead please use `axios.then`, and `axios.catch` respectively. + +```js +axios.get('some/url') + .then(function (res) { + /* ... */ + }) + .catch(function (err) { + /* ... */ + }); +``` + +#### UMD + +Previous versions of axios shipped with an AMD, CommonJS, and Global build. This has all been rolled into a single UMD build. + +```js +// AMD +require(['bower_components/axios/dist/axios'], function (axios) { + /* ... */ +}); + +// CommonJS +var axios = require('axios/dist/axios'); +``` diff --git a/node_modules/axios/dist/axios.js b/node_modules/axios/dist/axios.js new file mode 100644 index 0000000..e78f7ca --- /dev/null +++ b/node_modules/axios/dist/axios.js @@ -0,0 +1,2293 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(); + else if(typeof define === 'function' && define.amd) + define([], factory); + else if(typeof exports === 'object') + exports["axios"] = factory(); + else + root["axios"] = factory(); +})(this, function() { +return /******/ (function(modules) { // webpackBootstrap +/******/ // The module cache +/******/ var installedModules = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ +/******/ // Check if module is in cache +/******/ if(installedModules[moduleId]) { +/******/ return installedModules[moduleId].exports; +/******/ } +/******/ // Create a new module (and put it into the cache) +/******/ var module = installedModules[moduleId] = { +/******/ i: moduleId, +/******/ l: false, +/******/ exports: {} +/******/ }; +/******/ +/******/ // Execute the module function +/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); +/******/ +/******/ // Flag the module as loaded +/******/ module.l = true; +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/******/ +/******/ // expose the modules object (__webpack_modules__) +/******/ __webpack_require__.m = modules; +/******/ +/******/ // expose the module cache +/******/ __webpack_require__.c = installedModules; +/******/ +/******/ // define getter function for harmony exports +/******/ __webpack_require__.d = function(exports, name, getter) { +/******/ if(!__webpack_require__.o(exports, name)) { +/******/ Object.defineProperty(exports, name, { enumerable: true, get: getter }); +/******/ } +/******/ }; +/******/ +/******/ // define __esModule on exports +/******/ __webpack_require__.r = function(exports) { +/******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) { +/******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' }); +/******/ } +/******/ Object.defineProperty(exports, '__esModule', { value: true }); +/******/ }; +/******/ +/******/ // create a fake namespace object +/******/ // mode & 1: value is a module id, require it +/******/ // mode & 2: merge all properties of value into the ns +/******/ // mode & 4: return value when already ns object +/******/ // mode & 8|1: behave like require +/******/ __webpack_require__.t = function(value, mode) { +/******/ if(mode & 1) value = __webpack_require__(value); +/******/ if(mode & 8) return value; +/******/ if((mode & 4) && typeof value === 'object' && value && value.__esModule) return value; +/******/ var ns = Object.create(null); +/******/ __webpack_require__.r(ns); +/******/ Object.defineProperty(ns, 'default', { enumerable: true, value: value }); +/******/ if(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key)); +/******/ return ns; +/******/ }; +/******/ +/******/ // getDefaultExport function for compatibility with non-harmony modules +/******/ __webpack_require__.n = function(module) { +/******/ var getter = module && module.__esModule ? +/******/ function getDefault() { return module['default']; } : +/******/ function getModuleExports() { return module; }; +/******/ __webpack_require__.d(getter, 'a', getter); +/******/ return getter; +/******/ }; +/******/ +/******/ // Object.prototype.hasOwnProperty.call +/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); }; +/******/ +/******/ // __webpack_public_path__ +/******/ __webpack_require__.p = ""; +/******/ +/******/ +/******/ // Load entry module and return exports +/******/ return __webpack_require__(__webpack_require__.s = "./index.js"); +/******/ }) +/************************************************************************/ +/******/ ({ + +/***/ "./index.js": +/*!******************!*\ + !*** ./index.js ***! + \******************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +module.exports = __webpack_require__(/*! ./lib/axios */ "./lib/axios.js"); + +/***/ }), + +/***/ "./lib/adapters/xhr.js": +/*!*****************************!*\ + !*** ./lib/adapters/xhr.js ***! + \*****************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); +var settle = __webpack_require__(/*! ./../core/settle */ "./lib/core/settle.js"); +var cookies = __webpack_require__(/*! ./../helpers/cookies */ "./lib/helpers/cookies.js"); +var buildURL = __webpack_require__(/*! ./../helpers/buildURL */ "./lib/helpers/buildURL.js"); +var buildFullPath = __webpack_require__(/*! ../core/buildFullPath */ "./lib/core/buildFullPath.js"); +var parseHeaders = __webpack_require__(/*! ./../helpers/parseHeaders */ "./lib/helpers/parseHeaders.js"); +var isURLSameOrigin = __webpack_require__(/*! ./../helpers/isURLSameOrigin */ "./lib/helpers/isURLSameOrigin.js"); +var createError = __webpack_require__(/*! ../core/createError */ "./lib/core/createError.js"); +var transitionalDefaults = __webpack_require__(/*! ../defaults/transitional */ "./lib/defaults/transitional.js"); +var Cancel = __webpack_require__(/*! ../cancel/Cancel */ "./lib/cancel/Cancel.js"); + +module.exports = function xhrAdapter(config) { + return new Promise(function dispatchXhrRequest(resolve, reject) { + var requestData = config.data; + var requestHeaders = config.headers; + var responseType = config.responseType; + var onCanceled; + function done() { + if (config.cancelToken) { + config.cancelToken.unsubscribe(onCanceled); + } + + if (config.signal) { + config.signal.removeEventListener('abort', onCanceled); + } + } + + if (utils.isFormData(requestData)) { + delete requestHeaders['Content-Type']; // Let the browser set it + } + + var request = new XMLHttpRequest(); + + // HTTP basic authentication + if (config.auth) { + var username = config.auth.username || ''; + var password = config.auth.password ? unescape(encodeURIComponent(config.auth.password)) : ''; + requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password); + } + + var 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 + var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null; + var responseData = !responseType || responseType === 'text' || responseType === 'json' ? + request.responseText : request.response; + var response = { + data: responseData, + status: request.status, + statusText: request.statusText, + headers: responseHeaders, + config: config, + request: 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(createError('Request aborted', config, 'ECONNABORTED', 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(createError('Network Error', config, null, request)); + + // Clean up request + request = null; + }; + + // Handle timeout + request.ontimeout = function handleTimeout() { + var timeoutErrorMessage = config.timeout ? 'timeout of ' + config.timeout + 'ms exceeded' : 'timeout exceeded'; + var transitional = config.transitional || transitionalDefaults; + if (config.timeoutErrorMessage) { + timeoutErrorMessage = config.timeoutErrorMessage; + } + reject(createError( + timeoutErrorMessage, + config, + transitional.clarifyTimeoutError ? 'ETIMEDOUT' : 'ECONNABORTED', + 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 (utils.isStandardBrowserEnv()) { + // Add xsrf header + var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ? + cookies.read(config.xsrfCookieName) : + undefined; + + if (xsrfValue) { + requestHeaders[config.xsrfHeaderName] = xsrfValue; + } + } + + // Add headers to the request + if ('setRequestHeader' in request) { + utils.forEach(requestHeaders, function setRequestHeader(val, key) { + if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { + // Remove Content-Type if data is undefined + delete requestHeaders[key]; + } else { + // Otherwise add header to the request + request.setRequestHeader(key, val); + } + }); + } + + // Add withCredentials to request if needed + if (!utils.isUndefined(config.withCredentials)) { + request.withCredentials = !!config.withCredentials; + } + + // Add responseType to request if needed + if (responseType && responseType !== 'json') { + request.responseType = config.responseType; + } + + // Handle progress if needed + if (typeof config.onDownloadProgress === 'function') { + request.addEventListener('progress', config.onDownloadProgress); + } + + // Not all browsers support upload events + if (typeof config.onUploadProgress === 'function' && request.upload) { + request.upload.addEventListener('progress', config.onUploadProgress); + } + + if (config.cancelToken || config.signal) { + // Handle cancellation + // eslint-disable-next-line func-names + onCanceled = function(cancel) { + if (!request) { + return; + } + reject(!cancel || (cancel && cancel.type) ? new Cancel('canceled') : cancel); + request.abort(); + request = null; + }; + + config.cancelToken && config.cancelToken.subscribe(onCanceled); + if (config.signal) { + config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled); + } + } + + if (!requestData) { + requestData = null; + } + + // Send the request + request.send(requestData); + }); +}; + + +/***/ }), + +/***/ "./lib/axios.js": +/*!**********************!*\ + !*** ./lib/axios.js ***! + \**********************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./utils */ "./lib/utils.js"); +var bind = __webpack_require__(/*! ./helpers/bind */ "./lib/helpers/bind.js"); +var Axios = __webpack_require__(/*! ./core/Axios */ "./lib/core/Axios.js"); +var mergeConfig = __webpack_require__(/*! ./core/mergeConfig */ "./lib/core/mergeConfig.js"); +var defaults = __webpack_require__(/*! ./defaults */ "./lib/defaults/index.js"); + +/** + * Create an instance of Axios + * + * @param {Object} defaultConfig The default config for the instance + * @return {Axios} A new instance of Axios + */ +function createInstance(defaultConfig) { + var context = new Axios(defaultConfig); + var instance = bind(Axios.prototype.request, context); + + // Copy axios.prototype to instance + utils.extend(instance, Axios.prototype, context); + + // Copy context to instance + utils.extend(instance, context); + + // Factory for creating new instances + instance.create = function create(instanceConfig) { + return createInstance(mergeConfig(defaultConfig, instanceConfig)); + }; + + return instance; +} + +// Create the default instance to be exported +var axios = createInstance(defaults); + +// Expose Axios class to allow class inheritance +axios.Axios = Axios; + +// Expose Cancel & CancelToken +axios.Cancel = __webpack_require__(/*! ./cancel/Cancel */ "./lib/cancel/Cancel.js"); +axios.CancelToken = __webpack_require__(/*! ./cancel/CancelToken */ "./lib/cancel/CancelToken.js"); +axios.isCancel = __webpack_require__(/*! ./cancel/isCancel */ "./lib/cancel/isCancel.js"); +axios.VERSION = __webpack_require__(/*! ./env/data */ "./lib/env/data.js").version; + +// Expose all/spread +axios.all = function all(promises) { + return Promise.all(promises); +}; +axios.spread = __webpack_require__(/*! ./helpers/spread */ "./lib/helpers/spread.js"); + +// Expose isAxiosError +axios.isAxiosError = __webpack_require__(/*! ./helpers/isAxiosError */ "./lib/helpers/isAxiosError.js"); + +module.exports = axios; + +// Allow use of default import syntax in TypeScript +module.exports.default = axios; + + +/***/ }), + +/***/ "./lib/cancel/Cancel.js": +/*!******************************!*\ + !*** ./lib/cancel/Cancel.js ***! + \******************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +/** + * A `Cancel` is an object that is thrown when an operation is canceled. + * + * @class + * @param {string=} message The message. + */ +function Cancel(message) { + this.message = message; +} + +Cancel.prototype.toString = function toString() { + return 'Cancel' + (this.message ? ': ' + this.message : ''); +}; + +Cancel.prototype.__CANCEL__ = true; + +module.exports = Cancel; + + +/***/ }), + +/***/ "./lib/cancel/CancelToken.js": +/*!***********************************!*\ + !*** ./lib/cancel/CancelToken.js ***! + \***********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var Cancel = __webpack_require__(/*! ./Cancel */ "./lib/cancel/Cancel.js"); + +/** + * A `CancelToken` is an object that can be used to request cancellation of an operation. + * + * @class + * @param {Function} executor The executor function. + */ +function CancelToken(executor) { + if (typeof executor !== 'function') { + throw new TypeError('executor must be a function.'); + } + + var resolvePromise; + + this.promise = new Promise(function promiseExecutor(resolve) { + resolvePromise = resolve; + }); + + var token = this; + + // eslint-disable-next-line func-names + this.promise.then(function(cancel) { + if (!token._listeners) return; + + var i; + var l = token._listeners.length; + + for (i = 0; i < l; i++) { + token._listeners[i](cancel); + } + token._listeners = null; + }); + + // eslint-disable-next-line func-names + this.promise.then = function(onfulfilled) { + var _resolve; + // eslint-disable-next-line func-names + var promise = new Promise(function(resolve) { + token.subscribe(resolve); + _resolve = resolve; + }).then(onfulfilled); + + promise.cancel = function reject() { + token.unsubscribe(_resolve); + }; + + return promise; + }; + + executor(function cancel(message) { + if (token.reason) { + // Cancellation has already been requested + return; + } + + token.reason = new Cancel(message); + resolvePromise(token.reason); + }); +} + +/** + * Throws a `Cancel` if cancellation has been requested. + */ +CancelToken.prototype.throwIfRequested = function throwIfRequested() { + if (this.reason) { + throw this.reason; + } +}; + +/** + * Subscribe to the cancel signal + */ + +CancelToken.prototype.subscribe = function subscribe(listener) { + if (this.reason) { + listener(this.reason); + return; + } + + if (this._listeners) { + this._listeners.push(listener); + } else { + this._listeners = [listener]; + } +}; + +/** + * Unsubscribe from the cancel signal + */ + +CancelToken.prototype.unsubscribe = function unsubscribe(listener) { + if (!this._listeners) { + return; + } + var index = this._listeners.indexOf(listener); + if (index !== -1) { + this._listeners.splice(index, 1); + } +}; + +/** + * Returns an object that contains a new `CancelToken` and a function that, when called, + * cancels the `CancelToken`. + */ +CancelToken.source = function source() { + var cancel; + var token = new CancelToken(function executor(c) { + cancel = c; + }); + return { + token: token, + cancel: cancel + }; +}; + +module.exports = CancelToken; + + +/***/ }), + +/***/ "./lib/cancel/isCancel.js": +/*!********************************!*\ + !*** ./lib/cancel/isCancel.js ***! + \********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +module.exports = function isCancel(value) { + return !!(value && value.__CANCEL__); +}; + + +/***/ }), + +/***/ "./lib/core/Axios.js": +/*!***************************!*\ + !*** ./lib/core/Axios.js ***! + \***************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); +var buildURL = __webpack_require__(/*! ../helpers/buildURL */ "./lib/helpers/buildURL.js"); +var InterceptorManager = __webpack_require__(/*! ./InterceptorManager */ "./lib/core/InterceptorManager.js"); +var dispatchRequest = __webpack_require__(/*! ./dispatchRequest */ "./lib/core/dispatchRequest.js"); +var mergeConfig = __webpack_require__(/*! ./mergeConfig */ "./lib/core/mergeConfig.js"); +var validator = __webpack_require__(/*! ../helpers/validator */ "./lib/helpers/validator.js"); + +var validators = validator.validators; +/** + * Create a new instance of Axios + * + * @param {Object} instanceConfig The default config for the instance + */ +function Axios(instanceConfig) { + this.defaults = instanceConfig; + this.interceptors = { + request: new InterceptorManager(), + response: new InterceptorManager() + }; +} + +/** + * Dispatch a request + * + * @param {Object} config The config specific for this request (merged with this.defaults) + */ +Axios.prototype.request = function 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 || {}; + } + + config = mergeConfig(this.defaults, config); + + // Set config.method + if (config.method) { + config.method = config.method.toLowerCase(); + } else if (this.defaults.method) { + config.method = this.defaults.method.toLowerCase(); + } else { + config.method = 'get'; + } + + var transitional = config.transitional; + + if (transitional !== undefined) { + validator.assertOptions(transitional, { + silentJSONParsing: validators.transitional(validators.boolean), + forcedJSONParsing: validators.transitional(validators.boolean), + clarifyTimeoutError: validators.transitional(validators.boolean) + }, false); + } + + // filter out skipped interceptors + var requestInterceptorChain = []; + var 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); + }); + + var responseInterceptorChain = []; + this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { + responseInterceptorChain.push(interceptor.fulfilled, interceptor.rejected); + }); + + var promise; + + if (!synchronousRequestInterceptors) { + var chain = [dispatchRequest, undefined]; + + Array.prototype.unshift.apply(chain, requestInterceptorChain); + chain = chain.concat(responseInterceptorChain); + + promise = Promise.resolve(config); + while (chain.length) { + promise = promise.then(chain.shift(), chain.shift()); + } + + return promise; + } + + + var newConfig = config; + while (requestInterceptorChain.length) { + var onFulfilled = requestInterceptorChain.shift(); + var onRejected = requestInterceptorChain.shift(); + try { + newConfig = onFulfilled(newConfig); + } catch (error) { + onRejected(error); + break; + } + } + + try { + promise = dispatchRequest(newConfig); + } catch (error) { + return Promise.reject(error); + } + + while (responseInterceptorChain.length) { + promise = promise.then(responseInterceptorChain.shift(), responseInterceptorChain.shift()); + } + + return promise; +}; + +Axios.prototype.getUri = function getUri(config) { + config = mergeConfig(this.defaults, config); + return buildURL(config.url, config.params, config.paramsSerializer).replace(/^\?/, ''); +}; + +// Provide aliases for supported request methods +utils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { + /*eslint func-names:0*/ + Axios.prototype[method] = function(url, config) { + return this.request(mergeConfig(config || {}, { + method: method, + url: url, + data: (config || {}).data + })); + }; +}); + +utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { + /*eslint func-names:0*/ + Axios.prototype[method] = function(url, data, config) { + return this.request(mergeConfig(config || {}, { + method: method, + url: url, + data: data + })); + }; +}); + +module.exports = Axios; + + +/***/ }), + +/***/ "./lib/core/InterceptorManager.js": +/*!****************************************!*\ + !*** ./lib/core/InterceptorManager.js ***! + \****************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +function InterceptorManager() { + 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 + */ +InterceptorManager.prototype.use = function use(fulfilled, rejected, options) { + this.handlers.push({ + fulfilled: fulfilled, + rejected: 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` + */ +InterceptorManager.prototype.eject = function eject(id) { + if (this.handlers[id]) { + this.handlers[id] = null; + } +}; + +/** + * 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 + */ +InterceptorManager.prototype.forEach = function forEach(fn) { + utils.forEach(this.handlers, function forEachHandler(h) { + if (h !== null) { + fn(h); + } + }); +}; + +module.exports = InterceptorManager; + + +/***/ }), + +/***/ "./lib/core/buildFullPath.js": +/*!***********************************!*\ + !*** ./lib/core/buildFullPath.js ***! + \***********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var isAbsoluteURL = __webpack_require__(/*! ../helpers/isAbsoluteURL */ "./lib/helpers/isAbsoluteURL.js"); +var combineURLs = __webpack_require__(/*! ../helpers/combineURLs */ "./lib/helpers/combineURLs.js"); + +/** + * 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 + */ +module.exports = function buildFullPath(baseURL, requestedURL) { + if (baseURL && !isAbsoluteURL(requestedURL)) { + return combineURLs(baseURL, requestedURL); + } + return requestedURL; +}; + + +/***/ }), + +/***/ "./lib/core/createError.js": +/*!*********************************!*\ + !*** ./lib/core/createError.js ***! + \*********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var enhanceError = __webpack_require__(/*! ./enhanceError */ "./lib/core/enhanceError.js"); + +/** + * Create an Error with the specified message, config, error code, request and response. + * + * @param {string} message The error message. + * @param {Object} config The config. + * @param {string} [code] The error code (for example, 'ECONNABORTED'). + * @param {Object} [request] The request. + * @param {Object} [response] The response. + * @returns {Error} The created error. + */ +module.exports = function createError(message, config, code, request, response) { + var error = new Error(message); + return enhanceError(error, config, code, request, response); +}; + + +/***/ }), + +/***/ "./lib/core/dispatchRequest.js": +/*!*************************************!*\ + !*** ./lib/core/dispatchRequest.js ***! + \*************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); +var transformData = __webpack_require__(/*! ./transformData */ "./lib/core/transformData.js"); +var isCancel = __webpack_require__(/*! ../cancel/isCancel */ "./lib/cancel/isCancel.js"); +var defaults = __webpack_require__(/*! ../defaults */ "./lib/defaults/index.js"); +var Cancel = __webpack_require__(/*! ../cancel/Cancel */ "./lib/cancel/Cancel.js"); + +/** + * Throws a `Cancel` if cancellation has been requested. + */ +function throwIfCancellationRequested(config) { + if (config.cancelToken) { + config.cancelToken.throwIfRequested(); + } + + if (config.signal && config.signal.aborted) { + throw new Cancel('canceled'); + } +} + +/** + * Dispatch a request to the server using the configured adapter. + * + * @param {object} config The config that is to be used for the request + * @returns {Promise} The Promise to be fulfilled + */ +module.exports = function dispatchRequest(config) { + throwIfCancellationRequested(config); + + // Ensure headers exist + config.headers = config.headers || {}; + + // Transform request data + config.data = transformData.call( + config, + config.data, + config.headers, + config.transformRequest + ); + + // Flatten headers + config.headers = utils.merge( + config.headers.common || {}, + config.headers[config.method] || {}, + config.headers + ); + + utils.forEach( + ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], + function cleanHeaderConfig(method) { + delete config.headers[method]; + } + ); + + var adapter = config.adapter || defaults.adapter; + + return adapter(config).then(function onAdapterResolution(response) { + throwIfCancellationRequested(config); + + // Transform response data + response.data = transformData.call( + config, + response.data, + response.headers, + config.transformResponse + ); + + return response; + }, function onAdapterRejection(reason) { + if (!isCancel(reason)) { + throwIfCancellationRequested(config); + + // Transform response data + if (reason && reason.response) { + reason.response.data = transformData.call( + config, + reason.response.data, + reason.response.headers, + config.transformResponse + ); + } + } + + return Promise.reject(reason); + }); +}; + + +/***/ }), + +/***/ "./lib/core/enhanceError.js": +/*!**********************************!*\ + !*** ./lib/core/enhanceError.js ***! + \**********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +/** + * Update an Error with the specified config, error code, and response. + * + * @param {Error} error The error to update. + * @param {Object} config The config. + * @param {string} [code] The error code (for example, 'ECONNABORTED'). + * @param {Object} [request] The request. + * @param {Object} [response] The response. + * @returns {Error} The error. + */ +module.exports = function enhanceError(error, config, code, request, response) { + error.config = config; + if (code) { + error.code = code; + } + + error.request = request; + error.response = response; + error.isAxiosError = true; + + 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: this.config, + code: this.code, + status: this.response && this.response.status ? this.response.status : null + }; + }; + return error; +}; + + +/***/ }), + +/***/ "./lib/core/mergeConfig.js": +/*!*********************************!*\ + !*** ./lib/core/mergeConfig.js ***! + \*********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ../utils */ "./lib/utils.js"); + +/** + * Config-specific merge-function which creates a new config-object + * by merging two configuration objects together. + * + * @param {Object} config1 + * @param {Object} config2 + * @returns {Object} New object resulting from merging config2 to config1 + */ +module.exports = function mergeConfig(config1, config2) { + // eslint-disable-next-line no-param-reassign + config2 = config2 || {}; + var config = {}; + + function getMergedValue(target, source) { + if (utils.isPlainObject(target) && utils.isPlainObject(source)) { + return utils.merge(target, source); + } else if (utils.isPlainObject(source)) { + return utils.merge({}, source); + } else if (utils.isArray(source)) { + return source.slice(); + } + return source; + } + + // eslint-disable-next-line consistent-return + function mergeDeepProperties(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(config1[prop], config2[prop]); + } else if (!utils.isUndefined(config1[prop])) { + return getMergedValue(undefined, config1[prop]); + } + } + + // eslint-disable-next-line consistent-return + function valueFromConfig2(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(undefined, config2[prop]); + } + } + + // eslint-disable-next-line consistent-return + function defaultToConfig2(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(undefined, config2[prop]); + } else if (!utils.isUndefined(config1[prop])) { + return getMergedValue(undefined, config1[prop]); + } + } + + // eslint-disable-next-line consistent-return + function mergeDirectKeys(prop) { + if (prop in config2) { + return getMergedValue(config1[prop], config2[prop]); + } else if (prop in config1) { + return getMergedValue(undefined, config1[prop]); + } + } + + var mergeMap = { + 'url': valueFromConfig2, + 'method': valueFromConfig2, + 'data': valueFromConfig2, + 'baseURL': defaultToConfig2, + 'transformRequest': defaultToConfig2, + 'transformResponse': defaultToConfig2, + 'paramsSerializer': defaultToConfig2, + 'timeout': defaultToConfig2, + 'timeoutMessage': defaultToConfig2, + 'withCredentials': defaultToConfig2, + 'adapter': defaultToConfig2, + 'responseType': defaultToConfig2, + 'xsrfCookieName': defaultToConfig2, + 'xsrfHeaderName': defaultToConfig2, + 'onUploadProgress': defaultToConfig2, + 'onDownloadProgress': defaultToConfig2, + 'decompress': defaultToConfig2, + 'maxContentLength': defaultToConfig2, + 'maxBodyLength': defaultToConfig2, + 'transport': defaultToConfig2, + 'httpAgent': defaultToConfig2, + 'httpsAgent': defaultToConfig2, + 'cancelToken': defaultToConfig2, + 'socketPath': defaultToConfig2, + 'responseEncoding': defaultToConfig2, + 'validateStatus': mergeDirectKeys + }; + + utils.forEach(Object.keys(config1).concat(Object.keys(config2)), function computeConfigValue(prop) { + var merge = mergeMap[prop] || mergeDeepProperties; + var configValue = merge(prop); + (utils.isUndefined(configValue) && merge !== mergeDirectKeys) || (config[prop] = configValue); + }); + + return config; +}; + + +/***/ }), + +/***/ "./lib/core/settle.js": +/*!****************************!*\ + !*** ./lib/core/settle.js ***! + \****************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var createError = __webpack_require__(/*! ./createError */ "./lib/core/createError.js"); + +/** + * 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. + */ +module.exports = function settle(resolve, reject, response) { + var validateStatus = response.config.validateStatus; + if (!response.status || !validateStatus || validateStatus(response.status)) { + resolve(response); + } else { + reject(createError( + 'Request failed with status code ' + response.status, + response.config, + null, + response.request, + response + )); + } +}; + + +/***/ }), + +/***/ "./lib/core/transformData.js": +/*!***********************************!*\ + !*** ./lib/core/transformData.js ***! + \***********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); +var defaults = __webpack_require__(/*! ../defaults */ "./lib/defaults/index.js"); + +/** + * Transform the data for a request or a response + * + * @param {Object|String} data The data to be transformed + * @param {Array} headers The headers for the request or response + * @param {Array|Function} fns A single function or Array of functions + * @returns {*} The resulting transformed data + */ +module.exports = function transformData(data, headers, fns) { + var context = this || defaults; + /*eslint no-param-reassign:0*/ + utils.forEach(fns, function transform(fn) { + data = fn.call(context, data, headers); + }); + + return data; +}; + + +/***/ }), + +/***/ "./lib/defaults/index.js": +/*!*******************************!*\ + !*** ./lib/defaults/index.js ***! + \*******************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ../utils */ "./lib/utils.js"); +var normalizeHeaderName = __webpack_require__(/*! ../helpers/normalizeHeaderName */ "./lib/helpers/normalizeHeaderName.js"); +var enhanceError = __webpack_require__(/*! ../core/enhanceError */ "./lib/core/enhanceError.js"); +var transitionalDefaults = __webpack_require__(/*! ./transitional */ "./lib/defaults/transitional.js"); + +var DEFAULT_CONTENT_TYPE = { + 'Content-Type': 'application/x-www-form-urlencoded' +}; + +function setContentTypeIfUnset(headers, value) { + if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) { + headers['Content-Type'] = value; + } +} + +function getDefaultAdapter() { + var adapter; + if (typeof XMLHttpRequest !== 'undefined') { + // For browsers use XHR adapter + adapter = __webpack_require__(/*! ../adapters/xhr */ "./lib/adapters/xhr.js"); + } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') { + // For node use HTTP adapter + adapter = __webpack_require__(/*! ../adapters/http */ "./lib/adapters/xhr.js"); + } + return adapter; +} + +function stringifySafely(rawValue, parser, encoder) { + if (utils.isString(rawValue)) { + try { + (parser || JSON.parse)(rawValue); + return utils.trim(rawValue); + } catch (e) { + if (e.name !== 'SyntaxError') { + throw e; + } + } + } + + return (encoder || JSON.stringify)(rawValue); +} + +var defaults = { + + transitional: transitionalDefaults, + + adapter: getDefaultAdapter(), + + transformRequest: [function transformRequest(data, headers) { + normalizeHeaderName(headers, 'Accept'); + normalizeHeaderName(headers, 'Content-Type'); + + if (utils.isFormData(data) || + utils.isArrayBuffer(data) || + utils.isBuffer(data) || + utils.isStream(data) || + utils.isFile(data) || + utils.isBlob(data) + ) { + return data; + } + if (utils.isArrayBufferView(data)) { + return data.buffer; + } + if (utils.isURLSearchParams(data)) { + setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8'); + return data.toString(); + } + if (utils.isObject(data) || (headers && headers['Content-Type'] === 'application/json')) { + setContentTypeIfUnset(headers, 'application/json'); + return stringifySafely(data); + } + return data; + }], + + transformResponse: [function transformResponse(data) { + var transitional = this.transitional || defaults.transitional; + var silentJSONParsing = transitional && transitional.silentJSONParsing; + var forcedJSONParsing = transitional && transitional.forcedJSONParsing; + var strictJSONParsing = !silentJSONParsing && this.responseType === 'json'; + + if (strictJSONParsing || (forcedJSONParsing && utils.isString(data) && data.length)) { + try { + return JSON.parse(data); + } catch (e) { + if (strictJSONParsing) { + if (e.name === 'SyntaxError') { + throw enhanceError(e, this, 'E_JSON_PARSE'); + } + 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, + + validateStatus: function validateStatus(status) { + return status >= 200 && status < 300; + }, + + headers: { + common: { + 'Accept': 'application/json, text/plain, */*' + } + } +}; + +utils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { + defaults.headers[method] = {}; +}); + +utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { + defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE); +}); + +module.exports = defaults; + + +/***/ }), + +/***/ "./lib/defaults/transitional.js": +/*!**************************************!*\ + !*** ./lib/defaults/transitional.js ***! + \**************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +module.exports = { + silentJSONParsing: true, + forcedJSONParsing: true, + clarifyTimeoutError: false +}; + + +/***/ }), + +/***/ "./lib/env/data.js": +/*!*************************!*\ + !*** ./lib/env/data.js ***! + \*************************/ +/*! no static exports found */ +/***/ (function(module, exports) { + +module.exports = { + "version": "0.26.1" +}; + +/***/ }), + +/***/ "./lib/helpers/bind.js": +/*!*****************************!*\ + !*** ./lib/helpers/bind.js ***! + \*****************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +module.exports = function bind(fn, thisArg) { + return function wrap() { + var args = new Array(arguments.length); + for (var i = 0; i < args.length; i++) { + args[i] = arguments[i]; + } + return fn.apply(thisArg, args); + }; +}; + + +/***/ }), + +/***/ "./lib/helpers/buildURL.js": +/*!*********************************!*\ + !*** ./lib/helpers/buildURL.js ***! + \*********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +function encode(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 + * @returns {string} The formatted url + */ +module.exports = function buildURL(url, params, paramsSerializer) { + /*eslint no-param-reassign:0*/ + if (!params) { + return url; + } + + var serializedParams; + if (paramsSerializer) { + serializedParams = paramsSerializer(params); + } else if (utils.isURLSearchParams(params)) { + serializedParams = params.toString(); + } else { + var parts = []; + + utils.forEach(params, function serialize(val, key) { + if (val === null || typeof val === 'undefined') { + return; + } + + if (utils.isArray(val)) { + key = key + '[]'; + } else { + val = [val]; + } + + utils.forEach(val, function parseValue(v) { + if (utils.isDate(v)) { + v = v.toISOString(); + } else if (utils.isObject(v)) { + v = JSON.stringify(v); + } + parts.push(encode(key) + '=' + encode(v)); + }); + }); + + serializedParams = parts.join('&'); + } + + if (serializedParams) { + var hashmarkIndex = url.indexOf('#'); + if (hashmarkIndex !== -1) { + url = url.slice(0, hashmarkIndex); + } + + url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; + } + + return url; +}; + + +/***/ }), + +/***/ "./lib/helpers/combineURLs.js": +/*!************************************!*\ + !*** ./lib/helpers/combineURLs.js ***! + \************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +/** + * 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 + */ +module.exports = function combineURLs(baseURL, relativeURL) { + return relativeURL + ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') + : baseURL; +}; + + +/***/ }), + +/***/ "./lib/helpers/cookies.js": +/*!********************************!*\ + !*** ./lib/helpers/cookies.js ***! + \********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +module.exports = ( + utils.isStandardBrowserEnv() ? + + // Standard browser envs support document.cookie + (function standardBrowserEnv() { + return { + write: function write(name, value, expires, path, domain, secure) { + var cookie = []; + cookie.push(name + '=' + encodeURIComponent(value)); + + if (utils.isNumber(expires)) { + cookie.push('expires=' + new Date(expires).toGMTString()); + } + + if (utils.isString(path)) { + cookie.push('path=' + path); + } + + if (utils.isString(domain)) { + cookie.push('domain=' + domain); + } + + if (secure === true) { + cookie.push('secure'); + } + + document.cookie = cookie.join('; '); + }, + + read: function read(name) { + var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); + return (match ? decodeURIComponent(match[3]) : null); + }, + + remove: function remove(name) { + this.write(name, '', Date.now() - 86400000); + } + }; + })() : + + // Non standard browser env (web workers, react-native) lack needed support. + (function nonStandardBrowserEnv() { + return { + write: function write() {}, + read: function read() { return null; }, + remove: function remove() {} + }; + })() +); + + +/***/ }), + +/***/ "./lib/helpers/isAbsoluteURL.js": +/*!**************************************!*\ + !*** ./lib/helpers/isAbsoluteURL.js ***! + \**************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +/** + * 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 + */ +module.exports = 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); +}; + + +/***/ }), + +/***/ "./lib/helpers/isAxiosError.js": +/*!*************************************!*\ + !*** ./lib/helpers/isAxiosError.js ***! + \*************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +/** + * 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 + */ +module.exports = function isAxiosError(payload) { + return utils.isObject(payload) && (payload.isAxiosError === true); +}; + + +/***/ }), + +/***/ "./lib/helpers/isURLSameOrigin.js": +/*!****************************************!*\ + !*** ./lib/helpers/isURLSameOrigin.js ***! + \****************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +module.exports = ( + utils.isStandardBrowserEnv() ? + + // 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() { + var msie = /(msie|trident)/i.test(navigator.userAgent); + var urlParsingNode = document.createElement('a'); + var originURL; + + /** + * Parse a URL to discover it's components + * + * @param {String} url The URL to be parsed + * @returns {Object} + */ + function resolveURL(url) { + var 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) { + var parsed = (utils.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; + }; + })() +); + + +/***/ }), + +/***/ "./lib/helpers/normalizeHeaderName.js": +/*!********************************************!*\ + !*** ./lib/helpers/normalizeHeaderName.js ***! + \********************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ../utils */ "./lib/utils.js"); + +module.exports = function normalizeHeaderName(headers, normalizedName) { + utils.forEach(headers, function processHeader(value, name) { + if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { + headers[normalizedName] = value; + delete headers[name]; + } + }); +}; + + +/***/ }), + +/***/ "./lib/helpers/parseHeaders.js": +/*!*************************************!*\ + !*** ./lib/helpers/parseHeaders.js ***! + \*************************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var utils = __webpack_require__(/*! ./../utils */ "./lib/utils.js"); + +// Headers whose duplicates are ignored by node +// c.f. https://nodejs.org/api/http.html#http_message_headers +var ignoreDuplicateOf = [ + '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} headers Headers needing to be parsed + * @returns {Object} Headers parsed into an object + */ +module.exports = function parseHeaders(headers) { + var parsed = {}; + var key; + var val; + var i; + + if (!headers) { return parsed; } + + utils.forEach(headers.split('\n'), function parser(line) { + i = line.indexOf(':'); + key = utils.trim(line.substr(0, i)).toLowerCase(); + val = utils.trim(line.substr(i + 1)); + + if (key) { + if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) { + return; + } + if (key === 'set-cookie') { + parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); + } else { + parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; + } + } + }); + + return parsed; +}; + + +/***/ }), + +/***/ "./lib/helpers/spread.js": +/*!*******************************!*\ + !*** ./lib/helpers/spread.js ***! + \*******************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +/** + * 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} + */ +module.exports = function spread(callback) { + return function wrap(arr) { + return callback.apply(null, arr); + }; +}; + + +/***/ }), + +/***/ "./lib/helpers/validator.js": +/*!**********************************!*\ + !*** ./lib/helpers/validator.js ***! + \**********************************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var VERSION = __webpack_require__(/*! ../env/data */ "./lib/env/data.js").version; + +var validators = {}; + +// eslint-disable-next-line func-names +['object', 'boolean', 'number', 'function', 'string', 'symbol'].forEach(function(type, i) { + validators[type] = function validator(thing) { + return typeof thing === type || 'a' + (i < 1 ? 'n ' : ' ') + type; + }; +}); + +var deprecatedWarnings = {}; + +/** + * Transitional option validator + * @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 + * @returns {function} + */ +validators.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 + return function(value, opt, opts) { + if (validator === false) { + throw new Error(formatMessage(opt, ' has been removed' + (version ? ' in ' + version : ''))); + } + + 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 + * @param {object} options + * @param {object} schema + * @param {boolean?} allowUnknown + */ + +function assertOptions(options, schema, allowUnknown) { + if (typeof options !== 'object') { + throw new TypeError('options must be an object'); + } + var keys = Object.keys(options); + var i = keys.length; + while (i-- > 0) { + var opt = keys[i]; + var validator = schema[opt]; + if (validator) { + var value = options[opt]; + var result = value === undefined || validator(value, opt, options); + if (result !== true) { + throw new TypeError('option ' + opt + ' must be ' + result); + } + continue; + } + if (allowUnknown !== true) { + throw Error('Unknown option ' + opt); + } + } +} + +module.exports = { + assertOptions: assertOptions, + validators: validators +}; + + +/***/ }), + +/***/ "./lib/utils.js": +/*!**********************!*\ + !*** ./lib/utils.js ***! + \**********************/ +/*! no static exports found */ +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +var bind = __webpack_require__(/*! ./helpers/bind */ "./lib/helpers/bind.js"); + +// utils is a library of generic helper functions non-specific to axios + +var toString = Object.prototype.toString; + +/** + * Determine if a value is an Array + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an Array, otherwise false + */ +function isArray(val) { + return Array.isArray(val); +} + +/** + * Determine if a value is undefined + * + * @param {Object} val The value to test + * @returns {boolean} True if the value is undefined, otherwise false + */ +function isUndefined(val) { + return typeof val === 'undefined'; +} + +/** + * Determine if a value is a Buffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Buffer, otherwise false + */ +function isBuffer(val) { + return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor) + && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val); +} + +/** + * Determine if a value is an ArrayBuffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an ArrayBuffer, otherwise false + */ +function isArrayBuffer(val) { + return toString.call(val) === '[object ArrayBuffer]'; +} + +/** + * Determine if a value is a FormData + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an FormData, otherwise false + */ +function isFormData(val) { + return toString.call(val) === '[object FormData]'; +} + +/** + * Determine if a value is a view on an ArrayBuffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false + */ +function isArrayBufferView(val) { + var result; + 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 + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a String, otherwise false + */ +function isString(val) { + return typeof val === 'string'; +} + +/** + * Determine if a value is a Number + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Number, otherwise false + */ +function isNumber(val) { + return typeof val === 'number'; +} + +/** + * Determine if a value is an Object + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an Object, otherwise false + */ +function isObject(val) { + return val !== null && typeof val === 'object'; +} + +/** + * Determine if a value is a plain Object + * + * @param {Object} val The value to test + * @return {boolean} True if value is a plain Object, otherwise false + */ +function isPlainObject(val) { + if (toString.call(val) !== '[object Object]') { + return false; + } + + var prototype = Object.getPrototypeOf(val); + return prototype === null || prototype === Object.prototype; +} + +/** + * Determine if a value is a Date + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Date, otherwise false + */ +function isDate(val) { + return toString.call(val) === '[object Date]'; +} + +/** + * Determine if a value is a File + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a File, otherwise false + */ +function isFile(val) { + return toString.call(val) === '[object File]'; +} + +/** + * Determine if a value is a Blob + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Blob, otherwise false + */ +function isBlob(val) { + return toString.call(val) === '[object Blob]'; +} + +/** + * Determine if a value is a Function + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Function, otherwise false + */ +function isFunction(val) { + return toString.call(val) === '[object Function]'; +} + +/** + * Determine if a value is a Stream + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Stream, otherwise false + */ +function isStream(val) { + return isObject(val) && isFunction(val.pipe); +} + +/** + * Determine if a value is a URLSearchParams object + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a URLSearchParams object, otherwise false + */ +function isURLSearchParams(val) { + return toString.call(val) === '[object URLSearchParams]'; +} + +/** + * Trim excess whitespace off the beginning and end of a string + * + * @param {String} str The String to trim + * @returns {String} The String freed of excess whitespace + */ +function trim(str) { + return str.trim ? str.trim() : str.replace(/^\s+|\s+$/g, ''); +} + +/** + * 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' + */ +function isStandardBrowserEnv() { + if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' || + navigator.product === 'NativeScript' || + navigator.product === 'NS')) { + return false; + } + return ( + typeof window !== 'undefined' && + typeof document !== 'undefined' + ); +} + +/** + * 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 + */ +function forEach(obj, fn) { + // Don't bother if no value provided + if (obj === null || typeof obj === 'undefined') { + return; + } + + // Force an array if not already something iterable + if (typeof obj !== 'object') { + /*eslint no-param-reassign:0*/ + obj = [obj]; + } + + if (isArray(obj)) { + // Iterate over array values + for (var i = 0, l = obj.length; i < l; i++) { + fn.call(null, obj[i], i, obj); + } + } else { + // Iterate over object keys + for (var key in obj) { + if (Object.prototype.hasOwnProperty.call(obj, key)) { + fn.call(null, obj[key], key, obj); + } + } + } +} + +/** + * 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 + * @returns {Object} Result of all merge properties + */ +function merge(/* obj1, obj2, obj3, ... */) { + var result = {}; + function assignValue(val, key) { + if (isPlainObject(result[key]) && isPlainObject(val)) { + result[key] = merge(result[key], val); + } else if (isPlainObject(val)) { + result[key] = merge({}, val); + } else if (isArray(val)) { + result[key] = val.slice(); + } else { + result[key] = val; + } + } + + for (var i = 0, l = arguments.length; i < l; i++) { + forEach(arguments[i], assignValue); + } + 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 + * @return {Object} The resulting value of object a + */ +function extend(a, b, thisArg) { + forEach(b, function assignValue(val, key) { + if (thisArg && typeof val === 'function') { + a[key] = bind(val, thisArg); + } else { + a[key] = val; + } + }); + return a; +} + +/** + * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM) + * + * @param {string} content with BOM + * @return {string} content value without BOM + */ +function stripBOM(content) { + if (content.charCodeAt(0) === 0xFEFF) { + content = content.slice(1); + } + return content; +} + +module.exports = { + isArray: isArray, + isArrayBuffer: isArrayBuffer, + isBuffer: isBuffer, + isFormData: isFormData, + isArrayBufferView: isArrayBufferView, + isString: isString, + isNumber: isNumber, + isObject: isObject, + isPlainObject: isPlainObject, + isUndefined: isUndefined, + isDate: isDate, + isFile: isFile, + isBlob: isBlob, + isFunction: isFunction, + isStream: isStream, + isURLSearchParams: isURLSearchParams, + isStandardBrowserEnv: isStandardBrowserEnv, + forEach: forEach, + merge: merge, + extend: extend, + trim: trim, + stripBOM: stripBOM +}; + + +/***/ }) + +/******/ }); +}); +//# sourceMappingURL=axios.map
\ No newline at end of file diff --git a/node_modules/axios/dist/axios.map b/node_modules/axios/dist/axios.map new file mode 100644 index 0000000..f0beb46 --- /dev/null +++ b/node_modules/axios/dist/axios.map @@ -0,0 +1 @@ +{"version":3,"sources":["webpack://axios/webpack/universalModuleDefinition","webpack://axios/webpack/bootstrap","webpack://axios/./index.js","webpack://axios/./lib/adapters/xhr.js","webpack://axios/./lib/axios.js","webpack://axios/./lib/cancel/Cancel.js","webpack://axios/./lib/cancel/CancelToken.js","webpack://axios/./lib/cancel/isCancel.js","webpack://axios/./lib/core/Axios.js","webpack://axios/./lib/core/InterceptorManager.js","webpack://axios/./lib/core/buildFullPath.js","webpack://axios/./lib/core/createError.js","webpack://axios/./lib/core/dispatchRequest.js","webpack://axios/./lib/core/enhanceError.js","webpack://axios/./lib/core/mergeConfig.js","webpack://axios/./lib/core/settle.js","webpack://axios/./lib/core/transformData.js","webpack://axios/./lib/defaults/index.js","webpack://axios/./lib/defaults/transitional.js","webpack://axios/./lib/env/data.js","webpack://axios/./lib/helpers/bind.js","webpack://axios/./lib/helpers/buildURL.js","webpack://axios/./lib/helpers/combineURLs.js","webpack://axios/./lib/helpers/cookies.js","webpack://axios/./lib/helpers/isAbsoluteURL.js","webpack://axios/./lib/helpers/isAxiosError.js","webpack://axios/./lib/helpers/isURLSameOrigin.js","webpack://axios/./lib/helpers/normalizeHeaderName.js","webpack://axios/./lib/helpers/parseHeaders.js","webpack://axios/./lib/helpers/spread.js","webpack://axios/./lib/helpers/validator.js","webpack://axios/./lib/utils.js"],"names":[],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,CAAC;AACD,O;QCVA;QACA;;QAEA;QACA;;QAEA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;;QAEA;QACA;;QAEA;QACA;;QAEA;QACA;QACA;;;QAGA;QACA;;QAEA;QACA;;QAEA;QACA;QACA;QACA,0CAA0C,gCAAgC;QAC1E;QACA;;QAEA;QACA;QACA;QACA,wDAAwD,kBAAkB;QAC1E;QACA,iDAAiD,cAAc;QAC/D;;QAEA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA;QACA,yCAAyC,iCAAiC;QAC1E,gHAAgH,mBAAmB,EAAE;QACrI;QACA;;QAEA;QACA;QACA;QACA,2BAA2B,0BAA0B,EAAE;QACvD,iCAAiC,eAAe;QAChD;QACA;QACA;;QAEA;QACA,sDAAsD,+DAA+D;;QAErH;QACA;;;QAGA;QACA;;;;;;;;;;;;AClFA,iBAAiB,mBAAO,CAAC,mCAAa,E;;;;;;;;;;;;ACAzB;;AAEb,YAAY,mBAAO,CAAC,kCAAY;AAChC,aAAa,mBAAO,CAAC,8CAAkB;AACvC,cAAc,mBAAO,CAAC,sDAAsB;AAC5C,eAAe,mBAAO,CAAC,wDAAuB;AAC9C,oBAAoB,mBAAO,CAAC,0DAAuB;AACnD,mBAAmB,mBAAO,CAAC,gEAA2B;AACtD,sBAAsB,mBAAO,CAAC,sEAA8B;AAC5D,kBAAkB,mBAAO,CAAC,sDAAqB;AAC/C,2BAA2B,mBAAO,CAAC,gEAA0B;AAC7D,aAAa,mBAAO,CAAC,gDAAkB;;AAEvC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA,4CAA4C;AAC5C;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA;AACA,OAAO;;AAEP;AACA;AACA;;AAEA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;AACA,OAAO;AACP;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,GAAG;AACH;;;;;;;;;;;;;ACnNa;;AAEb,YAAY,mBAAO,CAAC,+BAAS;AAC7B,WAAW,mBAAO,CAAC,6CAAgB;AACnC,YAAY,mBAAO,CAAC,yCAAc;AAClC,kBAAkB,mBAAO,CAAC,qDAAoB;AAC9C,eAAe,mBAAO,CAAC,2CAAY;;AAEnC;AACA;AACA;AACA,WAAW,OAAO;AAClB,YAAY,MAAM;AAClB;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA,eAAe,mBAAO,CAAC,+CAAiB;AACxC,oBAAoB,mBAAO,CAAC,yDAAsB;AAClD,iBAAiB,mBAAO,CAAC,mDAAmB;AAC5C,gBAAgB,mBAAO,CAAC,qCAAY;;AAEpC;AACA;AACA;AACA;AACA,eAAe,mBAAO,CAAC,iDAAkB;;AAEzC;AACA,qBAAqB,mBAAO,CAAC,6DAAwB;;AAErD;;AAEA;AACA;;;;;;;;;;;;;ACxDa;;AAEb;AACA;AACA;AACA;AACA,WAAW,QAAQ;AACnB;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA;;;;;;;;;;;;;AClBa;;AAEb,aAAa,mBAAO,CAAC,wCAAU;;AAE/B;AACA;AACA;AACA;AACA,WAAW,SAAS;AACpB;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA,GAAG;;AAEH;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA,eAAe,OAAO;AACtB;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,GAAG;AACH;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,GAAG;AACH;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;;;ACtHa;;AAEb;AACA;AACA;;;;;;;;;;;;;ACJa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;AAChC,eAAe,mBAAO,CAAC,sDAAqB;AAC5C,yBAAyB,mBAAO,CAAC,8DAAsB;AACvD,sBAAsB,mBAAO,CAAC,wDAAmB;AACjD,kBAAkB,mBAAO,CAAC,gDAAe;AACzC,gBAAgB,mBAAO,CAAC,wDAAsB;;AAE9C;AACA;AACA;AACA;AACA,WAAW,OAAO;AAClB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;;AAEA;AACA;AACA;AACA,GAAG;AACH;AACA,GAAG;AACH;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,GAAG;;AAEH;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;;AAGA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;AACA;;AAEA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,gDAAgD;AAChD;AACA;AACA,yBAAyB;AACzB,KAAK;AACL;AACA,CAAC;;AAED;AACA;AACA;AACA,gDAAgD;AAChD;AACA;AACA;AACA,KAAK;AACL;AACA,CAAC;;AAED;;;;;;;;;;;;;ACnJa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,SAAS;AACpB,WAAW,SAAS;AACpB;AACA,YAAY,OAAO;AACnB;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,SAAS;AACpB;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;;AAEA;;;;;;;;;;;;;ACrDa;;AAEb,oBAAoB,mBAAO,CAAC,gEAA0B;AACtD,kBAAkB,mBAAO,CAAC,4DAAwB;;AAElD;AACA;AACA;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACnBa;;AAEb,mBAAmB,mBAAO,CAAC,kDAAgB;;AAE3C;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,MAAM;AACnB;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACjBa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;AAChC,oBAAoB,mBAAO,CAAC,oDAAiB;AAC7C,eAAe,mBAAO,CAAC,oDAAoB;AAC3C,eAAe,mBAAO,CAAC,4CAAa;AACpC,aAAa,mBAAO,CAAC,gDAAkB;;AAEvC;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,+BAA+B;AAC/B,uCAAuC;AACvC;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;AACH;;;;;;;;;;;;;ACtFa;;AAEb;AACA;AACA;AACA,WAAW,MAAM;AACjB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,MAAM;AACnB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;AC1Ca;;AAEb,YAAY,mBAAO,CAAC,gCAAU;;AAE9B;AACA;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,KAAK;AACL,2BAA2B;AAC3B,KAAK;AACL;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;;;;;;;;;;;;AClGa;;AAEb,kBAAkB,mBAAO,CAAC,gDAAe;;AAEzC;AACA;AACA;AACA,WAAW,SAAS;AACpB,WAAW,SAAS;AACpB,WAAW,OAAO;AAClB;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACxBa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;AAChC,eAAe,mBAAO,CAAC,4CAAa;;AAEpC;AACA;AACA;AACA,WAAW,cAAc;AACzB,WAAW,MAAM;AACjB,WAAW,eAAe;AAC1B,aAAa,EAAE;AACf;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;;;;;;;;;;;;ACrBa;;AAEb,YAAY,mBAAO,CAAC,gCAAU;AAC9B,0BAA0B,mBAAO,CAAC,4EAAgC;AAClE,mBAAmB,mBAAO,CAAC,wDAAsB;AACjD,2BAA2B,mBAAO,CAAC,sDAAgB;;AAEnD;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,cAAc,mBAAO,CAAC,8CAAiB;AACvC,GAAG;AACH;AACA,cAAc,mBAAO,CAAC,+CAAkB;AACxC;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,wEAAwE;AACxE;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,CAAC;;AAED;AACA;AACA,CAAC;;AAED;;;;;;;;;;;;;AClIa;;AAEb;AACA;AACA;AACA;AACA;;;;;;;;;;;;ACNA;AACA;AACA,E;;;;;;;;;;;;ACFa;;AAEb;AACA;AACA;AACA,mBAAmB,iBAAiB;AACpC;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACVa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,GAAG;AACH;AACA,GAAG;AACH;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;AACA,OAAO;AACP,KAAK;;AAEL;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;;;;;;;;;;;;ACrEa;;AAEb;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACba;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA,0CAA0C;AAC1C,SAAS;;AAET;AACA,4DAA4D,wBAAwB;AACpF;AACA,SAAS;;AAET;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA,kCAAkC;AAClC,+BAA+B,aAAa,EAAE;AAC9C;AACA;AACA,KAAK;AACL;;;;;;;;;;;;;ACpDa;;AAEb;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;ACba;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;AACA;AACA,WAAW,EAAE;AACb,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;;;;;;;;;;;;ACZa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,cAAc,OAAO;AACrB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA,cAAc,OAAO;AACrB,gBAAgB,QAAQ;AACxB;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;;;;;;;;;;;;;ACnEa;;AAEb,YAAY,mBAAO,CAAC,gCAAU;;AAE9B;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;;;;;;;;;;;;;ACXa;;AAEb,YAAY,mBAAO,CAAC,kCAAY;;AAEhC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;AACA;;AAEA,iBAAiB,eAAe;;AAEhC;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;AACA;AACA,GAAG;;AAEH;AACA;;;;;;;;;;;;;ACpDa;;AAEb;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,+BAA+B;AAC/B;AACA;AACA,WAAW,SAAS;AACpB,aAAa;AACb;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;;;AC1Ba;;AAEb,cAAc,mBAAO,CAAC,sCAAa;;AAEnC;;AAEA;AACA;AACA;AACA;AACA;AACA,CAAC;;AAED;;AAEA;AACA;AACA,WAAW,kBAAkB;AAC7B,WAAW,QAAQ;AACnB,WAAW,QAAQ;AACnB,aAAa;AACb;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,SAAS;AACpB;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;;;;;;;;;;;;ACjFa;;AAEb,WAAW,mBAAO,CAAC,6CAAgB;;AAEnC;;AAEA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,YAAY,QAAQ;AACpB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,aAAa;AACxB,WAAW,SAAS;AACpB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,mCAAmC,OAAO;AAC1C;AACA;AACA,GAAG;AACH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,uBAAuB,SAAS,GAAG,SAAS;AAC5C,2BAA2B;AAC3B;AACA;AACA,WAAW,OAAO;AAClB,aAAa,OAAO;AACpB;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,4BAA4B;AAC5B,KAAK;AACL;AACA,KAAK;AACL;AACA;AACA;;AAEA,uCAAuC,OAAO;AAC9C;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,WAAW,OAAO;AAClB,YAAY,OAAO;AACnB;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA,WAAW,OAAO;AAClB,YAAY,OAAO;AACnB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA","file":"axios.js","sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse if(typeof exports === 'object')\n\t\texports[\"axios\"] = factory();\n\telse\n\t\troot[\"axios\"] = factory();\n})(this, function() {\nreturn "," \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = \"./index.js\");\n","module.exports = require('./lib/axios');","'use strict';\n\nvar utils = require('./../utils');\nvar settle = require('./../core/settle');\nvar cookies = require('./../helpers/cookies');\nvar buildURL = require('./../helpers/buildURL');\nvar buildFullPath = require('../core/buildFullPath');\nvar parseHeaders = require('./../helpers/parseHeaders');\nvar isURLSameOrigin = require('./../helpers/isURLSameOrigin');\nvar createError = require('../core/createError');\nvar transitionalDefaults = require('../defaults/transitional');\nvar Cancel = require('../cancel/Cancel');\n\nmodule.exports = function xhrAdapter(config) {\n return new Promise(function dispatchXhrRequest(resolve, reject) {\n var requestData = config.data;\n var requestHeaders = config.headers;\n var responseType = config.responseType;\n var onCanceled;\n function done() {\n if (config.cancelToken) {\n config.cancelToken.unsubscribe(onCanceled);\n }\n\n if (config.signal) {\n config.signal.removeEventListener('abort', onCanceled);\n }\n }\n\n if (utils.isFormData(requestData)) {\n delete requestHeaders['Content-Type']; // Let the browser set it\n }\n\n var request = new XMLHttpRequest();\n\n // HTTP basic authentication\n if (config.auth) {\n var username = config.auth.username || '';\n var password = config.auth.password ? unescape(encodeURIComponent(config.auth.password)) : '';\n requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password);\n }\n\n var fullPath = buildFullPath(config.baseURL, config.url);\n request.open(config.method.toUpperCase(), buildURL(fullPath, config.params, config.paramsSerializer), true);\n\n // Set the request timeout in MS\n request.timeout = config.timeout;\n\n function onloadend() {\n if (!request) {\n return;\n }\n // Prepare the response\n var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null;\n var responseData = !responseType || responseType === 'text' || responseType === 'json' ?\n request.responseText : request.response;\n var response = {\n data: responseData,\n status: request.status,\n statusText: request.statusText,\n headers: responseHeaders,\n config: config,\n request: request\n };\n\n settle(function _resolve(value) {\n resolve(value);\n done();\n }, function _reject(err) {\n reject(err);\n done();\n }, response);\n\n // Clean up request\n request = null;\n }\n\n if ('onloadend' in request) {\n // Use onloadend if available\n request.onloadend = onloadend;\n } else {\n // Listen for ready state to emulate onloadend\n request.onreadystatechange = function handleLoad() {\n if (!request || request.readyState !== 4) {\n return;\n }\n\n // The request errored out and we didn't get a response, this will be\n // handled by onerror instead\n // With one exception: request that using file: protocol, most browsers\n // will return status as 0 even though it's a successful request\n if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) {\n return;\n }\n // readystate handler is calling before onerror or ontimeout handlers,\n // so we should call onloadend on the next 'tick'\n setTimeout(onloadend);\n };\n }\n\n // Handle browser request cancellation (as opposed to a manual cancellation)\n request.onabort = function handleAbort() {\n if (!request) {\n return;\n }\n\n reject(createError('Request aborted', config, 'ECONNABORTED', request));\n\n // Clean up request\n request = null;\n };\n\n // Handle low level network errors\n request.onerror = function handleError() {\n // Real errors are hidden from us by the browser\n // onerror should only fire if it's a network error\n reject(createError('Network Error', config, null, request));\n\n // Clean up request\n request = null;\n };\n\n // Handle timeout\n request.ontimeout = function handleTimeout() {\n var timeoutErrorMessage = config.timeout ? 'timeout of ' + config.timeout + 'ms exceeded' : 'timeout exceeded';\n var transitional = config.transitional || transitionalDefaults;\n if (config.timeoutErrorMessage) {\n timeoutErrorMessage = config.timeoutErrorMessage;\n }\n reject(createError(\n timeoutErrorMessage,\n config,\n transitional.clarifyTimeoutError ? 'ETIMEDOUT' : 'ECONNABORTED',\n request));\n\n // Clean up request\n request = null;\n };\n\n // Add xsrf header\n // This is only done if running in a standard browser environment.\n // Specifically not if we're in a web worker, or react-native.\n if (utils.isStandardBrowserEnv()) {\n // Add xsrf header\n var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ?\n cookies.read(config.xsrfCookieName) :\n undefined;\n\n if (xsrfValue) {\n requestHeaders[config.xsrfHeaderName] = xsrfValue;\n }\n }\n\n // Add headers to the request\n if ('setRequestHeader' in request) {\n utils.forEach(requestHeaders, function setRequestHeader(val, key) {\n if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') {\n // Remove Content-Type if data is undefined\n delete requestHeaders[key];\n } else {\n // Otherwise add header to the request\n request.setRequestHeader(key, val);\n }\n });\n }\n\n // Add withCredentials to request if needed\n if (!utils.isUndefined(config.withCredentials)) {\n request.withCredentials = !!config.withCredentials;\n }\n\n // Add responseType to request if needed\n if (responseType && responseType !== 'json') {\n request.responseType = config.responseType;\n }\n\n // Handle progress if needed\n if (typeof config.onDownloadProgress === 'function') {\n request.addEventListener('progress', config.onDownloadProgress);\n }\n\n // Not all browsers support upload events\n if (typeof config.onUploadProgress === 'function' && request.upload) {\n request.upload.addEventListener('progress', config.onUploadProgress);\n }\n\n if (config.cancelToken || config.signal) {\n // Handle cancellation\n // eslint-disable-next-line func-names\n onCanceled = function(cancel) {\n if (!request) {\n return;\n }\n reject(!cancel || (cancel && cancel.type) ? new Cancel('canceled') : cancel);\n request.abort();\n request = null;\n };\n\n config.cancelToken && config.cancelToken.subscribe(onCanceled);\n if (config.signal) {\n config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled);\n }\n }\n\n if (!requestData) {\n requestData = null;\n }\n\n // Send the request\n request.send(requestData);\n });\n};\n","'use strict';\n\nvar utils = require('./utils');\nvar bind = require('./helpers/bind');\nvar Axios = require('./core/Axios');\nvar mergeConfig = require('./core/mergeConfig');\nvar defaults = require('./defaults');\n\n/**\n * Create an instance of Axios\n *\n * @param {Object} defaultConfig The default config for the instance\n * @return {Axios} A new instance of Axios\n */\nfunction createInstance(defaultConfig) {\n var context = new Axios(defaultConfig);\n var instance = bind(Axios.prototype.request, context);\n\n // Copy axios.prototype to instance\n utils.extend(instance, Axios.prototype, context);\n\n // Copy context to instance\n utils.extend(instance, context);\n\n // Factory for creating new instances\n instance.create = function create(instanceConfig) {\n return createInstance(mergeConfig(defaultConfig, instanceConfig));\n };\n\n return instance;\n}\n\n// Create the default instance to be exported\nvar axios = createInstance(defaults);\n\n// Expose Axios class to allow class inheritance\naxios.Axios = Axios;\n\n// Expose Cancel & CancelToken\naxios.Cancel = require('./cancel/Cancel');\naxios.CancelToken = require('./cancel/CancelToken');\naxios.isCancel = require('./cancel/isCancel');\naxios.VERSION = require('./env/data').version;\n\n// Expose all/spread\naxios.all = function all(promises) {\n return Promise.all(promises);\n};\naxios.spread = require('./helpers/spread');\n\n// Expose isAxiosError\naxios.isAxiosError = require('./helpers/isAxiosError');\n\nmodule.exports = axios;\n\n// Allow use of default import syntax in TypeScript\nmodule.exports.default = axios;\n","'use strict';\n\n/**\n * A `Cancel` is an object that is thrown when an operation is canceled.\n *\n * @class\n * @param {string=} message The message.\n */\nfunction Cancel(message) {\n this.message = message;\n}\n\nCancel.prototype.toString = function toString() {\n return 'Cancel' + (this.message ? ': ' + this.message : '');\n};\n\nCancel.prototype.__CANCEL__ = true;\n\nmodule.exports = Cancel;\n","'use strict';\n\nvar Cancel = require('./Cancel');\n\n/**\n * A `CancelToken` is an object that can be used to request cancellation of an operation.\n *\n * @class\n * @param {Function} executor The executor function.\n */\nfunction CancelToken(executor) {\n if (typeof executor !== 'function') {\n throw new TypeError('executor must be a function.');\n }\n\n var resolvePromise;\n\n this.promise = new Promise(function promiseExecutor(resolve) {\n resolvePromise = resolve;\n });\n\n var token = this;\n\n // eslint-disable-next-line func-names\n this.promise.then(function(cancel) {\n if (!token._listeners) return;\n\n var i;\n var l = token._listeners.length;\n\n for (i = 0; i < l; i++) {\n token._listeners[i](cancel);\n }\n token._listeners = null;\n });\n\n // eslint-disable-next-line func-names\n this.promise.then = function(onfulfilled) {\n var _resolve;\n // eslint-disable-next-line func-names\n var promise = new Promise(function(resolve) {\n token.subscribe(resolve);\n _resolve = resolve;\n }).then(onfulfilled);\n\n promise.cancel = function reject() {\n token.unsubscribe(_resolve);\n };\n\n return promise;\n };\n\n executor(function cancel(message) {\n if (token.reason) {\n // Cancellation has already been requested\n return;\n }\n\n token.reason = new Cancel(message);\n resolvePromise(token.reason);\n });\n}\n\n/**\n * Throws a `Cancel` if cancellation has been requested.\n */\nCancelToken.prototype.throwIfRequested = function throwIfRequested() {\n if (this.reason) {\n throw this.reason;\n }\n};\n\n/**\n * Subscribe to the cancel signal\n */\n\nCancelToken.prototype.subscribe = function subscribe(listener) {\n if (this.reason) {\n listener(this.reason);\n return;\n }\n\n if (this._listeners) {\n this._listeners.push(listener);\n } else {\n this._listeners = [listener];\n }\n};\n\n/**\n * Unsubscribe from the cancel signal\n */\n\nCancelToken.prototype.unsubscribe = function unsubscribe(listener) {\n if (!this._listeners) {\n return;\n }\n var index = this._listeners.indexOf(listener);\n if (index !== -1) {\n this._listeners.splice(index, 1);\n }\n};\n\n/**\n * Returns an object that contains a new `CancelToken` and a function that, when called,\n * cancels the `CancelToken`.\n */\nCancelToken.source = function source() {\n var cancel;\n var token = new CancelToken(function executor(c) {\n cancel = c;\n });\n return {\n token: token,\n cancel: cancel\n };\n};\n\nmodule.exports = CancelToken;\n","'use strict';\n\nmodule.exports = function isCancel(value) {\n return !!(value && value.__CANCEL__);\n};\n","'use strict';\n\nvar utils = require('./../utils');\nvar buildURL = require('../helpers/buildURL');\nvar InterceptorManager = require('./InterceptorManager');\nvar dispatchRequest = require('./dispatchRequest');\nvar mergeConfig = require('./mergeConfig');\nvar validator = require('../helpers/validator');\n\nvar validators = validator.validators;\n/**\n * Create a new instance of Axios\n *\n * @param {Object} instanceConfig The default config for the instance\n */\nfunction Axios(instanceConfig) {\n this.defaults = instanceConfig;\n this.interceptors = {\n request: new InterceptorManager(),\n response: new InterceptorManager()\n };\n}\n\n/**\n * Dispatch a request\n *\n * @param {Object} config The config specific for this request (merged with this.defaults)\n */\nAxios.prototype.request = function request(configOrUrl, config) {\n /*eslint no-param-reassign:0*/\n // Allow for axios('example/url'[, config]) a la fetch API\n if (typeof configOrUrl === 'string') {\n config = config || {};\n config.url = configOrUrl;\n } else {\n config = configOrUrl || {};\n }\n\n config = mergeConfig(this.defaults, config);\n\n // Set config.method\n if (config.method) {\n config.method = config.method.toLowerCase();\n } else if (this.defaults.method) {\n config.method = this.defaults.method.toLowerCase();\n } else {\n config.method = 'get';\n }\n\n var transitional = config.transitional;\n\n if (transitional !== undefined) {\n validator.assertOptions(transitional, {\n silentJSONParsing: validators.transitional(validators.boolean),\n forcedJSONParsing: validators.transitional(validators.boolean),\n clarifyTimeoutError: validators.transitional(validators.boolean)\n }, false);\n }\n\n // filter out skipped interceptors\n var requestInterceptorChain = [];\n var synchronousRequestInterceptors = true;\n this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) {\n if (typeof interceptor.runWhen === 'function' && interceptor.runWhen(config) === false) {\n return;\n }\n\n synchronousRequestInterceptors = synchronousRequestInterceptors && interceptor.synchronous;\n\n requestInterceptorChain.unshift(interceptor.fulfilled, interceptor.rejected);\n });\n\n var responseInterceptorChain = [];\n this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) {\n responseInterceptorChain.push(interceptor.fulfilled, interceptor.rejected);\n });\n\n var promise;\n\n if (!synchronousRequestInterceptors) {\n var chain = [dispatchRequest, undefined];\n\n Array.prototype.unshift.apply(chain, requestInterceptorChain);\n chain = chain.concat(responseInterceptorChain);\n\n promise = Promise.resolve(config);\n while (chain.length) {\n promise = promise.then(chain.shift(), chain.shift());\n }\n\n return promise;\n }\n\n\n var newConfig = config;\n while (requestInterceptorChain.length) {\n var onFulfilled = requestInterceptorChain.shift();\n var onRejected = requestInterceptorChain.shift();\n try {\n newConfig = onFulfilled(newConfig);\n } catch (error) {\n onRejected(error);\n break;\n }\n }\n\n try {\n promise = dispatchRequest(newConfig);\n } catch (error) {\n return Promise.reject(error);\n }\n\n while (responseInterceptorChain.length) {\n promise = promise.then(responseInterceptorChain.shift(), responseInterceptorChain.shift());\n }\n\n return promise;\n};\n\nAxios.prototype.getUri = function getUri(config) {\n config = mergeConfig(this.defaults, config);\n return buildURL(config.url, config.params, config.paramsSerializer).replace(/^\\?/, '');\n};\n\n// Provide aliases for supported request methods\nutils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) {\n /*eslint func-names:0*/\n Axios.prototype[method] = function(url, config) {\n return this.request(mergeConfig(config || {}, {\n method: method,\n url: url,\n data: (config || {}).data\n }));\n };\n});\n\nutils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) {\n /*eslint func-names:0*/\n Axios.prototype[method] = function(url, data, config) {\n return this.request(mergeConfig(config || {}, {\n method: method,\n url: url,\n data: data\n }));\n };\n});\n\nmodule.exports = Axios;\n","'use strict';\n\nvar utils = require('./../utils');\n\nfunction InterceptorManager() {\n this.handlers = [];\n}\n\n/**\n * Add a new interceptor to the stack\n *\n * @param {Function} fulfilled The function to handle `then` for a `Promise`\n * @param {Function} rejected The function to handle `reject` for a `Promise`\n *\n * @return {Number} An ID used to remove interceptor later\n */\nInterceptorManager.prototype.use = function use(fulfilled, rejected, options) {\n this.handlers.push({\n fulfilled: fulfilled,\n rejected: rejected,\n synchronous: options ? options.synchronous : false,\n runWhen: options ? options.runWhen : null\n });\n return this.handlers.length - 1;\n};\n\n/**\n * Remove an interceptor from the stack\n *\n * @param {Number} id The ID that was returned by `use`\n */\nInterceptorManager.prototype.eject = function eject(id) {\n if (this.handlers[id]) {\n this.handlers[id] = null;\n }\n};\n\n/**\n * Iterate over all the registered interceptors\n *\n * This method is particularly useful for skipping over any\n * interceptors that may have become `null` calling `eject`.\n *\n * @param {Function} fn The function to call for each interceptor\n */\nInterceptorManager.prototype.forEach = function forEach(fn) {\n utils.forEach(this.handlers, function forEachHandler(h) {\n if (h !== null) {\n fn(h);\n }\n });\n};\n\nmodule.exports = InterceptorManager;\n","'use strict';\n\nvar isAbsoluteURL = require('../helpers/isAbsoluteURL');\nvar combineURLs = require('../helpers/combineURLs');\n\n/**\n * Creates a new URL by combining the baseURL with the requestedURL,\n * only when the requestedURL is not already an absolute URL.\n * If the requestURL is absolute, this function returns the requestedURL untouched.\n *\n * @param {string} baseURL The base URL\n * @param {string} requestedURL Absolute or relative URL to combine\n * @returns {string} The combined full path\n */\nmodule.exports = function buildFullPath(baseURL, requestedURL) {\n if (baseURL && !isAbsoluteURL(requestedURL)) {\n return combineURLs(baseURL, requestedURL);\n }\n return requestedURL;\n};\n","'use strict';\n\nvar enhanceError = require('./enhanceError');\n\n/**\n * Create an Error with the specified message, config, error code, request and response.\n *\n * @param {string} message The error message.\n * @param {Object} config The config.\n * @param {string} [code] The error code (for example, 'ECONNABORTED').\n * @param {Object} [request] The request.\n * @param {Object} [response] The response.\n * @returns {Error} The created error.\n */\nmodule.exports = function createError(message, config, code, request, response) {\n var error = new Error(message);\n return enhanceError(error, config, code, request, response);\n};\n","'use strict';\n\nvar utils = require('./../utils');\nvar transformData = require('./transformData');\nvar isCancel = require('../cancel/isCancel');\nvar defaults = require('../defaults');\nvar Cancel = require('../cancel/Cancel');\n\n/**\n * Throws a `Cancel` if cancellation has been requested.\n */\nfunction throwIfCancellationRequested(config) {\n if (config.cancelToken) {\n config.cancelToken.throwIfRequested();\n }\n\n if (config.signal && config.signal.aborted) {\n throw new Cancel('canceled');\n }\n}\n\n/**\n * Dispatch a request to the server using the configured adapter.\n *\n * @param {object} config The config that is to be used for the request\n * @returns {Promise} The Promise to be fulfilled\n */\nmodule.exports = function dispatchRequest(config) {\n throwIfCancellationRequested(config);\n\n // Ensure headers exist\n config.headers = config.headers || {};\n\n // Transform request data\n config.data = transformData.call(\n config,\n config.data,\n config.headers,\n config.transformRequest\n );\n\n // Flatten headers\n config.headers = utils.merge(\n config.headers.common || {},\n config.headers[config.method] || {},\n config.headers\n );\n\n utils.forEach(\n ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'],\n function cleanHeaderConfig(method) {\n delete config.headers[method];\n }\n );\n\n var adapter = config.adapter || defaults.adapter;\n\n return adapter(config).then(function onAdapterResolution(response) {\n throwIfCancellationRequested(config);\n\n // Transform response data\n response.data = transformData.call(\n config,\n response.data,\n response.headers,\n config.transformResponse\n );\n\n return response;\n }, function onAdapterRejection(reason) {\n if (!isCancel(reason)) {\n throwIfCancellationRequested(config);\n\n // Transform response data\n if (reason && reason.response) {\n reason.response.data = transformData.call(\n config,\n reason.response.data,\n reason.response.headers,\n config.transformResponse\n );\n }\n }\n\n return Promise.reject(reason);\n });\n};\n","'use strict';\n\n/**\n * Update an Error with the specified config, error code, and response.\n *\n * @param {Error} error The error to update.\n * @param {Object} config The config.\n * @param {string} [code] The error code (for example, 'ECONNABORTED').\n * @param {Object} [request] The request.\n * @param {Object} [response] The response.\n * @returns {Error} The error.\n */\nmodule.exports = function enhanceError(error, config, code, request, response) {\n error.config = config;\n if (code) {\n error.code = code;\n }\n\n error.request = request;\n error.response = response;\n error.isAxiosError = true;\n\n error.toJSON = function toJSON() {\n return {\n // Standard\n message: this.message,\n name: this.name,\n // Microsoft\n description: this.description,\n number: this.number,\n // Mozilla\n fileName: this.fileName,\n lineNumber: this.lineNumber,\n columnNumber: this.columnNumber,\n stack: this.stack,\n // Axios\n config: this.config,\n code: this.code,\n status: this.response && this.response.status ? this.response.status : null\n };\n };\n return error;\n};\n","'use strict';\n\nvar utils = require('../utils');\n\n/**\n * Config-specific merge-function which creates a new config-object\n * by merging two configuration objects together.\n *\n * @param {Object} config1\n * @param {Object} config2\n * @returns {Object} New object resulting from merging config2 to config1\n */\nmodule.exports = function mergeConfig(config1, config2) {\n // eslint-disable-next-line no-param-reassign\n config2 = config2 || {};\n var config = {};\n\n function getMergedValue(target, source) {\n if (utils.isPlainObject(target) && utils.isPlainObject(source)) {\n return utils.merge(target, source);\n } else if (utils.isPlainObject(source)) {\n return utils.merge({}, source);\n } else if (utils.isArray(source)) {\n return source.slice();\n }\n return source;\n }\n\n // eslint-disable-next-line consistent-return\n function mergeDeepProperties(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(config1[prop], config2[prop]);\n } else if (!utils.isUndefined(config1[prop])) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function valueFromConfig2(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(undefined, config2[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function defaultToConfig2(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(undefined, config2[prop]);\n } else if (!utils.isUndefined(config1[prop])) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function mergeDirectKeys(prop) {\n if (prop in config2) {\n return getMergedValue(config1[prop], config2[prop]);\n } else if (prop in config1) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n var mergeMap = {\n 'url': valueFromConfig2,\n 'method': valueFromConfig2,\n 'data': valueFromConfig2,\n 'baseURL': defaultToConfig2,\n 'transformRequest': defaultToConfig2,\n 'transformResponse': defaultToConfig2,\n 'paramsSerializer': defaultToConfig2,\n 'timeout': defaultToConfig2,\n 'timeoutMessage': defaultToConfig2,\n 'withCredentials': defaultToConfig2,\n 'adapter': defaultToConfig2,\n 'responseType': defaultToConfig2,\n 'xsrfCookieName': defaultToConfig2,\n 'xsrfHeaderName': defaultToConfig2,\n 'onUploadProgress': defaultToConfig2,\n 'onDownloadProgress': defaultToConfig2,\n 'decompress': defaultToConfig2,\n 'maxContentLength': defaultToConfig2,\n 'maxBodyLength': defaultToConfig2,\n 'transport': defaultToConfig2,\n 'httpAgent': defaultToConfig2,\n 'httpsAgent': defaultToConfig2,\n 'cancelToken': defaultToConfig2,\n 'socketPath': defaultToConfig2,\n 'responseEncoding': defaultToConfig2,\n 'validateStatus': mergeDirectKeys\n };\n\n utils.forEach(Object.keys(config1).concat(Object.keys(config2)), function computeConfigValue(prop) {\n var merge = mergeMap[prop] || mergeDeepProperties;\n var configValue = merge(prop);\n (utils.isUndefined(configValue) && merge !== mergeDirectKeys) || (config[prop] = configValue);\n });\n\n return config;\n};\n","'use strict';\n\nvar createError = require('./createError');\n\n/**\n * Resolve or reject a Promise based on response status.\n *\n * @param {Function} resolve A function that resolves the promise.\n * @param {Function} reject A function that rejects the promise.\n * @param {object} response The response.\n */\nmodule.exports = function settle(resolve, reject, response) {\n var validateStatus = response.config.validateStatus;\n if (!response.status || !validateStatus || validateStatus(response.status)) {\n resolve(response);\n } else {\n reject(createError(\n 'Request failed with status code ' + response.status,\n response.config,\n null,\n response.request,\n response\n ));\n }\n};\n","'use strict';\n\nvar utils = require('./../utils');\nvar defaults = require('../defaults');\n\n/**\n * Transform the data for a request or a response\n *\n * @param {Object|String} data The data to be transformed\n * @param {Array} headers The headers for the request or response\n * @param {Array|Function} fns A single function or Array of functions\n * @returns {*} The resulting transformed data\n */\nmodule.exports = function transformData(data, headers, fns) {\n var context = this || defaults;\n /*eslint no-param-reassign:0*/\n utils.forEach(fns, function transform(fn) {\n data = fn.call(context, data, headers);\n });\n\n return data;\n};\n","'use strict';\n\nvar utils = require('../utils');\nvar normalizeHeaderName = require('../helpers/normalizeHeaderName');\nvar enhanceError = require('../core/enhanceError');\nvar transitionalDefaults = require('./transitional');\n\nvar DEFAULT_CONTENT_TYPE = {\n 'Content-Type': 'application/x-www-form-urlencoded'\n};\n\nfunction setContentTypeIfUnset(headers, value) {\n if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) {\n headers['Content-Type'] = value;\n }\n}\n\nfunction getDefaultAdapter() {\n var adapter;\n if (typeof XMLHttpRequest !== 'undefined') {\n // For browsers use XHR adapter\n adapter = require('../adapters/xhr');\n } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') {\n // For node use HTTP adapter\n adapter = require('../adapters/http');\n }\n return adapter;\n}\n\nfunction stringifySafely(rawValue, parser, encoder) {\n if (utils.isString(rawValue)) {\n try {\n (parser || JSON.parse)(rawValue);\n return utils.trim(rawValue);\n } catch (e) {\n if (e.name !== 'SyntaxError') {\n throw e;\n }\n }\n }\n\n return (encoder || JSON.stringify)(rawValue);\n}\n\nvar defaults = {\n\n transitional: transitionalDefaults,\n\n adapter: getDefaultAdapter(),\n\n transformRequest: [function transformRequest(data, headers) {\n normalizeHeaderName(headers, 'Accept');\n normalizeHeaderName(headers, 'Content-Type');\n\n if (utils.isFormData(data) ||\n utils.isArrayBuffer(data) ||\n utils.isBuffer(data) ||\n utils.isStream(data) ||\n utils.isFile(data) ||\n utils.isBlob(data)\n ) {\n return data;\n }\n if (utils.isArrayBufferView(data)) {\n return data.buffer;\n }\n if (utils.isURLSearchParams(data)) {\n setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8');\n return data.toString();\n }\n if (utils.isObject(data) || (headers && headers['Content-Type'] === 'application/json')) {\n setContentTypeIfUnset(headers, 'application/json');\n return stringifySafely(data);\n }\n return data;\n }],\n\n transformResponse: [function transformResponse(data) {\n var transitional = this.transitional || defaults.transitional;\n var silentJSONParsing = transitional && transitional.silentJSONParsing;\n var forcedJSONParsing = transitional && transitional.forcedJSONParsing;\n var strictJSONParsing = !silentJSONParsing && this.responseType === 'json';\n\n if (strictJSONParsing || (forcedJSONParsing && utils.isString(data) && data.length)) {\n try {\n return JSON.parse(data);\n } catch (e) {\n if (strictJSONParsing) {\n if (e.name === 'SyntaxError') {\n throw enhanceError(e, this, 'E_JSON_PARSE');\n }\n throw e;\n }\n }\n }\n\n return data;\n }],\n\n /**\n * A timeout in milliseconds to abort a request. If set to 0 (default) a\n * timeout is not created.\n */\n timeout: 0,\n\n xsrfCookieName: 'XSRF-TOKEN',\n xsrfHeaderName: 'X-XSRF-TOKEN',\n\n maxContentLength: -1,\n maxBodyLength: -1,\n\n validateStatus: function validateStatus(status) {\n return status >= 200 && status < 300;\n },\n\n headers: {\n common: {\n 'Accept': 'application/json, text/plain, */*'\n }\n }\n};\n\nutils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) {\n defaults.headers[method] = {};\n});\n\nutils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) {\n defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE);\n});\n\nmodule.exports = defaults;\n","'use strict';\n\nmodule.exports = {\n silentJSONParsing: true,\n forcedJSONParsing: true,\n clarifyTimeoutError: false\n};\n","module.exports = {\n \"version\": \"0.26.1\"\n};","'use strict';\n\nmodule.exports = function bind(fn, thisArg) {\n return function wrap() {\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; i++) {\n args[i] = arguments[i];\n }\n return fn.apply(thisArg, args);\n };\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nfunction encode(val) {\n return encodeURIComponent(val).\n replace(/%3A/gi, ':').\n replace(/%24/g, '$').\n replace(/%2C/gi, ',').\n replace(/%20/g, '+').\n replace(/%5B/gi, '[').\n replace(/%5D/gi, ']');\n}\n\n/**\n * Build a URL by appending params to the end\n *\n * @param {string} url The base of the url (e.g., http://www.google.com)\n * @param {object} [params] The params to be appended\n * @returns {string} The formatted url\n */\nmodule.exports = function buildURL(url, params, paramsSerializer) {\n /*eslint no-param-reassign:0*/\n if (!params) {\n return url;\n }\n\n var serializedParams;\n if (paramsSerializer) {\n serializedParams = paramsSerializer(params);\n } else if (utils.isURLSearchParams(params)) {\n serializedParams = params.toString();\n } else {\n var parts = [];\n\n utils.forEach(params, function serialize(val, key) {\n if (val === null || typeof val === 'undefined') {\n return;\n }\n\n if (utils.isArray(val)) {\n key = key + '[]';\n } else {\n val = [val];\n }\n\n utils.forEach(val, function parseValue(v) {\n if (utils.isDate(v)) {\n v = v.toISOString();\n } else if (utils.isObject(v)) {\n v = JSON.stringify(v);\n }\n parts.push(encode(key) + '=' + encode(v));\n });\n });\n\n serializedParams = parts.join('&');\n }\n\n if (serializedParams) {\n var hashmarkIndex = url.indexOf('#');\n if (hashmarkIndex !== -1) {\n url = url.slice(0, hashmarkIndex);\n }\n\n url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams;\n }\n\n return url;\n};\n","'use strict';\n\n/**\n * Creates a new URL by combining the specified URLs\n *\n * @param {string} baseURL The base URL\n * @param {string} relativeURL The relative URL\n * @returns {string} The combined URL\n */\nmodule.exports = function combineURLs(baseURL, relativeURL) {\n return relativeURL\n ? baseURL.replace(/\\/+$/, '') + '/' + relativeURL.replace(/^\\/+/, '')\n : baseURL;\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nmodule.exports = (\n utils.isStandardBrowserEnv() ?\n\n // Standard browser envs support document.cookie\n (function standardBrowserEnv() {\n return {\n write: function write(name, value, expires, path, domain, secure) {\n var cookie = [];\n cookie.push(name + '=' + encodeURIComponent(value));\n\n if (utils.isNumber(expires)) {\n cookie.push('expires=' + new Date(expires).toGMTString());\n }\n\n if (utils.isString(path)) {\n cookie.push('path=' + path);\n }\n\n if (utils.isString(domain)) {\n cookie.push('domain=' + domain);\n }\n\n if (secure === true) {\n cookie.push('secure');\n }\n\n document.cookie = cookie.join('; ');\n },\n\n read: function read(name) {\n var match = document.cookie.match(new RegExp('(^|;\\\\s*)(' + name + ')=([^;]*)'));\n return (match ? decodeURIComponent(match[3]) : null);\n },\n\n remove: function remove(name) {\n this.write(name, '', Date.now() - 86400000);\n }\n };\n })() :\n\n // Non standard browser env (web workers, react-native) lack needed support.\n (function nonStandardBrowserEnv() {\n return {\n write: function write() {},\n read: function read() { return null; },\n remove: function remove() {}\n };\n })()\n);\n","'use strict';\n\n/**\n * Determines whether the specified URL is absolute\n *\n * @param {string} url The URL to test\n * @returns {boolean} True if the specified URL is absolute, otherwise false\n */\nmodule.exports = function isAbsoluteURL(url) {\n // A URL is considered absolute if it begins with \"<scheme>://\" or \"//\" (protocol-relative URL).\n // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed\n // by any combination of letters, digits, plus, period, or hyphen.\n return /^([a-z][a-z\\d+\\-.]*:)?\\/\\//i.test(url);\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\n/**\n * Determines whether the payload is an error thrown by Axios\n *\n * @param {*} payload The value to test\n * @returns {boolean} True if the payload is an error thrown by Axios, otherwise false\n */\nmodule.exports = function isAxiosError(payload) {\n return utils.isObject(payload) && (payload.isAxiosError === true);\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nmodule.exports = (\n utils.isStandardBrowserEnv() ?\n\n // Standard browser envs have full support of the APIs needed to test\n // whether the request URL is of the same origin as current location.\n (function standardBrowserEnv() {\n var msie = /(msie|trident)/i.test(navigator.userAgent);\n var urlParsingNode = document.createElement('a');\n var originURL;\n\n /**\n * Parse a URL to discover it's components\n *\n * @param {String} url The URL to be parsed\n * @returns {Object}\n */\n function resolveURL(url) {\n var href = url;\n\n if (msie) {\n // IE needs attribute set twice to normalize properties\n urlParsingNode.setAttribute('href', href);\n href = urlParsingNode.href;\n }\n\n urlParsingNode.setAttribute('href', href);\n\n // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils\n return {\n href: urlParsingNode.href,\n protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '',\n host: urlParsingNode.host,\n search: urlParsingNode.search ? urlParsingNode.search.replace(/^\\?/, '') : '',\n hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '',\n hostname: urlParsingNode.hostname,\n port: urlParsingNode.port,\n pathname: (urlParsingNode.pathname.charAt(0) === '/') ?\n urlParsingNode.pathname :\n '/' + urlParsingNode.pathname\n };\n }\n\n originURL = resolveURL(window.location.href);\n\n /**\n * Determine if a URL shares the same origin as the current location\n *\n * @param {String} requestURL The URL to test\n * @returns {boolean} True if URL shares the same origin, otherwise false\n */\n return function isURLSameOrigin(requestURL) {\n var parsed = (utils.isString(requestURL)) ? resolveURL(requestURL) : requestURL;\n return (parsed.protocol === originURL.protocol &&\n parsed.host === originURL.host);\n };\n })() :\n\n // Non standard browser envs (web workers, react-native) lack needed support.\n (function nonStandardBrowserEnv() {\n return function isURLSameOrigin() {\n return true;\n };\n })()\n);\n","'use strict';\n\nvar utils = require('../utils');\n\nmodule.exports = function normalizeHeaderName(headers, normalizedName) {\n utils.forEach(headers, function processHeader(value, name) {\n if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) {\n headers[normalizedName] = value;\n delete headers[name];\n }\n });\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\n// Headers whose duplicates are ignored by node\n// c.f. https://nodejs.org/api/http.html#http_message_headers\nvar ignoreDuplicateOf = [\n 'age', 'authorization', 'content-length', 'content-type', 'etag',\n 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since',\n 'last-modified', 'location', 'max-forwards', 'proxy-authorization',\n 'referer', 'retry-after', 'user-agent'\n];\n\n/**\n * Parse headers into an object\n *\n * ```\n * Date: Wed, 27 Aug 2014 08:58:49 GMT\n * Content-Type: application/json\n * Connection: keep-alive\n * Transfer-Encoding: chunked\n * ```\n *\n * @param {String} headers Headers needing to be parsed\n * @returns {Object} Headers parsed into an object\n */\nmodule.exports = function parseHeaders(headers) {\n var parsed = {};\n var key;\n var val;\n var i;\n\n if (!headers) { return parsed; }\n\n utils.forEach(headers.split('\\n'), function parser(line) {\n i = line.indexOf(':');\n key = utils.trim(line.substr(0, i)).toLowerCase();\n val = utils.trim(line.substr(i + 1));\n\n if (key) {\n if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) {\n return;\n }\n if (key === 'set-cookie') {\n parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]);\n } else {\n parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val;\n }\n }\n });\n\n return parsed;\n};\n","'use strict';\n\n/**\n * Syntactic sugar for invoking a function and expanding an array for arguments.\n *\n * Common use case would be to use `Function.prototype.apply`.\n *\n * ```js\n * function f(x, y, z) {}\n * var args = [1, 2, 3];\n * f.apply(null, args);\n * ```\n *\n * With `spread` this example can be re-written.\n *\n * ```js\n * spread(function(x, y, z) {})([1, 2, 3]);\n * ```\n *\n * @param {Function} callback\n * @returns {Function}\n */\nmodule.exports = function spread(callback) {\n return function wrap(arr) {\n return callback.apply(null, arr);\n };\n};\n","'use strict';\n\nvar VERSION = require('../env/data').version;\n\nvar validators = {};\n\n// eslint-disable-next-line func-names\n['object', 'boolean', 'number', 'function', 'string', 'symbol'].forEach(function(type, i) {\n validators[type] = function validator(thing) {\n return typeof thing === type || 'a' + (i < 1 ? 'n ' : ' ') + type;\n };\n});\n\nvar deprecatedWarnings = {};\n\n/**\n * Transitional option validator\n * @param {function|boolean?} validator - set to false if the transitional option has been removed\n * @param {string?} version - deprecated version / removed since version\n * @param {string?} message - some message with additional info\n * @returns {function}\n */\nvalidators.transitional = function transitional(validator, version, message) {\n function formatMessage(opt, desc) {\n return '[Axios v' + VERSION + '] Transitional option \\'' + opt + '\\'' + desc + (message ? '. ' + message : '');\n }\n\n // eslint-disable-next-line func-names\n return function(value, opt, opts) {\n if (validator === false) {\n throw new Error(formatMessage(opt, ' has been removed' + (version ? ' in ' + version : '')));\n }\n\n if (version && !deprecatedWarnings[opt]) {\n deprecatedWarnings[opt] = true;\n // eslint-disable-next-line no-console\n console.warn(\n formatMessage(\n opt,\n ' has been deprecated since v' + version + ' and will be removed in the near future'\n )\n );\n }\n\n return validator ? validator(value, opt, opts) : true;\n };\n};\n\n/**\n * Assert object's properties type\n * @param {object} options\n * @param {object} schema\n * @param {boolean?} allowUnknown\n */\n\nfunction assertOptions(options, schema, allowUnknown) {\n if (typeof options !== 'object') {\n throw new TypeError('options must be an object');\n }\n var keys = Object.keys(options);\n var i = keys.length;\n while (i-- > 0) {\n var opt = keys[i];\n var validator = schema[opt];\n if (validator) {\n var value = options[opt];\n var result = value === undefined || validator(value, opt, options);\n if (result !== true) {\n throw new TypeError('option ' + opt + ' must be ' + result);\n }\n continue;\n }\n if (allowUnknown !== true) {\n throw Error('Unknown option ' + opt);\n }\n }\n}\n\nmodule.exports = {\n assertOptions: assertOptions,\n validators: validators\n};\n","'use strict';\n\nvar bind = require('./helpers/bind');\n\n// utils is a library of generic helper functions non-specific to axios\n\nvar toString = Object.prototype.toString;\n\n/**\n * Determine if a value is an Array\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an Array, otherwise false\n */\nfunction isArray(val) {\n return Array.isArray(val);\n}\n\n/**\n * Determine if a value is undefined\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if the value is undefined, otherwise false\n */\nfunction isUndefined(val) {\n return typeof val === 'undefined';\n}\n\n/**\n * Determine if a value is a Buffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Buffer, otherwise false\n */\nfunction isBuffer(val) {\n return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor)\n && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val);\n}\n\n/**\n * Determine if a value is an ArrayBuffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an ArrayBuffer, otherwise false\n */\nfunction isArrayBuffer(val) {\n return toString.call(val) === '[object ArrayBuffer]';\n}\n\n/**\n * Determine if a value is a FormData\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an FormData, otherwise false\n */\nfunction isFormData(val) {\n return toString.call(val) === '[object FormData]';\n}\n\n/**\n * Determine if a value is a view on an ArrayBuffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false\n */\nfunction isArrayBufferView(val) {\n var result;\n if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) {\n result = ArrayBuffer.isView(val);\n } else {\n result = (val) && (val.buffer) && (isArrayBuffer(val.buffer));\n }\n return result;\n}\n\n/**\n * Determine if a value is a String\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a String, otherwise false\n */\nfunction isString(val) {\n return typeof val === 'string';\n}\n\n/**\n * Determine if a value is a Number\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Number, otherwise false\n */\nfunction isNumber(val) {\n return typeof val === 'number';\n}\n\n/**\n * Determine if a value is an Object\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an Object, otherwise false\n */\nfunction isObject(val) {\n return val !== null && typeof val === 'object';\n}\n\n/**\n * Determine if a value is a plain Object\n *\n * @param {Object} val The value to test\n * @return {boolean} True if value is a plain Object, otherwise false\n */\nfunction isPlainObject(val) {\n if (toString.call(val) !== '[object Object]') {\n return false;\n }\n\n var prototype = Object.getPrototypeOf(val);\n return prototype === null || prototype === Object.prototype;\n}\n\n/**\n * Determine if a value is a Date\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Date, otherwise false\n */\nfunction isDate(val) {\n return toString.call(val) === '[object Date]';\n}\n\n/**\n * Determine if a value is a File\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a File, otherwise false\n */\nfunction isFile(val) {\n return toString.call(val) === '[object File]';\n}\n\n/**\n * Determine if a value is a Blob\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Blob, otherwise false\n */\nfunction isBlob(val) {\n return toString.call(val) === '[object Blob]';\n}\n\n/**\n * Determine if a value is a Function\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Function, otherwise false\n */\nfunction isFunction(val) {\n return toString.call(val) === '[object Function]';\n}\n\n/**\n * Determine if a value is a Stream\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Stream, otherwise false\n */\nfunction isStream(val) {\n return isObject(val) && isFunction(val.pipe);\n}\n\n/**\n * Determine if a value is a URLSearchParams object\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a URLSearchParams object, otherwise false\n */\nfunction isURLSearchParams(val) {\n return toString.call(val) === '[object URLSearchParams]';\n}\n\n/**\n * Trim excess whitespace off the beginning and end of a string\n *\n * @param {String} str The String to trim\n * @returns {String} The String freed of excess whitespace\n */\nfunction trim(str) {\n return str.trim ? str.trim() : str.replace(/^\\s+|\\s+$/g, '');\n}\n\n/**\n * Determine if we're running in a standard browser environment\n *\n * This allows axios to run in a web worker, and react-native.\n * Both environments support XMLHttpRequest, but not fully standard globals.\n *\n * web workers:\n * typeof window -> undefined\n * typeof document -> undefined\n *\n * react-native:\n * navigator.product -> 'ReactNative'\n * nativescript\n * navigator.product -> 'NativeScript' or 'NS'\n */\nfunction isStandardBrowserEnv() {\n if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' ||\n navigator.product === 'NativeScript' ||\n navigator.product === 'NS')) {\n return false;\n }\n return (\n typeof window !== 'undefined' &&\n typeof document !== 'undefined'\n );\n}\n\n/**\n * Iterate over an Array or an Object invoking a function for each item.\n *\n * If `obj` is an Array callback will be called passing\n * the value, index, and complete array for each item.\n *\n * If 'obj' is an Object callback will be called passing\n * the value, key, and complete object for each property.\n *\n * @param {Object|Array} obj The object to iterate\n * @param {Function} fn The callback to invoke for each item\n */\nfunction forEach(obj, fn) {\n // Don't bother if no value provided\n if (obj === null || typeof obj === 'undefined') {\n return;\n }\n\n // Force an array if not already something iterable\n if (typeof obj !== 'object') {\n /*eslint no-param-reassign:0*/\n obj = [obj];\n }\n\n if (isArray(obj)) {\n // Iterate over array values\n for (var i = 0, l = obj.length; i < l; i++) {\n fn.call(null, obj[i], i, obj);\n }\n } else {\n // Iterate over object keys\n for (var key in obj) {\n if (Object.prototype.hasOwnProperty.call(obj, key)) {\n fn.call(null, obj[key], key, obj);\n }\n }\n }\n}\n\n/**\n * Accepts varargs expecting each argument to be an object, then\n * immutably merges the properties of each object and returns result.\n *\n * When multiple objects contain the same key the later object in\n * the arguments list will take precedence.\n *\n * Example:\n *\n * ```js\n * var result = merge({foo: 123}, {foo: 456});\n * console.log(result.foo); // outputs 456\n * ```\n *\n * @param {Object} obj1 Object to merge\n * @returns {Object} Result of all merge properties\n */\nfunction merge(/* obj1, obj2, obj3, ... */) {\n var result = {};\n function assignValue(val, key) {\n if (isPlainObject(result[key]) && isPlainObject(val)) {\n result[key] = merge(result[key], val);\n } else if (isPlainObject(val)) {\n result[key] = merge({}, val);\n } else if (isArray(val)) {\n result[key] = val.slice();\n } else {\n result[key] = val;\n }\n }\n\n for (var i = 0, l = arguments.length; i < l; i++) {\n forEach(arguments[i], assignValue);\n }\n return result;\n}\n\n/**\n * Extends object a by mutably adding to it the properties of object b.\n *\n * @param {Object} a The object to be extended\n * @param {Object} b The object to copy properties from\n * @param {Object} thisArg The object to bind function to\n * @return {Object} The resulting value of object a\n */\nfunction extend(a, b, thisArg) {\n forEach(b, function assignValue(val, key) {\n if (thisArg && typeof val === 'function') {\n a[key] = bind(val, thisArg);\n } else {\n a[key] = val;\n }\n });\n return a;\n}\n\n/**\n * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM)\n *\n * @param {string} content with BOM\n * @return {string} content value without BOM\n */\nfunction stripBOM(content) {\n if (content.charCodeAt(0) === 0xFEFF) {\n content = content.slice(1);\n }\n return content;\n}\n\nmodule.exports = {\n isArray: isArray,\n isArrayBuffer: isArrayBuffer,\n isBuffer: isBuffer,\n isFormData: isFormData,\n isArrayBufferView: isArrayBufferView,\n isString: isString,\n isNumber: isNumber,\n isObject: isObject,\n isPlainObject: isPlainObject,\n isUndefined: isUndefined,\n isDate: isDate,\n isFile: isFile,\n isBlob: isBlob,\n isFunction: isFunction,\n isStream: isStream,\n isURLSearchParams: isURLSearchParams,\n isStandardBrowserEnv: isStandardBrowserEnv,\n forEach: forEach,\n merge: merge,\n extend: extend,\n trim: trim,\n stripBOM: stripBOM\n};\n"],"sourceRoot":""}
\ No newline at end of file diff --git a/node_modules/axios/dist/axios.min.js b/node_modules/axios/dist/axios.min.js new file mode 100644 index 0000000..1ed7cf3 --- /dev/null +++ b/node_modules/axios/dist/axios.min.js @@ -0,0 +1,2 @@ +!function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports.axios=t():e.axios=t()}(this,(function(){return function(e){var t={};function n(r){if(t[r])return t[r].exports;var o=t[r]={i:r,l:!1,exports:{}};return e[r].call(o.exports,o,o.exports,n),o.l=!0,o.exports}return n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)n.d(r,o,function(t){return e[t]}.bind(null,o));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=12)}([function(e,t,n){"use strict";var r=n(3),o=Object.prototype.toString;function i(e){return Array.isArray(e)}function s(e){return void 0===e}function a(e){return"[object ArrayBuffer]"===o.call(e)}function u(e){return null!==e&&"object"==typeof e}function c(e){if("[object Object]"!==o.call(e))return!1;var t=Object.getPrototypeOf(e);return null===t||t===Object.prototype}function f(e){return"[object Function]"===o.call(e)}function l(e,t){if(null!=e)if("object"!=typeof e&&(e=[e]),i(e))for(var n=0,r=e.length;n<r;n++)t.call(null,e[n],n,e);else for(var o in e)Object.prototype.hasOwnProperty.call(e,o)&&t.call(null,e[o],o,e)}e.exports={isArray:i,isArrayBuffer:a,isBuffer:function(e){return null!==e&&!s(e)&&null!==e.constructor&&!s(e.constructor)&&"function"==typeof e.constructor.isBuffer&&e.constructor.isBuffer(e)},isFormData:function(e){return"[object FormData]"===o.call(e)},isArrayBufferView:function(e){return"undefined"!=typeof ArrayBuffer&&ArrayBuffer.isView?ArrayBuffer.isView(e):e&&e.buffer&&a(e.buffer)},isString:function(e){return"string"==typeof e},isNumber:function(e){return"number"==typeof e},isObject:u,isPlainObject:c,isUndefined:s,isDate:function(e){return"[object Date]"===o.call(e)},isFile:function(e){return"[object File]"===o.call(e)},isBlob:function(e){return"[object Blob]"===o.call(e)},isFunction:f,isStream:function(e){return u(e)&&f(e.pipe)},isURLSearchParams:function(e){return"[object URLSearchParams]"===o.call(e)},isStandardBrowserEnv:function(){return("undefined"==typeof navigator||"ReactNative"!==navigator.product&&"NativeScript"!==navigator.product&&"NS"!==navigator.product)&&("undefined"!=typeof window&&"undefined"!=typeof document)},forEach:l,merge:function e(){var t={};function n(n,r){c(t[r])&&c(n)?t[r]=e(t[r],n):c(n)?t[r]=e({},n):i(n)?t[r]=n.slice():t[r]=n}for(var r=0,o=arguments.length;r<o;r++)l(arguments[r],n);return t},extend:function(e,t,n){return l(t,(function(t,o){e[o]=n&&"function"==typeof t?r(t,n):t})),e},trim:function(e){return e.trim?e.trim():e.replace(/^\s+|\s+$/g,"")},stripBOM:function(e){return 65279===e.charCodeAt(0)&&(e=e.slice(1)),e}}},function(e,t,n){"use strict";function r(e){this.message=e}r.prototype.toString=function(){return"Cancel"+(this.message?": "+this.message:"")},r.prototype.__CANCEL__=!0,e.exports=r},function(e,t,n){"use strict";var r=n(0),o=n(18),i=n(5),s=n(6),a={"Content-Type":"application/x-www-form-urlencoded"};function u(e,t){!r.isUndefined(e)&&r.isUndefined(e["Content-Type"])&&(e["Content-Type"]=t)}var c,f={transitional:s,adapter:(("undefined"!=typeof XMLHttpRequest||"undefined"!=typeof process&&"[object process]"===Object.prototype.toString.call(process))&&(c=n(7)),c),transformRequest:[function(e,t){return o(t,"Accept"),o(t,"Content-Type"),r.isFormData(e)||r.isArrayBuffer(e)||r.isBuffer(e)||r.isStream(e)||r.isFile(e)||r.isBlob(e)?e:r.isArrayBufferView(e)?e.buffer:r.isURLSearchParams(e)?(u(t,"application/x-www-form-urlencoded;charset=utf-8"),e.toString()):r.isObject(e)||t&&"application/json"===t["Content-Type"]?(u(t,"application/json"),function(e,t,n){if(r.isString(e))try{return(t||JSON.parse)(e),r.trim(e)}catch(e){if("SyntaxError"!==e.name)throw e}return(n||JSON.stringify)(e)}(e)):e}],transformResponse:[function(e){var t=this.transitional||f.transitional,n=t&&t.silentJSONParsing,o=t&&t.forcedJSONParsing,s=!n&&"json"===this.responseType;if(s||o&&r.isString(e)&&e.length)try{return JSON.parse(e)}catch(e){if(s){if("SyntaxError"===e.name)throw i(e,this,"E_JSON_PARSE");throw e}}return e}],timeout:0,xsrfCookieName:"XSRF-TOKEN",xsrfHeaderName:"X-XSRF-TOKEN",maxContentLength:-1,maxBodyLength:-1,validateStatus:function(e){return e>=200&&e<300},headers:{common:{Accept:"application/json, text/plain, */*"}}};r.forEach(["delete","get","head"],(function(e){f.headers[e]={}})),r.forEach(["post","put","patch"],(function(e){f.headers[e]=r.merge(a)})),e.exports=f},function(e,t,n){"use strict";e.exports=function(e,t){return function(){for(var n=new Array(arguments.length),r=0;r<n.length;r++)n[r]=arguments[r];return e.apply(t,n)}}},function(e,t,n){"use strict";var r=n(0);function o(e){return encodeURIComponent(e).replace(/%3A/gi,":").replace(/%24/g,"$").replace(/%2C/gi,",").replace(/%20/g,"+").replace(/%5B/gi,"[").replace(/%5D/gi,"]")}e.exports=function(e,t,n){if(!t)return e;var i;if(n)i=n(t);else if(r.isURLSearchParams(t))i=t.toString();else{var s=[];r.forEach(t,(function(e,t){null!=e&&(r.isArray(e)?t+="[]":e=[e],r.forEach(e,(function(e){r.isDate(e)?e=e.toISOString():r.isObject(e)&&(e=JSON.stringify(e)),s.push(o(t)+"="+o(e))})))})),i=s.join("&")}if(i){var a=e.indexOf("#");-1!==a&&(e=e.slice(0,a)),e+=(-1===e.indexOf("?")?"?":"&")+i}return e}},function(e,t,n){"use strict";e.exports=function(e,t,n,r,o){return e.config=t,n&&(e.code=n),e.request=r,e.response=o,e.isAxiosError=!0,e.toJSON=function(){return{message:this.message,name:this.name,description:this.description,number:this.number,fileName:this.fileName,lineNumber:this.lineNumber,columnNumber:this.columnNumber,stack:this.stack,config:this.config,code:this.code,status:this.response&&this.response.status?this.response.status:null}},e}},function(e,t,n){"use strict";e.exports={silentJSONParsing:!0,forcedJSONParsing:!0,clarifyTimeoutError:!1}},function(e,t,n){"use strict";var r=n(0),o=n(19),i=n(20),s=n(4),a=n(21),u=n(24),c=n(25),f=n(8),l=n(6),p=n(1);e.exports=function(e){return new Promise((function(t,n){var d,h=e.data,m=e.headers,v=e.responseType;function y(){e.cancelToken&&e.cancelToken.unsubscribe(d),e.signal&&e.signal.removeEventListener("abort",d)}r.isFormData(h)&&delete m["Content-Type"];var g=new XMLHttpRequest;if(e.auth){var b=e.auth.username||"",x=e.auth.password?unescape(encodeURIComponent(e.auth.password)):"";m.Authorization="Basic "+btoa(b+":"+x)}var w=a(e.baseURL,e.url);function E(){if(g){var r="getAllResponseHeaders"in g?u(g.getAllResponseHeaders()):null,i={data:v&&"text"!==v&&"json"!==v?g.response:g.responseText,status:g.status,statusText:g.statusText,headers:r,config:e,request:g};o((function(e){t(e),y()}),(function(e){n(e),y()}),i),g=null}}if(g.open(e.method.toUpperCase(),s(w,e.params,e.paramsSerializer),!0),g.timeout=e.timeout,"onloadend"in g?g.onloadend=E:g.onreadystatechange=function(){g&&4===g.readyState&&(0!==g.status||g.responseURL&&0===g.responseURL.indexOf("file:"))&&setTimeout(E)},g.onabort=function(){g&&(n(f("Request aborted",e,"ECONNABORTED",g)),g=null)},g.onerror=function(){n(f("Network Error",e,null,g)),g=null},g.ontimeout=function(){var t=e.timeout?"timeout of "+e.timeout+"ms exceeded":"timeout exceeded",r=e.transitional||l;e.timeoutErrorMessage&&(t=e.timeoutErrorMessage),n(f(t,e,r.clarifyTimeoutError?"ETIMEDOUT":"ECONNABORTED",g)),g=null},r.isStandardBrowserEnv()){var O=(e.withCredentials||c(w))&&e.xsrfCookieName?i.read(e.xsrfCookieName):void 0;O&&(m[e.xsrfHeaderName]=O)}"setRequestHeader"in g&&r.forEach(m,(function(e,t){void 0===h&&"content-type"===t.toLowerCase()?delete m[t]:g.setRequestHeader(t,e)})),r.isUndefined(e.withCredentials)||(g.withCredentials=!!e.withCredentials),v&&"json"!==v&&(g.responseType=e.responseType),"function"==typeof e.onDownloadProgress&&g.addEventListener("progress",e.onDownloadProgress),"function"==typeof e.onUploadProgress&&g.upload&&g.upload.addEventListener("progress",e.onUploadProgress),(e.cancelToken||e.signal)&&(d=function(e){g&&(n(!e||e&&e.type?new p("canceled"):e),g.abort(),g=null)},e.cancelToken&&e.cancelToken.subscribe(d),e.signal&&(e.signal.aborted?d():e.signal.addEventListener("abort",d))),h||(h=null),g.send(h)}))}},function(e,t,n){"use strict";var r=n(5);e.exports=function(e,t,n,o,i){var s=new Error(e);return r(s,t,n,o,i)}},function(e,t,n){"use strict";e.exports=function(e){return!(!e||!e.__CANCEL__)}},function(e,t,n){"use strict";var r=n(0);e.exports=function(e,t){t=t||{};var n={};function o(e,t){return r.isPlainObject(e)&&r.isPlainObject(t)?r.merge(e,t):r.isPlainObject(t)?r.merge({},t):r.isArray(t)?t.slice():t}function i(n){return r.isUndefined(t[n])?r.isUndefined(e[n])?void 0:o(void 0,e[n]):o(e[n],t[n])}function s(e){if(!r.isUndefined(t[e]))return o(void 0,t[e])}function a(n){return r.isUndefined(t[n])?r.isUndefined(e[n])?void 0:o(void 0,e[n]):o(void 0,t[n])}function u(n){return n in t?o(e[n],t[n]):n in e?o(void 0,e[n]):void 0}var c={url:s,method:s,data:s,baseURL:a,transformRequest:a,transformResponse:a,paramsSerializer:a,timeout:a,timeoutMessage:a,withCredentials:a,adapter:a,responseType:a,xsrfCookieName:a,xsrfHeaderName:a,onUploadProgress:a,onDownloadProgress:a,decompress:a,maxContentLength:a,maxBodyLength:a,transport:a,httpAgent:a,httpsAgent:a,cancelToken:a,socketPath:a,responseEncoding:a,validateStatus:u};return r.forEach(Object.keys(e).concat(Object.keys(t)),(function(e){var t=c[e]||i,o=t(e);r.isUndefined(o)&&t!==u||(n[e]=o)})),n}},function(e,t){e.exports={version:"0.26.1"}},function(e,t,n){e.exports=n(13)},function(e,t,n){"use strict";var r=n(0),o=n(3),i=n(14),s=n(10);var a=function e(t){var n=new i(t),a=o(i.prototype.request,n);return r.extend(a,i.prototype,n),r.extend(a,n),a.create=function(n){return e(s(t,n))},a}(n(2));a.Axios=i,a.Cancel=n(1),a.CancelToken=n(27),a.isCancel=n(9),a.VERSION=n(11).version,a.all=function(e){return Promise.all(e)},a.spread=n(28),a.isAxiosError=n(29),e.exports=a,e.exports.default=a},function(e,t,n){"use strict";var r=n(0),o=n(4),i=n(15),s=n(16),a=n(10),u=n(26),c=u.validators;function f(e){this.defaults=e,this.interceptors={request:new i,response:new i}}f.prototype.request=function(e,t){"string"==typeof e?(t=t||{}).url=e:t=e||{},(t=a(this.defaults,t)).method?t.method=t.method.toLowerCase():this.defaults.method?t.method=this.defaults.method.toLowerCase():t.method="get";var n=t.transitional;void 0!==n&&u.assertOptions(n,{silentJSONParsing:c.transitional(c.boolean),forcedJSONParsing:c.transitional(c.boolean),clarifyTimeoutError:c.transitional(c.boolean)},!1);var r=[],o=!0;this.interceptors.request.forEach((function(e){"function"==typeof e.runWhen&&!1===e.runWhen(t)||(o=o&&e.synchronous,r.unshift(e.fulfilled,e.rejected))}));var i,f=[];if(this.interceptors.response.forEach((function(e){f.push(e.fulfilled,e.rejected)})),!o){var l=[s,void 0];for(Array.prototype.unshift.apply(l,r),l=l.concat(f),i=Promise.resolve(t);l.length;)i=i.then(l.shift(),l.shift());return i}for(var p=t;r.length;){var d=r.shift(),h=r.shift();try{p=d(p)}catch(e){h(e);break}}try{i=s(p)}catch(e){return Promise.reject(e)}for(;f.length;)i=i.then(f.shift(),f.shift());return i},f.prototype.getUri=function(e){return e=a(this.defaults,e),o(e.url,e.params,e.paramsSerializer).replace(/^\?/,"")},r.forEach(["delete","get","head","options"],(function(e){f.prototype[e]=function(t,n){return this.request(a(n||{},{method:e,url:t,data:(n||{}).data}))}})),r.forEach(["post","put","patch"],(function(e){f.prototype[e]=function(t,n,r){return this.request(a(r||{},{method:e,url:t,data:n}))}})),e.exports=f},function(e,t,n){"use strict";var r=n(0);function o(){this.handlers=[]}o.prototype.use=function(e,t,n){return this.handlers.push({fulfilled:e,rejected:t,synchronous:!!n&&n.synchronous,runWhen:n?n.runWhen:null}),this.handlers.length-1},o.prototype.eject=function(e){this.handlers[e]&&(this.handlers[e]=null)},o.prototype.forEach=function(e){r.forEach(this.handlers,(function(t){null!==t&&e(t)}))},e.exports=o},function(e,t,n){"use strict";var r=n(0),o=n(17),i=n(9),s=n(2),a=n(1);function u(e){if(e.cancelToken&&e.cancelToken.throwIfRequested(),e.signal&&e.signal.aborted)throw new a("canceled")}e.exports=function(e){return u(e),e.headers=e.headers||{},e.data=o.call(e,e.data,e.headers,e.transformRequest),e.headers=r.merge(e.headers.common||{},e.headers[e.method]||{},e.headers),r.forEach(["delete","get","head","post","put","patch","common"],(function(t){delete e.headers[t]})),(e.adapter||s.adapter)(e).then((function(t){return u(e),t.data=o.call(e,t.data,t.headers,e.transformResponse),t}),(function(t){return i(t)||(u(e),t&&t.response&&(t.response.data=o.call(e,t.response.data,t.response.headers,e.transformResponse))),Promise.reject(t)}))}},function(e,t,n){"use strict";var r=n(0),o=n(2);e.exports=function(e,t,n){var i=this||o;return r.forEach(n,(function(n){e=n.call(i,e,t)})),e}},function(e,t,n){"use strict";var r=n(0);e.exports=function(e,t){r.forEach(e,(function(n,r){r!==t&&r.toUpperCase()===t.toUpperCase()&&(e[t]=n,delete e[r])}))}},function(e,t,n){"use strict";var r=n(8);e.exports=function(e,t,n){var o=n.config.validateStatus;n.status&&o&&!o(n.status)?t(r("Request failed with status code "+n.status,n.config,null,n.request,n)):e(n)}},function(e,t,n){"use strict";var r=n(0);e.exports=r.isStandardBrowserEnv()?{write:function(e,t,n,o,i,s){var a=[];a.push(e+"="+encodeURIComponent(t)),r.isNumber(n)&&a.push("expires="+new Date(n).toGMTString()),r.isString(o)&&a.push("path="+o),r.isString(i)&&a.push("domain="+i),!0===s&&a.push("secure"),document.cookie=a.join("; ")},read:function(e){var t=document.cookie.match(new RegExp("(^|;\\s*)("+e+")=([^;]*)"));return t?decodeURIComponent(t[3]):null},remove:function(e){this.write(e,"",Date.now()-864e5)}}:{write:function(){},read:function(){return null},remove:function(){}}},function(e,t,n){"use strict";var r=n(22),o=n(23);e.exports=function(e,t){return e&&!r(t)?o(e,t):t}},function(e,t,n){"use strict";e.exports=function(e){return/^([a-z][a-z\d+\-.]*:)?\/\//i.test(e)}},function(e,t,n){"use strict";e.exports=function(e,t){return t?e.replace(/\/+$/,"")+"/"+t.replace(/^\/+/,""):e}},function(e,t,n){"use strict";var r=n(0),o=["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"];e.exports=function(e){var t,n,i,s={};return e?(r.forEach(e.split("\n"),(function(e){if(i=e.indexOf(":"),t=r.trim(e.substr(0,i)).toLowerCase(),n=r.trim(e.substr(i+1)),t){if(s[t]&&o.indexOf(t)>=0)return;s[t]="set-cookie"===t?(s[t]?s[t]:[]).concat([n]):s[t]?s[t]+", "+n:n}})),s):s}},function(e,t,n){"use strict";var r=n(0);e.exports=r.isStandardBrowserEnv()?function(){var e,t=/(msie|trident)/i.test(navigator.userAgent),n=document.createElement("a");function o(e){var r=e;return t&&(n.setAttribute("href",r),r=n.href),n.setAttribute("href",r),{href:n.href,protocol:n.protocol?n.protocol.replace(/:$/,""):"",host:n.host,search:n.search?n.search.replace(/^\?/,""):"",hash:n.hash?n.hash.replace(/^#/,""):"",hostname:n.hostname,port:n.port,pathname:"/"===n.pathname.charAt(0)?n.pathname:"/"+n.pathname}}return e=o(window.location.href),function(t){var n=r.isString(t)?o(t):t;return n.protocol===e.protocol&&n.host===e.host}}():function(){return!0}},function(e,t,n){"use strict";var r=n(11).version,o={};["object","boolean","number","function","string","symbol"].forEach((function(e,t){o[e]=function(n){return typeof n===e||"a"+(t<1?"n ":" ")+e}}));var i={};o.transitional=function(e,t,n){function o(e,t){return"[Axios v"+r+"] Transitional option '"+e+"'"+t+(n?". "+n:"")}return function(n,r,s){if(!1===e)throw new Error(o(r," has been removed"+(t?" in "+t:"")));return t&&!i[r]&&(i[r]=!0,console.warn(o(r," has been deprecated since v"+t+" and will be removed in the near future"))),!e||e(n,r,s)}},e.exports={assertOptions:function(e,t,n){if("object"!=typeof e)throw new TypeError("options must be an object");for(var r=Object.keys(e),o=r.length;o-- >0;){var i=r[o],s=t[i];if(s){var a=e[i],u=void 0===a||s(a,i,e);if(!0!==u)throw new TypeError("option "+i+" must be "+u)}else if(!0!==n)throw Error("Unknown option "+i)}},validators:o}},function(e,t,n){"use strict";var r=n(1);function o(e){if("function"!=typeof e)throw new TypeError("executor must be a function.");var t;this.promise=new Promise((function(e){t=e}));var n=this;this.promise.then((function(e){if(n._listeners){var t,r=n._listeners.length;for(t=0;t<r;t++)n._listeners[t](e);n._listeners=null}})),this.promise.then=function(e){var t,r=new Promise((function(e){n.subscribe(e),t=e})).then(e);return r.cancel=function(){n.unsubscribe(t)},r},e((function(e){n.reason||(n.reason=new r(e),t(n.reason))}))}o.prototype.throwIfRequested=function(){if(this.reason)throw this.reason},o.prototype.subscribe=function(e){this.reason?e(this.reason):this._listeners?this._listeners.push(e):this._listeners=[e]},o.prototype.unsubscribe=function(e){if(this._listeners){var t=this._listeners.indexOf(e);-1!==t&&this._listeners.splice(t,1)}},o.source=function(){var e;return{token:new o((function(t){e=t})),cancel:e}},e.exports=o},function(e,t,n){"use strict";e.exports=function(e){return function(t){return e.apply(null,t)}}},function(e,t,n){"use strict";var r=n(0);e.exports=function(e){return r.isObject(e)&&!0===e.isAxiosError}}])})); +//# sourceMappingURL=axios.min.map
\ No newline at end of file diff --git a/node_modules/axios/dist/axios.min.map b/node_modules/axios/dist/axios.min.map new file mode 100644 index 0000000..9ce1abb --- /dev/null +++ b/node_modules/axios/dist/axios.min.map @@ -0,0 +1 @@ +{"version":3,"sources":["webpack://axios/webpack/universalModuleDefinition","webpack://axios/webpack/bootstrap","webpack://axios/./lib/utils.js","webpack://axios/./lib/cancel/Cancel.js","webpack://axios/./lib/defaults/index.js","webpack://axios/./lib/helpers/bind.js","webpack://axios/./lib/helpers/buildURL.js","webpack://axios/./lib/core/enhanceError.js","webpack://axios/./lib/defaults/transitional.js","webpack://axios/./lib/adapters/xhr.js","webpack://axios/./lib/core/createError.js","webpack://axios/./lib/cancel/isCancel.js","webpack://axios/./lib/core/mergeConfig.js","webpack://axios/./lib/env/data.js","webpack://axios/./index.js","webpack://axios/./lib/axios.js","webpack://axios/./lib/core/Axios.js","webpack://axios/./lib/core/InterceptorManager.js","webpack://axios/./lib/core/dispatchRequest.js","webpack://axios/./lib/core/transformData.js","webpack://axios/./lib/helpers/normalizeHeaderName.js","webpack://axios/./lib/core/settle.js","webpack://axios/./lib/helpers/cookies.js","webpack://axios/./lib/core/buildFullPath.js","webpack://axios/./lib/helpers/isAbsoluteURL.js","webpack://axios/./lib/helpers/combineURLs.js","webpack://axios/./lib/helpers/parseHeaders.js","webpack://axios/./lib/helpers/isURLSameOrigin.js","webpack://axios/./lib/helpers/validator.js","webpack://axios/./lib/cancel/CancelToken.js","webpack://axios/./lib/helpers/spread.js","webpack://axios/./lib/helpers/isAxiosError.js"],"names":["root","factory","exports","module","define","amd","this","installedModules","__webpack_require__","moduleId","i","l","modules","call","m","c","d","name","getter","o","Object","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","prototype","hasOwnProperty","p","s","toString","isArray","val","Array","isUndefined","isArrayBuffer","isObject","isPlainObject","getPrototypeOf","isFunction","forEach","obj","fn","length","isBuffer","constructor","isFormData","isArrayBufferView","ArrayBuffer","isView","buffer","isString","isNumber","isDate","isFile","isBlob","isStream","pipe","isURLSearchParams","isStandardBrowserEnv","navigator","product","window","document","merge","result","assignValue","slice","arguments","extend","a","b","thisArg","trim","str","replace","stripBOM","content","charCodeAt","Cancel","message","__CANCEL__","utils","normalizeHeaderName","enhanceError","transitionalDefaults","DEFAULT_CONTENT_TYPE","setContentTypeIfUnset","headers","adapter","defaults","transitional","XMLHttpRequest","process","transformRequest","data","rawValue","parser","encoder","JSON","parse","e","stringify","stringifySafely","transformResponse","silentJSONParsing","forcedJSONParsing","strictJSONParsing","responseType","timeout","xsrfCookieName","xsrfHeaderName","maxContentLength","maxBodyLength","validateStatus","status","common","method","args","apply","encode","encodeURIComponent","url","params","paramsSerializer","serializedParams","parts","v","toISOString","push","join","hashmarkIndex","indexOf","error","config","code","request","response","isAxiosError","toJSON","description","number","fileName","lineNumber","columnNumber","stack","clarifyTimeoutError","settle","cookies","buildURL","buildFullPath","parseHeaders","isURLSameOrigin","createError","Promise","resolve","reject","onCanceled","requestData","requestHeaders","done","cancelToken","unsubscribe","signal","removeEventListener","auth","username","password","unescape","Authorization","btoa","fullPath","baseURL","onloadend","responseHeaders","getAllResponseHeaders","responseText","statusText","err","open","toUpperCase","onreadystatechange","readyState","responseURL","setTimeout","onabort","onerror","ontimeout","timeoutErrorMessage","xsrfValue","withCredentials","read","undefined","toLowerCase","setRequestHeader","onDownloadProgress","addEventListener","onUploadProgress","upload","cancel","type","abort","subscribe","aborted","send","Error","config1","config2","getMergedValue","target","source","mergeDeepProperties","prop","valueFromConfig2","defaultToConfig2","mergeDirectKeys","mergeMap","keys","concat","configValue","Axios","mergeConfig","axios","createInstance","defaultConfig","context","instance","instanceConfig","CancelToken","isCancel","VERSION","version","all","promises","spread","default","InterceptorManager","dispatchRequest","validator","validators","interceptors","configOrUrl","assertOptions","boolean","requestInterceptorChain","synchronousRequestInterceptors","interceptor","runWhen","synchronous","unshift","fulfilled","rejected","promise","responseInterceptorChain","chain","then","shift","newConfig","onFulfilled","onRejected","getUri","handlers","use","options","eject","id","h","transformData","throwIfCancellationRequested","throwIfRequested","reason","fns","normalizedName","write","expires","path","domain","secure","cookie","Date","toGMTString","match","RegExp","decodeURIComponent","remove","now","isAbsoluteURL","combineURLs","requestedURL","test","relativeURL","ignoreDuplicateOf","parsed","split","line","substr","originURL","msie","userAgent","urlParsingNode","createElement","resolveURL","href","setAttribute","protocol","host","search","hash","hostname","port","pathname","charAt","location","requestURL","thing","deprecatedWarnings","formatMessage","opt","desc","opts","console","warn","schema","allowUnknown","TypeError","executor","resolvePromise","token","_listeners","onfulfilled","_resolve","listener","index","splice","callback","arr","payload"],"mappings":"CAAA,SAA2CA,EAAMC,GAC1B,iBAAZC,SAA0C,iBAAXC,OACxCA,OAAOD,QAAUD,IACQ,mBAAXG,QAAyBA,OAAOC,IAC9CD,OAAO,GAAIH,GACe,iBAAZC,QACdA,QAAe,MAAID,IAEnBD,EAAY,MAAIC,IARlB,CASGK,MAAM,WACT,O,YCTE,IAAIC,EAAmB,GAGvB,SAASC,EAAoBC,GAG5B,GAAGF,EAAiBE,GACnB,OAAOF,EAAiBE,GAAUP,QAGnC,IAAIC,EAASI,EAAiBE,GAAY,CACzCC,EAAGD,EACHE,GAAG,EACHT,QAAS,IAUV,OANAU,EAAQH,GAAUI,KAAKV,EAAOD,QAASC,EAAQA,EAAOD,QAASM,GAG/DL,EAAOQ,GAAI,EAGJR,EAAOD,QA0Df,OArDAM,EAAoBM,EAAIF,EAGxBJ,EAAoBO,EAAIR,EAGxBC,EAAoBQ,EAAI,SAASd,EAASe,EAAMC,GAC3CV,EAAoBW,EAAEjB,EAASe,IAClCG,OAAOC,eAAenB,EAASe,EAAM,CAAEK,YAAY,EAAMC,IAAKL,KAKhEV,EAAoBgB,EAAI,SAAStB,GACX,oBAAXuB,QAA0BA,OAAOC,aAC1CN,OAAOC,eAAenB,EAASuB,OAAOC,YAAa,CAAEC,MAAO,WAE7DP,OAAOC,eAAenB,EAAS,aAAc,CAAEyB,OAAO,KAQvDnB,EAAoBoB,EAAI,SAASD,EAAOE,GAEvC,GADU,EAAPA,IAAUF,EAAQnB,EAAoBmB,IAC/B,EAAPE,EAAU,OAAOF,EACpB,GAAW,EAAPE,GAA8B,iBAAVF,GAAsBA,GAASA,EAAMG,WAAY,OAAOH,EAChF,IAAII,EAAKX,OAAOY,OAAO,MAGvB,GAFAxB,EAAoBgB,EAAEO,GACtBX,OAAOC,eAAeU,EAAI,UAAW,CAAET,YAAY,EAAMK,MAAOA,IACtD,EAAPE,GAA4B,iBAATF,EAAmB,IAAI,IAAIM,KAAON,EAAOnB,EAAoBQ,EAAEe,EAAIE,EAAK,SAASA,GAAO,OAAON,EAAMM,IAAQC,KAAK,KAAMD,IAC9I,OAAOF,GAIRvB,EAAoB2B,EAAI,SAAShC,GAChC,IAAIe,EAASf,GAAUA,EAAO2B,WAC7B,WAAwB,OAAO3B,EAAgB,SAC/C,WAA8B,OAAOA,GAEtC,OADAK,EAAoBQ,EAAEE,EAAQ,IAAKA,GAC5BA,GAIRV,EAAoBW,EAAI,SAASiB,EAAQC,GAAY,OAAOjB,OAAOkB,UAAUC,eAAe1B,KAAKuB,EAAQC,IAGzG7B,EAAoBgC,EAAI,GAIjBhC,EAAoBA,EAAoBiC,EAAI,I,+BChFrD,IAAIP,EAAO,EAAQ,GAIfQ,EAAWtB,OAAOkB,UAAUI,SAQhC,SAASC,EAAQC,GACf,OAAOC,MAAMF,QAAQC,GASvB,SAASE,EAAYF,GACnB,YAAsB,IAARA,EAoBhB,SAASG,EAAcH,GACrB,MAA8B,yBAAvBF,EAAS7B,KAAK+B,GAuDvB,SAASI,EAASJ,GAChB,OAAe,OAARA,GAA+B,iBAARA,EAShC,SAASK,EAAcL,GACrB,GAA2B,oBAAvBF,EAAS7B,KAAK+B,GAChB,OAAO,EAGT,IAAIN,EAAYlB,OAAO8B,eAAeN,GACtC,OAAqB,OAAdN,GAAsBA,IAAclB,OAAOkB,UAuCpD,SAASa,EAAWP,GAClB,MAA8B,sBAAvBF,EAAS7B,KAAK+B,GAwEvB,SAASQ,EAAQC,EAAKC,GAEpB,GAAID,QAUJ,GALmB,iBAARA,IAETA,EAAM,CAACA,IAGLV,EAAQU,GAEV,IAAK,IAAI3C,EAAI,EAAGC,EAAI0C,EAAIE,OAAQ7C,EAAIC,EAAGD,IACrC4C,EAAGzC,KAAK,KAAMwC,EAAI3C,GAAIA,EAAG2C,QAI3B,IAAK,IAAIpB,KAAOoB,EACVjC,OAAOkB,UAAUC,eAAe1B,KAAKwC,EAAKpB,IAC5CqB,EAAGzC,KAAK,KAAMwC,EAAIpB,GAAMA,EAAKoB,GA2ErClD,EAAOD,QAAU,CACfyC,QAASA,EACTI,cAAeA,EACfS,SAtSF,SAAkBZ,GAChB,OAAe,OAARA,IAAiBE,EAAYF,IAA4B,OAApBA,EAAIa,cAAyBX,EAAYF,EAAIa,cAChD,mBAA7Bb,EAAIa,YAAYD,UAA2BZ,EAAIa,YAAYD,SAASZ,IAqShFc,WAlRF,SAAoBd,GAClB,MAA8B,sBAAvBF,EAAS7B,KAAK+B,IAkRrBe,kBAzQF,SAA2Bf,GAOzB,MAL4B,oBAAhBgB,aAAiCA,YAAkB,OACpDA,YAAYC,OAAOjB,GAEnB,GAAUA,EAAU,QAAMG,EAAcH,EAAIkB,SAqQvDC,SA1PF,SAAkBnB,GAChB,MAAsB,iBAARA,GA0PdoB,SAjPF,SAAkBpB,GAChB,MAAsB,iBAARA,GAiPdI,SAAUA,EACVC,cAAeA,EACfH,YAAaA,EACbmB,OAlNF,SAAgBrB,GACd,MAA8B,kBAAvBF,EAAS7B,KAAK+B,IAkNrBsB,OAzMF,SAAgBtB,GACd,MAA8B,kBAAvBF,EAAS7B,KAAK+B,IAyMrBuB,OAhMF,SAAgBvB,GACd,MAA8B,kBAAvBF,EAAS7B,KAAK+B,IAgMrBO,WAAYA,EACZiB,SA9KF,SAAkBxB,GAChB,OAAOI,EAASJ,IAAQO,EAAWP,EAAIyB,OA8KvCC,kBArKF,SAA2B1B,GACzB,MAA8B,6BAAvBF,EAAS7B,KAAK+B,IAqKrB2B,qBAzIF,WACE,OAAyB,oBAAdC,WAAoD,gBAAtBA,UAAUC,SACY,iBAAtBD,UAAUC,SACY,OAAtBD,UAAUC,WAI/B,oBAAXC,QACa,oBAAbC,WAkITvB,QAASA,EACTwB,MAvEF,SAASA,IACP,IAAIC,EAAS,GACb,SAASC,EAAYlC,EAAKX,GACpBgB,EAAc4B,EAAO5C,KAASgB,EAAcL,GAC9CiC,EAAO5C,GAAO2C,EAAMC,EAAO5C,GAAMW,GACxBK,EAAcL,GACvBiC,EAAO5C,GAAO2C,EAAM,GAAIhC,GACfD,EAAQC,GACjBiC,EAAO5C,GAAOW,EAAImC,QAElBF,EAAO5C,GAAOW,EAIlB,IAAK,IAAIlC,EAAI,EAAGC,EAAIqE,UAAUzB,OAAQ7C,EAAIC,EAAGD,IAC3C0C,EAAQ4B,UAAUtE,GAAIoE,GAExB,OAAOD,GAuDPI,OA5CF,SAAgBC,EAAGC,EAAGC,GAQpB,OAPAhC,EAAQ+B,GAAG,SAAqBvC,EAAKX,GAEjCiD,EAAEjD,GADAmD,GAA0B,mBAARxC,EACXV,EAAKU,EAAKwC,GAEVxC,KAGNsC,GAqCPG,KAhKF,SAAcC,GACZ,OAAOA,EAAID,KAAOC,EAAID,OAASC,EAAIC,QAAQ,aAAc,KAgKzDC,SA7BF,SAAkBC,GAIhB,OAH8B,QAA1BA,EAAQC,WAAW,KACrBD,EAAUA,EAAQV,MAAM,IAEnBU,K,6BC1TT,SAASE,EAAOC,GACdtF,KAAKsF,QAAUA,EAGjBD,EAAOrD,UAAUI,SAAW,WAC1B,MAAO,UAAYpC,KAAKsF,QAAU,KAAOtF,KAAKsF,QAAU,KAG1DD,EAAOrD,UAAUuD,YAAa,EAE9B1F,EAAOD,QAAUyF,G,6BChBjB,IAAIG,EAAQ,EAAQ,GAChBC,EAAsB,EAAQ,IAC9BC,EAAe,EAAQ,GACvBC,EAAuB,EAAQ,GAE/BC,EAAuB,CACzB,eAAgB,qCAGlB,SAASC,EAAsBC,EAASzE,IACjCmE,EAAMhD,YAAYsD,IAAYN,EAAMhD,YAAYsD,EAAQ,mBAC3DA,EAAQ,gBAAkBzE,GA+B9B,IA1BM0E,EA0BFC,EAAW,CAEbC,aAAcN,EAEdI,UA7B8B,oBAAnBG,gBAGmB,oBAAZC,SAAuE,qBAA5CrF,OAAOkB,UAAUI,SAAS7B,KAAK4F,YAD1EJ,EAAU,EAAQ,IAKbA,GAwBPK,iBAAkB,CAAC,SAA0BC,EAAMP,GAIjD,OAHAL,EAAoBK,EAAS,UAC7BL,EAAoBK,EAAS,gBAEzBN,EAAMpC,WAAWiD,IACnBb,EAAM/C,cAAc4D,IACpBb,EAAMtC,SAASmD,IACfb,EAAM1B,SAASuC,IACfb,EAAM5B,OAAOyC,IACbb,EAAM3B,OAAOwC,GAENA,EAELb,EAAMnC,kBAAkBgD,GACnBA,EAAK7C,OAEVgC,EAAMxB,kBAAkBqC,IAC1BR,EAAsBC,EAAS,mDACxBO,EAAKjE,YAEVoD,EAAM9C,SAAS2D,IAAUP,GAAuC,qBAA5BA,EAAQ,iBAC9CD,EAAsBC,EAAS,oBA1CrC,SAAyBQ,EAAUC,EAAQC,GACzC,GAAIhB,EAAM/B,SAAS6C,GACjB,IAEE,OADCC,GAAUE,KAAKC,OAAOJ,GAChBd,EAAMT,KAAKuB,GAClB,MAAOK,GACP,GAAe,gBAAXA,EAAEhG,KACJ,MAAMgG,EAKZ,OAAQH,GAAWC,KAAKG,WAAWN,GA+BxBO,CAAgBR,IAElBA,IAGTS,kBAAmB,CAAC,SAA2BT,GAC7C,IAAIJ,EAAejG,KAAKiG,cAAgBD,EAASC,aAC7Cc,EAAoBd,GAAgBA,EAAac,kBACjDC,EAAoBf,GAAgBA,EAAae,kBACjDC,GAAqBF,GAA2C,SAAtB/G,KAAKkH,aAEnD,GAAID,GAAsBD,GAAqBxB,EAAM/B,SAAS4C,IAASA,EAAKpD,OAC1E,IACE,OAAOwD,KAAKC,MAAML,GAClB,MAAOM,GACP,GAAIM,EAAmB,CACrB,GAAe,gBAAXN,EAAEhG,KACJ,MAAM+E,EAAaiB,EAAG3G,KAAM,gBAE9B,MAAM2G,GAKZ,OAAON,IAOTc,QAAS,EAETC,eAAgB,aAChBC,eAAgB,eAEhBC,kBAAmB,EACnBC,eAAgB,EAEhBC,eAAgB,SAAwBC,GACtC,OAAOA,GAAU,KAAOA,EAAS,KAGnC3B,QAAS,CACP4B,OAAQ,CACN,OAAU,uCAKhBlC,EAAM1C,QAAQ,CAAC,SAAU,MAAO,SAAS,SAA6B6E,GACpE3B,EAASF,QAAQ6B,GAAU,MAG7BnC,EAAM1C,QAAQ,CAAC,OAAQ,MAAO,UAAU,SAA+B6E,GACrE3B,EAASF,QAAQ6B,GAAUnC,EAAMlB,MAAMsB,MAGzC/F,EAAOD,QAAUoG,G,6BChIjBnG,EAAOD,QAAU,SAAcoD,EAAI8B,GACjC,OAAO,WAEL,IADA,IAAI8C,EAAO,IAAIrF,MAAMmC,UAAUzB,QACtB7C,EAAI,EAAGA,EAAIwH,EAAK3E,OAAQ7C,IAC/BwH,EAAKxH,GAAKsE,UAAUtE,GAEtB,OAAO4C,EAAG6E,MAAM/C,EAAS8C,M,6BCN7B,IAAIpC,EAAQ,EAAQ,GAEpB,SAASsC,EAAOxF,GACd,OAAOyF,mBAAmBzF,GACxB2C,QAAQ,QAAS,KACjBA,QAAQ,OAAQ,KAChBA,QAAQ,QAAS,KACjBA,QAAQ,OAAQ,KAChBA,QAAQ,QAAS,KACjBA,QAAQ,QAAS,KAUrBpF,EAAOD,QAAU,SAAkBoI,EAAKC,EAAQC,GAE9C,IAAKD,EACH,OAAOD,EAGT,IAAIG,EACJ,GAAID,EACFC,EAAmBD,EAAiBD,QAC/B,GAAIzC,EAAMxB,kBAAkBiE,GACjCE,EAAmBF,EAAO7F,eACrB,CACL,IAAIgG,EAAQ,GAEZ5C,EAAM1C,QAAQmF,GAAQ,SAAmB3F,EAAKX,GACxCW,UAIAkD,EAAMnD,QAAQC,GAChBX,GAAY,KAEZW,EAAM,CAACA,GAGTkD,EAAM1C,QAAQR,GAAK,SAAoB+F,GACjC7C,EAAM7B,OAAO0E,GACfA,EAAIA,EAAEC,cACG9C,EAAM9C,SAAS2F,KACxBA,EAAI5B,KAAKG,UAAUyB,IAErBD,EAAMG,KAAKT,EAAOnG,GAAO,IAAMmG,EAAOO,WAI1CF,EAAmBC,EAAMI,KAAK,KAGhC,GAAIL,EAAkB,CACpB,IAAIM,EAAgBT,EAAIU,QAAQ,MACT,IAAnBD,IACFT,EAAMA,EAAIvD,MAAM,EAAGgE,IAGrBT,KAA8B,IAAtBA,EAAIU,QAAQ,KAAc,IAAM,KAAOP,EAGjD,OAAOH,I,6BCxDTnI,EAAOD,QAAU,SAAsB+I,EAAOC,EAAQC,EAAMC,EAASC,GA6BnE,OA5BAJ,EAAMC,OAASA,EACXC,IACFF,EAAME,KAAOA,GAGfF,EAAMG,QAAUA,EAChBH,EAAMI,SAAWA,EACjBJ,EAAMK,cAAe,EAErBL,EAAMM,OAAS,WACb,MAAO,CAEL3D,QAAStF,KAAKsF,QACd3E,KAAMX,KAAKW,KAEXuI,YAAalJ,KAAKkJ,YAClBC,OAAQnJ,KAAKmJ,OAEbC,SAAUpJ,KAAKoJ,SACfC,WAAYrJ,KAAKqJ,WACjBC,aAActJ,KAAKsJ,aACnBC,MAAOvJ,KAAKuJ,MAEZX,OAAQ5I,KAAK4I,OACbC,KAAM7I,KAAK6I,KACXpB,OAAQzH,KAAK+I,UAAY/I,KAAK+I,SAAStB,OAASzH,KAAK+I,SAAStB,OAAS,OAGpEkB,I,6BCvCT9I,EAAOD,QAAU,CACfmH,mBAAmB,EACnBC,mBAAmB,EACnBwC,qBAAqB,I,6BCHvB,IAAIhE,EAAQ,EAAQ,GAChBiE,EAAS,EAAQ,IACjBC,EAAU,EAAQ,IAClBC,EAAW,EAAQ,GACnBC,EAAgB,EAAQ,IACxBC,EAAe,EAAQ,IACvBC,EAAkB,EAAQ,IAC1BC,EAAc,EAAQ,GACtBpE,EAAuB,EAAQ,GAC/BN,EAAS,EAAQ,GAErBxF,EAAOD,QAAU,SAAoBgJ,GACnC,OAAO,IAAIoB,SAAQ,SAA4BC,EAASC,GACtD,IAGIC,EAHAC,EAAcxB,EAAOvC,KACrBgE,EAAiBzB,EAAO9C,QACxBoB,EAAe0B,EAAO1B,aAE1B,SAASoD,IACH1B,EAAO2B,aACT3B,EAAO2B,YAAYC,YAAYL,GAG7BvB,EAAO6B,QACT7B,EAAO6B,OAAOC,oBAAoB,QAASP,GAI3C3E,EAAMpC,WAAWgH,WACZC,EAAe,gBAGxB,IAAIvB,EAAU,IAAI5C,eAGlB,GAAI0C,EAAO+B,KAAM,CACf,IAAIC,EAAWhC,EAAO+B,KAAKC,UAAY,GACnCC,EAAWjC,EAAO+B,KAAKE,SAAWC,SAAS/C,mBAAmBa,EAAO+B,KAAKE,WAAa,GAC3FR,EAAeU,cAAgB,SAAWC,KAAKJ,EAAW,IAAMC,GAGlE,IAAII,EAAWrB,EAAchB,EAAOsC,QAAStC,EAAOZ,KAMpD,SAASmD,IACP,GAAKrC,EAAL,CAIA,IAAIsC,EAAkB,0BAA2BtC,EAAUe,EAAaf,EAAQuC,yBAA2B,KAGvGtC,EAAW,CACb1C,KAHkBa,GAAiC,SAAjBA,GAA6C,SAAjBA,EACvC4B,EAAQC,SAA/BD,EAAQwC,aAGR7D,OAAQqB,EAAQrB,OAChB8D,WAAYzC,EAAQyC,WACpBzF,QAASsF,EACTxC,OAAQA,EACRE,QAASA,GAGXW,GAAO,SAAkBpI,GACvB4I,EAAQ5I,GACRiJ,OACC,SAAiBkB,GAClBtB,EAAOsB,GACPlB,MACCvB,GAGHD,EAAU,MAoEZ,GAnGAA,EAAQ2C,KAAK7C,EAAOjB,OAAO+D,cAAe/B,EAASsB,EAAUrC,EAAOX,OAAQW,EAAOV,mBAAmB,GAGtGY,EAAQ3B,QAAUyB,EAAOzB,QA+BrB,cAAe2B,EAEjBA,EAAQqC,UAAYA,EAGpBrC,EAAQ6C,mBAAqB,WACtB7C,GAAkC,IAAvBA,EAAQ8C,aAQD,IAAnB9C,EAAQrB,QAAkBqB,EAAQ+C,aAAwD,IAAzC/C,EAAQ+C,YAAYnD,QAAQ,WAKjFoD,WAAWX,IAKfrC,EAAQiD,QAAU,WACXjD,IAILoB,EAAOH,EAAY,kBAAmBnB,EAAQ,eAAgBE,IAG9DA,EAAU,OAIZA,EAAQkD,QAAU,WAGhB9B,EAAOH,EAAY,gBAAiBnB,EAAQ,KAAME,IAGlDA,EAAU,MAIZA,EAAQmD,UAAY,WAClB,IAAIC,EAAsBtD,EAAOzB,QAAU,cAAgByB,EAAOzB,QAAU,cAAgB,mBACxFlB,EAAe2C,EAAO3C,cAAgBN,EACtCiD,EAAOsD,sBACTA,EAAsBtD,EAAOsD,qBAE/BhC,EAAOH,EACLmC,EACAtD,EACA3C,EAAauD,oBAAsB,YAAc,eACjDV,IAGFA,EAAU,MAMRtD,EAAMvB,uBAAwB,CAEhC,IAAIkI,GAAavD,EAAOwD,iBAAmBtC,EAAgBmB,KAAcrC,EAAOxB,eAC9EsC,EAAQ2C,KAAKzD,EAAOxB,qBACpBkF,EAEEH,IACF9B,EAAezB,EAAOvB,gBAAkB8E,GAKxC,qBAAsBrD,GACxBtD,EAAM1C,QAAQuH,GAAgB,SAA0B/H,EAAKX,QAChC,IAAhByI,GAAqD,iBAAtBzI,EAAI4K,qBAErClC,EAAe1I,GAGtBmH,EAAQ0D,iBAAiB7K,EAAKW,MAM/BkD,EAAMhD,YAAYoG,EAAOwD,mBAC5BtD,EAAQsD,kBAAoBxD,EAAOwD,iBAIjClF,GAAiC,SAAjBA,IAClB4B,EAAQ5B,aAAe0B,EAAO1B,cAIS,mBAA9B0B,EAAO6D,oBAChB3D,EAAQ4D,iBAAiB,WAAY9D,EAAO6D,oBAIP,mBAA5B7D,EAAO+D,kBAAmC7D,EAAQ8D,QAC3D9D,EAAQ8D,OAAOF,iBAAiB,WAAY9D,EAAO+D,mBAGjD/D,EAAO2B,aAAe3B,EAAO6B,UAG/BN,EAAa,SAAS0C,GACf/D,IAGLoB,GAAQ2C,GAAWA,GAAUA,EAAOC,KAAQ,IAAIzH,EAAO,YAAcwH,GACrE/D,EAAQiE,QACRjE,EAAU,OAGZF,EAAO2B,aAAe3B,EAAO2B,YAAYyC,UAAU7C,GAC/CvB,EAAO6B,SACT7B,EAAO6B,OAAOwC,QAAU9C,IAAevB,EAAO6B,OAAOiC,iBAAiB,QAASvC,KAI9EC,IACHA,EAAc,MAIhBtB,EAAQoE,KAAK9C,Q,6BC/MjB,IAAI1E,EAAe,EAAQ,GAY3B7F,EAAOD,QAAU,SAAqB0F,EAASsD,EAAQC,EAAMC,EAASC,GACpE,IAAIJ,EAAQ,IAAIwE,MAAM7H,GACtB,OAAOI,EAAaiD,EAAOC,EAAQC,EAAMC,EAASC,K,6BCdpDlJ,EAAOD,QAAU,SAAkByB,GACjC,SAAUA,IAASA,EAAMkE,c,6BCD3B,IAAIC,EAAQ,EAAQ,GAUpB3F,EAAOD,QAAU,SAAqBwN,EAASC,GAE7CA,EAAUA,GAAW,GACrB,IAAIzE,EAAS,GAEb,SAAS0E,EAAeC,EAAQC,GAC9B,OAAIhI,EAAM7C,cAAc4K,IAAW/H,EAAM7C,cAAc6K,GAC9ChI,EAAMlB,MAAMiJ,EAAQC,GAClBhI,EAAM7C,cAAc6K,GACtBhI,EAAMlB,MAAM,GAAIkJ,GACdhI,EAAMnD,QAAQmL,GAChBA,EAAO/I,QAET+I,EAIT,SAASC,EAAoBC,GAC3B,OAAKlI,EAAMhD,YAAY6K,EAAQK,IAEnBlI,EAAMhD,YAAY4K,EAAQM,SAA/B,EACEJ,OAAehB,EAAWc,EAAQM,IAFlCJ,EAAeF,EAAQM,GAAOL,EAAQK,IAOjD,SAASC,EAAiBD,GACxB,IAAKlI,EAAMhD,YAAY6K,EAAQK,IAC7B,OAAOJ,OAAehB,EAAWe,EAAQK,IAK7C,SAASE,EAAiBF,GACxB,OAAKlI,EAAMhD,YAAY6K,EAAQK,IAEnBlI,EAAMhD,YAAY4K,EAAQM,SAA/B,EACEJ,OAAehB,EAAWc,EAAQM,IAFlCJ,OAAehB,EAAWe,EAAQK,IAO7C,SAASG,EAAgBH,GACvB,OAAIA,KAAQL,EACHC,EAAeF,EAAQM,GAAOL,EAAQK,IACpCA,KAAQN,EACVE,OAAehB,EAAWc,EAAQM,SADpC,EAKT,IAAII,EAAW,CACb,IAAOH,EACP,OAAUA,EACV,KAAQA,EACR,QAAWC,EACX,iBAAoBA,EACpB,kBAAqBA,EACrB,iBAAoBA,EACpB,QAAWA,EACX,eAAkBA,EAClB,gBAAmBA,EACnB,QAAWA,EACX,aAAgBA,EAChB,eAAkBA,EAClB,eAAkBA,EAClB,iBAAoBA,EACpB,mBAAsBA,EACtB,WAAcA,EACd,iBAAoBA,EACpB,cAAiBA,EACjB,UAAaA,EACb,UAAaA,EACb,WAAcA,EACd,YAAeA,EACf,WAAcA,EACd,iBAAoBA,EACpB,eAAkBC,GASpB,OANArI,EAAM1C,QAAQhC,OAAOiN,KAAKX,GAASY,OAAOlN,OAAOiN,KAAKV,KAAW,SAA4BK,GAC3F,IAAIpJ,EAAQwJ,EAASJ,IAASD,EAC1BQ,EAAc3J,EAAMoJ,GACvBlI,EAAMhD,YAAYyL,IAAgB3J,IAAUuJ,IAAqBjF,EAAO8E,GAAQO,MAG5ErF,I,cCjGT/I,EAAOD,QAAU,CACf,QAAW,W,gBCDbC,EAAOD,QAAU,EAAQ,K,6BCEzB,IAAI4F,EAAQ,EAAQ,GAChB5D,EAAO,EAAQ,GACfsM,EAAQ,EAAQ,IAChBC,EAAc,EAAQ,IA4B1B,IAAIC,EAnBJ,SAASC,EAAeC,GACtB,IAAIC,EAAU,IAAIL,EAAMI,GACpBE,EAAW5M,EAAKsM,EAAMlM,UAAU8G,QAASyF,GAa7C,OAVA/I,EAAMb,OAAO6J,EAAUN,EAAMlM,UAAWuM,GAGxC/I,EAAMb,OAAO6J,EAAUD,GAGvBC,EAAS9M,OAAS,SAAgB+M,GAChC,OAAOJ,EAAeF,EAAYG,EAAeG,KAG5CD,EAIGH,CA3BG,EAAQ,IA8BvBD,EAAMF,MAAQA,EAGdE,EAAM/I,OAAS,EAAQ,GACvB+I,EAAMM,YAAc,EAAQ,IAC5BN,EAAMO,SAAW,EAAQ,GACzBP,EAAMQ,QAAU,EAAQ,IAAcC,QAGtCT,EAAMU,IAAM,SAAaC,GACvB,OAAO/E,QAAQ8E,IAAIC,IAErBX,EAAMY,OAAS,EAAQ,IAGvBZ,EAAMpF,aAAe,EAAQ,IAE7BnJ,EAAOD,QAAUwO,EAGjBvO,EAAOD,QAAQqP,QAAUb,G,6BCtDzB,IAAI5I,EAAQ,EAAQ,GAChBmE,EAAW,EAAQ,GACnBuF,EAAqB,EAAQ,IAC7BC,EAAkB,EAAQ,IAC1BhB,EAAc,EAAQ,IACtBiB,EAAY,EAAQ,IAEpBC,EAAaD,EAAUC,WAM3B,SAASnB,EAAMO,GACbzO,KAAKgG,SAAWyI,EAChBzO,KAAKsP,aAAe,CAClBxG,QAAS,IAAIoG,EACbnG,SAAU,IAAImG,GASlBhB,EAAMlM,UAAU8G,QAAU,SAAiByG,EAAa3G,GAG3B,iBAAhB2G,GACT3G,EAASA,GAAU,IACZZ,IAAMuH,EAEb3G,EAAS2G,GAAe,IAG1B3G,EAASuF,EAAYnO,KAAKgG,SAAU4C,IAGzBjB,OACTiB,EAAOjB,OAASiB,EAAOjB,OAAO4E,cACrBvM,KAAKgG,SAAS2B,OACvBiB,EAAOjB,OAAS3H,KAAKgG,SAAS2B,OAAO4E,cAErC3D,EAAOjB,OAAS,MAGlB,IAAI1B,EAAe2C,EAAO3C,kBAELqG,IAAjBrG,GACFmJ,EAAUI,cAAcvJ,EAAc,CACpCc,kBAAmBsI,EAAWpJ,aAAaoJ,EAAWI,SACtDzI,kBAAmBqI,EAAWpJ,aAAaoJ,EAAWI,SACtDjG,oBAAqB6F,EAAWpJ,aAAaoJ,EAAWI,WACvD,GAIL,IAAIC,EAA0B,GAC1BC,GAAiC,EACrC3P,KAAKsP,aAAaxG,QAAQhG,SAAQ,SAAoC8M,GACjC,mBAAxBA,EAAYC,UAA0D,IAAhCD,EAAYC,QAAQjH,KAIrE+G,EAAiCA,GAAkCC,EAAYE,YAE/EJ,EAAwBK,QAAQH,EAAYI,UAAWJ,EAAYK,cAGrE,IAKIC,EALAC,EAA2B,GAO/B,GANAnQ,KAAKsP,aAAavG,SAASjG,SAAQ,SAAkC8M,GACnEO,EAAyB5H,KAAKqH,EAAYI,UAAWJ,EAAYK,cAK9DN,EAAgC,CACnC,IAAIS,EAAQ,CAACjB,OAAiB7C,GAM9B,IAJA/J,MAAMP,UAAU+N,QAAQlI,MAAMuI,EAAOV,GACrCU,EAAQA,EAAMpC,OAAOmC,GAErBD,EAAUlG,QAAQC,QAAQrB,GACnBwH,EAAMnN,QACXiN,EAAUA,EAAQG,KAAKD,EAAME,QAASF,EAAME,SAG9C,OAAOJ,EAKT,IADA,IAAIK,EAAY3H,EACT8G,EAAwBzM,QAAQ,CACrC,IAAIuN,EAAcd,EAAwBY,QACtCG,EAAaf,EAAwBY,QACzC,IACEC,EAAYC,EAAYD,GACxB,MAAO5H,GACP8H,EAAW9H,GACX,OAIJ,IACEuH,EAAUf,EAAgBoB,GAC1B,MAAO5H,GACP,OAAOqB,QAAQE,OAAOvB,GAGxB,KAAOwH,EAAyBlN,QAC9BiN,EAAUA,EAAQG,KAAKF,EAAyBG,QAASH,EAAyBG,SAGpF,OAAOJ,GAGThC,EAAMlM,UAAU0O,OAAS,SAAgB9H,GAEvC,OADAA,EAASuF,EAAYnO,KAAKgG,SAAU4C,GAC7Be,EAASf,EAAOZ,IAAKY,EAAOX,OAAQW,EAAOV,kBAAkBjD,QAAQ,MAAO,KAIrFO,EAAM1C,QAAQ,CAAC,SAAU,MAAO,OAAQ,YAAY,SAA6B6E,GAE/EuG,EAAMlM,UAAU2F,GAAU,SAASK,EAAKY,GACtC,OAAO5I,KAAK8I,QAAQqF,EAAYvF,GAAU,GAAI,CAC5CjB,OAAQA,EACRK,IAAKA,EACL3B,MAAOuC,GAAU,IAAIvC,YAK3Bb,EAAM1C,QAAQ,CAAC,OAAQ,MAAO,UAAU,SAA+B6E,GAErEuG,EAAMlM,UAAU2F,GAAU,SAASK,EAAK3B,EAAMuC,GAC5C,OAAO5I,KAAK8I,QAAQqF,EAAYvF,GAAU,GAAI,CAC5CjB,OAAQA,EACRK,IAAKA,EACL3B,KAAMA,SAKZxG,EAAOD,QAAUsO,G,6BCjJjB,IAAI1I,EAAQ,EAAQ,GAEpB,SAAS0J,IACPlP,KAAK2Q,SAAW,GAWlBzB,EAAmBlN,UAAU4O,IAAM,SAAaZ,EAAWC,EAAUY,GAOnE,OANA7Q,KAAK2Q,SAASpI,KAAK,CACjByH,UAAWA,EACXC,SAAUA,EACVH,cAAae,GAAUA,EAAQf,YAC/BD,QAASgB,EAAUA,EAAQhB,QAAU,OAEhC7P,KAAK2Q,SAAS1N,OAAS,GAQhCiM,EAAmBlN,UAAU8O,MAAQ,SAAeC,GAC9C/Q,KAAK2Q,SAASI,KAChB/Q,KAAK2Q,SAASI,GAAM,OAYxB7B,EAAmBlN,UAAUc,QAAU,SAAiBE,GACtDwC,EAAM1C,QAAQ9C,KAAK2Q,UAAU,SAAwBK,GACzC,OAANA,GACFhO,EAAGgO,OAKTnR,EAAOD,QAAUsP,G,6BCnDjB,IAAI1J,EAAQ,EAAQ,GAChByL,EAAgB,EAAQ,IACxBtC,EAAW,EAAQ,GACnB3I,EAAW,EAAQ,GACnBX,EAAS,EAAQ,GAKrB,SAAS6L,EAA6BtI,GAKpC,GAJIA,EAAO2B,aACT3B,EAAO2B,YAAY4G,mBAGjBvI,EAAO6B,QAAU7B,EAAO6B,OAAOwC,QACjC,MAAM,IAAI5H,EAAO,YAUrBxF,EAAOD,QAAU,SAAyBgJ,GA8BxC,OA7BAsI,EAA6BtI,GAG7BA,EAAO9C,QAAU8C,EAAO9C,SAAW,GAGnC8C,EAAOvC,KAAO4K,EAAc1Q,KAC1BqI,EACAA,EAAOvC,KACPuC,EAAO9C,QACP8C,EAAOxC,kBAITwC,EAAO9C,QAAUN,EAAMlB,MACrBsE,EAAO9C,QAAQ4B,QAAU,GACzBkB,EAAO9C,QAAQ8C,EAAOjB,SAAW,GACjCiB,EAAO9C,SAGTN,EAAM1C,QACJ,CAAC,SAAU,MAAO,OAAQ,OAAQ,MAAO,QAAS,WAClD,SAA2B6E,UAClBiB,EAAO9C,QAAQ6B,OAIZiB,EAAO7C,SAAWC,EAASD,SAE1B6C,GAAQyH,MAAK,SAA6BtH,GAWvD,OAVAmI,EAA6BtI,GAG7BG,EAAS1C,KAAO4K,EAAc1Q,KAC5BqI,EACAG,EAAS1C,KACT0C,EAASjD,QACT8C,EAAO9B,mBAGFiC,KACN,SAA4BqI,GAe7B,OAdKzC,EAASyC,KACZF,EAA6BtI,GAGzBwI,GAAUA,EAAOrI,WACnBqI,EAAOrI,SAAS1C,KAAO4K,EAAc1Q,KACnCqI,EACAwI,EAAOrI,SAAS1C,KAChB+K,EAAOrI,SAASjD,QAChB8C,EAAO9B,qBAKNkD,QAAQE,OAAOkH,Q,6BClF1B,IAAI5L,EAAQ,EAAQ,GAChBQ,EAAW,EAAQ,GAUvBnG,EAAOD,QAAU,SAAuByG,EAAMP,EAASuL,GACrD,IAAI9C,EAAUvO,MAAQgG,EAMtB,OAJAR,EAAM1C,QAAQuO,GAAK,SAAmBrO,GACpCqD,EAAOrD,EAAGzC,KAAKgO,EAASlI,EAAMP,MAGzBO,I,6BClBT,IAAIb,EAAQ,EAAQ,GAEpB3F,EAAOD,QAAU,SAA6BkG,EAASwL,GACrD9L,EAAM1C,QAAQgD,GAAS,SAAuBzE,EAAOV,GAC/CA,IAAS2Q,GAAkB3Q,EAAK+K,gBAAkB4F,EAAe5F,gBACnE5F,EAAQwL,GAAkBjQ,SACnByE,EAAQnF,S,6BCNrB,IAAIoJ,EAAc,EAAQ,GAS1BlK,EAAOD,QAAU,SAAgBqK,EAASC,EAAQnB,GAChD,IAAIvB,EAAiBuB,EAASH,OAAOpB,eAChCuB,EAAStB,QAAWD,IAAkBA,EAAeuB,EAAStB,QAGjEyC,EAAOH,EACL,mCAAqChB,EAAStB,OAC9CsB,EAASH,OACT,KACAG,EAASD,QACTC,IAPFkB,EAAQlB,K,6BCZZ,IAAIvD,EAAQ,EAAQ,GAEpB3F,EAAOD,QACL4F,EAAMvB,uBAIK,CACLsN,MAAO,SAAe5Q,EAAMU,EAAOmQ,EAASC,EAAMC,EAAQC,GACxD,IAAIC,EAAS,GACbA,EAAOrJ,KAAK5H,EAAO,IAAMoH,mBAAmB1G,IAExCmE,EAAM9B,SAAS8N,IACjBI,EAAOrJ,KAAK,WAAa,IAAIsJ,KAAKL,GAASM,eAGzCtM,EAAM/B,SAASgO,IACjBG,EAAOrJ,KAAK,QAAUkJ,GAGpBjM,EAAM/B,SAASiO,IACjBE,EAAOrJ,KAAK,UAAYmJ,IAGX,IAAXC,GACFC,EAAOrJ,KAAK,UAGdlE,SAASuN,OAASA,EAAOpJ,KAAK,OAGhC6D,KAAM,SAAc1L,GAClB,IAAIoR,EAAQ1N,SAASuN,OAAOG,MAAM,IAAIC,OAAO,aAAerR,EAAO,cACnE,OAAQoR,EAAQE,mBAAmBF,EAAM,IAAM,MAGjDG,OAAQ,SAAgBvR,GACtBX,KAAKuR,MAAM5Q,EAAM,GAAIkR,KAAKM,MAAQ,SAO/B,CACLZ,MAAO,aACPlF,KAAM,WAAkB,OAAO,MAC/B6F,OAAQ,e,6BC/ChB,IAAIE,EAAgB,EAAQ,IACxBC,EAAc,EAAQ,IAW1BxS,EAAOD,QAAU,SAAuBsL,EAASoH,GAC/C,OAAIpH,IAAYkH,EAAcE,GACrBD,EAAYnH,EAASoH,GAEvBA,I,6BCVTzS,EAAOD,QAAU,SAAuBoI,GAItC,MAAO,8BAA8BuK,KAAKvK,K,6BCH5CnI,EAAOD,QAAU,SAAqBsL,EAASsH,GAC7C,OAAOA,EACHtH,EAAQjG,QAAQ,OAAQ,IAAM,IAAMuN,EAAYvN,QAAQ,OAAQ,IAChEiG,I,6BCVN,IAAI1F,EAAQ,EAAQ,GAIhBiN,EAAoB,CACtB,MAAO,gBAAiB,iBAAkB,eAAgB,OAC1D,UAAW,OAAQ,OAAQ,oBAAqB,sBAChD,gBAAiB,WAAY,eAAgB,sBAC7C,UAAW,cAAe,cAgB5B5S,EAAOD,QAAU,SAAsBkG,GACrC,IACInE,EACAW,EACAlC,EAHAsS,EAAS,GAKb,OAAK5M,GAELN,EAAM1C,QAAQgD,EAAQ6M,MAAM,OAAO,SAAgBC,GAKjD,GAJAxS,EAAIwS,EAAKlK,QAAQ,KACjB/G,EAAM6D,EAAMT,KAAK6N,EAAKC,OAAO,EAAGzS,IAAImM,cACpCjK,EAAMkD,EAAMT,KAAK6N,EAAKC,OAAOzS,EAAI,IAE7BuB,EAAK,CACP,GAAI+Q,EAAO/Q,IAAQ8Q,EAAkB/J,QAAQ/G,IAAQ,EACnD,OAGA+Q,EAAO/Q,GADG,eAARA,GACa+Q,EAAO/Q,GAAO+Q,EAAO/Q,GAAO,IAAIqM,OAAO,CAAC1L,IAEzCoQ,EAAO/Q,GAAO+Q,EAAO/Q,GAAO,KAAOW,EAAMA,MAKtDoQ,GAnBgBA,I,6BC9BzB,IAAIlN,EAAQ,EAAQ,GAEpB3F,EAAOD,QACL4F,EAAMvB,uBAIJ,WACE,IAEI6O,EAFAC,EAAO,kBAAkBR,KAAKrO,UAAU8O,WACxCC,EAAiB5O,SAAS6O,cAAc,KAS5C,SAASC,EAAWnL,GAClB,IAAIoL,EAAOpL,EAWX,OATI+K,IAEFE,EAAeI,aAAa,OAAQD,GACpCA,EAAOH,EAAeG,MAGxBH,EAAeI,aAAa,OAAQD,GAG7B,CACLA,KAAMH,EAAeG,KACrBE,SAAUL,EAAeK,SAAWL,EAAeK,SAASrO,QAAQ,KAAM,IAAM,GAChFsO,KAAMN,EAAeM,KACrBC,OAAQP,EAAeO,OAASP,EAAeO,OAAOvO,QAAQ,MAAO,IAAM,GAC3EwO,KAAMR,EAAeQ,KAAOR,EAAeQ,KAAKxO,QAAQ,KAAM,IAAM,GACpEyO,SAAUT,EAAeS,SACzBC,KAAMV,EAAeU,KACrBC,SAAiD,MAAtCX,EAAeW,SAASC,OAAO,GACxCZ,EAAeW,SACf,IAAMX,EAAeW,UAY3B,OARAd,EAAYK,EAAW/O,OAAO0P,SAASV,MAQhC,SAAyBW,GAC9B,IAAIrB,EAAUlN,EAAM/B,SAASsQ,GAAeZ,EAAWY,GAAcA,EACrE,OAAQrB,EAAOY,WAAaR,EAAUQ,UAClCZ,EAAOa,OAAST,EAAUS,MAhDlC,GAsDS,WACL,OAAO,I,6BC9Df,IAAI3E,EAAU,EAAQ,IAAeC,QAEjCQ,EAAa,GAGjB,CAAC,SAAU,UAAW,SAAU,WAAY,SAAU,UAAUvM,SAAQ,SAASgK,EAAM1M,GACrFiP,EAAWvC,GAAQ,SAAmBkH,GACpC,cAAcA,IAAUlH,GAAQ,KAAO1M,EAAI,EAAI,KAAO,KAAO0M,MAIjE,IAAImH,EAAqB,GASzB5E,EAAWpJ,aAAe,SAAsBmJ,EAAWP,EAASvJ,GAClE,SAAS4O,EAAcC,EAAKC,GAC1B,MAAO,WAAaxF,EAAU,0BAA6BuF,EAAM,IAAOC,GAAQ9O,EAAU,KAAOA,EAAU,IAI7G,OAAO,SAASjE,EAAO8S,EAAKE,GAC1B,IAAkB,IAAdjF,EACF,MAAM,IAAIjC,MAAM+G,EAAcC,EAAK,qBAAuBtF,EAAU,OAASA,EAAU,MAczF,OAXIA,IAAYoF,EAAmBE,KACjCF,EAAmBE,IAAO,EAE1BG,QAAQC,KACNL,EACEC,EACA,+BAAiCtF,EAAU,8CAK1CO,GAAYA,EAAU/N,EAAO8S,EAAKE,KAkC7CxU,EAAOD,QAAU,CACf4P,cAxBF,SAAuBqB,EAAS2D,EAAQC,GACtC,GAAuB,iBAAZ5D,EACT,MAAM,IAAI6D,UAAU,6BAItB,IAFA,IAAI3G,EAAOjN,OAAOiN,KAAK8C,GACnBzQ,EAAI2N,EAAK9K,OACN7C,KAAM,GAAG,CACd,IAAI+T,EAAMpG,EAAK3N,GACXgP,EAAYoF,EAAOL,GACvB,GAAI/E,EAAJ,CACE,IAAI/N,EAAQwP,EAAQsD,GAChB5P,OAAmB+H,IAAVjL,GAAuB+N,EAAU/N,EAAO8S,EAAKtD,GAC1D,IAAe,IAAXtM,EACF,MAAM,IAAImQ,UAAU,UAAYP,EAAM,YAAc5P,QAIxD,IAAqB,IAAjBkQ,EACF,MAAMtH,MAAM,kBAAoBgH,KAOpC9E,WAAYA,I,6BC9Ed,IAAIhK,EAAS,EAAQ,GAQrB,SAASqJ,EAAYiG,GACnB,GAAwB,mBAAbA,EACT,MAAM,IAAID,UAAU,gCAGtB,IAAIE,EAEJ5U,KAAKkQ,QAAU,IAAIlG,SAAQ,SAAyBC,GAClD2K,EAAiB3K,KAGnB,IAAI4K,EAAQ7U,KAGZA,KAAKkQ,QAAQG,MAAK,SAASxD,GACzB,GAAKgI,EAAMC,WAAX,CAEA,IAAI1U,EACAC,EAAIwU,EAAMC,WAAW7R,OAEzB,IAAK7C,EAAI,EAAGA,EAAIC,EAAGD,IACjByU,EAAMC,WAAW1U,GAAGyM,GAEtBgI,EAAMC,WAAa,SAIrB9U,KAAKkQ,QAAQG,KAAO,SAAS0E,GAC3B,IAAIC,EAEA9E,EAAU,IAAIlG,SAAQ,SAASC,GACjC4K,EAAM7H,UAAU/C,GAChB+K,EAAW/K,KACVoG,KAAK0E,GAMR,OAJA7E,EAAQrD,OAAS,WACfgI,EAAMrK,YAAYwK,IAGb9E,GAGTyE,GAAS,SAAgBrP,GACnBuP,EAAMzD,SAKVyD,EAAMzD,OAAS,IAAI/L,EAAOC,GAC1BsP,EAAeC,EAAMzD,YAOzB1C,EAAY1M,UAAUmP,iBAAmB,WACvC,GAAInR,KAAKoR,OACP,MAAMpR,KAAKoR,QAQf1C,EAAY1M,UAAUgL,UAAY,SAAmBiI,GAC/CjV,KAAKoR,OACP6D,EAASjV,KAAKoR,QAIZpR,KAAK8U,WACP9U,KAAK8U,WAAWvM,KAAK0M,GAErBjV,KAAK8U,WAAa,CAACG,IAQvBvG,EAAY1M,UAAUwI,YAAc,SAAqByK,GACvD,GAAKjV,KAAK8U,WAAV,CAGA,IAAII,EAAQlV,KAAK8U,WAAWpM,QAAQuM,IACrB,IAAXC,GACFlV,KAAK8U,WAAWK,OAAOD,EAAO,KAQlCxG,EAAYlB,OAAS,WACnB,IAAIX,EAIJ,MAAO,CACLgI,MAJU,IAAInG,GAAY,SAAkBjO,GAC5CoM,EAASpM,KAIToM,OAAQA,IAIZhN,EAAOD,QAAU8O,G,6BChGjB7O,EAAOD,QAAU,SAAgBwV,GAC/B,OAAO,SAAcC,GACnB,OAAOD,EAASvN,MAAM,KAAMwN,M,6BCtBhC,IAAI7P,EAAQ,EAAQ,GAQpB3F,EAAOD,QAAU,SAAsB0V,GACrC,OAAO9P,EAAM9C,SAAS4S,KAAsC,IAAzBA,EAAQtM","file":"axios.min.js","sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse if(typeof exports === 'object')\n\t\texports[\"axios\"] = factory();\n\telse\n\t\troot[\"axios\"] = factory();\n})(this, function() {\nreturn "," \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = 12);\n","'use strict';\n\nvar bind = require('./helpers/bind');\n\n// utils is a library of generic helper functions non-specific to axios\n\nvar toString = Object.prototype.toString;\n\n/**\n * Determine if a value is an Array\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an Array, otherwise false\n */\nfunction isArray(val) {\n return Array.isArray(val);\n}\n\n/**\n * Determine if a value is undefined\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if the value is undefined, otherwise false\n */\nfunction isUndefined(val) {\n return typeof val === 'undefined';\n}\n\n/**\n * Determine if a value is a Buffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Buffer, otherwise false\n */\nfunction isBuffer(val) {\n return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor)\n && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val);\n}\n\n/**\n * Determine if a value is an ArrayBuffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an ArrayBuffer, otherwise false\n */\nfunction isArrayBuffer(val) {\n return toString.call(val) === '[object ArrayBuffer]';\n}\n\n/**\n * Determine if a value is a FormData\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an FormData, otherwise false\n */\nfunction isFormData(val) {\n return toString.call(val) === '[object FormData]';\n}\n\n/**\n * Determine if a value is a view on an ArrayBuffer\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false\n */\nfunction isArrayBufferView(val) {\n var result;\n if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) {\n result = ArrayBuffer.isView(val);\n } else {\n result = (val) && (val.buffer) && (isArrayBuffer(val.buffer));\n }\n return result;\n}\n\n/**\n * Determine if a value is a String\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a String, otherwise false\n */\nfunction isString(val) {\n return typeof val === 'string';\n}\n\n/**\n * Determine if a value is a Number\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Number, otherwise false\n */\nfunction isNumber(val) {\n return typeof val === 'number';\n}\n\n/**\n * Determine if a value is an Object\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is an Object, otherwise false\n */\nfunction isObject(val) {\n return val !== null && typeof val === 'object';\n}\n\n/**\n * Determine if a value is a plain Object\n *\n * @param {Object} val The value to test\n * @return {boolean} True if value is a plain Object, otherwise false\n */\nfunction isPlainObject(val) {\n if (toString.call(val) !== '[object Object]') {\n return false;\n }\n\n var prototype = Object.getPrototypeOf(val);\n return prototype === null || prototype === Object.prototype;\n}\n\n/**\n * Determine if a value is a Date\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Date, otherwise false\n */\nfunction isDate(val) {\n return toString.call(val) === '[object Date]';\n}\n\n/**\n * Determine if a value is a File\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a File, otherwise false\n */\nfunction isFile(val) {\n return toString.call(val) === '[object File]';\n}\n\n/**\n * Determine if a value is a Blob\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Blob, otherwise false\n */\nfunction isBlob(val) {\n return toString.call(val) === '[object Blob]';\n}\n\n/**\n * Determine if a value is a Function\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Function, otherwise false\n */\nfunction isFunction(val) {\n return toString.call(val) === '[object Function]';\n}\n\n/**\n * Determine if a value is a Stream\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a Stream, otherwise false\n */\nfunction isStream(val) {\n return isObject(val) && isFunction(val.pipe);\n}\n\n/**\n * Determine if a value is a URLSearchParams object\n *\n * @param {Object} val The value to test\n * @returns {boolean} True if value is a URLSearchParams object, otherwise false\n */\nfunction isURLSearchParams(val) {\n return toString.call(val) === '[object URLSearchParams]';\n}\n\n/**\n * Trim excess whitespace off the beginning and end of a string\n *\n * @param {String} str The String to trim\n * @returns {String} The String freed of excess whitespace\n */\nfunction trim(str) {\n return str.trim ? str.trim() : str.replace(/^\\s+|\\s+$/g, '');\n}\n\n/**\n * Determine if we're running in a standard browser environment\n *\n * This allows axios to run in a web worker, and react-native.\n * Both environments support XMLHttpRequest, but not fully standard globals.\n *\n * web workers:\n * typeof window -> undefined\n * typeof document -> undefined\n *\n * react-native:\n * navigator.product -> 'ReactNative'\n * nativescript\n * navigator.product -> 'NativeScript' or 'NS'\n */\nfunction isStandardBrowserEnv() {\n if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' ||\n navigator.product === 'NativeScript' ||\n navigator.product === 'NS')) {\n return false;\n }\n return (\n typeof window !== 'undefined' &&\n typeof document !== 'undefined'\n );\n}\n\n/**\n * Iterate over an Array or an Object invoking a function for each item.\n *\n * If `obj` is an Array callback will be called passing\n * the value, index, and complete array for each item.\n *\n * If 'obj' is an Object callback will be called passing\n * the value, key, and complete object for each property.\n *\n * @param {Object|Array} obj The object to iterate\n * @param {Function} fn The callback to invoke for each item\n */\nfunction forEach(obj, fn) {\n // Don't bother if no value provided\n if (obj === null || typeof obj === 'undefined') {\n return;\n }\n\n // Force an array if not already something iterable\n if (typeof obj !== 'object') {\n /*eslint no-param-reassign:0*/\n obj = [obj];\n }\n\n if (isArray(obj)) {\n // Iterate over array values\n for (var i = 0, l = obj.length; i < l; i++) {\n fn.call(null, obj[i], i, obj);\n }\n } else {\n // Iterate over object keys\n for (var key in obj) {\n if (Object.prototype.hasOwnProperty.call(obj, key)) {\n fn.call(null, obj[key], key, obj);\n }\n }\n }\n}\n\n/**\n * Accepts varargs expecting each argument to be an object, then\n * immutably merges the properties of each object and returns result.\n *\n * When multiple objects contain the same key the later object in\n * the arguments list will take precedence.\n *\n * Example:\n *\n * ```js\n * var result = merge({foo: 123}, {foo: 456});\n * console.log(result.foo); // outputs 456\n * ```\n *\n * @param {Object} obj1 Object to merge\n * @returns {Object} Result of all merge properties\n */\nfunction merge(/* obj1, obj2, obj3, ... */) {\n var result = {};\n function assignValue(val, key) {\n if (isPlainObject(result[key]) && isPlainObject(val)) {\n result[key] = merge(result[key], val);\n } else if (isPlainObject(val)) {\n result[key] = merge({}, val);\n } else if (isArray(val)) {\n result[key] = val.slice();\n } else {\n result[key] = val;\n }\n }\n\n for (var i = 0, l = arguments.length; i < l; i++) {\n forEach(arguments[i], assignValue);\n }\n return result;\n}\n\n/**\n * Extends object a by mutably adding to it the properties of object b.\n *\n * @param {Object} a The object to be extended\n * @param {Object} b The object to copy properties from\n * @param {Object} thisArg The object to bind function to\n * @return {Object} The resulting value of object a\n */\nfunction extend(a, b, thisArg) {\n forEach(b, function assignValue(val, key) {\n if (thisArg && typeof val === 'function') {\n a[key] = bind(val, thisArg);\n } else {\n a[key] = val;\n }\n });\n return a;\n}\n\n/**\n * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM)\n *\n * @param {string} content with BOM\n * @return {string} content value without BOM\n */\nfunction stripBOM(content) {\n if (content.charCodeAt(0) === 0xFEFF) {\n content = content.slice(1);\n }\n return content;\n}\n\nmodule.exports = {\n isArray: isArray,\n isArrayBuffer: isArrayBuffer,\n isBuffer: isBuffer,\n isFormData: isFormData,\n isArrayBufferView: isArrayBufferView,\n isString: isString,\n isNumber: isNumber,\n isObject: isObject,\n isPlainObject: isPlainObject,\n isUndefined: isUndefined,\n isDate: isDate,\n isFile: isFile,\n isBlob: isBlob,\n isFunction: isFunction,\n isStream: isStream,\n isURLSearchParams: isURLSearchParams,\n isStandardBrowserEnv: isStandardBrowserEnv,\n forEach: forEach,\n merge: merge,\n extend: extend,\n trim: trim,\n stripBOM: stripBOM\n};\n","'use strict';\n\n/**\n * A `Cancel` is an object that is thrown when an operation is canceled.\n *\n * @class\n * @param {string=} message The message.\n */\nfunction Cancel(message) {\n this.message = message;\n}\n\nCancel.prototype.toString = function toString() {\n return 'Cancel' + (this.message ? ': ' + this.message : '');\n};\n\nCancel.prototype.__CANCEL__ = true;\n\nmodule.exports = Cancel;\n","'use strict';\n\nvar utils = require('../utils');\nvar normalizeHeaderName = require('../helpers/normalizeHeaderName');\nvar enhanceError = require('../core/enhanceError');\nvar transitionalDefaults = require('./transitional');\n\nvar DEFAULT_CONTENT_TYPE = {\n 'Content-Type': 'application/x-www-form-urlencoded'\n};\n\nfunction setContentTypeIfUnset(headers, value) {\n if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) {\n headers['Content-Type'] = value;\n }\n}\n\nfunction getDefaultAdapter() {\n var adapter;\n if (typeof XMLHttpRequest !== 'undefined') {\n // For browsers use XHR adapter\n adapter = require('../adapters/xhr');\n } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') {\n // For node use HTTP adapter\n adapter = require('../adapters/http');\n }\n return adapter;\n}\n\nfunction stringifySafely(rawValue, parser, encoder) {\n if (utils.isString(rawValue)) {\n try {\n (parser || JSON.parse)(rawValue);\n return utils.trim(rawValue);\n } catch (e) {\n if (e.name !== 'SyntaxError') {\n throw e;\n }\n }\n }\n\n return (encoder || JSON.stringify)(rawValue);\n}\n\nvar defaults = {\n\n transitional: transitionalDefaults,\n\n adapter: getDefaultAdapter(),\n\n transformRequest: [function transformRequest(data, headers) {\n normalizeHeaderName(headers, 'Accept');\n normalizeHeaderName(headers, 'Content-Type');\n\n if (utils.isFormData(data) ||\n utils.isArrayBuffer(data) ||\n utils.isBuffer(data) ||\n utils.isStream(data) ||\n utils.isFile(data) ||\n utils.isBlob(data)\n ) {\n return data;\n }\n if (utils.isArrayBufferView(data)) {\n return data.buffer;\n }\n if (utils.isURLSearchParams(data)) {\n setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8');\n return data.toString();\n }\n if (utils.isObject(data) || (headers && headers['Content-Type'] === 'application/json')) {\n setContentTypeIfUnset(headers, 'application/json');\n return stringifySafely(data);\n }\n return data;\n }],\n\n transformResponse: [function transformResponse(data) {\n var transitional = this.transitional || defaults.transitional;\n var silentJSONParsing = transitional && transitional.silentJSONParsing;\n var forcedJSONParsing = transitional && transitional.forcedJSONParsing;\n var strictJSONParsing = !silentJSONParsing && this.responseType === 'json';\n\n if (strictJSONParsing || (forcedJSONParsing && utils.isString(data) && data.length)) {\n try {\n return JSON.parse(data);\n } catch (e) {\n if (strictJSONParsing) {\n if (e.name === 'SyntaxError') {\n throw enhanceError(e, this, 'E_JSON_PARSE');\n }\n throw e;\n }\n }\n }\n\n return data;\n }],\n\n /**\n * A timeout in milliseconds to abort a request. If set to 0 (default) a\n * timeout is not created.\n */\n timeout: 0,\n\n xsrfCookieName: 'XSRF-TOKEN',\n xsrfHeaderName: 'X-XSRF-TOKEN',\n\n maxContentLength: -1,\n maxBodyLength: -1,\n\n validateStatus: function validateStatus(status) {\n return status >= 200 && status < 300;\n },\n\n headers: {\n common: {\n 'Accept': 'application/json, text/plain, */*'\n }\n }\n};\n\nutils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) {\n defaults.headers[method] = {};\n});\n\nutils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) {\n defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE);\n});\n\nmodule.exports = defaults;\n","'use strict';\n\nmodule.exports = function bind(fn, thisArg) {\n return function wrap() {\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; i++) {\n args[i] = arguments[i];\n }\n return fn.apply(thisArg, args);\n };\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nfunction encode(val) {\n return encodeURIComponent(val).\n replace(/%3A/gi, ':').\n replace(/%24/g, '$').\n replace(/%2C/gi, ',').\n replace(/%20/g, '+').\n replace(/%5B/gi, '[').\n replace(/%5D/gi, ']');\n}\n\n/**\n * Build a URL by appending params to the end\n *\n * @param {string} url The base of the url (e.g., http://www.google.com)\n * @param {object} [params] The params to be appended\n * @returns {string} The formatted url\n */\nmodule.exports = function buildURL(url, params, paramsSerializer) {\n /*eslint no-param-reassign:0*/\n if (!params) {\n return url;\n }\n\n var serializedParams;\n if (paramsSerializer) {\n serializedParams = paramsSerializer(params);\n } else if (utils.isURLSearchParams(params)) {\n serializedParams = params.toString();\n } else {\n var parts = [];\n\n utils.forEach(params, function serialize(val, key) {\n if (val === null || typeof val === 'undefined') {\n return;\n }\n\n if (utils.isArray(val)) {\n key = key + '[]';\n } else {\n val = [val];\n }\n\n utils.forEach(val, function parseValue(v) {\n if (utils.isDate(v)) {\n v = v.toISOString();\n } else if (utils.isObject(v)) {\n v = JSON.stringify(v);\n }\n parts.push(encode(key) + '=' + encode(v));\n });\n });\n\n serializedParams = parts.join('&');\n }\n\n if (serializedParams) {\n var hashmarkIndex = url.indexOf('#');\n if (hashmarkIndex !== -1) {\n url = url.slice(0, hashmarkIndex);\n }\n\n url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams;\n }\n\n return url;\n};\n","'use strict';\n\n/**\n * Update an Error with the specified config, error code, and response.\n *\n * @param {Error} error The error to update.\n * @param {Object} config The config.\n * @param {string} [code] The error code (for example, 'ECONNABORTED').\n * @param {Object} [request] The request.\n * @param {Object} [response] The response.\n * @returns {Error} The error.\n */\nmodule.exports = function enhanceError(error, config, code, request, response) {\n error.config = config;\n if (code) {\n error.code = code;\n }\n\n error.request = request;\n error.response = response;\n error.isAxiosError = true;\n\n error.toJSON = function toJSON() {\n return {\n // Standard\n message: this.message,\n name: this.name,\n // Microsoft\n description: this.description,\n number: this.number,\n // Mozilla\n fileName: this.fileName,\n lineNumber: this.lineNumber,\n columnNumber: this.columnNumber,\n stack: this.stack,\n // Axios\n config: this.config,\n code: this.code,\n status: this.response && this.response.status ? this.response.status : null\n };\n };\n return error;\n};\n","'use strict';\n\nmodule.exports = {\n silentJSONParsing: true,\n forcedJSONParsing: true,\n clarifyTimeoutError: false\n};\n","'use strict';\n\nvar utils = require('./../utils');\nvar settle = require('./../core/settle');\nvar cookies = require('./../helpers/cookies');\nvar buildURL = require('./../helpers/buildURL');\nvar buildFullPath = require('../core/buildFullPath');\nvar parseHeaders = require('./../helpers/parseHeaders');\nvar isURLSameOrigin = require('./../helpers/isURLSameOrigin');\nvar createError = require('../core/createError');\nvar transitionalDefaults = require('../defaults/transitional');\nvar Cancel = require('../cancel/Cancel');\n\nmodule.exports = function xhrAdapter(config) {\n return new Promise(function dispatchXhrRequest(resolve, reject) {\n var requestData = config.data;\n var requestHeaders = config.headers;\n var responseType = config.responseType;\n var onCanceled;\n function done() {\n if (config.cancelToken) {\n config.cancelToken.unsubscribe(onCanceled);\n }\n\n if (config.signal) {\n config.signal.removeEventListener('abort', onCanceled);\n }\n }\n\n if (utils.isFormData(requestData)) {\n delete requestHeaders['Content-Type']; // Let the browser set it\n }\n\n var request = new XMLHttpRequest();\n\n // HTTP basic authentication\n if (config.auth) {\n var username = config.auth.username || '';\n var password = config.auth.password ? unescape(encodeURIComponent(config.auth.password)) : '';\n requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password);\n }\n\n var fullPath = buildFullPath(config.baseURL, config.url);\n request.open(config.method.toUpperCase(), buildURL(fullPath, config.params, config.paramsSerializer), true);\n\n // Set the request timeout in MS\n request.timeout = config.timeout;\n\n function onloadend() {\n if (!request) {\n return;\n }\n // Prepare the response\n var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null;\n var responseData = !responseType || responseType === 'text' || responseType === 'json' ?\n request.responseText : request.response;\n var response = {\n data: responseData,\n status: request.status,\n statusText: request.statusText,\n headers: responseHeaders,\n config: config,\n request: request\n };\n\n settle(function _resolve(value) {\n resolve(value);\n done();\n }, function _reject(err) {\n reject(err);\n done();\n }, response);\n\n // Clean up request\n request = null;\n }\n\n if ('onloadend' in request) {\n // Use onloadend if available\n request.onloadend = onloadend;\n } else {\n // Listen for ready state to emulate onloadend\n request.onreadystatechange = function handleLoad() {\n if (!request || request.readyState !== 4) {\n return;\n }\n\n // The request errored out and we didn't get a response, this will be\n // handled by onerror instead\n // With one exception: request that using file: protocol, most browsers\n // will return status as 0 even though it's a successful request\n if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) {\n return;\n }\n // readystate handler is calling before onerror or ontimeout handlers,\n // so we should call onloadend on the next 'tick'\n setTimeout(onloadend);\n };\n }\n\n // Handle browser request cancellation (as opposed to a manual cancellation)\n request.onabort = function handleAbort() {\n if (!request) {\n return;\n }\n\n reject(createError('Request aborted', config, 'ECONNABORTED', request));\n\n // Clean up request\n request = null;\n };\n\n // Handle low level network errors\n request.onerror = function handleError() {\n // Real errors are hidden from us by the browser\n // onerror should only fire if it's a network error\n reject(createError('Network Error', config, null, request));\n\n // Clean up request\n request = null;\n };\n\n // Handle timeout\n request.ontimeout = function handleTimeout() {\n var timeoutErrorMessage = config.timeout ? 'timeout of ' + config.timeout + 'ms exceeded' : 'timeout exceeded';\n var transitional = config.transitional || transitionalDefaults;\n if (config.timeoutErrorMessage) {\n timeoutErrorMessage = config.timeoutErrorMessage;\n }\n reject(createError(\n timeoutErrorMessage,\n config,\n transitional.clarifyTimeoutError ? 'ETIMEDOUT' : 'ECONNABORTED',\n request));\n\n // Clean up request\n request = null;\n };\n\n // Add xsrf header\n // This is only done if running in a standard browser environment.\n // Specifically not if we're in a web worker, or react-native.\n if (utils.isStandardBrowserEnv()) {\n // Add xsrf header\n var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ?\n cookies.read(config.xsrfCookieName) :\n undefined;\n\n if (xsrfValue) {\n requestHeaders[config.xsrfHeaderName] = xsrfValue;\n }\n }\n\n // Add headers to the request\n if ('setRequestHeader' in request) {\n utils.forEach(requestHeaders, function setRequestHeader(val, key) {\n if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') {\n // Remove Content-Type if data is undefined\n delete requestHeaders[key];\n } else {\n // Otherwise add header to the request\n request.setRequestHeader(key, val);\n }\n });\n }\n\n // Add withCredentials to request if needed\n if (!utils.isUndefined(config.withCredentials)) {\n request.withCredentials = !!config.withCredentials;\n }\n\n // Add responseType to request if needed\n if (responseType && responseType !== 'json') {\n request.responseType = config.responseType;\n }\n\n // Handle progress if needed\n if (typeof config.onDownloadProgress === 'function') {\n request.addEventListener('progress', config.onDownloadProgress);\n }\n\n // Not all browsers support upload events\n if (typeof config.onUploadProgress === 'function' && request.upload) {\n request.upload.addEventListener('progress', config.onUploadProgress);\n }\n\n if (config.cancelToken || config.signal) {\n // Handle cancellation\n // eslint-disable-next-line func-names\n onCanceled = function(cancel) {\n if (!request) {\n return;\n }\n reject(!cancel || (cancel && cancel.type) ? new Cancel('canceled') : cancel);\n request.abort();\n request = null;\n };\n\n config.cancelToken && config.cancelToken.subscribe(onCanceled);\n if (config.signal) {\n config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled);\n }\n }\n\n if (!requestData) {\n requestData = null;\n }\n\n // Send the request\n request.send(requestData);\n });\n};\n","'use strict';\n\nvar enhanceError = require('./enhanceError');\n\n/**\n * Create an Error with the specified message, config, error code, request and response.\n *\n * @param {string} message The error message.\n * @param {Object} config The config.\n * @param {string} [code] The error code (for example, 'ECONNABORTED').\n * @param {Object} [request] The request.\n * @param {Object} [response] The response.\n * @returns {Error} The created error.\n */\nmodule.exports = function createError(message, config, code, request, response) {\n var error = new Error(message);\n return enhanceError(error, config, code, request, response);\n};\n","'use strict';\n\nmodule.exports = function isCancel(value) {\n return !!(value && value.__CANCEL__);\n};\n","'use strict';\n\nvar utils = require('../utils');\n\n/**\n * Config-specific merge-function which creates a new config-object\n * by merging two configuration objects together.\n *\n * @param {Object} config1\n * @param {Object} config2\n * @returns {Object} New object resulting from merging config2 to config1\n */\nmodule.exports = function mergeConfig(config1, config2) {\n // eslint-disable-next-line no-param-reassign\n config2 = config2 || {};\n var config = {};\n\n function getMergedValue(target, source) {\n if (utils.isPlainObject(target) && utils.isPlainObject(source)) {\n return utils.merge(target, source);\n } else if (utils.isPlainObject(source)) {\n return utils.merge({}, source);\n } else if (utils.isArray(source)) {\n return source.slice();\n }\n return source;\n }\n\n // eslint-disable-next-line consistent-return\n function mergeDeepProperties(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(config1[prop], config2[prop]);\n } else if (!utils.isUndefined(config1[prop])) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function valueFromConfig2(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(undefined, config2[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function defaultToConfig2(prop) {\n if (!utils.isUndefined(config2[prop])) {\n return getMergedValue(undefined, config2[prop]);\n } else if (!utils.isUndefined(config1[prop])) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n // eslint-disable-next-line consistent-return\n function mergeDirectKeys(prop) {\n if (prop in config2) {\n return getMergedValue(config1[prop], config2[prop]);\n } else if (prop in config1) {\n return getMergedValue(undefined, config1[prop]);\n }\n }\n\n var mergeMap = {\n 'url': valueFromConfig2,\n 'method': valueFromConfig2,\n 'data': valueFromConfig2,\n 'baseURL': defaultToConfig2,\n 'transformRequest': defaultToConfig2,\n 'transformResponse': defaultToConfig2,\n 'paramsSerializer': defaultToConfig2,\n 'timeout': defaultToConfig2,\n 'timeoutMessage': defaultToConfig2,\n 'withCredentials': defaultToConfig2,\n 'adapter': defaultToConfig2,\n 'responseType': defaultToConfig2,\n 'xsrfCookieName': defaultToConfig2,\n 'xsrfHeaderName': defaultToConfig2,\n 'onUploadProgress': defaultToConfig2,\n 'onDownloadProgress': defaultToConfig2,\n 'decompress': defaultToConfig2,\n 'maxContentLength': defaultToConfig2,\n 'maxBodyLength': defaultToConfig2,\n 'transport': defaultToConfig2,\n 'httpAgent': defaultToConfig2,\n 'httpsAgent': defaultToConfig2,\n 'cancelToken': defaultToConfig2,\n 'socketPath': defaultToConfig2,\n 'responseEncoding': defaultToConfig2,\n 'validateStatus': mergeDirectKeys\n };\n\n utils.forEach(Object.keys(config1).concat(Object.keys(config2)), function computeConfigValue(prop) {\n var merge = mergeMap[prop] || mergeDeepProperties;\n var configValue = merge(prop);\n (utils.isUndefined(configValue) && merge !== mergeDirectKeys) || (config[prop] = configValue);\n });\n\n return config;\n};\n","module.exports = {\n \"version\": \"0.26.1\"\n};","module.exports = require('./lib/axios');","'use strict';\n\nvar utils = require('./utils');\nvar bind = require('./helpers/bind');\nvar Axios = require('./core/Axios');\nvar mergeConfig = require('./core/mergeConfig');\nvar defaults = require('./defaults');\n\n/**\n * Create an instance of Axios\n *\n * @param {Object} defaultConfig The default config for the instance\n * @return {Axios} A new instance of Axios\n */\nfunction createInstance(defaultConfig) {\n var context = new Axios(defaultConfig);\n var instance = bind(Axios.prototype.request, context);\n\n // Copy axios.prototype to instance\n utils.extend(instance, Axios.prototype, context);\n\n // Copy context to instance\n utils.extend(instance, context);\n\n // Factory for creating new instances\n instance.create = function create(instanceConfig) {\n return createInstance(mergeConfig(defaultConfig, instanceConfig));\n };\n\n return instance;\n}\n\n// Create the default instance to be exported\nvar axios = createInstance(defaults);\n\n// Expose Axios class to allow class inheritance\naxios.Axios = Axios;\n\n// Expose Cancel & CancelToken\naxios.Cancel = require('./cancel/Cancel');\naxios.CancelToken = require('./cancel/CancelToken');\naxios.isCancel = require('./cancel/isCancel');\naxios.VERSION = require('./env/data').version;\n\n// Expose all/spread\naxios.all = function all(promises) {\n return Promise.all(promises);\n};\naxios.spread = require('./helpers/spread');\n\n// Expose isAxiosError\naxios.isAxiosError = require('./helpers/isAxiosError');\n\nmodule.exports = axios;\n\n// Allow use of default import syntax in TypeScript\nmodule.exports.default = axios;\n","'use strict';\n\nvar utils = require('./../utils');\nvar buildURL = require('../helpers/buildURL');\nvar InterceptorManager = require('./InterceptorManager');\nvar dispatchRequest = require('./dispatchRequest');\nvar mergeConfig = require('./mergeConfig');\nvar validator = require('../helpers/validator');\n\nvar validators = validator.validators;\n/**\n * Create a new instance of Axios\n *\n * @param {Object} instanceConfig The default config for the instance\n */\nfunction Axios(instanceConfig) {\n this.defaults = instanceConfig;\n this.interceptors = {\n request: new InterceptorManager(),\n response: new InterceptorManager()\n };\n}\n\n/**\n * Dispatch a request\n *\n * @param {Object} config The config specific for this request (merged with this.defaults)\n */\nAxios.prototype.request = function request(configOrUrl, config) {\n /*eslint no-param-reassign:0*/\n // Allow for axios('example/url'[, config]) a la fetch API\n if (typeof configOrUrl === 'string') {\n config = config || {};\n config.url = configOrUrl;\n } else {\n config = configOrUrl || {};\n }\n\n config = mergeConfig(this.defaults, config);\n\n // Set config.method\n if (config.method) {\n config.method = config.method.toLowerCase();\n } else if (this.defaults.method) {\n config.method = this.defaults.method.toLowerCase();\n } else {\n config.method = 'get';\n }\n\n var transitional = config.transitional;\n\n if (transitional !== undefined) {\n validator.assertOptions(transitional, {\n silentJSONParsing: validators.transitional(validators.boolean),\n forcedJSONParsing: validators.transitional(validators.boolean),\n clarifyTimeoutError: validators.transitional(validators.boolean)\n }, false);\n }\n\n // filter out skipped interceptors\n var requestInterceptorChain = [];\n var synchronousRequestInterceptors = true;\n this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) {\n if (typeof interceptor.runWhen === 'function' && interceptor.runWhen(config) === false) {\n return;\n }\n\n synchronousRequestInterceptors = synchronousRequestInterceptors && interceptor.synchronous;\n\n requestInterceptorChain.unshift(interceptor.fulfilled, interceptor.rejected);\n });\n\n var responseInterceptorChain = [];\n this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) {\n responseInterceptorChain.push(interceptor.fulfilled, interceptor.rejected);\n });\n\n var promise;\n\n if (!synchronousRequestInterceptors) {\n var chain = [dispatchRequest, undefined];\n\n Array.prototype.unshift.apply(chain, requestInterceptorChain);\n chain = chain.concat(responseInterceptorChain);\n\n promise = Promise.resolve(config);\n while (chain.length) {\n promise = promise.then(chain.shift(), chain.shift());\n }\n\n return promise;\n }\n\n\n var newConfig = config;\n while (requestInterceptorChain.length) {\n var onFulfilled = requestInterceptorChain.shift();\n var onRejected = requestInterceptorChain.shift();\n try {\n newConfig = onFulfilled(newConfig);\n } catch (error) {\n onRejected(error);\n break;\n }\n }\n\n try {\n promise = dispatchRequest(newConfig);\n } catch (error) {\n return Promise.reject(error);\n }\n\n while (responseInterceptorChain.length) {\n promise = promise.then(responseInterceptorChain.shift(), responseInterceptorChain.shift());\n }\n\n return promise;\n};\n\nAxios.prototype.getUri = function getUri(config) {\n config = mergeConfig(this.defaults, config);\n return buildURL(config.url, config.params, config.paramsSerializer).replace(/^\\?/, '');\n};\n\n// Provide aliases for supported request methods\nutils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) {\n /*eslint func-names:0*/\n Axios.prototype[method] = function(url, config) {\n return this.request(mergeConfig(config || {}, {\n method: method,\n url: url,\n data: (config || {}).data\n }));\n };\n});\n\nutils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) {\n /*eslint func-names:0*/\n Axios.prototype[method] = function(url, data, config) {\n return this.request(mergeConfig(config || {}, {\n method: method,\n url: url,\n data: data\n }));\n };\n});\n\nmodule.exports = Axios;\n","'use strict';\n\nvar utils = require('./../utils');\n\nfunction InterceptorManager() {\n this.handlers = [];\n}\n\n/**\n * Add a new interceptor to the stack\n *\n * @param {Function} fulfilled The function to handle `then` for a `Promise`\n * @param {Function} rejected The function to handle `reject` for a `Promise`\n *\n * @return {Number} An ID used to remove interceptor later\n */\nInterceptorManager.prototype.use = function use(fulfilled, rejected, options) {\n this.handlers.push({\n fulfilled: fulfilled,\n rejected: rejected,\n synchronous: options ? options.synchronous : false,\n runWhen: options ? options.runWhen : null\n });\n return this.handlers.length - 1;\n};\n\n/**\n * Remove an interceptor from the stack\n *\n * @param {Number} id The ID that was returned by `use`\n */\nInterceptorManager.prototype.eject = function eject(id) {\n if (this.handlers[id]) {\n this.handlers[id] = null;\n }\n};\n\n/**\n * Iterate over all the registered interceptors\n *\n * This method is particularly useful for skipping over any\n * interceptors that may have become `null` calling `eject`.\n *\n * @param {Function} fn The function to call for each interceptor\n */\nInterceptorManager.prototype.forEach = function forEach(fn) {\n utils.forEach(this.handlers, function forEachHandler(h) {\n if (h !== null) {\n fn(h);\n }\n });\n};\n\nmodule.exports = InterceptorManager;\n","'use strict';\n\nvar utils = require('./../utils');\nvar transformData = require('./transformData');\nvar isCancel = require('../cancel/isCancel');\nvar defaults = require('../defaults');\nvar Cancel = require('../cancel/Cancel');\n\n/**\n * Throws a `Cancel` if cancellation has been requested.\n */\nfunction throwIfCancellationRequested(config) {\n if (config.cancelToken) {\n config.cancelToken.throwIfRequested();\n }\n\n if (config.signal && config.signal.aborted) {\n throw new Cancel('canceled');\n }\n}\n\n/**\n * Dispatch a request to the server using the configured adapter.\n *\n * @param {object} config The config that is to be used for the request\n * @returns {Promise} The Promise to be fulfilled\n */\nmodule.exports = function dispatchRequest(config) {\n throwIfCancellationRequested(config);\n\n // Ensure headers exist\n config.headers = config.headers || {};\n\n // Transform request data\n config.data = transformData.call(\n config,\n config.data,\n config.headers,\n config.transformRequest\n );\n\n // Flatten headers\n config.headers = utils.merge(\n config.headers.common || {},\n config.headers[config.method] || {},\n config.headers\n );\n\n utils.forEach(\n ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'],\n function cleanHeaderConfig(method) {\n delete config.headers[method];\n }\n );\n\n var adapter = config.adapter || defaults.adapter;\n\n return adapter(config).then(function onAdapterResolution(response) {\n throwIfCancellationRequested(config);\n\n // Transform response data\n response.data = transformData.call(\n config,\n response.data,\n response.headers,\n config.transformResponse\n );\n\n return response;\n }, function onAdapterRejection(reason) {\n if (!isCancel(reason)) {\n throwIfCancellationRequested(config);\n\n // Transform response data\n if (reason && reason.response) {\n reason.response.data = transformData.call(\n config,\n reason.response.data,\n reason.response.headers,\n config.transformResponse\n );\n }\n }\n\n return Promise.reject(reason);\n });\n};\n","'use strict';\n\nvar utils = require('./../utils');\nvar defaults = require('../defaults');\n\n/**\n * Transform the data for a request or a response\n *\n * @param {Object|String} data The data to be transformed\n * @param {Array} headers The headers for the request or response\n * @param {Array|Function} fns A single function or Array of functions\n * @returns {*} The resulting transformed data\n */\nmodule.exports = function transformData(data, headers, fns) {\n var context = this || defaults;\n /*eslint no-param-reassign:0*/\n utils.forEach(fns, function transform(fn) {\n data = fn.call(context, data, headers);\n });\n\n return data;\n};\n","'use strict';\n\nvar utils = require('../utils');\n\nmodule.exports = function normalizeHeaderName(headers, normalizedName) {\n utils.forEach(headers, function processHeader(value, name) {\n if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) {\n headers[normalizedName] = value;\n delete headers[name];\n }\n });\n};\n","'use strict';\n\nvar createError = require('./createError');\n\n/**\n * Resolve or reject a Promise based on response status.\n *\n * @param {Function} resolve A function that resolves the promise.\n * @param {Function} reject A function that rejects the promise.\n * @param {object} response The response.\n */\nmodule.exports = function settle(resolve, reject, response) {\n var validateStatus = response.config.validateStatus;\n if (!response.status || !validateStatus || validateStatus(response.status)) {\n resolve(response);\n } else {\n reject(createError(\n 'Request failed with status code ' + response.status,\n response.config,\n null,\n response.request,\n response\n ));\n }\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nmodule.exports = (\n utils.isStandardBrowserEnv() ?\n\n // Standard browser envs support document.cookie\n (function standardBrowserEnv() {\n return {\n write: function write(name, value, expires, path, domain, secure) {\n var cookie = [];\n cookie.push(name + '=' + encodeURIComponent(value));\n\n if (utils.isNumber(expires)) {\n cookie.push('expires=' + new Date(expires).toGMTString());\n }\n\n if (utils.isString(path)) {\n cookie.push('path=' + path);\n }\n\n if (utils.isString(domain)) {\n cookie.push('domain=' + domain);\n }\n\n if (secure === true) {\n cookie.push('secure');\n }\n\n document.cookie = cookie.join('; ');\n },\n\n read: function read(name) {\n var match = document.cookie.match(new RegExp('(^|;\\\\s*)(' + name + ')=([^;]*)'));\n return (match ? decodeURIComponent(match[3]) : null);\n },\n\n remove: function remove(name) {\n this.write(name, '', Date.now() - 86400000);\n }\n };\n })() :\n\n // Non standard browser env (web workers, react-native) lack needed support.\n (function nonStandardBrowserEnv() {\n return {\n write: function write() {},\n read: function read() { return null; },\n remove: function remove() {}\n };\n })()\n);\n","'use strict';\n\nvar isAbsoluteURL = require('../helpers/isAbsoluteURL');\nvar combineURLs = require('../helpers/combineURLs');\n\n/**\n * Creates a new URL by combining the baseURL with the requestedURL,\n * only when the requestedURL is not already an absolute URL.\n * If the requestURL is absolute, this function returns the requestedURL untouched.\n *\n * @param {string} baseURL The base URL\n * @param {string} requestedURL Absolute or relative URL to combine\n * @returns {string} The combined full path\n */\nmodule.exports = function buildFullPath(baseURL, requestedURL) {\n if (baseURL && !isAbsoluteURL(requestedURL)) {\n return combineURLs(baseURL, requestedURL);\n }\n return requestedURL;\n};\n","'use strict';\n\n/**\n * Determines whether the specified URL is absolute\n *\n * @param {string} url The URL to test\n * @returns {boolean} True if the specified URL is absolute, otherwise false\n */\nmodule.exports = function isAbsoluteURL(url) {\n // A URL is considered absolute if it begins with \"<scheme>://\" or \"//\" (protocol-relative URL).\n // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed\n // by any combination of letters, digits, plus, period, or hyphen.\n return /^([a-z][a-z\\d+\\-.]*:)?\\/\\//i.test(url);\n};\n","'use strict';\n\n/**\n * Creates a new URL by combining the specified URLs\n *\n * @param {string} baseURL The base URL\n * @param {string} relativeURL The relative URL\n * @returns {string} The combined URL\n */\nmodule.exports = function combineURLs(baseURL, relativeURL) {\n return relativeURL\n ? baseURL.replace(/\\/+$/, '') + '/' + relativeURL.replace(/^\\/+/, '')\n : baseURL;\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\n// Headers whose duplicates are ignored by node\n// c.f. https://nodejs.org/api/http.html#http_message_headers\nvar ignoreDuplicateOf = [\n 'age', 'authorization', 'content-length', 'content-type', 'etag',\n 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since',\n 'last-modified', 'location', 'max-forwards', 'proxy-authorization',\n 'referer', 'retry-after', 'user-agent'\n];\n\n/**\n * Parse headers into an object\n *\n * ```\n * Date: Wed, 27 Aug 2014 08:58:49 GMT\n * Content-Type: application/json\n * Connection: keep-alive\n * Transfer-Encoding: chunked\n * ```\n *\n * @param {String} headers Headers needing to be parsed\n * @returns {Object} Headers parsed into an object\n */\nmodule.exports = function parseHeaders(headers) {\n var parsed = {};\n var key;\n var val;\n var i;\n\n if (!headers) { return parsed; }\n\n utils.forEach(headers.split('\\n'), function parser(line) {\n i = line.indexOf(':');\n key = utils.trim(line.substr(0, i)).toLowerCase();\n val = utils.trim(line.substr(i + 1));\n\n if (key) {\n if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) {\n return;\n }\n if (key === 'set-cookie') {\n parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]);\n } else {\n parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val;\n }\n }\n });\n\n return parsed;\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\nmodule.exports = (\n utils.isStandardBrowserEnv() ?\n\n // Standard browser envs have full support of the APIs needed to test\n // whether the request URL is of the same origin as current location.\n (function standardBrowserEnv() {\n var msie = /(msie|trident)/i.test(navigator.userAgent);\n var urlParsingNode = document.createElement('a');\n var originURL;\n\n /**\n * Parse a URL to discover it's components\n *\n * @param {String} url The URL to be parsed\n * @returns {Object}\n */\n function resolveURL(url) {\n var href = url;\n\n if (msie) {\n // IE needs attribute set twice to normalize properties\n urlParsingNode.setAttribute('href', href);\n href = urlParsingNode.href;\n }\n\n urlParsingNode.setAttribute('href', href);\n\n // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils\n return {\n href: urlParsingNode.href,\n protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '',\n host: urlParsingNode.host,\n search: urlParsingNode.search ? urlParsingNode.search.replace(/^\\?/, '') : '',\n hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '',\n hostname: urlParsingNode.hostname,\n port: urlParsingNode.port,\n pathname: (urlParsingNode.pathname.charAt(0) === '/') ?\n urlParsingNode.pathname :\n '/' + urlParsingNode.pathname\n };\n }\n\n originURL = resolveURL(window.location.href);\n\n /**\n * Determine if a URL shares the same origin as the current location\n *\n * @param {String} requestURL The URL to test\n * @returns {boolean} True if URL shares the same origin, otherwise false\n */\n return function isURLSameOrigin(requestURL) {\n var parsed = (utils.isString(requestURL)) ? resolveURL(requestURL) : requestURL;\n return (parsed.protocol === originURL.protocol &&\n parsed.host === originURL.host);\n };\n })() :\n\n // Non standard browser envs (web workers, react-native) lack needed support.\n (function nonStandardBrowserEnv() {\n return function isURLSameOrigin() {\n return true;\n };\n })()\n);\n","'use strict';\n\nvar VERSION = require('../env/data').version;\n\nvar validators = {};\n\n// eslint-disable-next-line func-names\n['object', 'boolean', 'number', 'function', 'string', 'symbol'].forEach(function(type, i) {\n validators[type] = function validator(thing) {\n return typeof thing === type || 'a' + (i < 1 ? 'n ' : ' ') + type;\n };\n});\n\nvar deprecatedWarnings = {};\n\n/**\n * Transitional option validator\n * @param {function|boolean?} validator - set to false if the transitional option has been removed\n * @param {string?} version - deprecated version / removed since version\n * @param {string?} message - some message with additional info\n * @returns {function}\n */\nvalidators.transitional = function transitional(validator, version, message) {\n function formatMessage(opt, desc) {\n return '[Axios v' + VERSION + '] Transitional option \\'' + opt + '\\'' + desc + (message ? '. ' + message : '');\n }\n\n // eslint-disable-next-line func-names\n return function(value, opt, opts) {\n if (validator === false) {\n throw new Error(formatMessage(opt, ' has been removed' + (version ? ' in ' + version : '')));\n }\n\n if (version && !deprecatedWarnings[opt]) {\n deprecatedWarnings[opt] = true;\n // eslint-disable-next-line no-console\n console.warn(\n formatMessage(\n opt,\n ' has been deprecated since v' + version + ' and will be removed in the near future'\n )\n );\n }\n\n return validator ? validator(value, opt, opts) : true;\n };\n};\n\n/**\n * Assert object's properties type\n * @param {object} options\n * @param {object} schema\n * @param {boolean?} allowUnknown\n */\n\nfunction assertOptions(options, schema, allowUnknown) {\n if (typeof options !== 'object') {\n throw new TypeError('options must be an object');\n }\n var keys = Object.keys(options);\n var i = keys.length;\n while (i-- > 0) {\n var opt = keys[i];\n var validator = schema[opt];\n if (validator) {\n var value = options[opt];\n var result = value === undefined || validator(value, opt, options);\n if (result !== true) {\n throw new TypeError('option ' + opt + ' must be ' + result);\n }\n continue;\n }\n if (allowUnknown !== true) {\n throw Error('Unknown option ' + opt);\n }\n }\n}\n\nmodule.exports = {\n assertOptions: assertOptions,\n validators: validators\n};\n","'use strict';\n\nvar Cancel = require('./Cancel');\n\n/**\n * A `CancelToken` is an object that can be used to request cancellation of an operation.\n *\n * @class\n * @param {Function} executor The executor function.\n */\nfunction CancelToken(executor) {\n if (typeof executor !== 'function') {\n throw new TypeError('executor must be a function.');\n }\n\n var resolvePromise;\n\n this.promise = new Promise(function promiseExecutor(resolve) {\n resolvePromise = resolve;\n });\n\n var token = this;\n\n // eslint-disable-next-line func-names\n this.promise.then(function(cancel) {\n if (!token._listeners) return;\n\n var i;\n var l = token._listeners.length;\n\n for (i = 0; i < l; i++) {\n token._listeners[i](cancel);\n }\n token._listeners = null;\n });\n\n // eslint-disable-next-line func-names\n this.promise.then = function(onfulfilled) {\n var _resolve;\n // eslint-disable-next-line func-names\n var promise = new Promise(function(resolve) {\n token.subscribe(resolve);\n _resolve = resolve;\n }).then(onfulfilled);\n\n promise.cancel = function reject() {\n token.unsubscribe(_resolve);\n };\n\n return promise;\n };\n\n executor(function cancel(message) {\n if (token.reason) {\n // Cancellation has already been requested\n return;\n }\n\n token.reason = new Cancel(message);\n resolvePromise(token.reason);\n });\n}\n\n/**\n * Throws a `Cancel` if cancellation has been requested.\n */\nCancelToken.prototype.throwIfRequested = function throwIfRequested() {\n if (this.reason) {\n throw this.reason;\n }\n};\n\n/**\n * Subscribe to the cancel signal\n */\n\nCancelToken.prototype.subscribe = function subscribe(listener) {\n if (this.reason) {\n listener(this.reason);\n return;\n }\n\n if (this._listeners) {\n this._listeners.push(listener);\n } else {\n this._listeners = [listener];\n }\n};\n\n/**\n * Unsubscribe from the cancel signal\n */\n\nCancelToken.prototype.unsubscribe = function unsubscribe(listener) {\n if (!this._listeners) {\n return;\n }\n var index = this._listeners.indexOf(listener);\n if (index !== -1) {\n this._listeners.splice(index, 1);\n }\n};\n\n/**\n * Returns an object that contains a new `CancelToken` and a function that, when called,\n * cancels the `CancelToken`.\n */\nCancelToken.source = function source() {\n var cancel;\n var token = new CancelToken(function executor(c) {\n cancel = c;\n });\n return {\n token: token,\n cancel: cancel\n };\n};\n\nmodule.exports = CancelToken;\n","'use strict';\n\n/**\n * Syntactic sugar for invoking a function and expanding an array for arguments.\n *\n * Common use case would be to use `Function.prototype.apply`.\n *\n * ```js\n * function f(x, y, z) {}\n * var args = [1, 2, 3];\n * f.apply(null, args);\n * ```\n *\n * With `spread` this example can be re-written.\n *\n * ```js\n * spread(function(x, y, z) {})([1, 2, 3]);\n * ```\n *\n * @param {Function} callback\n * @returns {Function}\n */\nmodule.exports = function spread(callback) {\n return function wrap(arr) {\n return callback.apply(null, arr);\n };\n};\n","'use strict';\n\nvar utils = require('./../utils');\n\n/**\n * Determines whether the payload is an error thrown by Axios\n *\n * @param {*} payload The value to test\n * @returns {boolean} True if the payload is an error thrown by Axios, otherwise false\n */\nmodule.exports = function isAxiosError(payload) {\n return utils.isObject(payload) && (payload.isAxiosError === true);\n};\n"],"sourceRoot":""}
\ No newline at end of file diff --git a/node_modules/axios/index.d.ts b/node_modules/axios/index.d.ts new file mode 100644 index 0000000..b681915 --- /dev/null +++ b/node_modules/axios/index.d.ts @@ -0,0 +1,221 @@ +// TypeScript Version: 3.0 + +export type AxiosRequestHeaders = Record<string, string | number | boolean>; + +export type AxiosResponseHeaders = Record<string, string> & { + "set-cookie"?: string[] +}; + +export interface AxiosRequestTransformer { + (data: any, headers?: AxiosRequestHeaders): any; +} + +export interface AxiosResponseTransformer { + (data: any, headers?: AxiosResponseHeaders): any; +} + +export interface AxiosAdapter { + (config: AxiosRequestConfig): AxiosPromise; +} + +export interface AxiosBasicCredentials { + username: string; + password: string; +} + +export interface AxiosProxyConfig { + host: string; + port: number; + auth?: { + username: string; + password: string; + }; + protocol?: string; +} + +export type Method = + | 'get' | 'GET' + | 'delete' | 'DELETE' + | 'head' | 'HEAD' + | 'options' | 'OPTIONS' + | 'post' | 'POST' + | 'put' | 'PUT' + | 'patch' | 'PATCH' + | 'purge' | 'PURGE' + | 'link' | 'LINK' + | 'unlink' | 'UNLINK'; + +export type ResponseType = + | 'arraybuffer' + | 'blob' + | 'document' + | 'json' + | 'text' + | 'stream'; + + export type responseEncoding = + | 'ascii' | 'ASCII' + | 'ansi' | 'ANSI' + | 'binary' | 'BINARY' + | 'base64' | 'BASE64' + | 'base64url' | 'BASE64URL' + | 'hex' | 'HEX' + | 'latin1' | 'LATIN1' + | 'ucs-2' | 'UCS-2' + | 'ucs2' | 'UCS2' + | 'utf-8' | 'UTF-8' + | 'utf8' | 'UTF8' + | 'utf16le' | 'UTF16LE'; + +export interface TransitionalOptions { + silentJSONParsing?: boolean; + forcedJSONParsing?: boolean; + clarifyTimeoutError?: boolean; +} + +export interface AxiosRequestConfig<D = any> { + url?: string; + method?: Method; + baseURL?: string; + transformRequest?: AxiosRequestTransformer | AxiosRequestTransformer[]; + transformResponse?: AxiosResponseTransformer | AxiosResponseTransformer[]; + headers?: AxiosRequestHeaders; + params?: any; + paramsSerializer?: (params: any) => string; + data?: D; + timeout?: number; + timeoutErrorMessage?: string; + withCredentials?: boolean; + adapter?: AxiosAdapter; + auth?: AxiosBasicCredentials; + responseType?: ResponseType; + responseEncoding?: responseEncoding | string; + xsrfCookieName?: string; + xsrfHeaderName?: string; + onUploadProgress?: (progressEvent: any) => void; + onDownloadProgress?: (progressEvent: any) => void; + maxContentLength?: number; + validateStatus?: ((status: number) => boolean) | null; + maxBodyLength?: number; + maxRedirects?: number; + socketPath?: string | null; + httpAgent?: any; + httpsAgent?: any; + proxy?: AxiosProxyConfig | false; + cancelToken?: CancelToken; + decompress?: boolean; + transitional?: TransitionalOptions; + signal?: AbortSignal; + insecureHTTPParser?: boolean; +} + +export interface HeadersDefaults { + common: AxiosRequestHeaders; + delete: AxiosRequestHeaders; + get: AxiosRequestHeaders; + head: AxiosRequestHeaders; + post: AxiosRequestHeaders; + put: AxiosRequestHeaders; + patch: AxiosRequestHeaders; + options?: AxiosRequestHeaders; + purge?: AxiosRequestHeaders; + link?: AxiosRequestHeaders; + unlink?: AxiosRequestHeaders; +} + +export interface AxiosDefaults<D = any> extends Omit<AxiosRequestConfig<D>, 'headers'> { + headers: HeadersDefaults; +} + +export interface AxiosResponse<T = any, D = any> { + data: T; + status: number; + statusText: string; + headers: AxiosResponseHeaders; + config: AxiosRequestConfig<D>; + request?: any; +} + +export interface AxiosError<T = any, D = any> extends Error { + config: AxiosRequestConfig<D>; + code?: string; + request?: any; + response?: AxiosResponse<T, D>; + isAxiosError: boolean; + toJSON: () => object; +} + +export interface AxiosPromise<T = any> extends Promise<AxiosResponse<T>> { +} + +export interface CancelStatic { + new (message?: string): Cancel; +} + +export interface Cancel { + message: string | undefined; +} + +export interface Canceler { + (message?: string): void; +} + +export interface CancelTokenStatic { + new (executor: (cancel: Canceler) => void): CancelToken; + source(): CancelTokenSource; +} + +export interface CancelToken { + promise: Promise<Cancel>; + reason?: Cancel; + throwIfRequested(): void; +} + +export interface CancelTokenSource { + token: CancelToken; + cancel: Canceler; +} + +export interface AxiosInterceptorManager<V> { + use<T = V>(onFulfilled?: (value: V) => T | Promise<T>, onRejected?: (error: any) => any): number; + eject(id: number): void; +} + +export class Axios { + constructor(config?: AxiosRequestConfig); + defaults: AxiosDefaults; + interceptors: { + request: AxiosInterceptorManager<AxiosRequestConfig>; + response: AxiosInterceptorManager<AxiosResponse>; + }; + getUri(config?: AxiosRequestConfig): string; + request<T = any, R = AxiosResponse<T>, D = any>(config: AxiosRequestConfig<D>): Promise<R>; + get<T = any, R = AxiosResponse<T>, D = any>(url: string, config?: AxiosRequestConfig<D>): Promise<R>; + delete<T = any, R = AxiosResponse<T>, D = any>(url: string, config?: AxiosRequestConfig<D>): Promise<R>; + head<T = any, R = AxiosResponse<T>, D = any>(url: string, config?: AxiosRequestConfig<D>): Promise<R>; + options<T = any, R = AxiosResponse<T>, D = any>(url: string, config?: AxiosRequestConfig<D>): Promise<R>; + post<T = any, R = AxiosResponse<T>, D = any>(url: string, data?: D, config?: AxiosRequestConfig<D>): Promise<R>; + put<T = any, R = AxiosResponse<T>, D = any>(url: string, data?: D, config?: AxiosRequestConfig<D>): Promise<R>; + patch<T = any, R = AxiosResponse<T>, D = any>(url: string, data?: D, config?: AxiosRequestConfig<D>): Promise<R>; +} + +export interface AxiosInstance extends Axios { + (config: AxiosRequestConfig): AxiosPromise; + (url: string, config?: AxiosRequestConfig): AxiosPromise; +} + +export interface AxiosStatic extends AxiosInstance { + create(config?: AxiosRequestConfig): AxiosInstance; + Cancel: CancelStatic; + CancelToken: CancelTokenStatic; + Axios: typeof Axios; + readonly VERSION: string; + isCancel(value: any): boolean; + all<T>(values: Array<T | Promise<T>>): Promise<T[]>; + spread<T, R>(callback: (...args: T[]) => R): (array: T[]) => R; + isAxiosError(payload: any): payload is AxiosError; +} + +declare const axios: AxiosStatic; + +export default axios; diff --git a/node_modules/axios/index.js b/node_modules/axios/index.js new file mode 100644 index 0000000..79dfd09 --- /dev/null +++ b/node_modules/axios/index.js @@ -0,0 +1 @@ +module.exports = require('./lib/axios');
\ No newline at end of file diff --git a/node_modules/axios/lib/adapters/README.md b/node_modules/axios/lib/adapters/README.md new file mode 100644 index 0000000..68f1118 --- /dev/null +++ b/node_modules/axios/lib/adapters/README.md @@ -0,0 +1,37 @@ +# axios // adapters + +The modules under `adapters/` are modules that handle dispatching a request and settling a returned `Promise` once a response is received. + +## Example + +```js +var settle = require('./../core/settle'); + +module.exports = function myAdapter(config) { + // At this point: + // - config has been merged with defaults + // - request transformers have already run + // - request interceptors have already run + + // Make the request using config provided + // Upon response settle the Promise + + return new Promise(function(resolve, reject) { + + var response = { + data: responseData, + status: request.status, + statusText: request.statusText, + headers: responseHeaders, + config: config, + request: request + }; + + settle(resolve, reject, response); + + // From here: + // - response transformers will run + // - response interceptors will run + }); +} +``` diff --git a/node_modules/axios/lib/adapters/http.js b/node_modules/axios/lib/adapters/http.js new file mode 100755 index 0000000..28317c1 --- /dev/null +++ b/node_modules/axios/lib/adapters/http.js @@ -0,0 +1,404 @@ +'use strict'; + +var utils = require('./../utils'); +var settle = require('./../core/settle'); +var buildFullPath = require('../core/buildFullPath'); +var buildURL = require('./../helpers/buildURL'); +var http = require('http'); +var https = require('https'); +var httpFollow = require('follow-redirects').http; +var httpsFollow = require('follow-redirects').https; +var url = require('url'); +var zlib = require('zlib'); +var VERSION = require('./../env/data').version; +var createError = require('../core/createError'); +var enhanceError = require('../core/enhanceError'); +var transitionalDefaults = require('../defaults/transitional'); +var Cancel = require('../cancel/Cancel'); + +var isHttps = /https:?/; + +/** + * + * @param {http.ClientRequestArgs} options + * @param {AxiosProxyConfig} proxy + * @param {string} location + */ +function setProxy(options, proxy, location) { + options.hostname = proxy.host; + options.host = proxy.host; + options.port = proxy.port; + options.path = location; + + // Basic proxy authorization + if (proxy.auth) { + var base64 = Buffer.from(proxy.auth.username + ':' + proxy.auth.password, 'utf8').toString('base64'); + options.headers['Proxy-Authorization'] = 'Basic ' + base64; + } + + // If a proxy is used, any redirects must also pass through the proxy + options.beforeRedirect = function beforeRedirect(redirection) { + redirection.headers.host = redirection.host; + setProxy(redirection, proxy, redirection.href); + }; +} + +/*eslint consistent-return:0*/ +module.exports = function httpAdapter(config) { + return new Promise(function dispatchHttpRequest(resolvePromise, rejectPromise) { + var onCanceled; + function done() { + if (config.cancelToken) { + config.cancelToken.unsubscribe(onCanceled); + } + + if (config.signal) { + config.signal.removeEventListener('abort', onCanceled); + } + } + var resolve = function resolve(value) { + done(); + resolvePromise(value); + }; + var rejected = false; + var reject = function reject(value) { + done(); + rejected = true; + rejectPromise(value); + }; + var data = config.data; + var headers = config.headers; + var headerNames = {}; + + Object.keys(headers).forEach(function storeLowerName(name) { + headerNames[name.toLowerCase()] = name; + }); + + // Set User-Agent (required by some servers) + // See https://github.com/axios/axios/issues/69 + if ('user-agent' in headerNames) { + // User-Agent is specified; handle case where no UA header is desired + if (!headers[headerNames['user-agent']]) { + delete headers[headerNames['user-agent']]; + } + // Otherwise, use specified value + } else { + // Only set header if it hasn't been set in config + headers['User-Agent'] = 'axios/' + VERSION; + } + + if (data && !utils.isStream(data)) { + if (Buffer.isBuffer(data)) { + // Nothing to do... + } else if (utils.isArrayBuffer(data)) { + data = Buffer.from(new Uint8Array(data)); + } else if (utils.isString(data)) { + data = Buffer.from(data, 'utf-8'); + } else { + return reject(createError( + 'Data after transformation must be a string, an ArrayBuffer, a Buffer, or a Stream', + config + )); + } + + if (config.maxBodyLength > -1 && data.length > config.maxBodyLength) { + return reject(createError('Request body larger than maxBodyLength limit', config)); + } + + // Add Content-Length header if data exists + if (!headerNames['content-length']) { + headers['Content-Length'] = data.length; + } + } + + // HTTP basic authentication + var auth = undefined; + if (config.auth) { + var username = config.auth.username || ''; + var password = config.auth.password || ''; + auth = username + ':' + password; + } + + // Parse url + var fullPath = buildFullPath(config.baseURL, config.url); + var parsed = url.parse(fullPath); + var protocol = parsed.protocol || 'http:'; + + if (!auth && parsed.auth) { + var urlAuth = parsed.auth.split(':'); + var urlUsername = urlAuth[0] || ''; + var urlPassword = urlAuth[1] || ''; + auth = urlUsername + ':' + urlPassword; + } + + if (auth && headerNames.authorization) { + delete headers[headerNames.authorization]; + } + + var isHttpsRequest = isHttps.test(protocol); + var agent = isHttpsRequest ? config.httpsAgent : config.httpAgent; + + try { + buildURL(parsed.path, config.params, config.paramsSerializer).replace(/^\?/, ''); + } catch (err) { + var customErr = new Error(err.message); + customErr.config = config; + customErr.url = config.url; + customErr.exists = true; + reject(customErr); + } + + var options = { + path: buildURL(parsed.path, config.params, config.paramsSerializer).replace(/^\?/, ''), + method: config.method.toUpperCase(), + headers: headers, + agent: agent, + agents: { http: config.httpAgent, https: config.httpsAgent }, + auth: auth + }; + + if (config.socketPath) { + options.socketPath = config.socketPath; + } else { + options.hostname = parsed.hostname; + options.port = parsed.port; + } + + var proxy = config.proxy; + if (!proxy && proxy !== false) { + var proxyEnv = protocol.slice(0, -1) + '_proxy'; + var proxyUrl = process.env[proxyEnv] || process.env[proxyEnv.toUpperCase()]; + if (proxyUrl) { + var parsedProxyUrl = url.parse(proxyUrl); + var noProxyEnv = process.env.no_proxy || process.env.NO_PROXY; + var shouldProxy = true; + + if (noProxyEnv) { + var noProxy = noProxyEnv.split(',').map(function trim(s) { + return s.trim(); + }); + + shouldProxy = !noProxy.some(function proxyMatch(proxyElement) { + if (!proxyElement) { + return false; + } + if (proxyElement === '*') { + return true; + } + if (proxyElement[0] === '.' && + parsed.hostname.substr(parsed.hostname.length - proxyElement.length) === proxyElement) { + return true; + } + + return parsed.hostname === proxyElement; + }); + } + + if (shouldProxy) { + proxy = { + host: parsedProxyUrl.hostname, + port: parsedProxyUrl.port, + protocol: parsedProxyUrl.protocol + }; + + if (parsedProxyUrl.auth) { + var proxyUrlAuth = parsedProxyUrl.auth.split(':'); + proxy.auth = { + username: proxyUrlAuth[0], + password: proxyUrlAuth[1] + }; + } + } + } + } + + if (proxy) { + options.headers.host = parsed.hostname + (parsed.port ? ':' + parsed.port : ''); + setProxy(options, proxy, protocol + '//' + parsed.hostname + (parsed.port ? ':' + parsed.port : '') + options.path); + } + + var transport; + var isHttpsProxy = isHttpsRequest && (proxy ? isHttps.test(proxy.protocol) : true); + if (config.transport) { + transport = config.transport; + } else if (config.maxRedirects === 0) { + transport = isHttpsProxy ? https : http; + } else { + if (config.maxRedirects) { + options.maxRedirects = config.maxRedirects; + } + transport = isHttpsProxy ? httpsFollow : httpFollow; + } + + if (config.maxBodyLength > -1) { + options.maxBodyLength = config.maxBodyLength; + } + + if (config.insecureHTTPParser) { + options.insecureHTTPParser = config.insecureHTTPParser; + } + + // Create the request + var req = transport.request(options, function handleResponse(res) { + if (req.aborted) return; + + // uncompress the response body transparently if required + var stream = res; + + // return the last request in case of redirects + var lastRequest = res.req || req; + + + // if no content, is HEAD request or decompress disabled we should not decompress + if (res.statusCode !== 204 && lastRequest.method !== 'HEAD' && config.decompress !== false) { + switch (res.headers['content-encoding']) { + /*eslint default-case:0*/ + case 'gzip': + case 'compress': + case 'deflate': + // add the unzipper to the body stream processing pipeline + stream = stream.pipe(zlib.createUnzip()); + + // remove the content-encoding in order to not confuse downstream operations + delete res.headers['content-encoding']; + break; + } + } + + var response = { + status: res.statusCode, + statusText: res.statusMessage, + headers: res.headers, + config: config, + request: lastRequest + }; + + if (config.responseType === 'stream') { + response.data = stream; + settle(resolve, reject, response); + } else { + var responseBuffer = []; + var totalResponseBytes = 0; + stream.on('data', function handleStreamData(chunk) { + responseBuffer.push(chunk); + totalResponseBytes += chunk.length; + + // make sure the content length is not over the maxContentLength if specified + if (config.maxContentLength > -1 && totalResponseBytes > config.maxContentLength) { + // stream.destoy() emit aborted event before calling reject() on Node.js v16 + rejected = true; + stream.destroy(); + reject(createError('maxContentLength size of ' + config.maxContentLength + ' exceeded', + config, null, lastRequest)); + } + }); + + stream.on('aborted', function handlerStreamAborted() { + if (rejected) { + return; + } + stream.destroy(); + reject(createError('error request aborted', config, 'ERR_REQUEST_ABORTED', lastRequest)); + }); + + stream.on('error', function handleStreamError(err) { + if (req.aborted) return; + reject(enhanceError(err, config, null, lastRequest)); + }); + + stream.on('end', function handleStreamEnd() { + try { + var responseData = responseBuffer.length === 1 ? responseBuffer[0] : Buffer.concat(responseBuffer); + if (config.responseType !== 'arraybuffer') { + responseData = responseData.toString(config.responseEncoding); + if (!config.responseEncoding || config.responseEncoding === 'utf8') { + responseData = utils.stripBOM(responseData); + } + } + response.data = responseData; + } catch (err) { + reject(enhanceError(err, config, err.code, response.request, response)); + } + settle(resolve, reject, response); + }); + } + }); + + // Handle errors + req.on('error', function handleRequestError(err) { + if (req.aborted && err.code !== 'ERR_FR_TOO_MANY_REDIRECTS') return; + reject(enhanceError(err, config, null, req)); + }); + + // set tcp keep alive to prevent drop connection by peer + req.on('socket', function handleRequestSocket(socket) { + // default interval of sending ack packet is 1 minute + socket.setKeepAlive(true, 1000 * 60); + }); + + // Handle request timeout + if (config.timeout) { + // This is forcing a int timeout to avoid problems if the `req` interface doesn't handle other types. + var timeout = parseInt(config.timeout, 10); + + if (isNaN(timeout)) { + reject(createError( + 'error trying to parse `config.timeout` to int', + config, + 'ERR_PARSE_TIMEOUT', + req + )); + + return; + } + + // Sometime, the response will be very slow, and does not respond, the connect event will be block by event loop system. + // And timer callback will be fired, and abort() will be invoked before connection, then get "socket hang up" and code ECONNRESET. + // At this time, if we have a large number of request, nodejs will hang up some socket on background. and the number will up and up. + // And then these socket which be hang up will devoring CPU little by little. + // ClientRequest.setTimeout will be fired on the specify milliseconds, and can make sure that abort() will be fired after connect. + req.setTimeout(timeout, function handleRequestTimeout() { + req.abort(); + var timeoutErrorMessage = ''; + if (config.timeoutErrorMessage) { + timeoutErrorMessage = config.timeoutErrorMessage; + } else { + timeoutErrorMessage = 'timeout of ' + config.timeout + 'ms exceeded'; + } + var transitional = config.transitional || transitionalDefaults; + reject(createError( + timeoutErrorMessage, + config, + transitional.clarifyTimeoutError ? 'ETIMEDOUT' : 'ECONNABORTED', + req + )); + }); + } + + if (config.cancelToken || config.signal) { + // Handle cancellation + // eslint-disable-next-line func-names + onCanceled = function(cancel) { + if (req.aborted) return; + + req.abort(); + reject(!cancel || (cancel && cancel.type) ? new Cancel('canceled') : cancel); + }; + + config.cancelToken && config.cancelToken.subscribe(onCanceled); + if (config.signal) { + config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled); + } + } + + + // Send the request + if (utils.isStream(data)) { + data.on('error', function handleStreamError(err) { + reject(enhanceError(err, config, null, req)); + }).pipe(req); + } else { + req.end(data); + } + }); +}; diff --git a/node_modules/axios/lib/adapters/xhr.js b/node_modules/axios/lib/adapters/xhr.js new file mode 100644 index 0000000..e58625a --- /dev/null +++ b/node_modules/axios/lib/adapters/xhr.js @@ -0,0 +1,212 @@ +'use strict'; + +var utils = require('./../utils'); +var settle = require('./../core/settle'); +var cookies = require('./../helpers/cookies'); +var buildURL = require('./../helpers/buildURL'); +var buildFullPath = require('../core/buildFullPath'); +var parseHeaders = require('./../helpers/parseHeaders'); +var isURLSameOrigin = require('./../helpers/isURLSameOrigin'); +var createError = require('../core/createError'); +var transitionalDefaults = require('../defaults/transitional'); +var Cancel = require('../cancel/Cancel'); + +module.exports = function xhrAdapter(config) { + return new Promise(function dispatchXhrRequest(resolve, reject) { + var requestData = config.data; + var requestHeaders = config.headers; + var responseType = config.responseType; + var onCanceled; + function done() { + if (config.cancelToken) { + config.cancelToken.unsubscribe(onCanceled); + } + + if (config.signal) { + config.signal.removeEventListener('abort', onCanceled); + } + } + + if (utils.isFormData(requestData)) { + delete requestHeaders['Content-Type']; // Let the browser set it + } + + var request = new XMLHttpRequest(); + + // HTTP basic authentication + if (config.auth) { + var username = config.auth.username || ''; + var password = config.auth.password ? unescape(encodeURIComponent(config.auth.password)) : ''; + requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password); + } + + var 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 + var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null; + var responseData = !responseType || responseType === 'text' || responseType === 'json' ? + request.responseText : request.response; + var response = { + data: responseData, + status: request.status, + statusText: request.statusText, + headers: responseHeaders, + config: config, + request: 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(createError('Request aborted', config, 'ECONNABORTED', 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(createError('Network Error', config, null, request)); + + // Clean up request + request = null; + }; + + // Handle timeout + request.ontimeout = function handleTimeout() { + var timeoutErrorMessage = config.timeout ? 'timeout of ' + config.timeout + 'ms exceeded' : 'timeout exceeded'; + var transitional = config.transitional || transitionalDefaults; + if (config.timeoutErrorMessage) { + timeoutErrorMessage = config.timeoutErrorMessage; + } + reject(createError( + timeoutErrorMessage, + config, + transitional.clarifyTimeoutError ? 'ETIMEDOUT' : 'ECONNABORTED', + 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 (utils.isStandardBrowserEnv()) { + // Add xsrf header + var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ? + cookies.read(config.xsrfCookieName) : + undefined; + + if (xsrfValue) { + requestHeaders[config.xsrfHeaderName] = xsrfValue; + } + } + + // Add headers to the request + if ('setRequestHeader' in request) { + utils.forEach(requestHeaders, function setRequestHeader(val, key) { + if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { + // Remove Content-Type if data is undefined + delete requestHeaders[key]; + } else { + // Otherwise add header to the request + request.setRequestHeader(key, val); + } + }); + } + + // Add withCredentials to request if needed + if (!utils.isUndefined(config.withCredentials)) { + request.withCredentials = !!config.withCredentials; + } + + // Add responseType to request if needed + if (responseType && responseType !== 'json') { + request.responseType = config.responseType; + } + + // Handle progress if needed + if (typeof config.onDownloadProgress === 'function') { + request.addEventListener('progress', config.onDownloadProgress); + } + + // Not all browsers support upload events + if (typeof config.onUploadProgress === 'function' && request.upload) { + request.upload.addEventListener('progress', config.onUploadProgress); + } + + if (config.cancelToken || config.signal) { + // Handle cancellation + // eslint-disable-next-line func-names + onCanceled = function(cancel) { + if (!request) { + return; + } + reject(!cancel || (cancel && cancel.type) ? new Cancel('canceled') : cancel); + request.abort(); + request = null; + }; + + config.cancelToken && config.cancelToken.subscribe(onCanceled); + if (config.signal) { + config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled); + } + } + + if (!requestData) { + requestData = null; + } + + // Send the request + request.send(requestData); + }); +}; diff --git a/node_modules/axios/lib/axios.js b/node_modules/axios/lib/axios.js new file mode 100644 index 0000000..c032327 --- /dev/null +++ b/node_modules/axios/lib/axios.js @@ -0,0 +1,57 @@ +'use strict'; + +var utils = require('./utils'); +var bind = require('./helpers/bind'); +var Axios = require('./core/Axios'); +var mergeConfig = require('./core/mergeConfig'); +var defaults = require('./defaults'); + +/** + * Create an instance of Axios + * + * @param {Object} defaultConfig The default config for the instance + * @return {Axios} A new instance of Axios + */ +function createInstance(defaultConfig) { + var context = new Axios(defaultConfig); + var instance = bind(Axios.prototype.request, context); + + // Copy axios.prototype to instance + utils.extend(instance, Axios.prototype, context); + + // Copy context to instance + utils.extend(instance, context); + + // Factory for creating new instances + instance.create = function create(instanceConfig) { + return createInstance(mergeConfig(defaultConfig, instanceConfig)); + }; + + return instance; +} + +// Create the default instance to be exported +var axios = createInstance(defaults); + +// Expose Axios class to allow class inheritance +axios.Axios = Axios; + +// Expose Cancel & CancelToken +axios.Cancel = require('./cancel/Cancel'); +axios.CancelToken = require('./cancel/CancelToken'); +axios.isCancel = require('./cancel/isCancel'); +axios.VERSION = require('./env/data').version; + +// Expose all/spread +axios.all = function all(promises) { + return Promise.all(promises); +}; +axios.spread = require('./helpers/spread'); + +// Expose isAxiosError +axios.isAxiosError = require('./helpers/isAxiosError'); + +module.exports = axios; + +// Allow use of default import syntax in TypeScript +module.exports.default = axios; diff --git a/node_modules/axios/lib/cancel/Cancel.js b/node_modules/axios/lib/cancel/Cancel.js new file mode 100644 index 0000000..e0de400 --- /dev/null +++ b/node_modules/axios/lib/cancel/Cancel.js @@ -0,0 +1,19 @@ +'use strict'; + +/** + * A `Cancel` is an object that is thrown when an operation is canceled. + * + * @class + * @param {string=} message The message. + */ +function Cancel(message) { + this.message = message; +} + +Cancel.prototype.toString = function toString() { + return 'Cancel' + (this.message ? ': ' + this.message : ''); +}; + +Cancel.prototype.__CANCEL__ = true; + +module.exports = Cancel; diff --git a/node_modules/axios/lib/cancel/CancelToken.js b/node_modules/axios/lib/cancel/CancelToken.js new file mode 100644 index 0000000..089d6b9 --- /dev/null +++ b/node_modules/axios/lib/cancel/CancelToken.js @@ -0,0 +1,119 @@ +'use strict'; + +var Cancel = require('./Cancel'); + +/** + * A `CancelToken` is an object that can be used to request cancellation of an operation. + * + * @class + * @param {Function} executor The executor function. + */ +function CancelToken(executor) { + if (typeof executor !== 'function') { + throw new TypeError('executor must be a function.'); + } + + var resolvePromise; + + this.promise = new Promise(function promiseExecutor(resolve) { + resolvePromise = resolve; + }); + + var token = this; + + // eslint-disable-next-line func-names + this.promise.then(function(cancel) { + if (!token._listeners) return; + + var i; + var l = token._listeners.length; + + for (i = 0; i < l; i++) { + token._listeners[i](cancel); + } + token._listeners = null; + }); + + // eslint-disable-next-line func-names + this.promise.then = function(onfulfilled) { + var _resolve; + // eslint-disable-next-line func-names + var promise = new Promise(function(resolve) { + token.subscribe(resolve); + _resolve = resolve; + }).then(onfulfilled); + + promise.cancel = function reject() { + token.unsubscribe(_resolve); + }; + + return promise; + }; + + executor(function cancel(message) { + if (token.reason) { + // Cancellation has already been requested + return; + } + + token.reason = new Cancel(message); + resolvePromise(token.reason); + }); +} + +/** + * Throws a `Cancel` if cancellation has been requested. + */ +CancelToken.prototype.throwIfRequested = function throwIfRequested() { + if (this.reason) { + throw this.reason; + } +}; + +/** + * Subscribe to the cancel signal + */ + +CancelToken.prototype.subscribe = function subscribe(listener) { + if (this.reason) { + listener(this.reason); + return; + } + + if (this._listeners) { + this._listeners.push(listener); + } else { + this._listeners = [listener]; + } +}; + +/** + * Unsubscribe from the cancel signal + */ + +CancelToken.prototype.unsubscribe = function unsubscribe(listener) { + if (!this._listeners) { + return; + } + var index = this._listeners.indexOf(listener); + if (index !== -1) { + this._listeners.splice(index, 1); + } +}; + +/** + * Returns an object that contains a new `CancelToken` and a function that, when called, + * cancels the `CancelToken`. + */ +CancelToken.source = function source() { + var cancel; + var token = new CancelToken(function executor(c) { + cancel = c; + }); + return { + token: token, + cancel: cancel + }; +}; + +module.exports = CancelToken; diff --git a/node_modules/axios/lib/cancel/isCancel.js b/node_modules/axios/lib/cancel/isCancel.js new file mode 100644 index 0000000..051f3ae --- /dev/null +++ b/node_modules/axios/lib/cancel/isCancel.js @@ -0,0 +1,5 @@ +'use strict'; + +module.exports = function isCancel(value) { + return !!(value && value.__CANCEL__); +}; diff --git a/node_modules/axios/lib/core/Axios.js b/node_modules/axios/lib/core/Axios.js new file mode 100644 index 0000000..a1be08a --- /dev/null +++ b/node_modules/axios/lib/core/Axios.js @@ -0,0 +1,148 @@ +'use strict'; + +var utils = require('./../utils'); +var buildURL = require('../helpers/buildURL'); +var InterceptorManager = require('./InterceptorManager'); +var dispatchRequest = require('./dispatchRequest'); +var mergeConfig = require('./mergeConfig'); +var validator = require('../helpers/validator'); + +var validators = validator.validators; +/** + * Create a new instance of Axios + * + * @param {Object} instanceConfig The default config for the instance + */ +function Axios(instanceConfig) { + this.defaults = instanceConfig; + this.interceptors = { + request: new InterceptorManager(), + response: new InterceptorManager() + }; +} + +/** + * Dispatch a request + * + * @param {Object} config The config specific for this request (merged with this.defaults) + */ +Axios.prototype.request = function 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 || {}; + } + + config = mergeConfig(this.defaults, config); + + // Set config.method + if (config.method) { + config.method = config.method.toLowerCase(); + } else if (this.defaults.method) { + config.method = this.defaults.method.toLowerCase(); + } else { + config.method = 'get'; + } + + var transitional = config.transitional; + + if (transitional !== undefined) { + validator.assertOptions(transitional, { + silentJSONParsing: validators.transitional(validators.boolean), + forcedJSONParsing: validators.transitional(validators.boolean), + clarifyTimeoutError: validators.transitional(validators.boolean) + }, false); + } + + // filter out skipped interceptors + var requestInterceptorChain = []; + var 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); + }); + + var responseInterceptorChain = []; + this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { + responseInterceptorChain.push(interceptor.fulfilled, interceptor.rejected); + }); + + var promise; + + if (!synchronousRequestInterceptors) { + var chain = [dispatchRequest, undefined]; + + Array.prototype.unshift.apply(chain, requestInterceptorChain); + chain = chain.concat(responseInterceptorChain); + + promise = Promise.resolve(config); + while (chain.length) { + promise = promise.then(chain.shift(), chain.shift()); + } + + return promise; + } + + + var newConfig = config; + while (requestInterceptorChain.length) { + var onFulfilled = requestInterceptorChain.shift(); + var onRejected = requestInterceptorChain.shift(); + try { + newConfig = onFulfilled(newConfig); + } catch (error) { + onRejected(error); + break; + } + } + + try { + promise = dispatchRequest(newConfig); + } catch (error) { + return Promise.reject(error); + } + + while (responseInterceptorChain.length) { + promise = promise.then(responseInterceptorChain.shift(), responseInterceptorChain.shift()); + } + + return promise; +}; + +Axios.prototype.getUri = function getUri(config) { + config = mergeConfig(this.defaults, config); + return buildURL(config.url, config.params, config.paramsSerializer).replace(/^\?/, ''); +}; + +// Provide aliases for supported request methods +utils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { + /*eslint func-names:0*/ + Axios.prototype[method] = function(url, config) { + return this.request(mergeConfig(config || {}, { + method: method, + url: url, + data: (config || {}).data + })); + }; +}); + +utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { + /*eslint func-names:0*/ + Axios.prototype[method] = function(url, data, config) { + return this.request(mergeConfig(config || {}, { + method: method, + url: url, + data: data + })); + }; +}); + +module.exports = Axios; diff --git a/node_modules/axios/lib/core/InterceptorManager.js b/node_modules/axios/lib/core/InterceptorManager.js new file mode 100644 index 0000000..900f448 --- /dev/null +++ b/node_modules/axios/lib/core/InterceptorManager.js @@ -0,0 +1,54 @@ +'use strict'; + +var utils = require('./../utils'); + +function InterceptorManager() { + 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 + */ +InterceptorManager.prototype.use = function use(fulfilled, rejected, options) { + this.handlers.push({ + fulfilled: fulfilled, + rejected: 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` + */ +InterceptorManager.prototype.eject = function eject(id) { + if (this.handlers[id]) { + this.handlers[id] = null; + } +}; + +/** + * 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 + */ +InterceptorManager.prototype.forEach = function forEach(fn) { + utils.forEach(this.handlers, function forEachHandler(h) { + if (h !== null) { + fn(h); + } + }); +}; + +module.exports = InterceptorManager; diff --git a/node_modules/axios/lib/core/README.md b/node_modules/axios/lib/core/README.md new file mode 100644 index 0000000..84559ce --- /dev/null +++ b/node_modules/axios/lib/core/README.md @@ -0,0 +1,8 @@ +# axios // core + +The modules found in `core/` should be modules that are specific to the domain logic of axios. These modules would most likely not make sense to be consumed outside of the axios module, as their logic is too specific. Some examples of core modules are: + +- Dispatching requests + - Requests sent via `adapters/` (see lib/adapters/README.md) +- Managing interceptors +- Handling config diff --git a/node_modules/axios/lib/core/buildFullPath.js b/node_modules/axios/lib/core/buildFullPath.js new file mode 100644 index 0000000..00b2b05 --- /dev/null +++ b/node_modules/axios/lib/core/buildFullPath.js @@ -0,0 +1,20 @@ +'use strict'; + +var isAbsoluteURL = require('../helpers/isAbsoluteURL'); +var combineURLs = require('../helpers/combineURLs'); + +/** + * 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 + */ +module.exports = function buildFullPath(baseURL, requestedURL) { + if (baseURL && !isAbsoluteURL(requestedURL)) { + return combineURLs(baseURL, requestedURL); + } + return requestedURL; +}; diff --git a/node_modules/axios/lib/core/createError.js b/node_modules/axios/lib/core/createError.js new file mode 100644 index 0000000..933680f --- /dev/null +++ b/node_modules/axios/lib/core/createError.js @@ -0,0 +1,18 @@ +'use strict'; + +var enhanceError = require('./enhanceError'); + +/** + * Create an Error with the specified message, config, error code, request and response. + * + * @param {string} message The error message. + * @param {Object} config The config. + * @param {string} [code] The error code (for example, 'ECONNABORTED'). + * @param {Object} [request] The request. + * @param {Object} [response] The response. + * @returns {Error} The created error. + */ +module.exports = function createError(message, config, code, request, response) { + var error = new Error(message); + return enhanceError(error, config, code, request, response); +}; diff --git a/node_modules/axios/lib/core/dispatchRequest.js b/node_modules/axios/lib/core/dispatchRequest.js new file mode 100644 index 0000000..36da48b --- /dev/null +++ b/node_modules/axios/lib/core/dispatchRequest.js @@ -0,0 +1,87 @@ +'use strict'; + +var utils = require('./../utils'); +var transformData = require('./transformData'); +var isCancel = require('../cancel/isCancel'); +var defaults = require('../defaults'); +var Cancel = require('../cancel/Cancel'); + +/** + * Throws a `Cancel` if cancellation has been requested. + */ +function throwIfCancellationRequested(config) { + if (config.cancelToken) { + config.cancelToken.throwIfRequested(); + } + + if (config.signal && config.signal.aborted) { + throw new Cancel('canceled'); + } +} + +/** + * Dispatch a request to the server using the configured adapter. + * + * @param {object} config The config that is to be used for the request + * @returns {Promise} The Promise to be fulfilled + */ +module.exports = function dispatchRequest(config) { + throwIfCancellationRequested(config); + + // Ensure headers exist + config.headers = config.headers || {}; + + // Transform request data + config.data = transformData.call( + config, + config.data, + config.headers, + config.transformRequest + ); + + // Flatten headers + config.headers = utils.merge( + config.headers.common || {}, + config.headers[config.method] || {}, + config.headers + ); + + utils.forEach( + ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], + function cleanHeaderConfig(method) { + delete config.headers[method]; + } + ); + + var adapter = config.adapter || defaults.adapter; + + return adapter(config).then(function onAdapterResolution(response) { + throwIfCancellationRequested(config); + + // Transform response data + response.data = transformData.call( + config, + response.data, + response.headers, + config.transformResponse + ); + + return response; + }, function onAdapterRejection(reason) { + if (!isCancel(reason)) { + throwIfCancellationRequested(config); + + // Transform response data + if (reason && reason.response) { + reason.response.data = transformData.call( + config, + reason.response.data, + reason.response.headers, + config.transformResponse + ); + } + } + + return Promise.reject(reason); + }); +}; diff --git a/node_modules/axios/lib/core/enhanceError.js b/node_modules/axios/lib/core/enhanceError.js new file mode 100644 index 0000000..db04ec8 --- /dev/null +++ b/node_modules/axios/lib/core/enhanceError.js @@ -0,0 +1,43 @@ +'use strict'; + +/** + * Update an Error with the specified config, error code, and response. + * + * @param {Error} error The error to update. + * @param {Object} config The config. + * @param {string} [code] The error code (for example, 'ECONNABORTED'). + * @param {Object} [request] The request. + * @param {Object} [response] The response. + * @returns {Error} The error. + */ +module.exports = function enhanceError(error, config, code, request, response) { + error.config = config; + if (code) { + error.code = code; + } + + error.request = request; + error.response = response; + error.isAxiosError = true; + + 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: this.config, + code: this.code, + status: this.response && this.response.status ? this.response.status : null + }; + }; + return error; +}; diff --git a/node_modules/axios/lib/core/mergeConfig.js b/node_modules/axios/lib/core/mergeConfig.js new file mode 100644 index 0000000..05d1438 --- /dev/null +++ b/node_modules/axios/lib/core/mergeConfig.js @@ -0,0 +1,99 @@ +'use strict'; + +var utils = require('../utils'); + +/** + * Config-specific merge-function which creates a new config-object + * by merging two configuration objects together. + * + * @param {Object} config1 + * @param {Object} config2 + * @returns {Object} New object resulting from merging config2 to config1 + */ +module.exports = function mergeConfig(config1, config2) { + // eslint-disable-next-line no-param-reassign + config2 = config2 || {}; + var config = {}; + + function getMergedValue(target, source) { + if (utils.isPlainObject(target) && utils.isPlainObject(source)) { + return utils.merge(target, source); + } else if (utils.isPlainObject(source)) { + return utils.merge({}, source); + } else if (utils.isArray(source)) { + return source.slice(); + } + return source; + } + + // eslint-disable-next-line consistent-return + function mergeDeepProperties(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(config1[prop], config2[prop]); + } else if (!utils.isUndefined(config1[prop])) { + return getMergedValue(undefined, config1[prop]); + } + } + + // eslint-disable-next-line consistent-return + function valueFromConfig2(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(undefined, config2[prop]); + } + } + + // eslint-disable-next-line consistent-return + function defaultToConfig2(prop) { + if (!utils.isUndefined(config2[prop])) { + return getMergedValue(undefined, config2[prop]); + } else if (!utils.isUndefined(config1[prop])) { + return getMergedValue(undefined, config1[prop]); + } + } + + // eslint-disable-next-line consistent-return + function mergeDirectKeys(prop) { + if (prop in config2) { + return getMergedValue(config1[prop], config2[prop]); + } else if (prop in config1) { + return getMergedValue(undefined, config1[prop]); + } + } + + var mergeMap = { + 'url': valueFromConfig2, + 'method': valueFromConfig2, + 'data': valueFromConfig2, + 'baseURL': defaultToConfig2, + 'transformRequest': defaultToConfig2, + 'transformResponse': defaultToConfig2, + 'paramsSerializer': defaultToConfig2, + 'timeout': defaultToConfig2, + 'timeoutMessage': defaultToConfig2, + 'withCredentials': defaultToConfig2, + 'adapter': defaultToConfig2, + 'responseType': defaultToConfig2, + 'xsrfCookieName': defaultToConfig2, + 'xsrfHeaderName': defaultToConfig2, + 'onUploadProgress': defaultToConfig2, + 'onDownloadProgress': defaultToConfig2, + 'decompress': defaultToConfig2, + 'maxContentLength': defaultToConfig2, + 'maxBodyLength': defaultToConfig2, + 'transport': defaultToConfig2, + 'httpAgent': defaultToConfig2, + 'httpsAgent': defaultToConfig2, + 'cancelToken': defaultToConfig2, + 'socketPath': defaultToConfig2, + 'responseEncoding': defaultToConfig2, + 'validateStatus': mergeDirectKeys + }; + + utils.forEach(Object.keys(config1).concat(Object.keys(config2)), function computeConfigValue(prop) { + var merge = mergeMap[prop] || mergeDeepProperties; + var configValue = merge(prop); + (utils.isUndefined(configValue) && merge !== mergeDirectKeys) || (config[prop] = configValue); + }); + + return config; +}; diff --git a/node_modules/axios/lib/core/settle.js b/node_modules/axios/lib/core/settle.js new file mode 100644 index 0000000..886adb0 --- /dev/null +++ b/node_modules/axios/lib/core/settle.js @@ -0,0 +1,25 @@ +'use strict'; + +var createError = require('./createError'); + +/** + * 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. + */ +module.exports = function settle(resolve, reject, response) { + var validateStatus = response.config.validateStatus; + if (!response.status || !validateStatus || validateStatus(response.status)) { + resolve(response); + } else { + reject(createError( + 'Request failed with status code ' + response.status, + response.config, + null, + response.request, + response + )); + } +}; diff --git a/node_modules/axios/lib/core/transformData.js b/node_modules/axios/lib/core/transformData.js new file mode 100644 index 0000000..82ee7dd --- /dev/null +++ b/node_modules/axios/lib/core/transformData.js @@ -0,0 +1,22 @@ +'use strict'; + +var utils = require('./../utils'); +var defaults = require('../defaults'); + +/** + * Transform the data for a request or a response + * + * @param {Object|String} data The data to be transformed + * @param {Array} headers The headers for the request or response + * @param {Array|Function} fns A single function or Array of functions + * @returns {*} The resulting transformed data + */ +module.exports = function transformData(data, headers, fns) { + var context = this || defaults; + /*eslint no-param-reassign:0*/ + utils.forEach(fns, function transform(fn) { + data = fn.call(context, data, headers); + }); + + return data; +}; diff --git a/node_modules/axios/lib/defaults/index.js b/node_modules/axios/lib/defaults/index.js new file mode 100644 index 0000000..8b57b88 --- /dev/null +++ b/node_modules/axios/lib/defaults/index.js @@ -0,0 +1,131 @@ +'use strict'; + +var utils = require('../utils'); +var normalizeHeaderName = require('../helpers/normalizeHeaderName'); +var enhanceError = require('../core/enhanceError'); +var transitionalDefaults = require('./transitional'); + +var DEFAULT_CONTENT_TYPE = { + 'Content-Type': 'application/x-www-form-urlencoded' +}; + +function setContentTypeIfUnset(headers, value) { + if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) { + headers['Content-Type'] = value; + } +} + +function getDefaultAdapter() { + var adapter; + if (typeof XMLHttpRequest !== 'undefined') { + // For browsers use XHR adapter + adapter = require('../adapters/xhr'); + } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') { + // For node use HTTP adapter + adapter = require('../adapters/http'); + } + return adapter; +} + +function stringifySafely(rawValue, parser, encoder) { + if (utils.isString(rawValue)) { + try { + (parser || JSON.parse)(rawValue); + return utils.trim(rawValue); + } catch (e) { + if (e.name !== 'SyntaxError') { + throw e; + } + } + } + + return (encoder || JSON.stringify)(rawValue); +} + +var defaults = { + + transitional: transitionalDefaults, + + adapter: getDefaultAdapter(), + + transformRequest: [function transformRequest(data, headers) { + normalizeHeaderName(headers, 'Accept'); + normalizeHeaderName(headers, 'Content-Type'); + + if (utils.isFormData(data) || + utils.isArrayBuffer(data) || + utils.isBuffer(data) || + utils.isStream(data) || + utils.isFile(data) || + utils.isBlob(data) + ) { + return data; + } + if (utils.isArrayBufferView(data)) { + return data.buffer; + } + if (utils.isURLSearchParams(data)) { + setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8'); + return data.toString(); + } + if (utils.isObject(data) || (headers && headers['Content-Type'] === 'application/json')) { + setContentTypeIfUnset(headers, 'application/json'); + return stringifySafely(data); + } + return data; + }], + + transformResponse: [function transformResponse(data) { + var transitional = this.transitional || defaults.transitional; + var silentJSONParsing = transitional && transitional.silentJSONParsing; + var forcedJSONParsing = transitional && transitional.forcedJSONParsing; + var strictJSONParsing = !silentJSONParsing && this.responseType === 'json'; + + if (strictJSONParsing || (forcedJSONParsing && utils.isString(data) && data.length)) { + try { + return JSON.parse(data); + } catch (e) { + if (strictJSONParsing) { + if (e.name === 'SyntaxError') { + throw enhanceError(e, this, 'E_JSON_PARSE'); + } + 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, + + validateStatus: function validateStatus(status) { + return status >= 200 && status < 300; + }, + + headers: { + common: { + 'Accept': 'application/json, text/plain, */*' + } + } +}; + +utils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { + defaults.headers[method] = {}; +}); + +utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { + defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE); +}); + +module.exports = defaults; diff --git a/node_modules/axios/lib/defaults/transitional.js b/node_modules/axios/lib/defaults/transitional.js new file mode 100644 index 0000000..601dd7e --- /dev/null +++ b/node_modules/axios/lib/defaults/transitional.js @@ -0,0 +1,7 @@ +'use strict'; + +module.exports = { + silentJSONParsing: true, + forcedJSONParsing: true, + clarifyTimeoutError: false +}; diff --git a/node_modules/axios/lib/env/README.md b/node_modules/axios/lib/env/README.md new file mode 100644 index 0000000..b41baff --- /dev/null +++ b/node_modules/axios/lib/env/README.md @@ -0,0 +1,3 @@ +# axios // env + +The `data.js` file is updated automatically when the package version is upgrading. Please do not edit it manually. diff --git a/node_modules/axios/lib/env/data.js b/node_modules/axios/lib/env/data.js new file mode 100644 index 0000000..9fd3106 --- /dev/null +++ b/node_modules/axios/lib/env/data.js @@ -0,0 +1,3 @@ +module.exports = { + "version": "0.26.1" +};
\ No newline at end of file diff --git a/node_modules/axios/lib/helpers/README.md b/node_modules/axios/lib/helpers/README.md new file mode 100644 index 0000000..4ae3419 --- /dev/null +++ b/node_modules/axios/lib/helpers/README.md @@ -0,0 +1,7 @@ +# axios // helpers + +The modules found in `helpers/` should be generic modules that are _not_ specific to the domain logic of axios. These modules could theoretically be published to npm on their own and consumed by other modules or apps. Some examples of generic modules are things like: + +- Browser polyfills +- Managing cookies +- Parsing HTTP headers diff --git a/node_modules/axios/lib/helpers/bind.js b/node_modules/axios/lib/helpers/bind.js new file mode 100644 index 0000000..6147c60 --- /dev/null +++ b/node_modules/axios/lib/helpers/bind.js @@ -0,0 +1,11 @@ +'use strict'; + +module.exports = function bind(fn, thisArg) { + return function wrap() { + var args = new Array(arguments.length); + for (var i = 0; i < args.length; i++) { + args[i] = arguments[i]; + } + return fn.apply(thisArg, args); + }; +}; diff --git a/node_modules/axios/lib/helpers/buildURL.js b/node_modules/axios/lib/helpers/buildURL.js new file mode 100644 index 0000000..31595c3 --- /dev/null +++ b/node_modules/axios/lib/helpers/buildURL.js @@ -0,0 +1,70 @@ +'use strict'; + +var utils = require('./../utils'); + +function encode(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 + * @returns {string} The formatted url + */ +module.exports = function buildURL(url, params, paramsSerializer) { + /*eslint no-param-reassign:0*/ + if (!params) { + return url; + } + + var serializedParams; + if (paramsSerializer) { + serializedParams = paramsSerializer(params); + } else if (utils.isURLSearchParams(params)) { + serializedParams = params.toString(); + } else { + var parts = []; + + utils.forEach(params, function serialize(val, key) { + if (val === null || typeof val === 'undefined') { + return; + } + + if (utils.isArray(val)) { + key = key + '[]'; + } else { + val = [val]; + } + + utils.forEach(val, function parseValue(v) { + if (utils.isDate(v)) { + v = v.toISOString(); + } else if (utils.isObject(v)) { + v = JSON.stringify(v); + } + parts.push(encode(key) + '=' + encode(v)); + }); + }); + + serializedParams = parts.join('&'); + } + + if (serializedParams) { + var hashmarkIndex = url.indexOf('#'); + if (hashmarkIndex !== -1) { + url = url.slice(0, hashmarkIndex); + } + + url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; + } + + return url; +}; diff --git a/node_modules/axios/lib/helpers/combineURLs.js b/node_modules/axios/lib/helpers/combineURLs.js new file mode 100644 index 0000000..f1b58a5 --- /dev/null +++ b/node_modules/axios/lib/helpers/combineURLs.js @@ -0,0 +1,14 @@ +'use strict'; + +/** + * 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 + */ +module.exports = function combineURLs(baseURL, relativeURL) { + return relativeURL + ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') + : baseURL; +}; diff --git a/node_modules/axios/lib/helpers/cookies.js b/node_modules/axios/lib/helpers/cookies.js new file mode 100644 index 0000000..5a8a666 --- /dev/null +++ b/node_modules/axios/lib/helpers/cookies.js @@ -0,0 +1,53 @@ +'use strict'; + +var utils = require('./../utils'); + +module.exports = ( + utils.isStandardBrowserEnv() ? + + // Standard browser envs support document.cookie + (function standardBrowserEnv() { + return { + write: function write(name, value, expires, path, domain, secure) { + var cookie = []; + cookie.push(name + '=' + encodeURIComponent(value)); + + if (utils.isNumber(expires)) { + cookie.push('expires=' + new Date(expires).toGMTString()); + } + + if (utils.isString(path)) { + cookie.push('path=' + path); + } + + if (utils.isString(domain)) { + cookie.push('domain=' + domain); + } + + if (secure === true) { + cookie.push('secure'); + } + + document.cookie = cookie.join('; '); + }, + + read: function read(name) { + var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); + return (match ? decodeURIComponent(match[3]) : null); + }, + + remove: function remove(name) { + this.write(name, '', Date.now() - 86400000); + } + }; + })() : + + // Non standard browser env (web workers, react-native) lack needed support. + (function nonStandardBrowserEnv() { + return { + write: function write() {}, + read: function read() { return null; }, + remove: function remove() {} + }; + })() +); diff --git a/node_modules/axios/lib/helpers/deprecatedMethod.js b/node_modules/axios/lib/helpers/deprecatedMethod.js new file mode 100644 index 0000000..ed40965 --- /dev/null +++ b/node_modules/axios/lib/helpers/deprecatedMethod.js @@ -0,0 +1,24 @@ +'use strict'; + +/*eslint no-console:0*/ + +/** + * Supply a warning to the developer that a method they are using + * has been deprecated. + * + * @param {string} method The name of the deprecated method + * @param {string} [instead] The alternate method to use if applicable + * @param {string} [docs] The documentation URL to get further details + */ +module.exports = function deprecatedMethod(method, instead, docs) { + try { + console.warn( + 'DEPRECATED method `' + method + '`.' + + (instead ? ' Use `' + instead + '` instead.' : '') + + ' This method will be removed in a future release.'); + + if (docs) { + console.warn('For more information about usage see ' + docs); + } + } catch (e) { /* Ignore */ } +}; diff --git a/node_modules/axios/lib/helpers/isAbsoluteURL.js b/node_modules/axios/lib/helpers/isAbsoluteURL.js new file mode 100644 index 0000000..43fea78 --- /dev/null +++ b/node_modules/axios/lib/helpers/isAbsoluteURL.js @@ -0,0 +1,14 @@ +'use strict'; + +/** + * 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 + */ +module.exports = 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); +}; diff --git a/node_modules/axios/lib/helpers/isAxiosError.js b/node_modules/axios/lib/helpers/isAxiosError.js new file mode 100644 index 0000000..a037bec --- /dev/null +++ b/node_modules/axios/lib/helpers/isAxiosError.js @@ -0,0 +1,13 @@ +'use strict'; + +var utils = require('./../utils'); + +/** + * 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 + */ +module.exports = function isAxiosError(payload) { + return utils.isObject(payload) && (payload.isAxiosError === true); +}; diff --git a/node_modules/axios/lib/helpers/isURLSameOrigin.js b/node_modules/axios/lib/helpers/isURLSameOrigin.js new file mode 100644 index 0000000..f1d89ad --- /dev/null +++ b/node_modules/axios/lib/helpers/isURLSameOrigin.js @@ -0,0 +1,68 @@ +'use strict'; + +var utils = require('./../utils'); + +module.exports = ( + utils.isStandardBrowserEnv() ? + + // 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() { + var msie = /(msie|trident)/i.test(navigator.userAgent); + var urlParsingNode = document.createElement('a'); + var originURL; + + /** + * Parse a URL to discover it's components + * + * @param {String} url The URL to be parsed + * @returns {Object} + */ + function resolveURL(url) { + var 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) { + var parsed = (utils.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; + }; + })() +); diff --git a/node_modules/axios/lib/helpers/normalizeHeaderName.js b/node_modules/axios/lib/helpers/normalizeHeaderName.js new file mode 100644 index 0000000..738c9fe --- /dev/null +++ b/node_modules/axios/lib/helpers/normalizeHeaderName.js @@ -0,0 +1,12 @@ +'use strict'; + +var utils = require('../utils'); + +module.exports = function normalizeHeaderName(headers, normalizedName) { + utils.forEach(headers, function processHeader(value, name) { + if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { + headers[normalizedName] = value; + delete headers[name]; + } + }); +}; diff --git a/node_modules/axios/lib/helpers/parseHeaders.js b/node_modules/axios/lib/helpers/parseHeaders.js new file mode 100644 index 0000000..8af2cc7 --- /dev/null +++ b/node_modules/axios/lib/helpers/parseHeaders.js @@ -0,0 +1,53 @@ +'use strict'; + +var utils = require('./../utils'); + +// Headers whose duplicates are ignored by node +// c.f. https://nodejs.org/api/http.html#http_message_headers +var ignoreDuplicateOf = [ + '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} headers Headers needing to be parsed + * @returns {Object} Headers parsed into an object + */ +module.exports = function parseHeaders(headers) { + var parsed = {}; + var key; + var val; + var i; + + if (!headers) { return parsed; } + + utils.forEach(headers.split('\n'), function parser(line) { + i = line.indexOf(':'); + key = utils.trim(line.substr(0, i)).toLowerCase(); + val = utils.trim(line.substr(i + 1)); + + if (key) { + if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) { + return; + } + if (key === 'set-cookie') { + parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); + } else { + parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; + } + } + }); + + return parsed; +}; diff --git a/node_modules/axios/lib/helpers/spread.js b/node_modules/axios/lib/helpers/spread.js new file mode 100644 index 0000000..25e3cdd --- /dev/null +++ b/node_modules/axios/lib/helpers/spread.js @@ -0,0 +1,27 @@ +'use strict'; + +/** + * 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} + */ +module.exports = function spread(callback) { + return function wrap(arr) { + return callback.apply(null, arr); + }; +}; diff --git a/node_modules/axios/lib/helpers/toFormData.js b/node_modules/axios/lib/helpers/toFormData.js new file mode 100644 index 0000000..e21d0a7 --- /dev/null +++ b/node_modules/axios/lib/helpers/toFormData.js @@ -0,0 +1,55 @@ +'use strict'; + +function combinedKey(parentKey, elKey) { + return parentKey + '.' + elKey; +} + +function buildFormData(formData, data, parentKey) { + if (Array.isArray(data)) { + data.forEach(function buildArray(el, i) { + buildFormData(formData, el, combinedKey(parentKey, i)); + }); + } else if ( + typeof data === 'object' && + !(data instanceof File || data === null) + ) { + Object.keys(data).forEach(function buildObject(key) { + buildFormData( + formData, + data[key], + parentKey ? combinedKey(parentKey, key) : key + ); + }); + } else { + if (data === undefined) { + return; + } + + var value = + typeof data === 'boolean' || typeof data === 'number' + ? data.toString() + : data; + formData.append(parentKey, value); + } +} + +/** + * convert a data object to FormData + * + * type FormDataPrimitive = string | Blob | number | boolean + * interface FormDataNest { + * [x: string]: FormVal + * } + * + * type FormVal = FormDataNest | FormDataPrimitive + * + * @param {FormVal} data + */ + +module.exports = function getFormData(data) { + var formData = new FormData(); + + buildFormData(formData, data); + + return formData; +}; diff --git a/node_modules/axios/lib/helpers/validator.js b/node_modules/axios/lib/helpers/validator.js new file mode 100644 index 0000000..a4ec413 --- /dev/null +++ b/node_modules/axios/lib/helpers/validator.js @@ -0,0 +1,82 @@ +'use strict'; + +var VERSION = require('../env/data').version; + +var validators = {}; + +// eslint-disable-next-line func-names +['object', 'boolean', 'number', 'function', 'string', 'symbol'].forEach(function(type, i) { + validators[type] = function validator(thing) { + return typeof thing === type || 'a' + (i < 1 ? 'n ' : ' ') + type; + }; +}); + +var deprecatedWarnings = {}; + +/** + * Transitional option validator + * @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 + * @returns {function} + */ +validators.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 + return function(value, opt, opts) { + if (validator === false) { + throw new Error(formatMessage(opt, ' has been removed' + (version ? ' in ' + version : ''))); + } + + 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 + * @param {object} options + * @param {object} schema + * @param {boolean?} allowUnknown + */ + +function assertOptions(options, schema, allowUnknown) { + if (typeof options !== 'object') { + throw new TypeError('options must be an object'); + } + var keys = Object.keys(options); + var i = keys.length; + while (i-- > 0) { + var opt = keys[i]; + var validator = schema[opt]; + if (validator) { + var value = options[opt]; + var result = value === undefined || validator(value, opt, options); + if (result !== true) { + throw new TypeError('option ' + opt + ' must be ' + result); + } + continue; + } + if (allowUnknown !== true) { + throw Error('Unknown option ' + opt); + } + } +} + +module.exports = { + assertOptions: assertOptions, + validators: validators +}; diff --git a/node_modules/axios/lib/utils.js b/node_modules/axios/lib/utils.js new file mode 100644 index 0000000..f0f9043 --- /dev/null +++ b/node_modules/axios/lib/utils.js @@ -0,0 +1,349 @@ +'use strict'; + +var bind = require('./helpers/bind'); + +// utils is a library of generic helper functions non-specific to axios + +var toString = Object.prototype.toString; + +/** + * Determine if a value is an Array + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an Array, otherwise false + */ +function isArray(val) { + return Array.isArray(val); +} + +/** + * Determine if a value is undefined + * + * @param {Object} val The value to test + * @returns {boolean} True if the value is undefined, otherwise false + */ +function isUndefined(val) { + return typeof val === 'undefined'; +} + +/** + * Determine if a value is a Buffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Buffer, otherwise false + */ +function isBuffer(val) { + return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor) + && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val); +} + +/** + * Determine if a value is an ArrayBuffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an ArrayBuffer, otherwise false + */ +function isArrayBuffer(val) { + return toString.call(val) === '[object ArrayBuffer]'; +} + +/** + * Determine if a value is a FormData + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an FormData, otherwise false + */ +function isFormData(val) { + return toString.call(val) === '[object FormData]'; +} + +/** + * Determine if a value is a view on an ArrayBuffer + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false + */ +function isArrayBufferView(val) { + var result; + 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 + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a String, otherwise false + */ +function isString(val) { + return typeof val === 'string'; +} + +/** + * Determine if a value is a Number + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Number, otherwise false + */ +function isNumber(val) { + return typeof val === 'number'; +} + +/** + * Determine if a value is an Object + * + * @param {Object} val The value to test + * @returns {boolean} True if value is an Object, otherwise false + */ +function isObject(val) { + return val !== null && typeof val === 'object'; +} + +/** + * Determine if a value is a plain Object + * + * @param {Object} val The value to test + * @return {boolean} True if value is a plain Object, otherwise false + */ +function isPlainObject(val) { + if (toString.call(val) !== '[object Object]') { + return false; + } + + var prototype = Object.getPrototypeOf(val); + return prototype === null || prototype === Object.prototype; +} + +/** + * Determine if a value is a Date + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Date, otherwise false + */ +function isDate(val) { + return toString.call(val) === '[object Date]'; +} + +/** + * Determine if a value is a File + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a File, otherwise false + */ +function isFile(val) { + return toString.call(val) === '[object File]'; +} + +/** + * Determine if a value is a Blob + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Blob, otherwise false + */ +function isBlob(val) { + return toString.call(val) === '[object Blob]'; +} + +/** + * Determine if a value is a Function + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Function, otherwise false + */ +function isFunction(val) { + return toString.call(val) === '[object Function]'; +} + +/** + * Determine if a value is a Stream + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a Stream, otherwise false + */ +function isStream(val) { + return isObject(val) && isFunction(val.pipe); +} + +/** + * Determine if a value is a URLSearchParams object + * + * @param {Object} val The value to test + * @returns {boolean} True if value is a URLSearchParams object, otherwise false + */ +function isURLSearchParams(val) { + return toString.call(val) === '[object URLSearchParams]'; +} + +/** + * Trim excess whitespace off the beginning and end of a string + * + * @param {String} str The String to trim + * @returns {String} The String freed of excess whitespace + */ +function trim(str) { + return str.trim ? str.trim() : str.replace(/^\s+|\s+$/g, ''); +} + +/** + * 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' + */ +function isStandardBrowserEnv() { + if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' || + navigator.product === 'NativeScript' || + navigator.product === 'NS')) { + return false; + } + return ( + typeof window !== 'undefined' && + typeof document !== 'undefined' + ); +} + +/** + * 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 + */ +function forEach(obj, fn) { + // Don't bother if no value provided + if (obj === null || typeof obj === 'undefined') { + return; + } + + // Force an array if not already something iterable + if (typeof obj !== 'object') { + /*eslint no-param-reassign:0*/ + obj = [obj]; + } + + if (isArray(obj)) { + // Iterate over array values + for (var i = 0, l = obj.length; i < l; i++) { + fn.call(null, obj[i], i, obj); + } + } else { + // Iterate over object keys + for (var key in obj) { + if (Object.prototype.hasOwnProperty.call(obj, key)) { + fn.call(null, obj[key], key, obj); + } + } + } +} + +/** + * 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 + * @returns {Object} Result of all merge properties + */ +function merge(/* obj1, obj2, obj3, ... */) { + var result = {}; + function assignValue(val, key) { + if (isPlainObject(result[key]) && isPlainObject(val)) { + result[key] = merge(result[key], val); + } else if (isPlainObject(val)) { + result[key] = merge({}, val); + } else if (isArray(val)) { + result[key] = val.slice(); + } else { + result[key] = val; + } + } + + for (var i = 0, l = arguments.length; i < l; i++) { + forEach(arguments[i], assignValue); + } + 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 + * @return {Object} The resulting value of object a + */ +function extend(a, b, thisArg) { + forEach(b, function assignValue(val, key) { + if (thisArg && typeof val === 'function') { + a[key] = bind(val, thisArg); + } else { + a[key] = val; + } + }); + return a; +} + +/** + * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM) + * + * @param {string} content with BOM + * @return {string} content value without BOM + */ +function stripBOM(content) { + if (content.charCodeAt(0) === 0xFEFF) { + content = content.slice(1); + } + return content; +} + +module.exports = { + isArray: isArray, + isArrayBuffer: isArrayBuffer, + isBuffer: isBuffer, + isFormData: isFormData, + isArrayBufferView: isArrayBufferView, + isString: isString, + isNumber: isNumber, + isObject: isObject, + isPlainObject: isPlainObject, + isUndefined: isUndefined, + isDate: isDate, + isFile: isFile, + isBlob: isBlob, + isFunction: isFunction, + isStream: isStream, + isURLSearchParams: isURLSearchParams, + isStandardBrowserEnv: isStandardBrowserEnv, + forEach: forEach, + merge: merge, + extend: extend, + trim: trim, + stripBOM: stripBOM +}; diff --git a/node_modules/axios/package.json b/node_modules/axios/package.json new file mode 100644 index 0000000..32c275c --- /dev/null +++ b/node_modules/axios/package.json @@ -0,0 +1,86 @@ +{ + "name": "axios", + "version": "0.26.1", + "description": "Promise based HTTP client for the browser and node.js", + "main": "index.js", + "types": "index.d.ts", + "scripts": { + "test": "grunt test && dtslint", + "start": "node ./sandbox/server.js", + "build": "NODE_ENV=production grunt build", + "preversion": "grunt version && npm test", + "version": "npm run build && git add -A dist && git add CHANGELOG.md bower.json package.json", + "postversion": "git push && git push --tags", + "examples": "node ./examples/server.js", + "coveralls": "cat coverage/lcov.info | ./node_modules/coveralls/bin/coveralls.js", + "fix": "eslint --fix lib/**/*.js" + }, + "repository": { + "type": "git", + "url": "https://github.com/axios/axios.git" + }, + "keywords": [ + "xhr", + "http", + "ajax", + "promise", + "node" + ], + "author": "Matt Zabriskie", + "license": "MIT", + "bugs": { + "url": "https://github.com/axios/axios/issues" + }, + "homepage": "https://axios-http.com", + "devDependencies": { + "abortcontroller-polyfill": "^1.5.0", + "coveralls": "^3.0.0", + "dtslint": "^4.1.6", + "es6-promise": "^4.2.4", + "grunt": "^1.3.0", + "grunt-banner": "^0.6.0", + "grunt-cli": "^1.2.0", + "grunt-contrib-clean": "^1.1.0", + "grunt-contrib-watch": "^1.0.0", + "grunt-eslint": "^23.0.0", + "grunt-karma": "^4.0.0", + "grunt-mocha-test": "^0.13.3", + "grunt-webpack": "^4.0.2", + "istanbul-instrumenter-loader": "^1.0.0", + "jasmine-core": "^2.4.1", + "karma": "^6.3.2", + "karma-chrome-launcher": "^3.1.0", + "karma-firefox-launcher": "^2.1.0", + "karma-jasmine": "^1.1.1", + "karma-jasmine-ajax": "^0.1.13", + "karma-safari-launcher": "^1.0.0", + "karma-sauce-launcher": "^4.3.6", + "karma-sinon": "^1.0.5", + "karma-sourcemap-loader": "^0.3.8", + "karma-webpack": "^4.0.2", + "load-grunt-tasks": "^3.5.2", + "minimist": "^1.2.0", + "mocha": "^8.2.1", + "sinon": "^4.5.0", + "terser-webpack-plugin": "^4.2.3", + "typescript": "^4.0.5", + "url-search-params": "^0.10.0", + "webpack": "^4.44.2", + "webpack-dev-server": "^3.11.0" + }, + "browser": { + "./lib/adapters/http.js": "./lib/adapters/xhr.js" + }, + "jsdelivr": "dist/axios.min.js", + "unpkg": "dist/axios.min.js", + "typings": "./index.d.ts", + "dependencies": { + "follow-redirects": "^1.14.8" + }, + "bundlesize": [ + { + "path": "./dist/axios.min.js", + "threshold": "5kB" + } + ] +} diff --git a/node_modules/axios/tsconfig.json b/node_modules/axios/tsconfig.json new file mode 100644 index 0000000..6665188 --- /dev/null +++ b/node_modules/axios/tsconfig.json @@ -0,0 +1,14 @@ +{ + "compilerOptions": { + "module": "es2015", + "lib": ["dom", "es2015"], + "types": [], + "moduleResolution": "node", + "strict": true, + "noEmit": true, + "baseUrl": ".", + "paths": { + "axios": ["."] + } + } +} diff --git a/node_modules/axios/tslint.json b/node_modules/axios/tslint.json new file mode 100644 index 0000000..3ec44a7 --- /dev/null +++ b/node_modules/axios/tslint.json @@ -0,0 +1,6 @@ +{ + "extends": "dtslint/dtslint.json", + "rules": { + "no-unnecessary-generics": false + } +} diff --git a/node_modules/cacheable-request/LICENSE b/node_modules/cacheable-request/LICENSE new file mode 100644 index 0000000..f27ee9b --- /dev/null +++ b/node_modules/cacheable-request/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2017 Luke Childs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/node_modules/cacheable-request/README.md b/node_modules/cacheable-request/README.md new file mode 100644 index 0000000..725e7e0 --- /dev/null +++ b/node_modules/cacheable-request/README.md @@ -0,0 +1,206 @@ +# cacheable-request + +> Wrap native HTTP requests with RFC compliant cache support + +[![Build Status](https://travis-ci.org/lukechilds/cacheable-request.svg?branch=master)](https://travis-ci.org/lukechilds/cacheable-request) +[![Coverage Status](https://coveralls.io/repos/github/lukechilds/cacheable-request/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/cacheable-request?branch=master) +[![npm](https://img.shields.io/npm/dm/cacheable-request.svg)](https://www.npmjs.com/package/cacheable-request) +[![npm](https://img.shields.io/npm/v/cacheable-request.svg)](https://www.npmjs.com/package/cacheable-request) + +[RFC 7234](http://httpwg.org/specs/rfc7234.html) compliant HTTP caching for native Node.js HTTP/HTTPS requests. Caching works out of the box in memory or is easily pluggable with a wide range of storage adapters. + +**Note:** This is a low level wrapper around the core HTTP modules, it's not a high level request library. + +## Features + +- Only stores cacheable responses as defined by RFC 7234 +- Fresh cache entries are served directly from cache +- Stale cache entries are revalidated with `If-None-Match`/`If-Modified-Since` headers +- 304 responses from revalidation requests use cached body +- Updates `Age` header on cached responses +- Can completely bypass cache on a per request basis +- In memory cache by default +- Official support for Redis, MongoDB, SQLite, PostgreSQL and MySQL storage adapters +- Easily plug in your own or third-party storage adapters +- If DB connection fails, cache is automatically bypassed ([disabled by default](#optsautomaticfailover)) +- Adds cache support to any existing HTTP code with minimal changes +- Uses [http-cache-semantics](https://github.com/pornel/http-cache-semantics) internally for HTTP RFC 7234 compliance + +## Install + +```shell +npm install cacheable-request +``` + +## Usage + +```js +const http = require('http'); +const CacheableRequest = require('cacheable-request'); + +// Then instead of +const req = http.request('http://example.com', cb); +req.end(); + +// You can do +const cacheableRequest = new CacheableRequest(http.request); +const cacheReq = cacheableRequest('http://example.com', cb); +cacheReq.on('request', req => req.end()); +// Future requests to 'example.com' will be returned from cache if still valid + +// You pass in any other http.request API compatible method to be wrapped with cache support: +const cacheableRequest = new CacheableRequest(https.request); +const cacheableRequest = new CacheableRequest(electron.net); +``` + +## Storage Adapters + +`cacheable-request` uses [Keyv](https://github.com/lukechilds/keyv) to support a wide range of storage adapters. + +For example, to use Redis as a cache backend, you just need to install the official Redis Keyv storage adapter: + +``` +npm install @keyv/redis +``` + +And then you can pass `CacheableRequest` your connection string: + +```js +const cacheableRequest = new CacheableRequest(http.request, 'redis://user:pass@localhost:6379'); +``` + +[View all official Keyv storage adapters.](https://github.com/lukechilds/keyv#official-storage-adapters) + +Keyv also supports anything that follows the Map API so it's easy to write your own storage adapter or use a third-party solution. + +e.g The following are all valid storage adapters + +```js +const storageAdapter = new Map(); +// or +const storageAdapter = require('./my-storage-adapter'); +// or +const QuickLRU = require('quick-lru'); +const storageAdapter = new QuickLRU({ maxSize: 1000 }); + +const cacheableRequest = new CacheableRequest(http.request, storageAdapter); +``` + +View the [Keyv docs](https://github.com/lukechilds/keyv) for more information on how to use storage adapters. + +## API + +### new cacheableRequest(request, [storageAdapter]) + +Returns the provided request function wrapped with cache support. + +#### request + +Type: `function` + +Request function to wrap with cache support. Should be [`http.request`](https://nodejs.org/api/http.html#http_http_request_options_callback) or a similar API compatible request function. + +#### storageAdapter + +Type: `Keyv storage adapter`<br> +Default: `new Map()` + +A [Keyv](https://github.com/lukechilds/keyv) storage adapter instance, or connection string if using with an official Keyv storage adapter. + +### Instance + +#### cacheableRequest(opts, [cb]) + +Returns an event emitter. + +##### opts + +Type: `object`, `string` + +- Any of the default request functions options. +- Any [`http-cache-semantics`](https://github.com/kornelski/http-cache-semantics#constructor-options) options. +- Any of the following: + +###### opts.cache + +Type: `boolean`<br> +Default: `true` + +If the cache should be used. Setting this to false will completely bypass the cache for the current request. + +###### opts.strictTtl + +Type: `boolean`<br> +Default: `false` + +If set to `true` once a cached resource has expired it is deleted and will have to be re-requested. + +If set to `false` (default), after a cached resource's TTL expires it is kept in the cache and will be revalidated on the next request with `If-None-Match`/`If-Modified-Since` headers. + +###### opts.maxTtl + +Type: `number`<br> +Default: `undefined` + +Limits TTL. The `number` represents milliseconds. + +###### opts.automaticFailover + +Type: `boolean`<br> +Default: `false` + +When set to `true`, if the DB connection fails we will automatically fallback to a network request. DB errors will still be emitted to notify you of the problem even though the request callback may succeed. + +###### opts.forceRefresh + +Type: `boolean`<br> +Default: `false` + +Forces refreshing the cache. If the response could be retrieved from the cache, it will perform a new request and override the cache instead. + +##### cb + +Type: `function` + +The callback function which will receive the response as an argument. + +The response can be either a [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage) or a [responselike object](https://github.com/lukechilds/responselike). The response will also have a `fromCache` property set with a boolean value. + +##### .on('request', request) + +`request` event to get the request object of the request. + +**Note:** This event will only fire if an HTTP request is actually made, not when a response is retrieved from cache. However, you should always handle the `request` event to end the request and handle any potential request errors. + +##### .on('response', response) + +`response` event to get the response object from the HTTP request or cache. + +##### .on('error', error) + +`error` event emitted in case of an error with the cache. + +Errors emitted here will be an instance of `CacheableRequest.RequestError` or `CacheableRequest.CacheError`. You will only ever receive a `RequestError` if the request function throws (normally caused by invalid user input). Normal request errors should be handled inside the `request` event. + +To properly handle all error scenarios you should use the following pattern: + +```js +cacheableRequest('example.com', cb) + .on('error', err => { + if (err instanceof CacheableRequest.CacheError) { + handleCacheError(err); // Cache error + } else if (err instanceof CacheableRequest.RequestError) { + handleRequestError(err); // Request function thrown + } + }) + .on('request', req => { + req.on('error', handleRequestError); // Request error emitted + req.end(); + }); +``` + +**Note:** Database connection errors are emitted here, however `cacheable-request` will attempt to re-request the resource and bypass the cache on a connection error. Therefore a database connection error doesn't necessarily mean the request won't be fulfilled. + +## License + +MIT © Luke Childs diff --git a/node_modules/cacheable-request/node_modules/get-stream/buffer-stream.js b/node_modules/cacheable-request/node_modules/get-stream/buffer-stream.js new file mode 100644 index 0000000..2dd7574 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/buffer-stream.js @@ -0,0 +1,52 @@ +'use strict'; +const {PassThrough: PassThroughStream} = require('stream'); + +module.exports = options => { + options = {...options}; + + const {array} = options; + let {encoding} = options; + const isBuffer = encoding === 'buffer'; + let objectMode = false; + + if (array) { + objectMode = !(encoding || isBuffer); + } else { + encoding = encoding || 'utf8'; + } + + if (isBuffer) { + encoding = null; + } + + const stream = new PassThroughStream({objectMode}); + + if (encoding) { + stream.setEncoding(encoding); + } + + let length = 0; + const chunks = []; + + stream.on('data', chunk => { + chunks.push(chunk); + + if (objectMode) { + length = chunks.length; + } else { + length += chunk.length; + } + }); + + stream.getBufferedValue = () => { + if (array) { + return chunks; + } + + return isBuffer ? Buffer.concat(chunks, length) : chunks.join(''); + }; + + stream.getBufferedLength = () => length; + + return stream; +}; diff --git a/node_modules/cacheable-request/node_modules/get-stream/index.d.ts b/node_modules/cacheable-request/node_modules/get-stream/index.d.ts new file mode 100644 index 0000000..7b98134 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/index.d.ts @@ -0,0 +1,108 @@ +/// <reference types="node"/> +import {Stream} from 'stream'; + +declare class MaxBufferErrorClass extends Error { + readonly name: 'MaxBufferError'; + constructor(); +} + +declare namespace getStream { + interface Options { + /** + Maximum length of the returned string. If it exceeds this value before the stream ends, the promise will be rejected with a `MaxBufferError` error. + + @default Infinity + */ + readonly maxBuffer?: number; + } + + interface OptionsWithEncoding<EncodingType = BufferEncoding> extends Options { + /** + [Encoding](https://nodejs.org/api/buffer.html#buffer_buffer) of the incoming stream. + + @default 'utf8' + */ + readonly encoding?: EncodingType; + } + + type MaxBufferError = MaxBufferErrorClass; +} + +declare const getStream: { + /** + Get the `stream` as a string. + + @returns A promise that resolves when the end event fires on the stream, indicating that there is no more data to be read. The stream is switched to flowing mode. + + @example + ``` + import * as fs from 'fs'; + import getStream = require('get-stream'); + + (async () => { + const stream = fs.createReadStream('unicorn.txt'); + + console.log(await getStream(stream)); + // ,,))))))));, + // __)))))))))))))), + // \|/ -\(((((''''((((((((. + // -*-==//////(('' . `)))))), + // /|\ ))| o ;-. '((((( ,(, + // ( `| / ) ;))))' ,_))^;(~ + // | | | ,))((((_ _____------~~~-. %,;(;(>';'~ + // o_); ; )))(((` ~---~ `:: \ %%~~)(v;(`('~ + // ; ''''```` `: `:::|\,__,%% );`'; ~ + // | _ ) / `:|`----' `-' + // ______/\/~ | / / + // /~;;.____/;;' / ___--,-( `;;;/ + // / // _;______;'------~~~~~ /;;/\ / + // // | | / ; \;;,\ + // (<_ | ; /',/-----' _> + // \_| ||_ //~;~~~~~~~~~ + // `\_| (,~~ + // \~\ + // ~~ + })(); + ``` + */ + (stream: Stream, options?: getStream.OptionsWithEncoding): Promise<string>; + + /** + Get the `stream` as a buffer. + + It honors the `maxBuffer` option as above, but it refers to byte length rather than string length. + */ + buffer( + stream: Stream, + options?: getStream.OptionsWithEncoding + ): Promise<Buffer>; + + /** + Get the `stream` as an array of values. + + It honors both the `maxBuffer` and `encoding` options. The behavior changes slightly based on the encoding chosen: + + - When `encoding` is unset, it assumes an [object mode stream](https://nodesource.com/blog/understanding-object-streams/) and collects values emitted from `stream` unmodified. In this case `maxBuffer` refers to the number of items in the array (not the sum of their sizes). + - When `encoding` is set to `buffer`, it collects an array of buffers. `maxBuffer` refers to the summed byte lengths of every buffer in the array. + - When `encoding` is set to anything else, it collects an array of strings. `maxBuffer` refers to the summed character lengths of every string in the array. + */ + array<StreamObjectModeType>( + stream: Stream, + options?: getStream.Options + ): Promise<StreamObjectModeType[]>; + array( + stream: Stream, + options: getStream.OptionsWithEncoding<'buffer'> + ): Promise<Buffer[]>; + array( + stream: Stream, + options: getStream.OptionsWithEncoding<BufferEncoding> + ): Promise<string[]>; + + MaxBufferError: typeof MaxBufferErrorClass; + + // TODO: Remove this for the next major release + default: typeof getStream; +}; + +export = getStream; diff --git a/node_modules/cacheable-request/node_modules/get-stream/index.js b/node_modules/cacheable-request/node_modules/get-stream/index.js new file mode 100644 index 0000000..71f3991 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/index.js @@ -0,0 +1,60 @@ +'use strict'; +const {constants: BufferConstants} = require('buffer'); +const pump = require('pump'); +const bufferStream = require('./buffer-stream'); + +class MaxBufferError extends Error { + constructor() { + super('maxBuffer exceeded'); + this.name = 'MaxBufferError'; + } +} + +async function getStream(inputStream, options) { + if (!inputStream) { + return Promise.reject(new Error('Expected a stream')); + } + + options = { + maxBuffer: Infinity, + ...options + }; + + const {maxBuffer} = options; + + let stream; + await new Promise((resolve, reject) => { + const rejectPromise = error => { + // Don't retrieve an oversized buffer. + if (error && stream.getBufferedLength() <= BufferConstants.MAX_LENGTH) { + error.bufferedData = stream.getBufferedValue(); + } + + reject(error); + }; + + stream = pump(inputStream, bufferStream(options), error => { + if (error) { + rejectPromise(error); + return; + } + + resolve(); + }); + + stream.on('data', () => { + if (stream.getBufferedLength() > maxBuffer) { + rejectPromise(new MaxBufferError()); + } + }); + }); + + return stream.getBufferedValue(); +} + +module.exports = getStream; +// TODO: Remove this for the next major release +module.exports.default = getStream; +module.exports.buffer = (stream, options) => getStream(stream, {...options, encoding: 'buffer'}); +module.exports.array = (stream, options) => getStream(stream, {...options, array: true}); +module.exports.MaxBufferError = MaxBufferError; diff --git a/node_modules/cacheable-request/node_modules/get-stream/license b/node_modules/cacheable-request/node_modules/get-stream/license new file mode 100644 index 0000000..fa7ceba --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (https://sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/cacheable-request/node_modules/get-stream/package.json b/node_modules/cacheable-request/node_modules/get-stream/package.json new file mode 100644 index 0000000..e2f1687 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/package.json @@ -0,0 +1,50 @@ +{ + "name": "get-stream", + "version": "5.2.0", + "description": "Get a stream as a string, buffer, or array", + "license": "MIT", + "repository": "sindresorhus/get-stream", + "funding": "https://github.com/sponsors/sindresorhus", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "https://sindresorhus.com" + }, + "engines": { + "node": ">=8" + }, + "scripts": { + "test": "xo && ava && tsd" + }, + "files": [ + "index.js", + "index.d.ts", + "buffer-stream.js" + ], + "keywords": [ + "get", + "stream", + "promise", + "concat", + "string", + "text", + "buffer", + "read", + "data", + "consume", + "readable", + "readablestream", + "array", + "object" + ], + "dependencies": { + "pump": "^3.0.0" + }, + "devDependencies": { + "@types/node": "^12.0.7", + "ava": "^2.0.0", + "into-stream": "^5.0.0", + "tsd": "^0.7.2", + "xo": "^0.24.0" + } +} diff --git a/node_modules/cacheable-request/node_modules/get-stream/readme.md b/node_modules/cacheable-request/node_modules/get-stream/readme.md new file mode 100644 index 0000000..7d7565d --- /dev/null +++ b/node_modules/cacheable-request/node_modules/get-stream/readme.md @@ -0,0 +1,124 @@ +# get-stream [![Build Status](https://travis-ci.com/sindresorhus/get-stream.svg?branch=master)](https://travis-ci.com/github/sindresorhus/get-stream) + +> Get a stream as a string, buffer, or array + +## Install + +``` +$ npm install get-stream +``` + +## Usage + +```js +const fs = require('fs'); +const getStream = require('get-stream'); + +(async () => { + const stream = fs.createReadStream('unicorn.txt'); + + console.log(await getStream(stream)); + /* + ,,))))))));, + __)))))))))))))), + \|/ -\(((((''''((((((((. + -*-==//////(('' . `)))))), + /|\ ))| o ;-. '((((( ,(, + ( `| / ) ;))))' ,_))^;(~ + | | | ,))((((_ _____------~~~-. %,;(;(>';'~ + o_); ; )))(((` ~---~ `:: \ %%~~)(v;(`('~ + ; ''''```` `: `:::|\,__,%% );`'; ~ + | _ ) / `:|`----' `-' + ______/\/~ | / / + /~;;.____/;;' / ___--,-( `;;;/ + / // _;______;'------~~~~~ /;;/\ / + // | | / ; \;;,\ + (<_ | ; /',/-----' _> + \_| ||_ //~;~~~~~~~~~ + `\_| (,~~ + \~\ + ~~ + */ +})(); +``` + +## API + +The methods returns a promise that resolves when the `end` event fires on the stream, indicating that there is no more data to be read. The stream is switched to flowing mode. + +### getStream(stream, options?) + +Get the `stream` as a string. + +#### options + +Type: `object` + +##### encoding + +Type: `string`\ +Default: `'utf8'` + +[Encoding](https://nodejs.org/api/buffer.html#buffer_buffer) of the incoming stream. + +##### maxBuffer + +Type: `number`\ +Default: `Infinity` + +Maximum length of the returned string. If it exceeds this value before the stream ends, the promise will be rejected with a `getStream.MaxBufferError` error. + +### getStream.buffer(stream, options?) + +Get the `stream` as a buffer. + +It honors the `maxBuffer` option as above, but it refers to byte length rather than string length. + +### getStream.array(stream, options?) + +Get the `stream` as an array of values. + +It honors both the `maxBuffer` and `encoding` options. The behavior changes slightly based on the encoding chosen: + +- When `encoding` is unset, it assumes an [object mode stream](https://nodesource.com/blog/understanding-object-streams/) and collects values emitted from `stream` unmodified. In this case `maxBuffer` refers to the number of items in the array (not the sum of their sizes). + +- When `encoding` is set to `buffer`, it collects an array of buffers. `maxBuffer` refers to the summed byte lengths of every buffer in the array. + +- When `encoding` is set to anything else, it collects an array of strings. `maxBuffer` refers to the summed character lengths of every string in the array. + +## Errors + +If the input stream emits an `error` event, the promise will be rejected with the error. The buffered data will be attached to the `bufferedData` property of the error. + +```js +(async () => { + try { + await getStream(streamThatErrorsAtTheEnd('unicorn')); + } catch (error) { + console.log(error.bufferedData); + //=> 'unicorn' + } +})() +``` + +## FAQ + +### How is this different from [`concat-stream`](https://github.com/maxogden/concat-stream)? + +This module accepts a stream instead of being one and returns a promise instead of using a callback. The API is simpler and it only supports returning a string, buffer, or array. It doesn't have a fragile type inference. You explicitly choose what you want. And it doesn't depend on the huge `readable-stream` package. + +## Related + +- [get-stdin](https://github.com/sindresorhus/get-stdin) - Get stdin as a string or buffer + +--- + +<div align="center"> + <b> + <a href="https://tidelift.com/subscription/pkg/npm-get-stream?utm_source=npm-get-stream&utm_medium=referral&utm_campaign=readme">Get professional support for this package with a Tidelift subscription</a> + </b> + <br> + <sub> + Tidelift helps make open source sustainable for maintainers while giving companies<br>assurances about security, maintenance, and licensing for their dependencies. + </sub> +</div> diff --git a/node_modules/cacheable-request/node_modules/lowercase-keys/index.d.ts b/node_modules/cacheable-request/node_modules/lowercase-keys/index.d.ts new file mode 100644 index 0000000..dc90a75 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/lowercase-keys/index.d.ts @@ -0,0 +1,16 @@ +/** +Lowercase the keys of an object. + +@returns A new object with the keys lowercased. + +@example +``` +import lowercaseKeys = require('lowercase-keys'); + +lowercaseKeys({FOO: true, bAr: false}); +//=> {foo: true, bar: false} +``` +*/ +declare function lowercaseKeys<T extends unknown>(object: {[key: string]: T}): {[key: string]: T}; + +export = lowercaseKeys; diff --git a/node_modules/cacheable-request/node_modules/lowercase-keys/index.js b/node_modules/cacheable-request/node_modules/lowercase-keys/index.js new file mode 100644 index 0000000..357fb8f --- /dev/null +++ b/node_modules/cacheable-request/node_modules/lowercase-keys/index.js @@ -0,0 +1,10 @@ +'use strict'; +module.exports = object => { + const result = {}; + + for (const [key, value] of Object.entries(object)) { + result[key.toLowerCase()] = value; + } + + return result; +}; diff --git a/node_modules/cacheable-request/node_modules/lowercase-keys/license b/node_modules/cacheable-request/node_modules/lowercase-keys/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/lowercase-keys/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/cacheable-request/node_modules/lowercase-keys/package.json b/node_modules/cacheable-request/node_modules/lowercase-keys/package.json new file mode 100644 index 0000000..c11d813 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/lowercase-keys/package.json @@ -0,0 +1,38 @@ +{ + "name": "lowercase-keys", + "version": "2.0.0", + "description": "Lowercase the keys of an object", + "license": "MIT", + "repository": "sindresorhus/lowercase-keys", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=8" + }, + "scripts": { + "test": "xo && ava && tsd" + }, + "files": [ + "index.js", + "index.d.ts" + ], + "keywords": [ + "object", + "assign", + "extend", + "properties", + "lowercase", + "lower-case", + "case", + "keys", + "key" + ], + "devDependencies": { + "ava": "^1.4.1", + "tsd": "^0.7.2", + "xo": "^0.24.0" + } +} diff --git a/node_modules/cacheable-request/node_modules/lowercase-keys/readme.md b/node_modules/cacheable-request/node_modules/lowercase-keys/readme.md new file mode 100644 index 0000000..b1ed061 --- /dev/null +++ b/node_modules/cacheable-request/node_modules/lowercase-keys/readme.md @@ -0,0 +1,32 @@ +# lowercase-keys [![Build Status](https://travis-ci.org/sindresorhus/lowercase-keys.svg?branch=master)](https://travis-ci.org/sindresorhus/lowercase-keys) + +> Lowercase the keys of an object + + +## Install + +``` +$ npm install lowercase-keys +``` + + +## Usage + +```js +const lowercaseKeys = require('lowercase-keys'); + +lowercaseKeys({FOO: true, bAr: false}); +//=> {foo: true, bar: false} +``` + + +## API + +### lowercaseKeys(object) + +Returns a new object with the keys lowercased. + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/cacheable-request/package.json b/node_modules/cacheable-request/package.json new file mode 100644 index 0000000..7734e03 --- /dev/null +++ b/node_modules/cacheable-request/package.json @@ -0,0 +1,56 @@ +{ + "name": "cacheable-request", + "version": "6.1.0", + "description": "Wrap native HTTP requests with RFC compliant cache support", + "license": "MIT", + "repository": "lukechilds/cacheable-request", + "author": "Luke Childs <lukechilds123@gmail.com> (http://lukechilds.co.uk)", + "main": "src/index.js", + "engines": { + "node": ">=8" + }, + "scripts": { + "test": "xo && nyc ava", + "coverage": "nyc report --reporter=text-lcov | coveralls" + }, + "files": [ + "src" + ], + "keywords": [ + "HTTP", + "HTTPS", + "cache", + "caching", + "layer", + "cacheable", + "RFC 7234", + "RFC", + "7234", + "compliant" + ], + "dependencies": { + "clone-response": "^1.0.2", + "get-stream": "^5.1.0", + "http-cache-semantics": "^4.0.0", + "keyv": "^3.0.0", + "lowercase-keys": "^2.0.0", + "normalize-url": "^4.1.0", + "responselike": "^1.0.2" + }, + "devDependencies": { + "@keyv/sqlite": "^2.0.0", + "ava": "^1.1.0", + "coveralls": "^3.0.0", + "create-test-server": "3.0.0", + "delay": "^4.0.0", + "eslint-config-xo-lukechilds": "^1.0.0", + "nyc": "^14.1.1", + "pify": "^4.0.0", + "sqlite3": "^4.0.2", + "this": "^1.0.2", + "xo": "^0.23.0" + }, + "xo": { + "extends": "xo-lukechilds" + } +} diff --git a/node_modules/cacheable-request/src/index.js b/node_modules/cacheable-request/src/index.js new file mode 100644 index 0000000..3fcea3f --- /dev/null +++ b/node_modules/cacheable-request/src/index.js @@ -0,0 +1,251 @@ +'use strict'; + +const EventEmitter = require('events'); +const urlLib = require('url'); +const normalizeUrl = require('normalize-url'); +const getStream = require('get-stream'); +const CachePolicy = require('http-cache-semantics'); +const Response = require('responselike'); +const lowercaseKeys = require('lowercase-keys'); +const cloneResponse = require('clone-response'); +const Keyv = require('keyv'); + +class CacheableRequest { + constructor(request, cacheAdapter) { + if (typeof request !== 'function') { + throw new TypeError('Parameter `request` must be a function'); + } + + this.cache = new Keyv({ + uri: typeof cacheAdapter === 'string' && cacheAdapter, + store: typeof cacheAdapter !== 'string' && cacheAdapter, + namespace: 'cacheable-request' + }); + + return this.createCacheableRequest(request); + } + + createCacheableRequest(request) { + return (opts, cb) => { + let url; + if (typeof opts === 'string') { + url = normalizeUrlObject(urlLib.parse(opts)); + opts = {}; + } else if (opts instanceof urlLib.URL) { + url = normalizeUrlObject(urlLib.parse(opts.toString())); + opts = {}; + } else { + const [pathname, ...searchParts] = (opts.path || '').split('?'); + const search = searchParts.length > 0 ? + `?${searchParts.join('?')}` : + ''; + url = normalizeUrlObject({ ...opts, pathname, search }); + } + + opts = { + headers: {}, + method: 'GET', + cache: true, + strictTtl: false, + automaticFailover: false, + ...opts, + ...urlObjectToRequestOptions(url) + }; + opts.headers = lowercaseKeys(opts.headers); + + const ee = new EventEmitter(); + const normalizedUrlString = normalizeUrl( + urlLib.format(url), + { + stripWWW: false, + removeTrailingSlash: false, + stripAuthentication: false + } + ); + const key = `${opts.method}:${normalizedUrlString}`; + let revalidate = false; + let madeRequest = false; + + const makeRequest = opts => { + madeRequest = true; + let requestErrored = false; + let requestErrorCallback; + + const requestErrorPromise = new Promise(resolve => { + requestErrorCallback = () => { + if (!requestErrored) { + requestErrored = true; + resolve(); + } + }; + }); + + const handler = response => { + if (revalidate && !opts.forceRefresh) { + response.status = response.statusCode; + const revalidatedPolicy = CachePolicy.fromObject(revalidate.cachePolicy).revalidatedPolicy(opts, response); + if (!revalidatedPolicy.modified) { + const headers = revalidatedPolicy.policy.responseHeaders(); + response = new Response(revalidate.statusCode, headers, revalidate.body, revalidate.url); + response.cachePolicy = revalidatedPolicy.policy; + response.fromCache = true; + } + } + + if (!response.fromCache) { + response.cachePolicy = new CachePolicy(opts, response, opts); + response.fromCache = false; + } + + let clonedResponse; + if (opts.cache && response.cachePolicy.storable()) { + clonedResponse = cloneResponse(response); + + (async () => { + try { + const bodyPromise = getStream.buffer(response); + + await Promise.race([ + requestErrorPromise, + new Promise(resolve => response.once('end', resolve)) + ]); + + if (requestErrored) { + return; + } + + const body = await bodyPromise; + + const value = { + cachePolicy: response.cachePolicy.toObject(), + url: response.url, + statusCode: response.fromCache ? revalidate.statusCode : response.statusCode, + body + }; + + let ttl = opts.strictTtl ? response.cachePolicy.timeToLive() : undefined; + if (opts.maxTtl) { + ttl = ttl ? Math.min(ttl, opts.maxTtl) : opts.maxTtl; + } + + await this.cache.set(key, value, ttl); + } catch (error) { + ee.emit('error', new CacheableRequest.CacheError(error)); + } + })(); + } else if (opts.cache && revalidate) { + (async () => { + try { + await this.cache.delete(key); + } catch (error) { + ee.emit('error', new CacheableRequest.CacheError(error)); + } + })(); + } + + ee.emit('response', clonedResponse || response); + if (typeof cb === 'function') { + cb(clonedResponse || response); + } + }; + + try { + const req = request(opts, handler); + req.once('error', requestErrorCallback); + req.once('abort', requestErrorCallback); + ee.emit('request', req); + } catch (error) { + ee.emit('error', new CacheableRequest.RequestError(error)); + } + }; + + (async () => { + const get = async opts => { + await Promise.resolve(); + + const cacheEntry = opts.cache ? await this.cache.get(key) : undefined; + if (typeof cacheEntry === 'undefined') { + return makeRequest(opts); + } + + const policy = CachePolicy.fromObject(cacheEntry.cachePolicy); + if (policy.satisfiesWithoutRevalidation(opts) && !opts.forceRefresh) { + const headers = policy.responseHeaders(); + const response = new Response(cacheEntry.statusCode, headers, cacheEntry.body, cacheEntry.url); + response.cachePolicy = policy; + response.fromCache = true; + + ee.emit('response', response); + if (typeof cb === 'function') { + cb(response); + } + } else { + revalidate = cacheEntry; + opts.headers = policy.revalidationHeaders(opts); + makeRequest(opts); + } + }; + + const errorHandler = error => ee.emit('error', new CacheableRequest.CacheError(error)); + this.cache.once('error', errorHandler); + ee.on('response', () => this.cache.removeListener('error', errorHandler)); + + try { + await get(opts); + } catch (error) { + if (opts.automaticFailover && !madeRequest) { + makeRequest(opts); + } + + ee.emit('error', new CacheableRequest.CacheError(error)); + } + })(); + + return ee; + }; + } +} + +function urlObjectToRequestOptions(url) { + const options = { ...url }; + options.path = `${url.pathname || '/'}${url.search || ''}`; + delete options.pathname; + delete options.search; + return options; +} + +function normalizeUrlObject(url) { + // If url was parsed by url.parse or new URL: + // - hostname will be set + // - host will be hostname[:port] + // - port will be set if it was explicit in the parsed string + // Otherwise, url was from request options: + // - hostname or host may be set + // - host shall not have port encoded + return { + protocol: url.protocol, + auth: url.auth, + hostname: url.hostname || url.host || 'localhost', + port: url.port, + pathname: url.pathname, + search: url.search + }; +} + +CacheableRequest.RequestError = class extends Error { + constructor(error) { + super(error.message); + this.name = 'RequestError'; + Object.assign(this, error); + } +}; + +CacheableRequest.CacheError = class extends Error { + constructor(error) { + super(error.message); + this.name = 'CacheError'; + Object.assign(this, error); + } +}; + +module.exports = CacheableRequest; diff --git a/node_modules/clone-response/LICENSE b/node_modules/clone-response/LICENSE new file mode 100644 index 0000000..f27ee9b --- /dev/null +++ b/node_modules/clone-response/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2017 Luke Childs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/node_modules/clone-response/README.md b/node_modules/clone-response/README.md new file mode 100644 index 0000000..d037cfe --- /dev/null +++ b/node_modules/clone-response/README.md @@ -0,0 +1,62 @@ +# clone-response + +> Clone a Node.js HTTP response stream + +[![Build Status](https://travis-ci.org/lukechilds/clone-response.svg?branch=master)](https://travis-ci.org/lukechilds/clone-response) +[![Coverage Status](https://coveralls.io/repos/github/lukechilds/clone-response/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/clone-response?branch=master) +[![npm](https://img.shields.io/npm/dm/clone-response.svg)](https://www.npmjs.com/package/clone-response) +[![npm](https://img.shields.io/npm/v/clone-response.svg)](https://www.npmjs.com/package/clone-response) + +Returns a new stream and copies over all properties and methods from the original response giving you a complete duplicate. + +This is useful in situations where you need to consume the response stream but also want to pass an unconsumed stream somewhere else to be consumed later. + +## Install + +```shell +npm install --save clone-response +``` + +## Usage + +```js +const http = require('http'); +const cloneResponse = require('clone-response'); + +http.get('http://example.com', response => { + const clonedResponse = cloneResponse(response); + response.pipe(process.stdout); + + setImmediate(() => { + // The response stream has already been consumed by the time this executes, + // however the cloned response stream is still available. + doSomethingWithResponse(clonedResponse); + }); +}); +``` + +Please bear in mind that the process of cloning a stream consumes it. However, you can consume a stream multiple times in the same tick, therefore allowing you to create multiple clones. e.g: + +```js +const clone1 = cloneResponse(response); +const clone2 = cloneResponse(response); +// response can still be consumed in this tick but cannot be consumed if passed +// into any async callbacks. clone1 and clone2 can be passed around and be +// consumed in the future. +``` + +## API + +### cloneResponse(response) + +Returns a clone of the passed in response. + +#### response + +Type: `stream` + +A [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage) to clone. + +## License + +MIT © Luke Childs diff --git a/node_modules/clone-response/package.json b/node_modules/clone-response/package.json new file mode 100644 index 0000000..2cb9aa6 --- /dev/null +++ b/node_modules/clone-response/package.json @@ -0,0 +1,44 @@ +{ + "name": "clone-response", + "version": "1.0.2", + "description": "Clone a Node.js HTTP response stream", + "main": "src/index.js", + "scripts": { + "test": "xo && nyc ava", + "coverage": "nyc report --reporter=text-lcov | coveralls" + }, + "xo": { + "extends": "xo-lukechilds" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/lukechilds/clone-response.git" + }, + "keywords": [ + "clone", + "duplicate", + "copy", + "response", + "HTTP", + "stream" + ], + "author": "Luke Childs <lukechilds123@gmail.com> (http://lukechilds.co.uk)", + "license": "MIT", + "bugs": { + "url": "https://github.com/lukechilds/clone-response/issues" + }, + "homepage": "https://github.com/lukechilds/clone-response", + "dependencies": { + "mimic-response": "^1.0.0" + }, + "devDependencies": { + "ava": "^0.22.0", + "coveralls": "^2.13.1", + "create-test-server": "^2.0.1", + "eslint-config-xo-lukechilds": "^1.0.0", + "get-stream": "^3.0.0", + "nyc": "^11.0.2", + "pify": "^3.0.0", + "xo": "^0.19.0" + } +} diff --git a/node_modules/clone-response/src/index.js b/node_modules/clone-response/src/index.js new file mode 100644 index 0000000..0285dff --- /dev/null +++ b/node_modules/clone-response/src/index.js @@ -0,0 +1,17 @@ +'use strict'; + +const PassThrough = require('stream').PassThrough; +const mimicResponse = require('mimic-response'); + +const cloneResponse = response => { + if (!(response && response.pipe)) { + throw new TypeError('Parameter `response` must be a response stream.'); + } + + const clone = new PassThrough(); + mimicResponse(response, clone); + + return response.pipe(clone); +}; + +module.exports = cloneResponse; diff --git a/node_modules/configstore/index.js b/node_modules/configstore/index.js new file mode 100644 index 0000000..cd8f19f --- /dev/null +++ b/node_modules/configstore/index.js @@ -0,0 +1,106 @@ +'use strict'; +const path = require('path'); +const os = require('os'); +const fs = require('graceful-fs'); +const makeDir = require('make-dir'); +const xdgBasedir = require('xdg-basedir'); +const writeFileAtomic = require('write-file-atomic'); +const dotProp = require('dot-prop'); +const uniqueString = require('unique-string'); + +const configDir = xdgBasedir.config || path.join(os.tmpdir(), uniqueString()); +const permissionError = 'You don\'t have access to this file.'; +const makeDirOptions = {mode: 0o0700}; +const writeFileOptions = {mode: 0o0600}; + +class Configstore { + constructor(id, defaults, options = {}) { + const pathPrefix = options.globalConfigPath ? + path.join(id, 'config.json') : + path.join('configstore', `${id}.json`); + + this.path = options.configPath || path.join(configDir, pathPrefix); + + if (defaults) { + this.all = Object.assign({}, defaults, this.all); + } + } + + get all() { + try { + return JSON.parse(fs.readFileSync(this.path, 'utf8')); + } catch (error) { + // Create directory if it doesn't exist + if (error.code === 'ENOENT') { + return {}; + } + + // Improve the message of permission errors + if (error.code === 'EACCES') { + error.message = `${error.message}\n${permissionError}\n`; + } + + // Empty the file if it encounters invalid JSON + if (error.name === 'SyntaxError') { + writeFileAtomic.sync(this.path, '', writeFileOptions); + return {}; + } + + throw error; + } + } + + set all(value) { + try { + // Make sure the folder exists as it could have been deleted in the meantime + makeDir.sync(path.dirname(this.path), makeDirOptions); + + writeFileAtomic.sync(this.path, JSON.stringify(value, null, '\t'), writeFileOptions); + } catch (error) { + // Improve the message of permission errors + if (error.code === 'EACCES') { + error.message = `${error.message}\n${permissionError}\n`; + } + + throw error; + } + } + + get size() { + return Object.keys(this.all || {}).length; + } + + get(key) { + return dotProp.get(this.all, key); + } + + set(key, value) { + const config = this.all; + + if (arguments.length === 1) { + for (const k of Object.keys(key)) { + dotProp.set(config, k, key[k]); + } + } else { + dotProp.set(config, key, value); + } + + this.all = config; + } + + has(key) { + return dotProp.has(this.all, key); + } + + delete(key) { + const config = this.all; + dotProp.delete(config, key); + this.all = config; + } + + clear() { + this.all = {}; + } +} + +module.exports = Configstore; diff --git a/node_modules/configstore/license b/node_modules/configstore/license new file mode 100644 index 0000000..1043c8b --- /dev/null +++ b/node_modules/configstore/license @@ -0,0 +1,25 @@ +BSD 2-Clause License + +Copyright (c) Google +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/node_modules/configstore/package.json b/node_modules/configstore/package.json new file mode 100644 index 0000000..d14913f --- /dev/null +++ b/node_modules/configstore/package.json @@ -0,0 +1,47 @@ +{ + "name": "configstore", + "version": "4.0.0", + "description": "Easily load and save config without having to think about where and how", + "license": "BSD-2-Clause", + "repository": "yeoman/configstore", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=6" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "config", + "store", + "storage", + "conf", + "configuration", + "settings", + "preferences", + "json", + "data", + "persist", + "persistent", + "save" + ], + "dependencies": { + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" + }, + "devDependencies": { + "ava": "*", + "xo": "*" + } +} diff --git a/node_modules/configstore/readme.md b/node_modules/configstore/readme.md new file mode 100644 index 0000000..797d6a0 --- /dev/null +++ b/node_modules/configstore/readme.md @@ -0,0 +1,132 @@ +# configstore [![Build Status](https://travis-ci.org/yeoman/configstore.svg?branch=master)](https://travis-ci.org/yeoman/configstore) + +> Easily load and persist config without having to think about where and how + +Config is stored in a JSON file located in `$XDG_CONFIG_HOME` or `~/.config`.<br> +Example: `~/.config/configstore/some-id.json` + +*If you need this for Electron, check out [`electron-store`](https://github.com/sindresorhus/electron-store) instead.* + + +## Install + +``` +$ npm install configstore +``` + + +## Usage + +```js +const Configstore = require('configstore'); +const pkg = require('./package.json'); + +// create a Configstore instance with an unique ID e.g. +// Package name and optionally some default values +const conf = new Configstore(pkg.name, {foo: 'bar'}); + +console.log(conf.get('foo')); +//=> 'bar' + +conf.set('awesome', true); +console.log(conf.get('awesome')); +//=> true + +// Use dot-notation to access nested properties +conf.set('bar.baz', true); +console.log(conf.get('bar')); +//=> {baz: true} + +conf.delete('awesome'); +console.log(conf.get('awesome')); +//=> undefined +``` + + +## API + +### Configstore(packageName, [defaults], [options]) + +Returns a new instance. + +#### packageName + +Type: `string` + +Name of your package. + +#### defaults + +Type: `Object` + +Default config. + +#### options + +##### globalConfigPath + +Type: `boolean`<br> +Default: `false` + +Store the config at `$CONFIG/package-name/config.json` instead of the default `$CONFIG/configstore/package-name.json`. This is not recommended as you might end up conflicting with other tools, rendering the "without having to think" idea moot. + +##### configPath + +Type: `string`<br> +Default: Automatic + +**Please don't use this option unless absolutely necessary and you know what you're doing.** + +Set the path of the config file. Overrides the `packageName` and `globalConfigPath` options. + +### Instance + +You can use [dot-notation](https://github.com/sindresorhus/dot-prop) in a `key` to access nested properties. + +### .set(key, value) + +Set an item. + +### .set(object) + +Set multiple items at once. + +### .get(key) + +Get an item. + +### .has(key) + +Check if an item exists. + +### .delete(key) + +Delete an item. + +### .clear() + +Delete all items. + +### .size + +Get the item count. + +### .path + +Get the path to the config file. Can be used to show the user where the config file is located or even better open it for them. + +### .all + +Get all the config as an object or replace the current config with an object: + +```js +conf.all = { + hello: 'world' +}; +``` + + +## License + +[BSD license](http://opensource.org/licenses/bsd-license.php)<br> +Copyright Google diff --git a/node_modules/crypto-random-string/index.js b/node_modules/crypto-random-string/index.js new file mode 100644 index 0000000..ceaf65b --- /dev/null +++ b/node_modules/crypto-random-string/index.js @@ -0,0 +1,10 @@ +'use strict'; +const crypto = require('crypto'); + +module.exports = len => { + if (!Number.isFinite(len)) { + throw new TypeError('Expected a finite number'); + } + + return crypto.randomBytes(Math.ceil(len / 2)).toString('hex').slice(0, len); +}; diff --git a/node_modules/crypto-random-string/license b/node_modules/crypto-random-string/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/crypto-random-string/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/crypto-random-string/package.json b/node_modules/crypto-random-string/package.json new file mode 100644 index 0000000..d70c1f0 --- /dev/null +++ b/node_modules/crypto-random-string/package.json @@ -0,0 +1,43 @@ +{ + "name": "crypto-random-string", + "version": "1.0.0", + "description": "Generate a cryptographically strong random string", + "license": "MIT", + "repository": "sindresorhus/crypto-random-string", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "random", + "string", + "str", + "rand", + "text", + "id", + "identifier", + "slug", + "salt", + "crypto", + "strong", + "secure", + "hex" + ], + "devDependencies": { + "ava": "*", + "xo": "*" + }, + "xo": { + "esnext": true + } +} diff --git a/node_modules/crypto-random-string/readme.md b/node_modules/crypto-random-string/readme.md new file mode 100644 index 0000000..dab5a2e --- /dev/null +++ b/node_modules/crypto-random-string/readme.md @@ -0,0 +1,49 @@ +# crypto-random-string [![Build Status](https://travis-ci.org/sindresorhus/crypto-random-string.svg?branch=master)](https://travis-ci.org/sindresorhus/crypto-random-string) + +> Generate a [cryptographically strong](https://en.m.wikipedia.org/wiki/Strong_cryptography) random string + +Can be useful for creating an identifier, slug, salt, fixture, etc. + + +## Install + +``` +$ npm install --save crypto-random-string +``` + + +## Usage + +```js +const cryptoRandomString = require('crypto-random-string'); + +cryptoRandomString(10); +//=> '2cf05d94db' +``` + + +## API + +### cryptoRandomString(length) + +#### length + +Type: `number` + +Length of the returned string. + + +## Related + +- [random-int](https://github.com/sindresorhus/random-int) - Generate a random integer +- [random-float](https://github.com/sindresorhus/random-float) - Generate a random float +- [random-item](https://github.com/sindresorhus/random-item) - Get a random item from an array +- [random-boolean](https://github.com/arthurvr/random-boolean) - Get a random boolean +- [random-obj-key](https://github.com/sindresorhus/random-obj-key) - Get a random key from an object +- [random-obj-prop](https://github.com/sindresorhus/random-obj-prop) - Get a random property from an object +- [unique-random](https://github.com/sindresorhus/unique-random) - Generate random numbers that are consecutively unique + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/decompress-response/index.js b/node_modules/decompress-response/index.js new file mode 100644 index 0000000..d8acd4a --- /dev/null +++ b/node_modules/decompress-response/index.js @@ -0,0 +1,29 @@ +'use strict'; +const PassThrough = require('stream').PassThrough; +const zlib = require('zlib'); +const mimicResponse = require('mimic-response'); + +module.exports = response => { + // TODO: Use Array#includes when targeting Node.js 6 + if (['gzip', 'deflate'].indexOf(response.headers['content-encoding']) === -1) { + return response; + } + + const unzip = zlib.createUnzip(); + const stream = new PassThrough(); + + mimicResponse(response, stream); + + unzip.on('error', err => { + if (err.code === 'Z_BUF_ERROR') { + stream.end(); + return; + } + + stream.emit('error', err); + }); + + response.pipe(unzip).pipe(stream); + + return stream; +}; diff --git a/node_modules/decompress-response/license b/node_modules/decompress-response/license new file mode 100644 index 0000000..32a16ce --- /dev/null +++ b/node_modules/decompress-response/license @@ -0,0 +1,21 @@ +`The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/decompress-response/package.json b/node_modules/decompress-response/package.json new file mode 100644 index 0000000..3574dc2 --- /dev/null +++ b/node_modules/decompress-response/package.json @@ -0,0 +1,53 @@ +{ + "name": "decompress-response", + "version": "3.3.0", + "description": "Decompress a HTTP response if needed", + "license": "MIT", + "repository": "sindresorhus/decompress-response", + "maintainers": [ + { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + { + "name": "Vsevolod Strukchinsky", + "email": "floatdrop@gmail.com", + "url": "github.com/floatdrop" + } + ], + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "decompress", + "response", + "http", + "https", + "zlib", + "gzip", + "zip", + "deflate", + "unzip", + "ungzip", + "incoming", + "message", + "stream", + "compressed" + ], + "dependencies": { + "mimic-response": "^1.0.0" + }, + "devDependencies": { + "ava": "*", + "get-stream": "^3.0.0", + "pify": "^3.0.0", + "xo": "*" + } +} diff --git a/node_modules/decompress-response/readme.md b/node_modules/decompress-response/readme.md new file mode 100644 index 0000000..1b98767 --- /dev/null +++ b/node_modules/decompress-response/readme.md @@ -0,0 +1,31 @@ +# decompress-response [![Build Status](https://travis-ci.org/sindresorhus/decompress-response.svg?branch=master)](https://travis-ci.org/sindresorhus/decompress-response) + +> Decompress a HTTP response if needed + +Decompresses the [response](https://nodejs.org/api/http.html#http_class_http_incomingmessage) from [`http.request`](https://nodejs.org/api/http.html#http_http_request_options_callback) if it's gzipped or deflated, otherwise just passes it through. + +Used by [`got`](https://github.com/sindresorhus/got). + + +## Install + +``` +$ npm install decompress-response +``` + + +## Usage + +```js +const http = require('http'); +const decompressResponse = require('decompress-response'); + +http.get('http://sindresorhus.com', response => { + response = decompressResponse(response); +}); +``` + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/defer-to-connect/LICENSE b/node_modules/defer-to-connect/LICENSE new file mode 100644 index 0000000..15ad2e8 --- /dev/null +++ b/node_modules/defer-to-connect/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2018 Szymon Marczak + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/node_modules/defer-to-connect/README.md b/node_modules/defer-to-connect/README.md new file mode 100644 index 0000000..4dd36c2 --- /dev/null +++ b/node_modules/defer-to-connect/README.md @@ -0,0 +1,38 @@ +# defer-to-connect + +> The safe way to handle the `connect` socket event + +[![Coverage Status](https://coveralls.io/repos/github/szmarczak/defer-to-connect/badge.svg?branch=master)](https://coveralls.io/github/szmarczak/defer-to-connect?branch=master) + +Once you receive the socket, it may be already connected (or disconnected).<br> +To avoid checking that, use `defer-to-connect`. It'll do that for you. + +## Usage + +```js +const deferToConnect = require('defer-to-connect'); + +deferToConnect(socket, () => { + console.log('Connected!'); +}); +``` + +## API + +### deferToConnect(socket, connectListener) + +Calls `connectListener()` when connected. + +### deferToConnect(socket, listeners) + +#### listeners + +An object representing `connect`, `secureConnect` and `close` properties. + +Calls `connect()` when the socket is connected.<br> +Calls `secureConnect()` when the socket is securely connected.<br> +Calls `close()` when the socket is destroyed. + +## License + +MIT diff --git a/node_modules/defer-to-connect/dist/index.d.ts b/node_modules/defer-to-connect/dist/index.d.ts new file mode 100644 index 0000000..323bd12 --- /dev/null +++ b/node_modules/defer-to-connect/dist/index.d.ts @@ -0,0 +1,10 @@ +/// <reference types="node" /> +import { Socket } from 'net'; +import { TLSSocket } from 'tls'; +interface Listeners { + connect?: () => void; + secureConnect?: () => void; + close?: (hadError: boolean) => void; +} +declare const deferToConnect: (socket: Socket | TLSSocket, fn: Listeners | (() => void)) => void; +export default deferToConnect; diff --git a/node_modules/defer-to-connect/dist/index.js b/node_modules/defer-to-connect/dist/index.js new file mode 100644 index 0000000..aaf1cf5 --- /dev/null +++ b/node_modules/defer-to-connect/dist/index.js @@ -0,0 +1,45 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); +const tls_1 = require("tls"); +const deferToConnect = (socket, fn) => { + let listeners; + if (typeof fn === 'function') { + const connect = fn; + listeners = { connect }; + } + else { + listeners = fn; + } + const hasConnectListener = typeof listeners.connect === 'function'; + const hasSecureConnectListener = typeof listeners.secureConnect === 'function'; + const hasCloseListener = typeof listeners.close === 'function'; + const onConnect = () => { + if (hasConnectListener) { + listeners.connect(); + } + if (socket instanceof tls_1.TLSSocket && hasSecureConnectListener) { + if (socket.authorized) { + listeners.secureConnect(); + } + else if (!socket.authorizationError) { + socket.once('secureConnect', listeners.secureConnect); + } + } + if (hasCloseListener) { + socket.once('close', listeners.close); + } + }; + if (socket.writable && !socket.connecting) { + onConnect(); + } + else if (socket.connecting) { + socket.once('connect', onConnect); + } + else if (socket.destroyed && hasCloseListener) { + listeners.close(socket._hadError); + } +}; +exports.default = deferToConnect; +// For CommonJS default export support +module.exports = deferToConnect; +module.exports.default = deferToConnect; diff --git a/node_modules/defer-to-connect/package.json b/node_modules/defer-to-connect/package.json new file mode 100644 index 0000000..34a1170 --- /dev/null +++ b/node_modules/defer-to-connect/package.json @@ -0,0 +1,74 @@ +{ + "name": "defer-to-connect", + "version": "1.1.3", + "description": "The safe way to handle the `connect` socket event", + "main": "dist", + "files": [ + "dist" + ], + "scripts": { + "build": "del-cli dist && tsc", + "prepublishOnly": "npm run build", + "test": "xo && nyc ava", + "coveralls": "nyc report --reporter=text-lcov | coveralls" + }, + "keywords": [ + "socket", + "connect", + "event" + ], + "author": "Szymon Marczak", + "license": "MIT", + "repository": { + "type": "git", + "url": "git+https://github.com/szmarczak/defer-to-connect.git" + }, + "bugs": { + "url": "https://github.com/szmarczak/defer-to-connect/issues" + }, + "homepage": "https://github.com/szmarczak/defer-to-connect#readme", + "xo": { + "extends": "xo-typescript", + "extensions": [ + "ts" + ], + "rules": { + "ava/no-ignored-test-files": "off" + } + }, + "devDependencies": { + "@sindresorhus/tsconfig": "^0.5.0", + "@types/node": "^12.12.4", + "@typescript-eslint/eslint-plugin": "^1.11.0", + "@typescript-eslint/parser": "^1.11.0", + "ava": "^2.1.0", + "coveralls": "^3.0.7", + "create-cert": "^1.0.6", + "del-cli": "^3.0.0", + "eslint-config-xo-typescript": "^0.15.0", + "nyc": "^14.0.0", + "p-event": "^4.1.0", + "ts-node": "^8.1.0", + "typescript": "^3.6.4", + "xo": "^0.25.3" + }, + "nyc": { + "extension": [ + ".ts" + ] + }, + "ava": { + "babel": false, + "compileEnhancements": false, + "extensions": [ + "ts" + ], + "require": [ + "ts-node/register" + ], + "files": [ + "!dist/tests/test.d.ts" + ] + }, + "types": "dist" +} diff --git a/node_modules/dot-prop/index.js b/node_modules/dot-prop/index.js new file mode 100644 index 0000000..189831c --- /dev/null +++ b/node_modules/dot-prop/index.js @@ -0,0 +1,141 @@ +'use strict'; +const isObj = require('is-obj'); + +const disallowedKeys = [ + '__proto__', + 'prototype', + 'constructor' +]; + +const isValidPath = pathSegments => !pathSegments.some(segment => disallowedKeys.includes(segment)); + +function getPathSegments(path) { + const pathArr = path.split('.'); + const parts = []; + + for (let i = 0; i < pathArr.length; i++) { + let p = pathArr[i]; + + while (p[p.length - 1] === '\\' && pathArr[i + 1] !== undefined) { + p = p.slice(0, -1) + '.'; + p += pathArr[++i]; + } + + parts.push(p); + } + + if (!isValidPath(parts)) { + return []; + } + + return parts; +} + +module.exports = { + get(obj, path, value) { + if (!isObj(obj) || typeof path !== 'string') { + return value === undefined ? obj : value; + } + + const pathArr = getPathSegments(path); + if (pathArr.length === 0) { + return; + } + + for (let i = 0; i < pathArr.length; i++) { + if (!Object.prototype.propertyIsEnumerable.call(obj, pathArr[i])) { + return value; + } + + obj = obj[pathArr[i]]; + + if (obj === undefined || obj === null) { + // `obj` is either `undefined` or `null` so we want to stop the loop, and + // if this is not the last bit of the path, and + // if it did't return `undefined` + // it would return `null` if `obj` is `null` + // but we want `get({foo: null}, 'foo.bar')` to equal `undefined`, or the supplied value, not `null` + if (i !== pathArr.length - 1) { + return value; + } + + break; + } + } + + return obj; + }, + + set(obj, path, value) { + if (!isObj(obj) || typeof path !== 'string') { + return obj; + } + + const root = obj; + const pathArr = getPathSegments(path); + if (pathArr.length === 0) { + return; + } + + for (let i = 0; i < pathArr.length; i++) { + const p = pathArr[i]; + + if (!isObj(obj[p])) { + obj[p] = {}; + } + + if (i === pathArr.length - 1) { + obj[p] = value; + } + + obj = obj[p]; + } + + return root; + }, + + delete(obj, path) { + if (!isObj(obj) || typeof path !== 'string') { + return; + } + + const pathArr = getPathSegments(path); + + for (let i = 0; i < pathArr.length; i++) { + const p = pathArr[i]; + + if (i === pathArr.length - 1) { + delete obj[p]; + return; + } + + obj = obj[p]; + + if (!isObj(obj)) { + return; + } + } + }, + + has(obj, path) { + if (!isObj(obj) || typeof path !== 'string') { + return false; + } + + const pathArr = getPathSegments(path); + + for (let i = 0; i < pathArr.length; i++) { + if (isObj(obj)) { + if (!(pathArr[i] in obj)) { + return false; + } + + obj = obj[pathArr[i]]; + } else { + return false; + } + } + + return true; + } +}; diff --git a/node_modules/dot-prop/license b/node_modules/dot-prop/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/dot-prop/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/dot-prop/package.json b/node_modules/dot-prop/package.json new file mode 100644 index 0000000..c9b0f58 --- /dev/null +++ b/node_modules/dot-prop/package.json @@ -0,0 +1,48 @@ +{ + "name": "dot-prop", + "version": "4.2.1", + "description": "Get, set, or delete a property from a nested object using a dot path", + "license": "MIT", + "repository": "sindresorhus/dot-prop", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava", + "bench": "matcha bench.js" + }, + "files": [ + "index.js" + ], + "keywords": [ + "obj", + "object", + "prop", + "property", + "dot", + "path", + "get", + "set", + "delete", + "del", + "access", + "notation", + "dotty" + ], + "dependencies": { + "is-obj": "^1.0.0" + }, + "devDependencies": { + "ava": "1.4.1", + "matcha": "^0.7.0", + "xo": "0.24.0" + }, + "xo": { + "esnext": true + } +} diff --git a/node_modules/dot-prop/readme.md b/node_modules/dot-prop/readme.md new file mode 100644 index 0000000..0e18f78 --- /dev/null +++ b/node_modules/dot-prop/readme.md @@ -0,0 +1,105 @@ +# dot-prop [![Build Status](https://travis-ci.org/sindresorhus/dot-prop.svg?branch=master)](https://travis-ci.org/sindresorhus/dot-prop) + +> Get, set, or delete a property from a nested object using a dot path + + +## Install + +``` +$ npm install --save dot-prop +``` + + +## Usage + +```js +const dotProp = require('dot-prop'); + +// getter +dotProp.get({foo: {bar: 'unicorn'}}, 'foo.bar'); +//=> 'unicorn' + +dotProp.get({foo: {bar: 'a'}}, 'foo.notDefined.deep'); +//=> undefined + +dotProp.get({foo: {bar: 'a'}}, 'foo.notDefined.deep', 'default value'); +//=> 'default value' + +dotProp.get({foo: {'dot.dot': 'unicorn'}}, 'foo.dot\\.dot'); +//=> 'unicorn' + +// setter +const obj = {foo: {bar: 'a'}}; +dotProp.set(obj, 'foo.bar', 'b'); +console.log(obj); +//=> {foo: {bar: 'b'}} + +const foo = dotProp.set({}, 'foo.bar', 'c'); +console.log(foo); +//=> {foo: {bar: 'c'}} + +dotProp.set(obj, 'foo.baz', 'x'); +console.log(obj); +//=> {foo: {bar: 'b', baz: 'x'}} + +// has +dotProp.has({foo: {bar: 'unicorn'}}, 'foo.bar'); +//=> true + +// deleter +const obj = {foo: {bar: 'a'}}; +dotProp.delete(obj, 'foo.bar'); +console.log(obj); +//=> {foo: {}} + +obj.foo.bar = {x: 'y', y: 'x'}; +dotProp.delete(obj, 'foo.bar.x'); +console.log(obj); +//=> {foo: {bar: {y: 'x'}}} +``` + + +## API + +### get(obj, path, [defaultValue]) + +### set(obj, path, value) + +Returns the object. + +### has(obj, path) + +### delete(obj, path) + +#### obj + +Type: `Object` + +Object to get, set, or delete the `path` value. + +#### path + +Type: `string` + +Path of the property in the object, using `.` to separate each nested key. + +Use `\\.` if you have a `.` in the key. + +The following path components are invalid and results in `undefined` being returned: `__proto__`, `prototype`, `constructor`. + +#### value + +Type: `any` + +Value to set at `path`. + +#### defaultValue + +Type: `any` + +Default value. + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/duplexer3/LICENSE.md b/node_modules/duplexer3/LICENSE.md new file mode 100644 index 0000000..547189a --- /dev/null +++ b/node_modules/duplexer3/LICENSE.md @@ -0,0 +1,26 @@ +Copyright (c) 2013, Deoxxa Development +====================================== +All rights reserved. +-------------------- + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: +1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. +2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. +3. Neither the name of Deoxxa Development nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY DEOXXA DEVELOPMENT ''AS IS'' AND ANY +EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL DEOXXA DEVELOPMENT BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/node_modules/duplexer3/README.md b/node_modules/duplexer3/README.md new file mode 100644 index 0000000..9f95ddf --- /dev/null +++ b/node_modules/duplexer3/README.md @@ -0,0 +1,115 @@ +# duplexer3 [![Build Status](https://travis-ci.org/floatdrop/duplexer3.svg?branch=master)](https://travis-ci.org/floatdrop/duplexer3) [![Coverage Status](https://coveralls.io/repos/floatdrop/duplexer3/badge.svg?branch=master&service=github)](https://coveralls.io/github/floatdrop/duplexer3?branch=master) + +Like [duplexer2](https://github.com/deoxxa/duplexer2) but using Streams3 without readable-stream dependency + +```javascript +var stream = require("stream"); + +var duplexer3 = require("duplexer3"); + +var writable = new stream.Writable({objectMode: true}), + readable = new stream.Readable({objectMode: true}); + +writable._write = function _write(input, encoding, done) { + if (readable.push(input)) { + return done(); + } else { + readable.once("drain", done); + } +}; + +readable._read = function _read(n) { + // no-op +}; + +// simulate the readable thing closing after a bit +writable.once("finish", function() { + setTimeout(function() { + readable.push(null); + }, 500); +}); + +var duplex = duplexer3(writable, readable); + +duplex.on("data", function(e) { + console.log("got data", JSON.stringify(e)); +}); + +duplex.on("finish", function() { + console.log("got finish event"); +}); + +duplex.on("end", function() { + console.log("got end event"); +}); + +duplex.write("oh, hi there", function() { + console.log("finished writing"); +}); + +duplex.end(function() { + console.log("finished ending"); +}); +``` + +``` +got data "oh, hi there" +finished writing +got finish event +finished ending +got end event +``` + +## Overview + +This is a reimplementation of [duplexer](https://www.npmjs.com/package/duplexer) using the +Streams3 API which is standard in Node as of v4. Everything largely +works the same. + + + +## Installation + +[Available via `npm`](https://docs.npmjs.com/cli/install): + +``` +$ npm i duplexer3 +``` + +## API + +### duplexer3 + +Creates a new `DuplexWrapper` object, which is the actual class that implements +most of the fun stuff. All that fun stuff is hidden. DON'T LOOK. + +```javascript +duplexer3([options], writable, readable) +``` + +```javascript +const duplex = duplexer3(new stream.Writable(), new stream.Readable()); +``` + +Arguments + +* __options__ - an object specifying the regular `stream.Duplex` options, as + well as the properties described below. +* __writable__ - a writable stream +* __readable__ - a readable stream + +Options + +* __bubbleErrors__ - a boolean value that specifies whether to bubble errors + from the underlying readable/writable streams. Default is `true`. + + +## License + +3-clause BSD. [A copy](./LICENSE) is included with the source. + +## Contact + +* GitHub ([deoxxa](http://github.com/deoxxa)) +* Twitter ([@deoxxa](http://twitter.com/deoxxa)) +* Email ([deoxxa@fknsrs.biz](mailto:deoxxa@fknsrs.biz)) diff --git a/node_modules/duplexer3/index.js b/node_modules/duplexer3/index.js new file mode 100644 index 0000000..1339ffc --- /dev/null +++ b/node_modules/duplexer3/index.js @@ -0,0 +1,76 @@ +"use strict"; + +var stream = require("stream"); + +function DuplexWrapper(options, writable, readable) { + if (typeof readable === "undefined") { + readable = writable; + writable = options; + options = null; + } + + stream.Duplex.call(this, options); + + if (typeof readable.read !== "function") { + readable = (new stream.Readable(options)).wrap(readable); + } + + this._writable = writable; + this._readable = readable; + this._waiting = false; + + var self = this; + + writable.once("finish", function() { + self.end(); + }); + + this.once("finish", function() { + writable.end(); + }); + + readable.on("readable", function() { + if (self._waiting) { + self._waiting = false; + self._read(); + } + }); + + readable.once("end", function() { + self.push(null); + }); + + if (!options || typeof options.bubbleErrors === "undefined" || options.bubbleErrors) { + writable.on("error", function(err) { + self.emit("error", err); + }); + + readable.on("error", function(err) { + self.emit("error", err); + }); + } +} + +DuplexWrapper.prototype = Object.create(stream.Duplex.prototype, {constructor: {value: DuplexWrapper}}); + +DuplexWrapper.prototype._write = function _write(input, encoding, done) { + this._writable.write(input, encoding, done); +}; + +DuplexWrapper.prototype._read = function _read() { + var buf; + var reads = 0; + while ((buf = this._readable.read()) !== null) { + this.push(buf); + reads++; + } + if (reads === 0) { + this._waiting = true; + } +}; + +module.exports = function duplex2(options, writable, readable) { + return new DuplexWrapper(options, writable, readable); +}; + +module.exports.DuplexWrapper = DuplexWrapper; diff --git a/node_modules/duplexer3/package.json b/node_modules/duplexer3/package.json new file mode 100644 index 0000000..251f78f --- /dev/null +++ b/node_modules/duplexer3/package.json @@ -0,0 +1,28 @@ +{ + "name": "duplexer3", + "version": "0.1.4", + "description": "Like duplexer but using streams3", + "engine": { + "node": ">=4" + }, + "files": [ + "index.js" + ], + "scripts": { + "test": "mocha -R tap" + }, + "repository": "floatdrop/duplexer3", + "keywords": [ + "duplex", + "duplexer", + "stream", + "stream3", + "join", + "combine" + ], + "author": "Conrad Pankoff <deoxxa@fknsrs.biz> (http://www.fknsrs.biz/)", + "license": "BSD-3-Clause", + "devDependencies": { + "mocha": "^2.2.5" + } +} diff --git a/node_modules/end-of-stream/LICENSE b/node_modules/end-of-stream/LICENSE new file mode 100644 index 0000000..757562e --- /dev/null +++ b/node_modules/end-of-stream/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE.
\ No newline at end of file diff --git a/node_modules/end-of-stream/README.md b/node_modules/end-of-stream/README.md new file mode 100644 index 0000000..857b14b --- /dev/null +++ b/node_modules/end-of-stream/README.md @@ -0,0 +1,54 @@ +# end-of-stream + +A node module that calls a callback when a readable/writable/duplex stream has completed or failed. + + npm install end-of-stream + +[![Build status](https://travis-ci.org/mafintosh/end-of-stream.svg?branch=master)](https://travis-ci.org/mafintosh/end-of-stream) + +## Usage + +Simply pass a stream and a callback to the `eos`. +Both legacy streams, streams2 and stream3 are supported. + +``` js +var eos = require('end-of-stream'); + +eos(readableStream, function(err) { + // this will be set to the stream instance + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended', this === readableStream); +}); + +eos(writableStream, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has finished', this === writableStream); +}); + +eos(duplexStream, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended and finished', this === duplexStream); +}); + +eos(duplexStream, {readable:false}, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has finished but might still be readable'); +}); + +eos(duplexStream, {writable:false}, function(err) { + if (err) return console.log('stream had an error or closed early'); + console.log('stream has ended but might still be writable'); +}); + +eos(readableStream, {error:false}, function(err) { + // do not treat emit('error', err) as a end-of-stream +}); +``` + +## License + +MIT + +## Related + +`end-of-stream` is part of the [mississippi stream utility collection](https://github.com/maxogden/mississippi) which includes more useful stream modules similar to this one. diff --git a/node_modules/end-of-stream/index.js b/node_modules/end-of-stream/index.js new file mode 100644 index 0000000..c77f0d5 --- /dev/null +++ b/node_modules/end-of-stream/index.js @@ -0,0 +1,94 @@ +var once = require('once'); + +var noop = function() {}; + +var isRequest = function(stream) { + return stream.setHeader && typeof stream.abort === 'function'; +}; + +var isChildProcess = function(stream) { + return stream.stdio && Array.isArray(stream.stdio) && stream.stdio.length === 3 +}; + +var eos = function(stream, opts, callback) { + if (typeof opts === 'function') return eos(stream, null, opts); + if (!opts) opts = {}; + + callback = once(callback || noop); + + var ws = stream._writableState; + var rs = stream._readableState; + var readable = opts.readable || (opts.readable !== false && stream.readable); + var writable = opts.writable || (opts.writable !== false && stream.writable); + var cancelled = false; + + var onlegacyfinish = function() { + if (!stream.writable) onfinish(); + }; + + var onfinish = function() { + writable = false; + if (!readable) callback.call(stream); + }; + + var onend = function() { + readable = false; + if (!writable) callback.call(stream); + }; + + var onexit = function(exitCode) { + callback.call(stream, exitCode ? new Error('exited with error code: ' + exitCode) : null); + }; + + var onerror = function(err) { + callback.call(stream, err); + }; + + var onclose = function() { + process.nextTick(onclosenexttick); + }; + + var onclosenexttick = function() { + if (cancelled) return; + if (readable && !(rs && (rs.ended && !rs.destroyed))) return callback.call(stream, new Error('premature close')); + if (writable && !(ws && (ws.ended && !ws.destroyed))) return callback.call(stream, new Error('premature close')); + }; + + var onrequest = function() { + stream.req.on('finish', onfinish); + }; + + if (isRequest(stream)) { + stream.on('complete', onfinish); + stream.on('abort', onclose); + if (stream.req) onrequest(); + else stream.on('request', onrequest); + } else if (writable && !ws) { // legacy streams + stream.on('end', onlegacyfinish); + stream.on('close', onlegacyfinish); + } + + if (isChildProcess(stream)) stream.on('exit', onexit); + + stream.on('end', onend); + stream.on('finish', onfinish); + if (opts.error !== false) stream.on('error', onerror); + stream.on('close', onclose); + + return function() { + cancelled = true; + stream.removeListener('complete', onfinish); + stream.removeListener('abort', onclose); + stream.removeListener('request', onrequest); + if (stream.req) stream.req.removeListener('finish', onfinish); + stream.removeListener('end', onlegacyfinish); + stream.removeListener('close', onlegacyfinish); + stream.removeListener('finish', onfinish); + stream.removeListener('exit', onexit); + stream.removeListener('end', onend); + stream.removeListener('error', onerror); + stream.removeListener('close', onclose); + }; +}; + +module.exports = eos; diff --git a/node_modules/end-of-stream/package.json b/node_modules/end-of-stream/package.json new file mode 100644 index 0000000..b75bbf0 --- /dev/null +++ b/node_modules/end-of-stream/package.json @@ -0,0 +1,37 @@ +{ + "name": "end-of-stream", + "version": "1.4.4", + "description": "Call a callback when a readable/writable/duplex stream has completed or failed.", + "repository": { + "type": "git", + "url": "git://github.com/mafintosh/end-of-stream.git" + }, + "dependencies": { + "once": "^1.4.0" + }, + "scripts": { + "test": "node test.js" + }, + "files": [ + "index.js" + ], + "keywords": [ + "stream", + "streams", + "callback", + "finish", + "close", + "end", + "wait" + ], + "bugs": { + "url": "https://github.com/mafintosh/end-of-stream/issues" + }, + "homepage": "https://github.com/mafintosh/end-of-stream", + "main": "index.js", + "author": "Mathias Buus <mathiasbuus@gmail.com>", + "license": "MIT", + "devDependencies": { + "tape": "^4.11.0" + } +} diff --git a/node_modules/follow-redirects/LICENSE b/node_modules/follow-redirects/LICENSE new file mode 100644 index 0000000..742cbad --- /dev/null +++ b/node_modules/follow-redirects/LICENSE @@ -0,0 +1,18 @@ +Copyright 2014–present Olivier Lalonde <olalonde@gmail.com>, James Talmage <james@talmage.io>, Ruben Verborgh + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies +of the Software, and to permit persons to whom the Software is furnished to do +so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR +IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/follow-redirects/README.md b/node_modules/follow-redirects/README.md new file mode 100644 index 0000000..ea618ab --- /dev/null +++ b/node_modules/follow-redirects/README.md @@ -0,0 +1,148 @@ +## Follow Redirects + +Drop-in replacement for Node's `http` and `https` modules that automatically follows redirects. + +[![npm version](https://img.shields.io/npm/v/follow-redirects.svg)](https://www.npmjs.com/package/follow-redirects) +[![Build Status](https://github.com/follow-redirects/follow-redirects/workflows/CI/badge.svg)](https://github.com/follow-redirects/follow-redirects/actions) +[![Coverage Status](https://coveralls.io/repos/follow-redirects/follow-redirects/badge.svg?branch=master)](https://coveralls.io/r/follow-redirects/follow-redirects?branch=master) +[![npm downloads](https://img.shields.io/npm/dm/follow-redirects.svg)](https://www.npmjs.com/package/follow-redirects) +[![Sponsor on GitHub](https://img.shields.io/static/v1?label=Sponsor&message=%F0%9F%92%96&logo=GitHub)](https://github.com/sponsors/RubenVerborgh) + +`follow-redirects` provides [request](https://nodejs.org/api/http.html#http_http_request_options_callback) and [get](https://nodejs.org/api/http.html#http_http_get_options_callback) + methods that behave identically to those found on the native [http](https://nodejs.org/api/http.html#http_http_request_options_callback) and [https](https://nodejs.org/api/https.html#https_https_request_options_callback) + modules, with the exception that they will seamlessly follow redirects. + +```javascript +const { http, https } = require('follow-redirects'); + +http.get('http://bit.ly/900913', response => { + response.on('data', chunk => { + console.log(chunk); + }); +}).on('error', err => { + console.error(err); +}); +``` + +You can inspect the final redirected URL through the `responseUrl` property on the `response`. +If no redirection happened, `responseUrl` is the original request URL. + +```javascript +const request = https.request({ + host: 'bitly.com', + path: '/UHfDGO', +}, response => { + console.log(response.responseUrl); + // 'http://duckduckgo.com/robots.txt' +}); +request.end(); +``` + +## Options +### Global options +Global options are set directly on the `follow-redirects` module: + +```javascript +const followRedirects = require('follow-redirects'); +followRedirects.maxRedirects = 10; +followRedirects.maxBodyLength = 20 * 1024 * 1024; // 20 MB +``` + +The following global options are supported: + +- `maxRedirects` (default: `21`) – sets the maximum number of allowed redirects; if exceeded, an error will be emitted. + +- `maxBodyLength` (default: 10MB) – sets the maximum size of the request body; if exceeded, an error will be emitted. + +### Per-request options +Per-request options are set by passing an `options` object: + +```javascript +const url = require('url'); +const { http, https } = require('follow-redirects'); + +const options = url.parse('http://bit.ly/900913'); +options.maxRedirects = 10; +options.beforeRedirect = (options, { headers }) => { + // Use this to adjust the request options upon redirecting, + // to inspect the latest response headers, + // or to cancel the request by throwing an error + if (options.hostname === "example.com") { + options.auth = "user:password"; + } +}; +http.request(options); +``` + +In addition to the [standard HTTP](https://nodejs.org/api/http.html#http_http_request_options_callback) and [HTTPS options](https://nodejs.org/api/https.html#https_https_request_options_callback), +the following per-request options are supported: +- `followRedirects` (default: `true`) – whether redirects should be followed. + +- `maxRedirects` (default: `21`) – sets the maximum number of allowed redirects; if exceeded, an error will be emitted. + +- `maxBodyLength` (default: 10MB) – sets the maximum size of the request body; if exceeded, an error will be emitted. + +- `beforeRedirect` (default: `undefined`) – optionally change the request `options` on redirects, or abort the request by throwing an error. + +- `agents` (default: `undefined`) – sets the `agent` option per protocol, since HTTP and HTTPS use different agents. Example value: `{ http: new http.Agent(), https: new https.Agent() }` + +- `trackRedirects` (default: `false`) – whether to store the redirected response details into the `redirects` array on the response object. + + +### Advanced usage +By default, `follow-redirects` will use the Node.js default implementations +of [`http`](https://nodejs.org/api/http.html) +and [`https`](https://nodejs.org/api/https.html). +To enable features such as caching and/or intermediate request tracking, +you might instead want to wrap `follow-redirects` around custom protocol implementations: + +```javascript +const { http, https } = require('follow-redirects').wrap({ + http: require('your-custom-http'), + https: require('your-custom-https'), +}); +``` + +Such custom protocols only need an implementation of the `request` method. + +## Browser Usage + +Due to the way the browser works, +the `http` and `https` browser equivalents perform redirects by default. + +By requiring `follow-redirects` this way: +```javascript +const http = require('follow-redirects/http'); +const https = require('follow-redirects/https'); +``` +you can easily tell webpack and friends to replace +`follow-redirect` by the built-in versions: + +```json +{ + "follow-redirects/http" : "http", + "follow-redirects/https" : "https" +} +``` + +## Contributing + +Pull Requests are always welcome. Please [file an issue](https://github.com/follow-redirects/follow-redirects/issues) + detailing your proposal before you invest your valuable time. Additional features and bug fixes should be accompanied + by tests. You can run the test suite locally with a simple `npm test` command. + +## Debug Logging + +`follow-redirects` uses the excellent [debug](https://www.npmjs.com/package/debug) for logging. To turn on logging + set the environment variable `DEBUG=follow-redirects` for debug output from just this module. When running the test + suite it is sometimes advantageous to set `DEBUG=*` to see output from the express server as well. + +## Authors + +- [Ruben Verborgh](https://ruben.verborgh.org/) +- [Olivier Lalonde](mailto:olalonde@gmail.com) +- [James Talmage](mailto:james@talmage.io) + +## License + +[MIT License](https://github.com/follow-redirects/follow-redirects/blob/master/LICENSE) diff --git a/node_modules/follow-redirects/debug.js b/node_modules/follow-redirects/debug.js new file mode 100644 index 0000000..decb77d --- /dev/null +++ b/node_modules/follow-redirects/debug.js @@ -0,0 +1,15 @@ +var debug; + +module.exports = function () { + if (!debug) { + try { + /* eslint global-require: off */ + debug = require("debug")("follow-redirects"); + } + catch (error) { /* */ } + if (typeof debug !== "function") { + debug = function () { /* */ }; + } + } + debug.apply(null, arguments); +}; diff --git a/node_modules/follow-redirects/http.js b/node_modules/follow-redirects/http.js new file mode 100644 index 0000000..695e356 --- /dev/null +++ b/node_modules/follow-redirects/http.js @@ -0,0 +1 @@ +module.exports = require("./").http; diff --git a/node_modules/follow-redirects/https.js b/node_modules/follow-redirects/https.js new file mode 100644 index 0000000..d21c921 --- /dev/null +++ b/node_modules/follow-redirects/https.js @@ -0,0 +1 @@ +module.exports = require("./").https; diff --git a/node_modules/follow-redirects/index.js b/node_modules/follow-redirects/index.js new file mode 100644 index 0000000..3f819d1 --- /dev/null +++ b/node_modules/follow-redirects/index.js @@ -0,0 +1,574 @@ +var url = require("url"); +var URL = url.URL; +var http = require("http"); +var https = require("https"); +var Writable = require("stream").Writable; +var assert = require("assert"); +var debug = require("./debug"); + +// Create handlers that pass events from native requests +var events = ["abort", "aborted", "connect", "error", "socket", "timeout"]; +var eventHandlers = Object.create(null); +events.forEach(function (event) { + eventHandlers[event] = function (arg1, arg2, arg3) { + this._redirectable.emit(event, arg1, arg2, arg3); + }; +}); + +// Error types with codes +var RedirectionError = createErrorType( + "ERR_FR_REDIRECTION_FAILURE", + "Redirected request failed" +); +var TooManyRedirectsError = createErrorType( + "ERR_FR_TOO_MANY_REDIRECTS", + "Maximum number of redirects exceeded" +); +var MaxBodyLengthExceededError = createErrorType( + "ERR_FR_MAX_BODY_LENGTH_EXCEEDED", + "Request body larger than maxBodyLength limit" +); +var WriteAfterEndError = createErrorType( + "ERR_STREAM_WRITE_AFTER_END", + "write after end" +); + +// An HTTP(S) request that can be redirected +function RedirectableRequest(options, responseCallback) { + // Initialize the request + Writable.call(this); + this._sanitizeOptions(options); + this._options = options; + this._ended = false; + this._ending = false; + this._redirectCount = 0; + this._redirects = []; + this._requestBodyLength = 0; + this._requestBodyBuffers = []; + + // Attach a callback if passed + if (responseCallback) { + this.on("response", responseCallback); + } + + // React to responses of native requests + var self = this; + this._onNativeResponse = function (response) { + self._processResponse(response); + }; + + // Perform the first request + this._performRequest(); +} +RedirectableRequest.prototype = Object.create(Writable.prototype); + +RedirectableRequest.prototype.abort = function () { + abortRequest(this._currentRequest); + this.emit("abort"); +}; + +// Writes buffered data to the current native request +RedirectableRequest.prototype.write = function (data, encoding, callback) { + // Writing is not allowed if end has been called + if (this._ending) { + throw new WriteAfterEndError(); + } + + // Validate input and shift parameters if necessary + if (!(typeof data === "string" || typeof data === "object" && ("length" in data))) { + throw new TypeError("data should be a string, Buffer or Uint8Array"); + } + if (typeof encoding === "function") { + callback = encoding; + encoding = null; + } + + // Ignore empty buffers, since writing them doesn't invoke the callback + // https://github.com/nodejs/node/issues/22066 + if (data.length === 0) { + if (callback) { + callback(); + } + return; + } + // Only write when we don't exceed the maximum body length + if (this._requestBodyLength + data.length <= this._options.maxBodyLength) { + this._requestBodyLength += data.length; + this._requestBodyBuffers.push({ data: data, encoding: encoding }); + this._currentRequest.write(data, encoding, callback); + } + // Error when we exceed the maximum body length + else { + this.emit("error", new MaxBodyLengthExceededError()); + this.abort(); + } +}; + +// Ends the current native request +RedirectableRequest.prototype.end = function (data, encoding, callback) { + // Shift parameters if necessary + if (typeof data === "function") { + callback = data; + data = encoding = null; + } + else if (typeof encoding === "function") { + callback = encoding; + encoding = null; + } + + // Write data if needed and end + if (!data) { + this._ended = this._ending = true; + this._currentRequest.end(null, null, callback); + } + else { + var self = this; + var currentRequest = this._currentRequest; + this.write(data, encoding, function () { + self._ended = true; + currentRequest.end(null, null, callback); + }); + this._ending = true; + } +}; + +// Sets a header value on the current native request +RedirectableRequest.prototype.setHeader = function (name, value) { + this._options.headers[name] = value; + this._currentRequest.setHeader(name, value); +}; + +// Clears a header value on the current native request +RedirectableRequest.prototype.removeHeader = function (name) { + delete this._options.headers[name]; + this._currentRequest.removeHeader(name); +}; + +// Global timeout for all underlying requests +RedirectableRequest.prototype.setTimeout = function (msecs, callback) { + var self = this; + + // Destroys the socket on timeout + function destroyOnTimeout(socket) { + socket.setTimeout(msecs); + socket.removeListener("timeout", socket.destroy); + socket.addListener("timeout", socket.destroy); + } + + // Sets up a timer to trigger a timeout event + function startTimer(socket) { + if (self._timeout) { + clearTimeout(self._timeout); + } + self._timeout = setTimeout(function () { + self.emit("timeout"); + clearTimer(); + }, msecs); + destroyOnTimeout(socket); + } + + // Stops a timeout from triggering + function clearTimer() { + // Clear the timeout + if (self._timeout) { + clearTimeout(self._timeout); + self._timeout = null; + } + + // Clean up all attached listeners + self.removeListener("abort", clearTimer); + self.removeListener("error", clearTimer); + self.removeListener("response", clearTimer); + if (callback) { + self.removeListener("timeout", callback); + } + if (!self.socket) { + self._currentRequest.removeListener("socket", startTimer); + } + } + + // Attach callback if passed + if (callback) { + this.on("timeout", callback); + } + + // Start the timer if or when the socket is opened + if (this.socket) { + startTimer(this.socket); + } + else { + this._currentRequest.once("socket", startTimer); + } + + // Clean up on events + this.on("socket", destroyOnTimeout); + this.on("abort", clearTimer); + this.on("error", clearTimer); + this.on("response", clearTimer); + + return this; +}; + +// Proxy all other public ClientRequest methods +[ + "flushHeaders", "getHeader", + "setNoDelay", "setSocketKeepAlive", +].forEach(function (method) { + RedirectableRequest.prototype[method] = function (a, b) { + return this._currentRequest[method](a, b); + }; +}); + +// Proxy all public ClientRequest properties +["aborted", "connection", "socket"].forEach(function (property) { + Object.defineProperty(RedirectableRequest.prototype, property, { + get: function () { return this._currentRequest[property]; }, + }); +}); + +RedirectableRequest.prototype._sanitizeOptions = function (options) { + // Ensure headers are always present + if (!options.headers) { + options.headers = {}; + } + + // Since http.request treats host as an alias of hostname, + // but the url module interprets host as hostname plus port, + // eliminate the host property to avoid confusion. + if (options.host) { + // Use hostname if set, because it has precedence + if (!options.hostname) { + options.hostname = options.host; + } + delete options.host; + } + + // Complete the URL object when necessary + if (!options.pathname && options.path) { + var searchPos = options.path.indexOf("?"); + if (searchPos < 0) { + options.pathname = options.path; + } + else { + options.pathname = options.path.substring(0, searchPos); + options.search = options.path.substring(searchPos); + } + } +}; + + +// Executes the next native request (initial or redirect) +RedirectableRequest.prototype._performRequest = function () { + // Load the native protocol + var protocol = this._options.protocol; + var nativeProtocol = this._options.nativeProtocols[protocol]; + if (!nativeProtocol) { + this.emit("error", new TypeError("Unsupported protocol " + protocol)); + return; + } + + // If specified, use the agent corresponding to the protocol + // (HTTP and HTTPS use different types of agents) + if (this._options.agents) { + var scheme = protocol.substr(0, protocol.length - 1); + this._options.agent = this._options.agents[scheme]; + } + + // Create the native request + var request = this._currentRequest = + nativeProtocol.request(this._options, this._onNativeResponse); + this._currentUrl = url.format(this._options); + + // Set up event handlers + request._redirectable = this; + for (var e = 0; e < events.length; e++) { + request.on(events[e], eventHandlers[events[e]]); + } + + // End a redirected request + // (The first request must be ended explicitly with RedirectableRequest#end) + if (this._isRedirect) { + // Write the request entity and end. + var i = 0; + var self = this; + var buffers = this._requestBodyBuffers; + (function writeNext(error) { + // Only write if this request has not been redirected yet + /* istanbul ignore else */ + if (request === self._currentRequest) { + // Report any write errors + /* istanbul ignore if */ + if (error) { + self.emit("error", error); + } + // Write the next buffer if there are still left + else if (i < buffers.length) { + var buffer = buffers[i++]; + /* istanbul ignore else */ + if (!request.finished) { + request.write(buffer.data, buffer.encoding, writeNext); + } + } + // End the request if `end` has been called on us + else if (self._ended) { + request.end(); + } + } + }()); + } +}; + +// Processes a response from the current native request +RedirectableRequest.prototype._processResponse = function (response) { + // Store the redirected response + var statusCode = response.statusCode; + if (this._options.trackRedirects) { + this._redirects.push({ + url: this._currentUrl, + headers: response.headers, + statusCode: statusCode, + }); + } + + // RFC7231§6.4: The 3xx (Redirection) class of status code indicates + // that further action needs to be taken by the user agent in order to + // fulfill the request. If a Location header field is provided, + // the user agent MAY automatically redirect its request to the URI + // referenced by the Location field value, + // even if the specific status code is not understood. + + // If the response is not a redirect; return it as-is + var location = response.headers.location; + if (!location || this._options.followRedirects === false || + statusCode < 300 || statusCode >= 400) { + response.responseUrl = this._currentUrl; + response.redirects = this._redirects; + this.emit("response", response); + + // Clean up + this._requestBodyBuffers = []; + return; + } + + // The response is a redirect, so abort the current request + abortRequest(this._currentRequest); + // Discard the remainder of the response to avoid waiting for data + response.destroy(); + + // RFC7231§6.4: A client SHOULD detect and intervene + // in cyclical redirections (i.e., "infinite" redirection loops). + if (++this._redirectCount > this._options.maxRedirects) { + this.emit("error", new TooManyRedirectsError()); + return; + } + + // RFC7231§6.4: Automatic redirection needs to done with + // care for methods not known to be safe, […] + // RFC7231§6.4.2–3: For historical reasons, a user agent MAY change + // the request method from POST to GET for the subsequent request. + if ((statusCode === 301 || statusCode === 302) && this._options.method === "POST" || + // RFC7231§6.4.4: The 303 (See Other) status code indicates that + // the server is redirecting the user agent to a different resource […] + // A user agent can perform a retrieval request targeting that URI + // (a GET or HEAD request if using HTTP) […] + (statusCode === 303) && !/^(?:GET|HEAD)$/.test(this._options.method)) { + this._options.method = "GET"; + // Drop a possible entity and headers related to it + this._requestBodyBuffers = []; + removeMatchingHeaders(/^content-/i, this._options.headers); + } + + // Drop the Host header, as the redirect might lead to a different host + var currentHostHeader = removeMatchingHeaders(/^host$/i, this._options.headers); + + // If the redirect is relative, carry over the host of the last request + var currentUrlParts = url.parse(this._currentUrl); + var currentHost = currentHostHeader || currentUrlParts.host; + var currentUrl = /^\w+:/.test(location) ? this._currentUrl : + url.format(Object.assign(currentUrlParts, { host: currentHost })); + + // Determine the URL of the redirection + var redirectUrl; + try { + redirectUrl = url.resolve(currentUrl, location); + } + catch (cause) { + this.emit("error", new RedirectionError(cause)); + return; + } + + // Create the redirected request + debug("redirecting to", redirectUrl); + this._isRedirect = true; + var redirectUrlParts = url.parse(redirectUrl); + Object.assign(this._options, redirectUrlParts); + + // Drop confidential headers when redirecting to a less secure protocol + // or to a different domain that is not a superdomain + if (redirectUrlParts.protocol !== currentUrlParts.protocol && + redirectUrlParts.protocol !== "https:" || + redirectUrlParts.host !== currentHost && + !isSubdomain(redirectUrlParts.host, currentHost)) { + removeMatchingHeaders(/^(?:authorization|cookie)$/i, this._options.headers); + } + + // Evaluate the beforeRedirect callback + if (typeof this._options.beforeRedirect === "function") { + var responseDetails = { headers: response.headers }; + try { + this._options.beforeRedirect.call(null, this._options, responseDetails); + } + catch (err) { + this.emit("error", err); + return; + } + this._sanitizeOptions(this._options); + } + + // Perform the redirected request + try { + this._performRequest(); + } + catch (cause) { + this.emit("error", new RedirectionError(cause)); + } +}; + +// Wraps the key/value object of protocols with redirect functionality +function wrap(protocols) { + // Default settings + var exports = { + maxRedirects: 21, + maxBodyLength: 10 * 1024 * 1024, + }; + + // Wrap each protocol + var nativeProtocols = {}; + Object.keys(protocols).forEach(function (scheme) { + var protocol = scheme + ":"; + var nativeProtocol = nativeProtocols[protocol] = protocols[scheme]; + var wrappedProtocol = exports[scheme] = Object.create(nativeProtocol); + + // Executes a request, following redirects + function request(input, options, callback) { + // Parse parameters + if (typeof input === "string") { + var urlStr = input; + try { + input = urlToOptions(new URL(urlStr)); + } + catch (err) { + /* istanbul ignore next */ + input = url.parse(urlStr); + } + } + else if (URL && (input instanceof URL)) { + input = urlToOptions(input); + } + else { + callback = options; + options = input; + input = { protocol: protocol }; + } + if (typeof options === "function") { + callback = options; + options = null; + } + + // Set defaults + options = Object.assign({ + maxRedirects: exports.maxRedirects, + maxBodyLength: exports.maxBodyLength, + }, input, options); + options.nativeProtocols = nativeProtocols; + + assert.equal(options.protocol, protocol, "protocol mismatch"); + debug("options", options); + return new RedirectableRequest(options, callback); + } + + // Executes a GET request, following redirects + function get(input, options, callback) { + var wrappedRequest = wrappedProtocol.request(input, options, callback); + wrappedRequest.end(); + return wrappedRequest; + } + + // Expose the properties on the wrapped protocol + Object.defineProperties(wrappedProtocol, { + request: { value: request, configurable: true, enumerable: true, writable: true }, + get: { value: get, configurable: true, enumerable: true, writable: true }, + }); + }); + return exports; +} + +/* istanbul ignore next */ +function noop() { /* empty */ } + +// from https://github.com/nodejs/node/blob/master/lib/internal/url.js +function urlToOptions(urlObject) { + var options = { + protocol: urlObject.protocol, + hostname: urlObject.hostname.startsWith("[") ? + /* istanbul ignore next */ + urlObject.hostname.slice(1, -1) : + urlObject.hostname, + hash: urlObject.hash, + search: urlObject.search, + pathname: urlObject.pathname, + path: urlObject.pathname + urlObject.search, + href: urlObject.href, + }; + if (urlObject.port !== "") { + options.port = Number(urlObject.port); + } + return options; +} + +function removeMatchingHeaders(regex, headers) { + var lastValue; + for (var header in headers) { + if (regex.test(header)) { + lastValue = headers[header]; + delete headers[header]; + } + } + return (lastValue === null || typeof lastValue === "undefined") ? + undefined : String(lastValue).trim(); +} + +function createErrorType(code, defaultMessage) { + function CustomError(cause) { + Error.captureStackTrace(this, this.constructor); + if (!cause) { + this.message = defaultMessage; + } + else { + this.message = defaultMessage + ": " + cause.message; + this.cause = cause; + } + } + CustomError.prototype = new Error(); + CustomError.prototype.constructor = CustomError; + CustomError.prototype.name = "Error [" + code + "]"; + CustomError.prototype.code = code; + return CustomError; +} + +function abortRequest(request) { + for (var e = 0; e < events.length; e++) { + request.removeListener(events[e], eventHandlers[events[e]]); + } + request.on("error", noop); + request.abort(); +} + +function isSubdomain(subdomain, domain) { + const dot = subdomain.length - domain.length - 1; + return dot > 0 && subdomain[dot] === "." && subdomain.endsWith(domain); +} + +// Exports +module.exports = wrap({ http: http, https: https }); +module.exports.wrap = wrap; diff --git a/node_modules/follow-redirects/package.json b/node_modules/follow-redirects/package.json new file mode 100644 index 0000000..742fb44 --- /dev/null +++ b/node_modules/follow-redirects/package.json @@ -0,0 +1,59 @@ +{ + "name": "follow-redirects", + "version": "1.14.9", + "description": "HTTP and HTTPS modules that follow redirects.", + "license": "MIT", + "main": "index.js", + "files": [ + "*.js" + ], + "engines": { + "node": ">=4.0" + }, + "scripts": { + "test": "npm run lint && npm run mocha", + "lint": "eslint *.js test", + "mocha": "nyc mocha" + }, + "repository": { + "type": "git", + "url": "git@github.com:follow-redirects/follow-redirects.git" + }, + "homepage": "https://github.com/follow-redirects/follow-redirects", + "bugs": { + "url": "https://github.com/follow-redirects/follow-redirects/issues" + }, + "keywords": [ + "http", + "https", + "url", + "redirect", + "client", + "location", + "utility" + ], + "author": "Ruben Verborgh <ruben@verborgh.org> (https://ruben.verborgh.org/)", + "contributors": [ + "Olivier Lalonde <olalonde@gmail.com> (http://www.syskall.com)", + "James Talmage <james@talmage.io>" + ], + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "peerDependenciesMeta": { + "debug": { + "optional": true + } + }, + "devDependencies": { + "concat-stream": "^2.0.0", + "eslint": "^5.16.0", + "express": "^4.16.4", + "lolex": "^3.1.0", + "mocha": "^6.0.2", + "nyc": "^14.1.1" + } +} diff --git a/node_modules/get-stream/buffer-stream.js b/node_modules/get-stream/buffer-stream.js new file mode 100644 index 0000000..4121c8e --- /dev/null +++ b/node_modules/get-stream/buffer-stream.js @@ -0,0 +1,51 @@ +'use strict'; +const {PassThrough} = require('stream'); + +module.exports = options => { + options = Object.assign({}, options); + + const {array} = options; + let {encoding} = options; + const buffer = encoding === 'buffer'; + let objectMode = false; + + if (array) { + objectMode = !(encoding || buffer); + } else { + encoding = encoding || 'utf8'; + } + + if (buffer) { + encoding = null; + } + + let len = 0; + const ret = []; + const stream = new PassThrough({objectMode}); + + if (encoding) { + stream.setEncoding(encoding); + } + + stream.on('data', chunk => { + ret.push(chunk); + + if (objectMode) { + len = ret.length; + } else { + len += chunk.length; + } + }); + + stream.getBufferedValue = () => { + if (array) { + return ret; + } + + return buffer ? Buffer.concat(ret, len) : ret.join(''); + }; + + stream.getBufferedLength = () => len; + + return stream; +}; diff --git a/node_modules/get-stream/index.js b/node_modules/get-stream/index.js new file mode 100644 index 0000000..7e5584a --- /dev/null +++ b/node_modules/get-stream/index.js @@ -0,0 +1,50 @@ +'use strict'; +const pump = require('pump'); +const bufferStream = require('./buffer-stream'); + +class MaxBufferError extends Error { + constructor() { + super('maxBuffer exceeded'); + this.name = 'MaxBufferError'; + } +} + +function getStream(inputStream, options) { + if (!inputStream) { + return Promise.reject(new Error('Expected a stream')); + } + + options = Object.assign({maxBuffer: Infinity}, options); + + const {maxBuffer} = options; + + let stream; + return new Promise((resolve, reject) => { + const rejectPromise = error => { + if (error) { // A null check + error.bufferedData = stream.getBufferedValue(); + } + reject(error); + }; + + stream = pump(inputStream, bufferStream(options), error => { + if (error) { + rejectPromise(error); + return; + } + + resolve(); + }); + + stream.on('data', () => { + if (stream.getBufferedLength() > maxBuffer) { + rejectPromise(new MaxBufferError()); + } + }); + }).then(() => stream.getBufferedValue()); +} + +module.exports = getStream; +module.exports.buffer = (stream, options) => getStream(stream, Object.assign({}, options, {encoding: 'buffer'})); +module.exports.array = (stream, options) => getStream(stream, Object.assign({}, options, {array: true})); +module.exports.MaxBufferError = MaxBufferError; diff --git a/node_modules/get-stream/license b/node_modules/get-stream/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/get-stream/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/get-stream/package.json b/node_modules/get-stream/package.json new file mode 100644 index 0000000..619651c --- /dev/null +++ b/node_modules/get-stream/package.json @@ -0,0 +1,46 @@ +{ + "name": "get-stream", + "version": "4.1.0", + "description": "Get a stream as a string, buffer, or array", + "license": "MIT", + "repository": "sindresorhus/get-stream", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=6" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js", + "buffer-stream.js" + ], + "keywords": [ + "get", + "stream", + "promise", + "concat", + "string", + "text", + "buffer", + "read", + "data", + "consume", + "readable", + "readablestream", + "array", + "object" + ], + "dependencies": { + "pump": "^3.0.0" + }, + "devDependencies": { + "ava": "*", + "into-stream": "^3.0.0", + "xo": "*" + } +} diff --git a/node_modules/get-stream/readme.md b/node_modules/get-stream/readme.md new file mode 100644 index 0000000..b87a4d3 --- /dev/null +++ b/node_modules/get-stream/readme.md @@ -0,0 +1,123 @@ +# get-stream [![Build Status](https://travis-ci.org/sindresorhus/get-stream.svg?branch=master)](https://travis-ci.org/sindresorhus/get-stream) + +> Get a stream as a string, buffer, or array + + +## Install + +``` +$ npm install get-stream +``` + + +## Usage + +```js +const fs = require('fs'); +const getStream = require('get-stream'); + +(async () => { + const stream = fs.createReadStream('unicorn.txt'); + + console.log(await getStream(stream)); + /* + ,,))))))));, + __)))))))))))))), + \|/ -\(((((''''((((((((. + -*-==//////(('' . `)))))), + /|\ ))| o ;-. '((((( ,(, + ( `| / ) ;))))' ,_))^;(~ + | | | ,))((((_ _____------~~~-. %,;(;(>';'~ + o_); ; )))(((` ~---~ `:: \ %%~~)(v;(`('~ + ; ''''```` `: `:::|\,__,%% );`'; ~ + | _ ) / `:|`----' `-' + ______/\/~ | / / + /~;;.____/;;' / ___--,-( `;;;/ + / // _;______;'------~~~~~ /;;/\ / + // | | / ; \;;,\ + (<_ | ; /',/-----' _> + \_| ||_ //~;~~~~~~~~~ + `\_| (,~~ + \~\ + ~~ + */ +})(); +``` + + +## API + +The methods returns a promise that resolves when the `end` event fires on the stream, indicating that there is no more data to be read. The stream is switched to flowing mode. + +### getStream(stream, [options]) + +Get the `stream` as a string. + +#### options + +Type: `Object` + +##### encoding + +Type: `string`<br> +Default: `utf8` + +[Encoding](https://nodejs.org/api/buffer.html#buffer_buffer) of the incoming stream. + +##### maxBuffer + +Type: `number`<br> +Default: `Infinity` + +Maximum length of the returned string. If it exceeds this value before the stream ends, the promise will be rejected with a `getStream.MaxBufferError` error. + +### getStream.buffer(stream, [options]) + +Get the `stream` as a buffer. + +It honors the `maxBuffer` option as above, but it refers to byte length rather than string length. + +### getStream.array(stream, [options]) + +Get the `stream` as an array of values. + +It honors both the `maxBuffer` and `encoding` options. The behavior changes slightly based on the encoding chosen: + +- When `encoding` is unset, it assumes an [object mode stream](https://nodesource.com/blog/understanding-object-streams/) and collects values emitted from `stream` unmodified. In this case `maxBuffer` refers to the number of items in the array (not the sum of their sizes). + +- When `encoding` is set to `buffer`, it collects an array of buffers. `maxBuffer` refers to the summed byte lengths of every buffer in the array. + +- When `encoding` is set to anything else, it collects an array of strings. `maxBuffer` refers to the summed character lengths of every string in the array. + + +## Errors + +If the input stream emits an `error` event, the promise will be rejected with the error. The buffered data will be attached to the `bufferedData` property of the error. + +```js +(async () => { + try { + await getStream(streamThatErrorsAtTheEnd('unicorn')); + } catch (error) { + console.log(error.bufferedData); + //=> 'unicorn' + } +})() +``` + + +## FAQ + +### How is this different from [`concat-stream`](https://github.com/maxogden/concat-stream)? + +This module accepts a stream instead of being one and returns a promise instead of using a callback. The API is simpler and it only supports returning a string, buffer, or array. It doesn't have a fragile type inference. You explicitly choose what you want. And it doesn't depend on the huge `readable-stream` package. + + +## Related + +- [get-stdin](https://github.com/sindresorhus/get-stdin) - Get stdin as a string or buffer + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/got/license b/node_modules/got/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/got/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/got/package.json b/node_modules/got/package.json new file mode 100644 index 0000000..f2bef85 --- /dev/null +++ b/node_modules/got/package.json @@ -0,0 +1,74 @@ +{ + "name": "got", + "version": "9.6.0", + "description": "Simplified HTTP requests", + "license": "MIT", + "repository": "sindresorhus/got", + "main": "source", + "engines": { + "node": ">=8.6" + }, + "scripts": { + "test": "xo && nyc ava", + "release": "np" + }, + "files": [ + "source" + ], + "keywords": [ + "http", + "https", + "get", + "got", + "url", + "uri", + "request", + "util", + "utility", + "simple", + "curl", + "wget", + "fetch", + "net", + "network", + "electron" + ], + "dependencies": { + "@sindresorhus/is": "^0.14.0", + "@szmarczak/http-timer": "^1.1.2", + "cacheable-request": "^6.0.0", + "decompress-response": "^3.3.0", + "duplexer3": "^0.1.4", + "get-stream": "^4.1.0", + "lowercase-keys": "^1.0.1", + "mimic-response": "^1.0.1", + "p-cancelable": "^1.0.0", + "to-readable-stream": "^1.0.0", + "url-parse-lax": "^3.0.0" + }, + "devDependencies": { + "ava": "^1.1.0", + "coveralls": "^3.0.0", + "delay": "^4.1.0", + "form-data": "^2.3.3", + "get-port": "^4.0.0", + "np": "^3.1.0", + "nyc": "^13.1.0", + "p-event": "^2.1.0", + "pem": "^1.13.2", + "proxyquire": "^2.0.1", + "sinon": "^7.2.2", + "slow-stream": "0.0.4", + "tempfile": "^2.0.0", + "tempy": "^0.2.1", + "tough-cookie": "^3.0.0", + "xo": "^0.24.0" + }, + "ava": { + "concurrency": 4 + }, + "browser": { + "decompress-response": false, + "electron": false + } +} diff --git a/node_modules/got/readme.md b/node_modules/got/readme.md new file mode 100644 index 0000000..37132ab --- /dev/null +++ b/node_modules/got/readme.md @@ -0,0 +1,1237 @@ +<div align="center"> + <br> + <br> + <img width="360" src="media/logo.svg" alt="Got"> + <br> + <br> + <br> + <p align="center">Huge thanks to <a href="https://moxy.studio"><img src="https://sindresorhus.com/assets/thanks/moxy-logo.svg" width="150"></a> for sponsoring me! + </p> + <br> + <br> +</div> + +> Simplified HTTP requests + +[![Build Status: Linux](https://travis-ci.org/sindresorhus/got.svg?branch=master)](https://travis-ci.org/sindresorhus/got) [![Coverage Status](https://coveralls.io/repos/github/sindresorhus/got/badge.svg?branch=master)](https://coveralls.io/github/sindresorhus/got?branch=master) [![Downloads](https://img.shields.io/npm/dm/got.svg)](https://npmjs.com/got) [![Install size](https://packagephobia.now.sh/badge?p=got)](https://packagephobia.now.sh/result?p=got) + +Got is a human-friendly and powerful HTTP request library. + +It was created because the popular [`request`](https://github.com/request/request) package is bloated: [![Install size](https://packagephobia.now.sh/badge?p=request)](https://packagephobia.now.sh/result?p=request) + +Got is for Node.js. For browsers, we recommend [Ky](https://github.com/sindresorhus/ky). + + +## Highlights + +- [Promise & stream API](#api) +- [Request cancelation](#aborting-the-request) +- [RFC compliant caching](#cache-adapters) +- [Follows redirects](#followredirect) +- [Retries on failure](#retry) +- [Progress events](#onuploadprogress-progress) +- [Handles gzip/deflate](#decompress) +- [Timeout handling](#timeout) +- [Errors with metadata](#errors) +- [JSON mode](#json) +- [WHATWG URL support](#url) +- [Hooks](#hooks) +- [Instances with custom defaults](#instances) +- [Composable](advanced-creation.md#merging-instances) +- [Electron support](#useelectronnet) +- [Used by ~2000 packages and ~500K repos](https://github.com/sindresorhus/got/network/dependents) +- Actively maintained + +[Moving from Request?](migration-guides.md) + +[See how Got compares to other HTTP libraries](#comparison) + +## Install + +``` +$ npm install got +``` + +<a href="https://www.patreon.com/sindresorhus"> + <img src="https://c5.patreon.com/external/logo/become_a_patron_button@2x.png" width="160"> +</a> + + +## Usage + +```js +const got = require('got'); + +(async () => { + try { + const response = await got('sindresorhus.com'); + console.log(response.body); + //=> '<!doctype html> ...' + } catch (error) { + console.log(error.response.body); + //=> 'Internal server error ...' + } +})(); +``` + +###### Streams + +```js +const fs = require('fs'); +const got = require('got'); + +got.stream('sindresorhus.com').pipe(fs.createWriteStream('index.html')); + +// For POST, PUT, and PATCH methods `got.stream` returns a `stream.Writable` +fs.createReadStream('index.html').pipe(got.stream.post('sindresorhus.com')); +``` + + +### API + +It's a `GET` request by default, but can be changed by using different methods or in the `options`. + +#### got(url, [options]) + +Returns a Promise for a [`response` object](#response) or a [stream](#streams-1) if `options.stream` is set to true. + +##### url + +Type: `string` `Object` + +The URL to request, as a string, a [`https.request` options object](https://nodejs.org/api/https.html#https_https_request_options_callback), or a [WHATWG `URL`](https://nodejs.org/api/url.html#url_class_url). + +Properties from `options` will override properties in the parsed `url`. + +If no protocol is specified, it will default to `https`. + +##### options + +Type: `Object` + +Any of the [`https.request`](https://nodejs.org/api/https.html#https_https_request_options_callback) options. + +###### baseUrl + +Type: `string` `Object` + +When specified, `url` will be prepended by `baseUrl`.<br> +If you specify an absolute URL, it will skip the `baseUrl`. + +Very useful when used with `got.extend()` to create niche-specific Got instances. + +Can be a string or a [WHATWG `URL`](https://nodejs.org/api/url.html#url_class_url). + +Slash at the end of `baseUrl` and at the beginning of the `url` argument is optional: + +```js +await got('hello', {baseUrl: 'https://example.com/v1'}); +//=> 'https://example.com/v1/hello' + +await got('/hello', {baseUrl: 'https://example.com/v1/'}); +//=> 'https://example.com/v1/hello' + +await got('/hello', {baseUrl: 'https://example.com/v1'}); +//=> 'https://example.com/v1/hello' +``` + +###### headers + +Type: `Object`<br> +Default: `{}` + +Request headers. + +Existing headers will be overwritten. Headers set to `null` will be omitted. + +###### stream + +Type: `boolean`<br> +Default: `false` + +Returns a `Stream` instead of a `Promise`. This is equivalent to calling `got.stream(url, [options])`. + +###### body + +Type: `string` `Buffer` `stream.Readable` [`form-data` instance](https://github.com/form-data/form-data) + +**Note:** If you provide this option, `got.stream()` will be read-only. + +The body that will be sent with a `POST` request. + +If present in `options` and `options.method` is not set, `options.method` will be set to `POST`. + +The `content-length` header will be automatically set if `body` is a `string` / `Buffer` / `fs.createReadStream` instance / [`form-data` instance](https://github.com/form-data/form-data), and `content-length` and `transfer-encoding` are not manually set in `options.headers`. + +###### cookieJar + +Type: [`tough.CookieJar` instance](https://github.com/salesforce/tough-cookie#cookiejar) + +**Note:** If you provide this option, `options.headers.cookie` will be overridden. + +Cookie support. You don't have to care about parsing or how to store them. [Example.](#cookies) + +###### encoding + +Type: `string` `null`<br> +Default: `'utf8'` + +[Encoding](https://nodejs.org/api/buffer.html#buffer_buffers_and_character_encodings) to be used on `setEncoding` of the response data. If `null`, the body is returned as a [`Buffer`](https://nodejs.org/api/buffer.html) (binary data). + +###### form + +Type: `boolean`<br> +Default: `false` + +**Note:** If you provide this option, `got.stream()` will be read-only. +**Note:** `body` must be a plain object. It will be converted to a query string using [`(new URLSearchParams(object)).toString()`](https://nodejs.org/api/url.html#url_constructor_new_urlsearchparams_obj). + +If set to `true` and `Content-Type` header is not set, it will be set to `application/x-www-form-urlencoded`. + +###### json + +Type: `boolean`<br> +Default: `false` + +**Note:** If you use `got.stream()`, this option will be ignored. +**Note:** `body` must be a plain object or array and will be stringified. + +If set to `true` and `Content-Type` header is not set, it will be set to `application/json`. + +Parse response body with `JSON.parse` and set `accept` header to `application/json`. If used in conjunction with the `form` option, the `body` will the stringified as querystring and the response parsed as JSON. + +###### query + +Type: `string` `Object<string, string|number>` [`URLSearchParams`](https://developer.mozilla.org/en-US/docs/Web/API/URLSearchParams) + +Query string that will be added to the request URL. This will override the query string in `url`. + +If you need to pass in an array, you can do it using a `URLSearchParams` instance: + +```js +const got = require('got'); + +const query = new URLSearchParams([['key', 'a'], ['key', 'b']]); + +got('https://example.com', {query}); + +console.log(query.toString()); +//=> 'key=a&key=b' +``` + +And if you need a different array format, you could use the [`query-string`](https://github.com/sindresorhus/query-string) package: + +```js +const got = require('got'); +const queryString = require('query-string'); + +const query = queryString.stringify({key: ['a', 'b']}, {arrayFormat: 'bracket'}); + +got('https://example.com', {query}); + +console.log(query); +//=> 'key[]=a&key[]=b' +``` + +###### timeout + +Type: `number` `Object` + +Milliseconds to wait for the server to end the response before aborting the request with [`got.TimeoutError`](#gottimeouterror) error (a.k.a. `request` property). By default, there's no timeout. + +This also accepts an `object` with the following fields to constrain the duration of each phase of the request lifecycle: + +- `lookup` starts when a socket is assigned and ends when the hostname has been resolved. Does not apply when using a Unix domain socket. +- `connect` starts when `lookup` completes (or when the socket is assigned if lookup does not apply to the request) and ends when the socket is connected. +- `secureConnect` starts when `connect` completes and ends when the handshaking process completes (HTTPS only). +- `socket` starts when the socket is connected. See [request.setTimeout](https://nodejs.org/api/http.html#http_request_settimeout_timeout_callback). +- `response` starts when the request has been written to the socket and ends when the response headers are received. +- `send` starts when the socket is connected and ends with the request has been written to the socket. +- `request` starts when the request is initiated and ends when the response's end event fires. + +###### retry + +Type: `number` `Object`<br> +Default: +- retries: `2` +- methods: `GET` `PUT` `HEAD` `DELETE` `OPTIONS` `TRACE` +- statusCodes: [`408`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/408) [`413`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/413) [`429`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/429) [`500`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/500) [`502`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/502) [`503`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/503) [`504`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/504) +- maxRetryAfter: `undefined` +- errorCodes: `ETIMEDOUT` `ECONNRESET` `EADDRINUSE` `ECONNREFUSED` `EPIPE` `ENOTFOUND` `ENETUNREACH` `EAI_AGAIN` + +An object representing `retries`, `methods`, `statusCodes`, `maxRetryAfter` and `errorCodes` fields for the time until retry, allowed methods, allowed status codes, maximum [`Retry-After`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Retry-After) time and allowed error codes. + +If `maxRetryAfter` is set to `undefined`, it will use `options.timeout`.<br> +If [`Retry-After`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Retry-After) header is greater than `maxRetryAfter`, it will cancel the request. + +Delays between retries counts with function `1000 * Math.pow(2, retry) + Math.random() * 100`, where `retry` is attempt number (starts from 1). + +The `retries` property can be a `number` or a `function` with `retry` and `error` arguments. The function must return a delay in milliseconds (`0` return value cancels retry). + +By default, it retries *only* on the specified methods, status codes, and on these network errors: +- `ETIMEDOUT`: One of the [timeout](#timeout) limits were reached. +- `ECONNRESET`: Connection was forcibly closed by a peer. +- `EADDRINUSE`: Could not bind to any free port. +- `ECONNREFUSED`: Connection was refused by the server. +- `EPIPE`: The remote side of the stream being written has been closed. +- `ENOTFOUND`: Couldn't resolve the hostname to an IP address. +- `ENETUNREACH`: No internet connection. +- `EAI_AGAIN`: DNS lookup timed out. + +###### followRedirect + +Type: `boolean`<br> +Default: `true` + +Defines if redirect responses should be followed automatically. + +Note that if a `303` is sent by the server in response to any request type (`POST`, `DELETE`, etc.), Got will automatically request the resource pointed to in the location header via `GET`. This is in accordance with [the spec](https://tools.ietf.org/html/rfc7231#section-6.4.4). + +###### decompress + +Type: `boolean`<br> +Default: `true` + +Decompress the response automatically. This will set the `accept-encoding` header to `gzip, deflate` unless you set it yourself. + +If this is disabled, a compressed response is returned as a `Buffer`. This may be useful if you want to handle decompression yourself or stream the raw compressed data. + +###### cache + +Type: `Object`<br> +Default: `false` + +[Cache adapter instance](#cache-adapters) for storing cached data. + +###### request + +Type: `Function`<br> +Default: `http.request` `https.request` *(depending on the protocol)* + +Custom request function. The main purpose of this is to [support HTTP2 using a wrapper](#experimental-http2-support). + +###### useElectronNet + +Type: `boolean`<br> +Default: `false` + +When used in Electron, Got will use [`electron.net`](https://electronjs.org/docs/api/net/) instead of the Node.js `http` module. According to the Electron docs, it should be fully compatible, but it's not entirely. See [#443](https://github.com/sindresorhus/got/issues/443) and [#461](https://github.com/sindresorhus/got/issues/461). + +###### throwHttpErrors + +Type: `boolean`<br> +Default: `true` + +Determines if a `got.HTTPError` is thrown for error responses (non-2xx status codes). + +If this is disabled, requests that encounter an error status code will be resolved with the `response` instead of throwing. This may be useful if you are checking for resource availability and are expecting error responses. + +###### agent + +Same as the [`agent` option](https://nodejs.org/api/http.html#http_http_request_url_options_callback) for `http.request`, but with an extra feature: + +If you require different agents for different protocols, you can pass a map of agents to the `agent` option. This is necessary because a request to one protocol might redirect to another. In such a scenario, Got will switch over to the right protocol agent for you. + +```js +const got = require('got'); +const HttpAgent = require('agentkeepalive'); +const {HttpsAgent} = HttpAgent; + +got('sindresorhus.com', { + agent: { + http: new HttpAgent(), + https: new HttpsAgent() + } +}); +``` + +###### hooks + +Type: `Object<string, Function[]>` + +Hooks allow modifications during the request lifecycle. Hook functions may be async and are run serially. + +###### hooks.init + +Type: `Function[]`<br> +Default: `[]` + +Called with plain [request options](#options), right before their normalization. This is especially useful in conjunction with [`got.extend()`](#instances) and [`got.create()`](advanced-creation.md) when the input needs custom handling. + +See the [Request migration guide](migration-guides.md#breaking-changes) for an example. + +**Note**: This hook must be synchronous! + +###### hooks.beforeRequest + +Type: `Function[]`<br> +Default: `[]` + +Called with [normalized](source/normalize-arguments.js) [request options](#options). Got will make no further changes to the request before it is sent. This is especially useful in conjunction with [`got.extend()`](#instances) and [`got.create()`](advanced-creation.md) when you want to create an API client that, for example, uses HMAC-signing. + +See the [AWS section](#aws) for an example. + +**Note:** If you modify the `body` you will need to modify the `content-length` header too, because it has already been computed and assigned. + +###### hooks.beforeRedirect + +Type: `Function[]`<br> +Default: `[]` + +Called with [normalized](source/normalize-arguments.js) [request options](#options). Got will make no further changes to the request. This is especially useful when you want to avoid dead sites. Example: + +```js +const got = require('got'); + +got('example.com', { + hooks: { + beforeRedirect: [ + options => { + if (options.hostname === 'deadSite') { + options.hostname = 'fallbackSite'; + } + } + ] + } +}); +``` + +###### hooks.beforeRetry + +Type: `Function[]`<br> +Default: `[]` + +Called with [normalized](source/normalize-arguments.js) [request options](#options), the error and the retry count. Got will make no further changes to the request. This is especially useful when some extra work is required before the next try. Example: + +```js +const got = require('got'); + +got('example.com', { + hooks: { + beforeRetry: [ + (options, error, retryCount) => { + if (error.statusCode === 413) { // Payload too large + options.body = getNewBody(); + } + } + ] + } +}); +``` + +###### hooks.afterResponse + +Type: `Function[]`<br> +Default: `[]` + +Called with [response object](#response) and a retry function. + +Each function should return the response. This is especially useful when you want to refresh an access token. Example: + +```js +const got = require('got'); + +const instance = got.extend({ + hooks: { + afterResponse: [ + (response, retryWithMergedOptions) => { + if (response.statusCode === 401) { // Unauthorized + const updatedOptions = { + headers: { + token: getNewToken() // Refresh the access token + } + }; + + // Save for further requests + instance.defaults.options = got.mergeOptions(instance.defaults.options, updatedOptions); + + // Make a new retry + return retryWithMergedOptions(updatedOptions); + } + + // No changes otherwise + return response; + } + ] + }, + mutableDefaults: true +}); +``` + +###### hooks.beforeError + +Type: `Function[]`<br> +Default: `[]` + +Called with an `Error` instance. The error is passed to the hook right before it's thrown. This is especially useful when you want to have more detailed errors. + +**Note**: Errors thrown while normalizing input options are thrown directly and not part of this hook. + +```js +const got = require('got'); + +got('api.github.com/some-endpoint', { + hooks: { + onError: [ + error => { + const {response} = error; + if (response && response.body) { + error.name = 'GitHubError'; + error.message = `${response.body.message} (${error.statusCode})`; + } + + return error; + } + ] + } +}); +``` + +#### Response + +The response object will typically be a [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage), however, if returned from the cache it will be a [response-like object](https://github.com/lukechilds/responselike) which behaves in the same way. + +##### request + +Type: `Object` + +**Note:** This is not a [http.ClientRequest](https://nodejs.org/api/http.html#http_class_http_clientrequest). + +- `gotOptions` - The options that were set on this request. + +##### body + +Type: `string` `Object` *(depending on `options.json`)* + +The result of the request. + +##### url + +Type: `string` + +The request URL or the final URL after redirects. + +##### requestUrl + +Type: `string` + +The original request URL. + +##### timings + +Type: `Object` + +The object contains the following properties: + +- `start` - Time when the request started. +- `socket` - Time when a socket was assigned to the request. +- `lookup` - Time when the DNS lookup finished. +- `connect` - Time when the socket successfully connected. +- `upload` - Time when the request finished uploading. +- `response` - Time when the request fired the `response` event. +- `end` - Time when the response fired the `end` event. +- `error` - Time when the request fired the `error` event. +- `phases` + - `wait` - `timings.socket - timings.start` + - `dns` - `timings.lookup - timings.socket` + - `tcp` - `timings.connect - timings.lookup` + - `request` - `timings.upload - timings.connect` + - `firstByte` - `timings.response - timings.upload` + - `download` - `timings.end - timings.response` + - `total` - `timings.end - timings.start` or `timings.error - timings.start` + +**Note:** The time is a `number` representing the milliseconds elapsed since the UNIX epoch. + +##### fromCache + +Type: `boolean` + +Whether the response was retrieved from the cache. + +##### redirectUrls + +Type: `Array` + +The redirect URLs. + +##### retryCount + +Type: `number` + +The number of times the request was retried. + +#### Streams + +**Note:** Progress events, redirect events and request/response events can also be used with promises. + +#### got.stream(url, [options]) + +Sets `options.stream` to `true`. + +Returns a [duplex stream](https://nodejs.org/api/stream.html#stream_class_stream_duplex) with additional events: + +##### .on('request', request) + +`request` event to get the request object of the request. + +**Tip:** You can use `request` event to abort request: + +```js +got.stream('github.com') + .on('request', request => setTimeout(() => request.abort(), 50)); +``` + +##### .on('response', response) + +The `response` event to get the response object of the final request. + +##### .on('redirect', response, nextOptions) + +The `redirect` event to get the response object of a redirect. The second argument is options for the next request to the redirect location. + +##### .on('uploadProgress', progress) +##### .on('downloadProgress', progress) + +Progress events for uploading (sending a request) and downloading (receiving a response). The `progress` argument is an object like: + +```js +{ + percent: 0.1, + transferred: 1024, + total: 10240 +} +``` + +If it's not possible to retrieve the body size (can happen when streaming), `total` will be `null`. + +```js +(async () => { + const response = await got('sindresorhus.com') + .on('downloadProgress', progress => { + // Report download progress + }) + .on('uploadProgress', progress => { + // Report upload progress + }); + + console.log(response); +})(); +``` + +##### .on('error', error, body, response) + +The `error` event emitted in case of a protocol error (like `ENOTFOUND` etc.) or status error (4xx or 5xx). The second argument is the body of the server response in case of status error. The third argument is a response object. + +#### got.get(url, [options]) +#### got.post(url, [options]) +#### got.put(url, [options]) +#### got.patch(url, [options]) +#### got.head(url, [options]) +#### got.delete(url, [options]) + +Sets `options.method` to the method name and makes a request. + +### Instances + +#### got.extend([options]) + +Configure a new `got` instance with default `options`. The `options` are merged with the parent instance's `defaults.options` using [`got.mergeOptions`](#gotmergeoptionsparentoptions-newoptions). You can access the resolved options with the `.defaults` property on the instance. + +```js +const client = got.extend({ + baseUrl: 'https://example.com', + headers: { + 'x-unicorn': 'rainbow' + } +}); + +client.get('/demo'); + +/* HTTP Request => + * GET /demo HTTP/1.1 + * Host: example.com + * x-unicorn: rainbow + */ +``` + +```js +(async () => { + const client = got.extend({ + baseUrl: 'httpbin.org', + headers: { + 'x-foo': 'bar' + } + }); + const {headers} = (await client.get('/headers', {json: true})).body; + //=> headers['x-foo'] === 'bar' + + const jsonClient = client.extend({ + json: true, + headers: { + 'x-baz': 'qux' + } + }); + const {headers: headers2} = (await jsonClient.get('/headers')).body; + //=> headers2['x-foo'] === 'bar' + //=> headers2['x-baz'] === 'qux' +})(); +``` + +**Tip:** Need more control over the behavior of Got? Check out the [`got.create()`](advanced-creation.md). + +#### got.mergeOptions(parentOptions, newOptions) + +Extends parent options. Avoid using [object spread](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Spread_syntax#Spread_in_object_literals) as it doesn't work recursively: + +```js +const a = {headers: {cat: 'meow', wolf: ['bark', 'wrrr']}}; +const b = {headers: {cow: 'moo', wolf: ['auuu']}}; + +{...a, ...b} // => {headers: {cow: 'moo', wolf: ['auuu']}} +got.mergeOptions(a, b) // => {headers: {cat: 'meow', cow: 'moo', wolf: ['auuu']}} +``` + +Options are deeply merged to a new object. The value of each key is determined as follows: + +- If the new property is set to `undefined`, it keeps the old one. +- If the parent property is an instance of `URL` and the new value is a `string` or `URL`, a new URL instance is created: [`new URL(new, parent)`](https://developer.mozilla.org/en-US/docs/Web/API/URL/URL#Syntax). +- If the new property is a plain `Object`: + - If the parent property is a plain `Object` too, both values are merged recursively into a new `Object`. + - Otherwise, only the new value is deeply cloned. +- If the new property is an `Array`, it overwrites the old one with a deep clone of the new property. +- Otherwise, the new value is assigned to the key. + +#### got.defaults + +Type: `Object` + +The default Got options. + +## Errors + +Each error contains `host`, `hostname`, `method`, `path`, `protocol`, `url` and `gotOptions` properties to make debugging easier. + +In Promise mode, the `response` is attached to the error. + +#### got.CacheError + +When a cache method fails, for example, if the database goes down or there's a filesystem error. + +#### got.RequestError + +When a request fails. Contains a `code` property with error class code, like `ECONNREFUSED`. + +#### got.ReadError + +When reading from response stream fails. + +#### got.ParseError + +When `json` option is enabled, server response code is 2xx, and `JSON.parse` fails. Includes `statusCode` and `statusMessage` properties. + +#### got.HTTPError + +When the server response code is not 2xx. Includes `body`, `statusCode`, `statusMessage`, and `redirectUrls` properties. + +#### got.MaxRedirectsError + +When the server redirects you more than ten times. Includes a `statusCode`, `statusMessage`, and `redirectUrls` property which is an array of the URLs Got was redirected to before giving up. + +#### got.UnsupportedProtocolError + +When given an unsupported protocol. + +#### got.CancelError + +When the request is aborted with `.cancel()`. + +#### got.TimeoutError + +When the request is aborted due to a [timeout](#timeout). Includes an `event` property. + +## Aborting the request + +The promise returned by Got has a [`.cancel()`](https://github.com/sindresorhus/p-cancelable) method which when called, aborts the request. + +```js +(async () => { + const request = got(url, options); + + // … + + // In another part of the code + if (something) { + request.cancel(); + } + + // … + + try { + await request; + } catch (error) { + if (request.isCanceled) { // Or `error instanceof got.CancelError` + // Handle cancelation + } + + // Handle other errors + } +})(); +``` + +<a name="cache-adapters"></a> +## Cache + +Got implements [RFC 7234](http://httpwg.org/specs/rfc7234.html) compliant HTTP caching which works out of the box in-memory and is easily pluggable with a wide range of storage adapters. Fresh cache entries are served directly from the cache, and stale cache entries are revalidated with `If-None-Match`/`If-Modified-Since` headers. You can read more about the underlying cache behavior in the [`cacheable-request` documentation](https://github.com/lukechilds/cacheable-request). + +You can use the JavaScript `Map` type as an in-memory cache: + +```js +const got = require('got'); +const map = new Map(); + +(async () => { + let response = await got('sindresorhus.com', {cache: map}); + console.log(response.fromCache); + //=> false + + response = await got('sindresorhus.com', {cache: map}); + console.log(response.fromCache); + //=> true +})(); +``` + +Got uses [Keyv](https://github.com/lukechilds/keyv) internally to support a wide range of storage adapters. For something more scalable you could use an [official Keyv storage adapter](https://github.com/lukechilds/keyv#official-storage-adapters): + +``` +$ npm install @keyv/redis +``` + +```js +const got = require('got'); +const KeyvRedis = require('@keyv/redis'); + +const redis = new KeyvRedis('redis://user:pass@localhost:6379'); + +got('sindresorhus.com', {cache: redis}); +``` + +Got supports anything that follows the Map API, so it's easy to write your own storage adapter or use a third-party solution. + +For example, the following are all valid storage adapters: + +```js +const storageAdapter = new Map(); +// Or +const storageAdapter = require('./my-storage-adapter'); +// Or +const QuickLRU = require('quick-lru'); +const storageAdapter = new QuickLRU({maxSize: 1000}); + +got('sindresorhus.com', {cache: storageAdapter}); +``` + +View the [Keyv docs](https://github.com/lukechilds/keyv) for more information on how to use storage adapters. + + +## Proxies + +You can use the [`tunnel`](https://github.com/koichik/node-tunnel) package with the `agent` option to work with proxies: + +```js +const got = require('got'); +const tunnel = require('tunnel'); + +got('sindresorhus.com', { + agent: tunnel.httpOverHttp({ + proxy: { + host: 'localhost' + } + }) +}); +``` + +Check out [`global-tunnel`](https://github.com/np-maintain/global-tunnel) if you want to configure proxy support for all HTTP/HTTPS traffic in your app. + + +## Cookies + +You can use the [`tough-cookie`](https://github.com/salesforce/tough-cookie) package: + +```js +const got = require('got'); +const {CookieJar} = require('tough-cookie'); + +const cookieJar = new CookieJar(); +cookieJar.setCookie('foo=bar', 'https://www.google.com'); + +got('google.com', {cookieJar}); +``` + + +## Form data + +You can use the [`form-data`](https://github.com/form-data/form-data) package to create POST request with form data: + +```js +const fs = require('fs'); +const got = require('got'); +const FormData = require('form-data'); +const form = new FormData(); + +form.append('my_file', fs.createReadStream('/foo/bar.jpg')); + +got.post('google.com', { + body: form +}); +``` + + +## OAuth + +You can use the [`oauth-1.0a`](https://github.com/ddo/oauth-1.0a) package to create a signed OAuth request: + +```js +const got = require('got'); +const crypto = require('crypto'); +const OAuth = require('oauth-1.0a'); + +const oauth = OAuth({ + consumer: { + key: process.env.CONSUMER_KEY, + secret: process.env.CONSUMER_SECRET + }, + signature_method: 'HMAC-SHA1', + hash_function: (baseString, key) => crypto.createHmac('sha1', key).update(baseString).digest('base64') +}); + +const token = { + key: process.env.ACCESS_TOKEN, + secret: process.env.ACCESS_TOKEN_SECRET +}; + +const url = 'https://api.twitter.com/1.1/statuses/home_timeline.json'; + +got(url, { + headers: oauth.toHeader(oauth.authorize({url, method: 'GET'}, token)), + json: true +}); +``` + + +## Unix Domain Sockets + +Requests can also be sent via [unix domain sockets](http://serverfault.com/questions/124517/whats-the-difference-between-unix-socket-and-tcp-ip-socket). Use the following URL scheme: `PROTOCOL://unix:SOCKET:PATH`. + +- `PROTOCOL` - `http` or `https` *(optional)* +- `SOCKET` - Absolute path to a unix domain socket, for example: `/var/run/docker.sock` +- `PATH` - Request path, for example: `/v2/keys` + +```js +got('http://unix:/var/run/docker.sock:/containers/json'); + +// Or without protocol (HTTP by default) +got('unix:/var/run/docker.sock:/containers/json'); +``` + + +## AWS + +Requests to AWS services need to have their headers signed. This can be accomplished by using the [`aws4`](https://www.npmjs.com/package/aws4) package. This is an example for querying an ["API Gateway"](https://docs.aws.amazon.com/apigateway/api-reference/signing-requests/) with a signed request. + +```js +const AWS = require('aws-sdk'); +const aws4 = require('aws4'); +const got = require('got'); + +const chain = new AWS.CredentialProviderChain(); + +// Create a Got instance to use relative paths and signed requests +const awsClient = got.extend({ + baseUrl: 'https://<api-id>.execute-api.<api-region>.amazonaws.com/<stage>/', + hooks: { + beforeRequest: [ + async options => { + const credentials = await chain.resolvePromise(); + aws4.sign(options, credentials); + } + ] + } +}); + +const response = await awsClient('endpoint/path', { + // Request-specific options +}); +``` + + +## Testing + +You can test your requests by using the [`nock`](https://github.com/node-nock/nock) package to mock an endpoint: + +```js +const got = require('got'); +const nock = require('nock'); + +nock('https://sindresorhus.com') + .get('/') + .reply(200, 'Hello world!'); + +(async () => { + const response = await got('sindresorhus.com'); + console.log(response.body); + //=> 'Hello world!' +})(); +``` + +If you need real integration tests you can use [`create-test-server`](https://github.com/lukechilds/create-test-server): + +```js +const got = require('got'); +const createTestServer = require('create-test-server'); + +(async () => { + const server = await createTestServer(); + server.get('/', 'Hello world!'); + + const response = await got(server.url); + console.log(response.body); + //=> 'Hello world!' + + await server.close(); +})(); +``` + + +## Tips + +### User Agent + +It's a good idea to set the `'user-agent'` header so the provider can more easily see how their resource is used. By default, it's the URL to this repo. You can omit this header by setting it to `null`. + +```js +const got = require('got'); +const pkg = require('./package.json'); + +got('sindresorhus.com', { + headers: { + 'user-agent': `my-package/${pkg.version} (https://github.com/username/my-package)` + } +}); + +got('sindresorhus.com', { + headers: { + 'user-agent': null + } +}); +``` + +### 304 Responses + +Bear in mind; if you send an `if-modified-since` header and receive a `304 Not Modified` response, the body will be empty. It's your responsibility to cache and retrieve the body contents. + +### Custom endpoints + +Use `got.extend()` to make it nicer to work with REST APIs. Especially if you use the `baseUrl` option. + +**Note:** Not to be confused with [`got.create()`](advanced-creation.md), which has no defaults. + +```js +const got = require('got'); +const pkg = require('./package.json'); + +const custom = got.extend({ + baseUrl: 'example.com', + json: true, + headers: { + 'user-agent': `my-package/${pkg.version} (https://github.com/username/my-package)` + } +}); + +// Use `custom` exactly how you use `got` +(async () => { + const list = await custom('/v1/users/list'); +})(); +``` + +**Tip:** Need to merge some instances into a single one? Check out [`got.mergeInstances()`](advanced-creation.md#merging-instances). + +### Experimental HTTP2 support + +Got provides an experimental support for HTTP2 using the [`http2-wrapper`](https://github.com/szmarczak/http2-wrapper) package: + +```js +const got = require('got'); +const {request} = require('http2-wrapper'); + +const h2got = got.extend({request}); + +(async () => { + const {body} = await h2got('https://nghttp2.org/httpbin/headers'); + console.log(body); +})(); +``` + +## Comparison + +| | `got` | [`request`][r0] | [`node-fetch`][n0] | [`axios`][a0] | [`superagent`][s0] | +|-----------------------|:--------------:|:---------------:|:------------------:|:---------------:|:--------------------:| +| HTTP/2 support | ❔ | ✖ | ✖ | ✖ | ✔\*\* | +| Browser support | ✖ | ✖ | ✔\* | ✔ | ✔ | +| Electron support | ✔ | ✖ | ✖ | ✖ | ✖ | +| Promise API | ✔ | ✔ | ✔ | ✔ | ✔ | +| Stream API | ✔ | ✔ | Node.js only | ✖ | ✔ | +| Request cancelation | ✔ | ✖ | ✔ | ✔ | ✔ | +| RFC compliant caching | ✔ | ✖ | ✖ | ✖ | ✖ | +| Cookies (out-of-box) | ✔ | ✔ | ✖ | ✖ | ✖ | +| Follows redirects | ✔ | ✔ | ✔ | ✔ | ✔ | +| Retries on failure | ✔ | ✖ | ✖ | ✖ | ✔ | +| Progress events | ✔ | ✖ | ✖ | Browser only | ✔ | +| Handles gzip/deflate | ✔ | ✔ | ✔ | ✔ | ✔ | +| Advanced timeouts | ✔ | ✖ | ✖ | ✖ | ✖ | +| Timings | ✔ | ✔ | ✖ | ✖ | ✖ | +| Errors with metadata | ✔ | ✖ | ✖ | ✔ | ✖ | +| JSON mode | ✔ | ✔ | ✖ | ✔ | ✔ | +| Custom defaults | ✔ | ✔ | ✖ | ✔ | ✖ | +| Composable | ✔ | ✖ | ✖ | ✖ | ✔ | +| Hooks | ✔ | ✖ | ✖ | ✔ | ✖ | +| Issues open | [![][gio]][g1] | [![][rio]][r1] | [![][nio]][n1] | [![][aio]][a1] | [![][sio]][s1] | +| Issues closed | [![][gic]][g2] | [![][ric]][r2] | [![][nic]][n2] | [![][aic]][a2] | [![][sic]][s2] | +| Downloads | [![][gd]][g3] | [![][rd]][r3] | [![][nd]][n3] | [![][ad]][a3] | [![][sd]][s3] | +| Coverage | [![][gc]][g4] | [![][rc]][r4] | [![][nc]][n4] | [![][ac]][a4] | unknown | +| Build | [![][gb]][g5] | [![][rb]][r5] | [![][nb]][n5] | [![][ab]][a5] | [![][sb]][s5] | +| Bugs | [![][gbg]][g6] | [![][rbg]][r6] | [![][nbg]][n6] | [![][abg]][a6] | [![][sbg]][s6] | +| Dependents | [![][gdp]][g7] | [![][rdp]][r7] | [![][ndp]][n7] | [![][adp]][a7] | [![][sdp]][s7] | +| Install size | [![][gis]][g8] | [![][ris]][r8] | [![][nis]][n8] | [![][ais]][a8] | [![][sis]][s8] | + +\* It's almost API compatible with the browser `fetch` API.<br> +\*\* Need to switch the protocol manually.<br> +❔ Experimental support. + +<!-- GITHUB --> +[r0]: https://github.com/request/request +[n0]: https://github.com/bitinn/node-fetch +[a0]: https://github.com/axios/axios +[s0]: https://github.com/visionmedia/superagent + +<!-- ISSUES OPEN --> +[gio]: https://badgen.net/github/open-issues/sindresorhus/got?label +[rio]: https://badgen.net/github/open-issues/request/request?label +[nio]: https://badgen.net/github/open-issues/bitinn/node-fetch?label +[aio]: https://badgen.net/github/open-issues/axios/axios?label +[sio]: https://badgen.net/github/open-issues/visionmedia/superagent?label + +[g1]: https://github.com/sindresorhus/got/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc +[r1]: https://github.com/request/request/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc +[n1]: https://github.com/bitinn/node-fetch/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc +[a1]: https://github.com/axios/axios/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc +[s1]: https://github.com/visionmedia/superagent/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc + +<!-- ISSUES CLOSED --> +[gic]: https://badgen.net/github/closed-issues/sindresorhus/got?label +[ric]: https://badgen.net/github/closed-issues/request/request?label +[nic]: https://badgen.net/github/closed-issues/bitinn/node-fetch?label +[aic]: https://badgen.net/github/closed-issues/axios/axios?label +[sic]: https://badgen.net/github/closed-issues/visionmedia/superagent?label + +[g2]: https://github.com/sindresorhus/got/issues?q=is%3Aissue+is%3Aclosed+sort%3Aupdated-desc +[r2]: https://github.com/request/request/issues?q=is%3Aissue+is%3Aclosed+sort%3Aupdated-desc +[n2]: https://github.com/bitinn/node-fetch/issues?q=is%3Aissue+is%3Aclosed+sort%3Aupdated-desc +[a2]: https://github.com/axios/axios/issues?q=is%3Aissue+is%3Aclosed+sort%3Aupdated-desc +[s2]: https://github.com/visionmedia/superagent/issues?q=is%3Aissue+is%3Aclosed+sort%3Aupdated-desc + +<!-- DOWNLOADS --> +[gd]: https://badgen.net/npm/dm/got?label +[rd]: https://badgen.net/npm/dm/request?label +[nd]: https://badgen.net/npm/dm/node-fetch?label +[ad]: https://badgen.net/npm/dm/axios?label +[sd]: https://badgen.net/npm/dm/superagent?label + +[g3]: https://www.npmjs.com/package/got +[r3]: https://www.npmjs.com/package/request +[n3]: https://www.npmjs.com/package/node-fetch +[a3]: https://www.npmjs.com/package/axios +[s3]: https://www.npmjs.com/package/superagent + +<!-- COVERAGE --> +[gc]: https://badgen.net/coveralls/c/github/sindresorhus/got?label +[rc]: https://badgen.net/coveralls/c/github/request/request?label +[nc]: https://badgen.net/coveralls/c/github/bitinn/node-fetch?label +[ac]: https://badgen.net/coveralls/c/github/mzabriskie/axios?label + +[g4]: https://coveralls.io/github/sindresorhus/got +[r4]: https://coveralls.io/github/request/request +[n4]: https://coveralls.io/github/bitinn/node-fetch +[a4]: https://coveralls.io/github/mzabriskie/axios + +<!-- BUILD --> +[gb]: https://badgen.net/travis/sindresorhus/got?label +[rb]: https://badgen.net/travis/request/request?label +[nb]: https://badgen.net/travis/bitinn/node-fetch?label +[ab]: https://badgen.net/travis/axios/axios?label +[sb]: https://badgen.net/travis/visionmedia/superagent?label + +[g5]: https://travis-ci.org/sindresorhus/got +[r5]: https://travis-ci.org/request/request +[n5]: https://travis-ci.org/bitinn/node-fetch +[a5]: https://travis-ci.org/axios/axios +[s5]: https://travis-ci.org/visionmedia/superagent + +<!-- BUGS --> +[gbg]: https://badgen.net/github/label-issues/sindresorhus/got/bug/open?label +[rbg]: https://badgen.net/github/label-issues/request/request/Needs%20investigation/open?label +[nbg]: https://badgen.net/github/label-issues/bitinn/node-fetch/bug/open?label +[abg]: https://badgen.net/github/label-issues/axios/axios/bug/open?label +[sbg]: https://badgen.net/github/label-issues/visionmedia/superagent/Bug/open?label + +[g6]: https://github.com/sindresorhus/got/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc+label%3Abug +[r6]: https://github.com/request/request/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc+label%3A"Needs+investigation" +[n6]: https://github.com/bitinn/node-fetch/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc+label%3Abug +[a6]: https://github.com/axios/axios/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc+label%3Abug +[s6]: https://github.com/visionmedia/superagent/issues?q=is%3Aissue+is%3Aopen+sort%3Aupdated-desc+label%3ABug + +<!-- DEPENDENTS --> +[gdp]: https://badgen.net/npm/dependents/got?label +[rdp]: https://badgen.net/npm/dependents/request?label +[ndp]: https://badgen.net/npm/dependents/node-fetch?label +[adp]: https://badgen.net/npm/dependents/axios?label +[sdp]: https://badgen.net/npm/dependents/superagent?label + +[g7]: https://www.npmjs.com/package/got?activeTab=dependents +[r7]: https://www.npmjs.com/package/request?activeTab=dependents +[n7]: https://www.npmjs.com/package/node-fetch?activeTab=dependents +[a7]: https://www.npmjs.com/package/axios?activeTab=dependents +[s7]: https://www.npmjs.com/package/visionmedia?activeTab=dependents + +<!-- INSTALL SIZE --> +[gis]: https://badgen.net/packagephobia/install/got?label +[ris]: https://badgen.net/packagephobia/install/request?label +[nis]: https://badgen.net/packagephobia/install/node-fetch?label +[ais]: https://badgen.net/packagephobia/install/axios?label +[sis]: https://badgen.net/packagephobia/install/superagent?label + +[g8]: https://packagephobia.now.sh/result?p=got +[r8]: https://packagephobia.now.sh/result?p=request +[n8]: https://packagephobia.now.sh/result?p=node-fetch +[a8]: https://packagephobia.now.sh/result?p=axios +[s8]: https://packagephobia.now.sh/result?p=superagent + + +## Related + +- [gh-got](https://github.com/sindresorhus/gh-got) - Got convenience wrapper to interact with the GitHub API +- [gl-got](https://github.com/singapore/gl-got) - Got convenience wrapper to interact with the GitLab API +- [travis-got](https://github.com/samverschueren/travis-got) - Got convenience wrapper to interact with the Travis API +- [graphql-got](https://github.com/kevva/graphql-got) - Got convenience wrapper to interact with GraphQL +- [GotQL](https://github.com/khaosdoctor/gotql) - Got convenience wrapper to interact with GraphQL using JSON-parsed queries instead of strings + + +## Maintainers + +[![Sindre Sorhus](https://github.com/sindresorhus.png?size=100)](https://sindresorhus.com) | [![Vsevolod Strukchinsky](https://github.com/floatdrop.png?size=100)](https://github.com/floatdrop) | [![Alexander Tesfamichael](https://github.com/AlexTes.png?size=100)](https://github.com/AlexTes) | [![Luke Childs](https://github.com/lukechilds.png?size=100)](https://github.com/lukechilds) | [![Szymon Marczak](https://github.com/szmarczak.png?size=100)](https://github.com/szmarczak) | [![Brandon Smith](https://github.com/brandon93s.png?size=100)](https://github.com/brandon93s) +---|---|---|---|---|--- +[Sindre Sorhus](https://sindresorhus.com) | [Vsevolod Strukchinsky](https://github.com/floatdrop) | [Alexander Tesfamichael](https://alextes.me) | [Luke Childs](https://github.com/lukechilds) | [Szymon Marczak](https://github.com/szmarczak) | [Brandon Smith](https://github.com/brandon93s) + + +## License + +MIT diff --git a/node_modules/got/source/as-promise.js b/node_modules/got/source/as-promise.js new file mode 100644 index 0000000..c502325 --- /dev/null +++ b/node_modules/got/source/as-promise.js @@ -0,0 +1,108 @@ +'use strict'; +const EventEmitter = require('events'); +const getStream = require('get-stream'); +const is = require('@sindresorhus/is'); +const PCancelable = require('p-cancelable'); +const requestAsEventEmitter = require('./request-as-event-emitter'); +const {HTTPError, ParseError, ReadError} = require('./errors'); +const {options: mergeOptions} = require('./merge'); +const {reNormalize} = require('./normalize-arguments'); + +const asPromise = options => { + const proxy = new EventEmitter(); + + const promise = new PCancelable((resolve, reject, onCancel) => { + const emitter = requestAsEventEmitter(options); + + onCancel(emitter.abort); + + emitter.on('response', async response => { + proxy.emit('response', response); + + const stream = is.null(options.encoding) ? getStream.buffer(response) : getStream(response, options); + + let data; + try { + data = await stream; + } catch (error) { + reject(new ReadError(error, options)); + return; + } + + const limitStatusCode = options.followRedirect ? 299 : 399; + + response.body = data; + + try { + for (const [index, hook] of Object.entries(options.hooks.afterResponse)) { + // eslint-disable-next-line no-await-in-loop + response = await hook(response, updatedOptions => { + updatedOptions = reNormalize(mergeOptions(options, { + ...updatedOptions, + retry: 0, + throwHttpErrors: false + })); + + // Remove any further hooks for that request, because we we'll call them anyway. + // The loop continues. We don't want duplicates (asPromise recursion). + updatedOptions.hooks.afterResponse = options.hooks.afterResponse.slice(0, index); + + return asPromise(updatedOptions); + }); + } + } catch (error) { + reject(error); + return; + } + + const {statusCode} = response; + + if (options.json && response.body) { + try { + response.body = JSON.parse(response.body); + } catch (error) { + if (statusCode >= 200 && statusCode < 300) { + const parseError = new ParseError(error, statusCode, options, data); + Object.defineProperty(parseError, 'response', {value: response}); + reject(parseError); + return; + } + } + } + + if (statusCode !== 304 && (statusCode < 200 || statusCode > limitStatusCode)) { + const error = new HTTPError(response, options); + Object.defineProperty(error, 'response', {value: response}); + if (emitter.retry(error) === false) { + if (options.throwHttpErrors) { + reject(error); + return; + } + + resolve(response); + } + + return; + } + + resolve(response); + }); + + emitter.once('error', reject); + [ + 'request', + 'redirect', + 'uploadProgress', + 'downloadProgress' + ].forEach(event => emitter.on(event, (...args) => proxy.emit(event, ...args))); + }); + + promise.on = (name, fn) => { + proxy.on(name, fn); + return promise; + }; + + return promise; +}; + +module.exports = asPromise; diff --git a/node_modules/got/source/as-stream.js b/node_modules/got/source/as-stream.js new file mode 100644 index 0000000..98c5342 --- /dev/null +++ b/node_modules/got/source/as-stream.js @@ -0,0 +1,93 @@ +'use strict'; +const {PassThrough} = require('stream'); +const duplexer3 = require('duplexer3'); +const requestAsEventEmitter = require('./request-as-event-emitter'); +const {HTTPError, ReadError} = require('./errors'); + +module.exports = options => { + const input = new PassThrough(); + const output = new PassThrough(); + const proxy = duplexer3(input, output); + const piped = new Set(); + let isFinished = false; + + options.retry.retries = () => 0; + + if (options.body) { + proxy.write = () => { + throw new Error('Got\'s stream is not writable when the `body` option is used'); + }; + } + + const emitter = requestAsEventEmitter(options, input); + + // Cancels the request + proxy._destroy = emitter.abort; + + emitter.on('response', response => { + const {statusCode} = response; + + response.on('error', error => { + proxy.emit('error', new ReadError(error, options)); + }); + + if (options.throwHttpErrors && statusCode !== 304 && (statusCode < 200 || statusCode > 299)) { + proxy.emit('error', new HTTPError(response, options), null, response); + return; + } + + isFinished = true; + + response.pipe(output); + + for (const destination of piped) { + if (destination.headersSent) { + continue; + } + + for (const [key, value] of Object.entries(response.headers)) { + // Got gives *decompressed* data. Overriding `content-encoding` header would result in an error. + // It's not possible to decompress already decompressed data, is it? + const allowed = options.decompress ? key !== 'content-encoding' : true; + if (allowed) { + destination.setHeader(key, value); + } + } + + destination.statusCode = response.statusCode; + } + + proxy.emit('response', response); + }); + + [ + 'error', + 'request', + 'redirect', + 'uploadProgress', + 'downloadProgress' + ].forEach(event => emitter.on(event, (...args) => proxy.emit(event, ...args))); + + const pipe = proxy.pipe.bind(proxy); + const unpipe = proxy.unpipe.bind(proxy); + proxy.pipe = (destination, options) => { + if (isFinished) { + throw new Error('Failed to pipe. The response has been emitted already.'); + } + + const result = pipe(destination, options); + + if (Reflect.has(destination, 'setHeader')) { + piped.add(destination); + } + + return result; + }; + + proxy.unpipe = stream => { + piped.delete(stream); + return unpipe(stream); + }; + + return proxy; +}; diff --git a/node_modules/got/source/create.js b/node_modules/got/source/create.js new file mode 100644 index 0000000..b78c51f --- /dev/null +++ b/node_modules/got/source/create.js @@ -0,0 +1,79 @@ +'use strict'; +const errors = require('./errors'); +const asStream = require('./as-stream'); +const asPromise = require('./as-promise'); +const normalizeArguments = require('./normalize-arguments'); +const merge = require('./merge'); +const deepFreeze = require('./utils/deep-freeze'); + +const getPromiseOrStream = options => options.stream ? asStream(options) : asPromise(options); + +const aliases = [ + 'get', + 'post', + 'put', + 'patch', + 'head', + 'delete' +]; + +const create = defaults => { + defaults = merge({}, defaults); + normalizeArguments.preNormalize(defaults.options); + + if (!defaults.handler) { + // This can't be getPromiseOrStream, because when merging + // the chain would stop at this point and no further handlers would be called. + defaults.handler = (options, next) => next(options); + } + + function got(url, options) { + try { + return defaults.handler(normalizeArguments(url, options, defaults), getPromiseOrStream); + } catch (error) { + if (options && options.stream) { + throw error; + } else { + return Promise.reject(error); + } + } + } + + got.create = create; + got.extend = options => { + let mutableDefaults; + if (options && Reflect.has(options, 'mutableDefaults')) { + mutableDefaults = options.mutableDefaults; + delete options.mutableDefaults; + } else { + mutableDefaults = defaults.mutableDefaults; + } + + return create({ + options: merge.options(defaults.options, options), + handler: defaults.handler, + mutableDefaults + }); + }; + + got.mergeInstances = (...args) => create(merge.instances(args)); + + got.stream = (url, options) => got(url, {...options, stream: true}); + + for (const method of aliases) { + got[method] = (url, options) => got(url, {...options, method}); + got.stream[method] = (url, options) => got.stream(url, {...options, method}); + } + + Object.assign(got, {...errors, mergeOptions: merge.options}); + Object.defineProperty(got, 'defaults', { + value: defaults.mutableDefaults ? defaults : deepFreeze(defaults), + writable: defaults.mutableDefaults, + configurable: defaults.mutableDefaults, + enumerable: true + }); + + return got; +}; + +module.exports = create; diff --git a/node_modules/got/source/errors.js b/node_modules/got/source/errors.js new file mode 100644 index 0000000..b6cbadc --- /dev/null +++ b/node_modules/got/source/errors.js @@ -0,0 +1,107 @@ +'use strict'; +const urlLib = require('url'); +const http = require('http'); +const PCancelable = require('p-cancelable'); +const is = require('@sindresorhus/is'); + +class GotError extends Error { + constructor(message, error, options) { + super(message); + Error.captureStackTrace(this, this.constructor); + this.name = 'GotError'; + + if (!is.undefined(error.code)) { + this.code = error.code; + } + + Object.assign(this, { + host: options.host, + hostname: options.hostname, + method: options.method, + path: options.path, + socketPath: options.socketPath, + protocol: options.protocol, + url: options.href, + gotOptions: options + }); + } +} + +module.exports.GotError = GotError; + +module.exports.CacheError = class extends GotError { + constructor(error, options) { + super(error.message, error, options); + this.name = 'CacheError'; + } +}; + +module.exports.RequestError = class extends GotError { + constructor(error, options) { + super(error.message, error, options); + this.name = 'RequestError'; + } +}; + +module.exports.ReadError = class extends GotError { + constructor(error, options) { + super(error.message, error, options); + this.name = 'ReadError'; + } +}; + +module.exports.ParseError = class extends GotError { + constructor(error, statusCode, options, data) { + super(`${error.message} in "${urlLib.format(options)}": \n${data.slice(0, 77)}...`, error, options); + this.name = 'ParseError'; + this.statusCode = statusCode; + this.statusMessage = http.STATUS_CODES[this.statusCode]; + } +}; + +module.exports.HTTPError = class extends GotError { + constructor(response, options) { + const {statusCode} = response; + let {statusMessage} = response; + + if (statusMessage) { + statusMessage = statusMessage.replace(/\r?\n/g, ' ').trim(); + } else { + statusMessage = http.STATUS_CODES[statusCode]; + } + + super(`Response code ${statusCode} (${statusMessage})`, {}, options); + this.name = 'HTTPError'; + this.statusCode = statusCode; + this.statusMessage = statusMessage; + this.headers = response.headers; + this.body = response.body; + } +}; + +module.exports.MaxRedirectsError = class extends GotError { + constructor(statusCode, redirectUrls, options) { + super('Redirected 10 times. Aborting.', {}, options); + this.name = 'MaxRedirectsError'; + this.statusCode = statusCode; + this.statusMessage = http.STATUS_CODES[this.statusCode]; + this.redirectUrls = redirectUrls; + } +}; + +module.exports.UnsupportedProtocolError = class extends GotError { + constructor(options) { + super(`Unsupported protocol "${options.protocol}"`, {}, options); + this.name = 'UnsupportedProtocolError'; + } +}; + +module.exports.TimeoutError = class extends GotError { + constructor(error, options) { + super(error.message, {code: 'ETIMEDOUT'}, options); + this.name = 'TimeoutError'; + this.event = error.event; + } +}; + +module.exports.CancelError = PCancelable.CancelError; diff --git a/node_modules/got/source/get-response.js b/node_modules/got/source/get-response.js new file mode 100644 index 0000000..18453c2 --- /dev/null +++ b/node_modules/got/source/get-response.js @@ -0,0 +1,31 @@ +'use strict'; +const decompressResponse = require('decompress-response'); +const is = require('@sindresorhus/is'); +const mimicResponse = require('mimic-response'); +const progress = require('./progress'); + +module.exports = (response, options, emitter) => { + const downloadBodySize = Number(response.headers['content-length']) || null; + + const progressStream = progress.download(response, emitter, downloadBodySize); + + mimicResponse(response, progressStream); + + const newResponse = options.decompress === true && + is.function(decompressResponse) && + options.method !== 'HEAD' ? decompressResponse(progressStream) : progressStream; + + if (!options.decompress && ['gzip', 'deflate'].includes(response.headers['content-encoding'])) { + options.encoding = null; + } + + emitter.emit('response', newResponse); + + emitter.emit('downloadProgress', { + percent: 0, + transferred: 0, + total: downloadBodySize + }); + + response.pipe(progressStream); +}; diff --git a/node_modules/got/source/index.js b/node_modules/got/source/index.js new file mode 100644 index 0000000..cbf7c37 --- /dev/null +++ b/node_modules/got/source/index.js @@ -0,0 +1,60 @@ +'use strict'; +const pkg = require('../package.json'); +const create = require('./create'); + +const defaults = { + options: { + retry: { + retries: 2, + methods: [ + 'GET', + 'PUT', + 'HEAD', + 'DELETE', + 'OPTIONS', + 'TRACE' + ], + statusCodes: [ + 408, + 413, + 429, + 500, + 502, + 503, + 504 + ], + errorCodes: [ + 'ETIMEDOUT', + 'ECONNRESET', + 'EADDRINUSE', + 'ECONNREFUSED', + 'EPIPE', + 'ENOTFOUND', + 'ENETUNREACH', + 'EAI_AGAIN' + ] + }, + headers: { + 'user-agent': `${pkg.name}/${pkg.version} (https://github.com/sindresorhus/got)` + }, + hooks: { + beforeRequest: [], + beforeRedirect: [], + beforeRetry: [], + afterResponse: [] + }, + decompress: true, + throwHttpErrors: true, + followRedirect: true, + stream: false, + form: false, + json: false, + cache: false, + useElectronNet: false + }, + mutableDefaults: false +}; + +const got = create(defaults); + +module.exports = got; diff --git a/node_modules/got/source/known-hook-events.js b/node_modules/got/source/known-hook-events.js new file mode 100644 index 0000000..cd245e1 --- /dev/null +++ b/node_modules/got/source/known-hook-events.js @@ -0,0 +1,10 @@ +'use strict'; + +module.exports = [ + 'beforeError', + 'init', + 'beforeRequest', + 'beforeRedirect', + 'beforeRetry', + 'afterResponse' +]; diff --git a/node_modules/got/source/merge.js b/node_modules/got/source/merge.js new file mode 100644 index 0000000..900f09a --- /dev/null +++ b/node_modules/got/source/merge.js @@ -0,0 +1,73 @@ +'use strict'; +const {URL} = require('url'); +const is = require('@sindresorhus/is'); +const knownHookEvents = require('./known-hook-events'); + +const merge = (target, ...sources) => { + for (const source of sources) { + for (const [key, sourceValue] of Object.entries(source)) { + if (is.undefined(sourceValue)) { + continue; + } + + const targetValue = target[key]; + if (is.urlInstance(targetValue) && (is.urlInstance(sourceValue) || is.string(sourceValue))) { + target[key] = new URL(sourceValue, targetValue); + } else if (is.plainObject(sourceValue)) { + if (is.plainObject(targetValue)) { + target[key] = merge({}, targetValue, sourceValue); + } else { + target[key] = merge({}, sourceValue); + } + } else if (is.array(sourceValue)) { + target[key] = merge([], sourceValue); + } else { + target[key] = sourceValue; + } + } + } + + return target; +}; + +const mergeOptions = (...sources) => { + sources = sources.map(source => source || {}); + const merged = merge({}, ...sources); + + const hooks = {}; + for (const hook of knownHookEvents) { + hooks[hook] = []; + } + + for (const source of sources) { + if (source.hooks) { + for (const hook of knownHookEvents) { + hooks[hook] = hooks[hook].concat(source.hooks[hook]); + } + } + } + + merged.hooks = hooks; + + return merged; +}; + +const mergeInstances = (instances, methods) => { + const handlers = instances.map(instance => instance.defaults.handler); + const size = instances.length - 1; + + return { + methods, + options: mergeOptions(...instances.map(instance => instance.defaults.options)), + handler: (options, next) => { + let iteration = -1; + const iterate = options => handlers[++iteration](options, iteration === size ? next : iterate); + + return iterate(options); + } + }; +}; + +module.exports = merge; +module.exports.options = mergeOptions; +module.exports.instances = mergeInstances; diff --git a/node_modules/got/source/normalize-arguments.js b/node_modules/got/source/normalize-arguments.js new file mode 100644 index 0000000..665cbce --- /dev/null +++ b/node_modules/got/source/normalize-arguments.js @@ -0,0 +1,265 @@ +'use strict'; +const {URL, URLSearchParams} = require('url'); // TODO: Use the `URL` global when targeting Node.js 10 +const urlLib = require('url'); +const is = require('@sindresorhus/is'); +const urlParseLax = require('url-parse-lax'); +const lowercaseKeys = require('lowercase-keys'); +const urlToOptions = require('./utils/url-to-options'); +const isFormData = require('./utils/is-form-data'); +const merge = require('./merge'); +const knownHookEvents = require('./known-hook-events'); + +const retryAfterStatusCodes = new Set([413, 429, 503]); + +// `preNormalize` handles static options (e.g. headers). +// For example, when you create a custom instance and make a request +// with no static changes, they won't be normalized again. +// +// `normalize` operates on dynamic options - they cannot be saved. +// For example, `body` is everytime different per request. +// When it's done normalizing the new options, it performs merge() +// on the prenormalized options and the normalized ones. + +const preNormalize = (options, defaults) => { + if (is.nullOrUndefined(options.headers)) { + options.headers = {}; + } else { + options.headers = lowercaseKeys(options.headers); + } + + if (options.baseUrl && !options.baseUrl.toString().endsWith('/')) { + options.baseUrl += '/'; + } + + if (options.stream) { + options.json = false; + } + + if (is.nullOrUndefined(options.hooks)) { + options.hooks = {}; + } else if (!is.object(options.hooks)) { + throw new TypeError(`Parameter \`hooks\` must be an object, not ${is(options.hooks)}`); + } + + for (const event of knownHookEvents) { + if (is.nullOrUndefined(options.hooks[event])) { + if (defaults) { + options.hooks[event] = [...defaults.hooks[event]]; + } else { + options.hooks[event] = []; + } + } + } + + if (is.number(options.timeout)) { + options.gotTimeout = {request: options.timeout}; + } else if (is.object(options.timeout)) { + options.gotTimeout = options.timeout; + } + + delete options.timeout; + + const {retry} = options; + options.retry = { + retries: 0, + methods: [], + statusCodes: [], + errorCodes: [] + }; + + if (is.nonEmptyObject(defaults) && retry !== false) { + options.retry = {...defaults.retry}; + } + + if (retry !== false) { + if (is.number(retry)) { + options.retry.retries = retry; + } else { + options.retry = {...options.retry, ...retry}; + } + } + + if (options.gotTimeout) { + options.retry.maxRetryAfter = Math.min(...[options.gotTimeout.request, options.gotTimeout.connection].filter(n => !is.nullOrUndefined(n))); + } + + if (is.array(options.retry.methods)) { + options.retry.methods = new Set(options.retry.methods.map(method => method.toUpperCase())); + } + + if (is.array(options.retry.statusCodes)) { + options.retry.statusCodes = new Set(options.retry.statusCodes); + } + + if (is.array(options.retry.errorCodes)) { + options.retry.errorCodes = new Set(options.retry.errorCodes); + } + + return options; +}; + +const normalize = (url, options, defaults) => { + if (is.plainObject(url)) { + options = {...url, ...options}; + url = options.url || {}; + delete options.url; + } + + if (defaults) { + options = merge({}, defaults.options, options ? preNormalize(options, defaults.options) : {}); + } else { + options = merge({}, preNormalize(options)); + } + + if (!is.string(url) && !is.object(url)) { + throw new TypeError(`Parameter \`url\` must be a string or object, not ${is(url)}`); + } + + if (is.string(url)) { + if (options.baseUrl) { + if (url.toString().startsWith('/')) { + url = url.toString().slice(1); + } + + url = urlToOptions(new URL(url, options.baseUrl)); + } else { + url = url.replace(/^unix:/, 'http://$&'); + url = urlParseLax(url); + } + } else if (is(url) === 'URL') { + url = urlToOptions(url); + } + + // Override both null/undefined with default protocol + options = merge({path: ''}, url, {protocol: url.protocol || 'https:'}, options); + + for (const hook of options.hooks.init) { + const called = hook(options); + + if (is.promise(called)) { + throw new TypeError('The `init` hook must be a synchronous function'); + } + } + + const {baseUrl} = options; + Object.defineProperty(options, 'baseUrl', { + set: () => { + throw new Error('Failed to set baseUrl. Options are normalized already.'); + }, + get: () => baseUrl + }); + + const {query} = options; + if (is.nonEmptyString(query) || is.nonEmptyObject(query) || query instanceof URLSearchParams) { + if (!is.string(query)) { + options.query = (new URLSearchParams(query)).toString(); + } + + options.path = `${options.path.split('?')[0]}?${options.query}`; + delete options.query; + } + + if (options.hostname === 'unix') { + const matches = /(.+?):(.+)/.exec(options.path); + + if (matches) { + const [, socketPath, path] = matches; + options = { + ...options, + socketPath, + path, + host: null + }; + } + } + + const {headers} = options; + for (const [key, value] of Object.entries(headers)) { + if (is.nullOrUndefined(value)) { + delete headers[key]; + } + } + + if (options.json && is.undefined(headers.accept)) { + headers.accept = 'application/json'; + } + + if (options.decompress && is.undefined(headers['accept-encoding'])) { + headers['accept-encoding'] = 'gzip, deflate'; + } + + const {body} = options; + if (is.nullOrUndefined(body)) { + options.method = options.method ? options.method.toUpperCase() : 'GET'; + } else { + const isObject = is.object(body) && !is.buffer(body) && !is.nodeStream(body); + if (!is.nodeStream(body) && !is.string(body) && !is.buffer(body) && !(options.form || options.json)) { + throw new TypeError('The `body` option must be a stream.Readable, string or Buffer'); + } + + if (options.json && !(isObject || is.array(body))) { + throw new TypeError('The `body` option must be an Object or Array when the `json` option is used'); + } + + if (options.form && !isObject) { + throw new TypeError('The `body` option must be an Object when the `form` option is used'); + } + + if (isFormData(body)) { + // Special case for https://github.com/form-data/form-data + headers['content-type'] = headers['content-type'] || `multipart/form-data; boundary=${body.getBoundary()}`; + } else if (options.form) { + headers['content-type'] = headers['content-type'] || 'application/x-www-form-urlencoded'; + options.body = (new URLSearchParams(body)).toString(); + } else if (options.json) { + headers['content-type'] = headers['content-type'] || 'application/json'; + options.body = JSON.stringify(body); + } + + options.method = options.method ? options.method.toUpperCase() : 'POST'; + } + + if (!is.function(options.retry.retries)) { + const {retries} = options.retry; + + options.retry.retries = (iteration, error) => { + if (iteration > retries) { + return 0; + } + + if ((!error || !options.retry.errorCodes.has(error.code)) && (!options.retry.methods.has(error.method) || !options.retry.statusCodes.has(error.statusCode))) { + return 0; + } + + if (Reflect.has(error, 'headers') && Reflect.has(error.headers, 'retry-after') && retryAfterStatusCodes.has(error.statusCode)) { + let after = Number(error.headers['retry-after']); + if (is.nan(after)) { + after = Date.parse(error.headers['retry-after']) - Date.now(); + } else { + after *= 1000; + } + + if (after > options.retry.maxRetryAfter) { + return 0; + } + + return after; + } + + if (error.statusCode === 413) { + return 0; + } + + const noise = Math.random() * 100; + return ((2 ** (iteration - 1)) * 1000) + noise; + }; + } + + return options; +}; + +const reNormalize = options => normalize(urlLib.format(options), options); + +module.exports = normalize; +module.exports.preNormalize = preNormalize; +module.exports.reNormalize = reNormalize; diff --git a/node_modules/got/source/progress.js b/node_modules/got/source/progress.js new file mode 100644 index 0000000..666abcf --- /dev/null +++ b/node_modules/got/source/progress.js @@ -0,0 +1,96 @@ +'use strict'; +const {Transform} = require('stream'); + +module.exports = { + download(response, emitter, downloadBodySize) { + let downloaded = 0; + + return new Transform({ + transform(chunk, encoding, callback) { + downloaded += chunk.length; + + const percent = downloadBodySize ? downloaded / downloadBodySize : 0; + + // Let `flush()` be responsible for emitting the last event + if (percent < 1) { + emitter.emit('downloadProgress', { + percent, + transferred: downloaded, + total: downloadBodySize + }); + } + + callback(null, chunk); + }, + + flush(callback) { + emitter.emit('downloadProgress', { + percent: 1, + transferred: downloaded, + total: downloadBodySize + }); + + callback(); + } + }); + }, + + upload(request, emitter, uploadBodySize) { + const uploadEventFrequency = 150; + let uploaded = 0; + let progressInterval; + + emitter.emit('uploadProgress', { + percent: 0, + transferred: 0, + total: uploadBodySize + }); + + request.once('error', () => { + clearInterval(progressInterval); + }); + + request.once('response', () => { + clearInterval(progressInterval); + + emitter.emit('uploadProgress', { + percent: 1, + transferred: uploaded, + total: uploadBodySize + }); + }); + + request.once('socket', socket => { + const onSocketConnect = () => { + progressInterval = setInterval(() => { + const lastUploaded = uploaded; + /* istanbul ignore next: see #490 (occurs randomly!) */ + const headersSize = request._header ? Buffer.byteLength(request._header) : 0; + uploaded = socket.bytesWritten - headersSize; + + // Don't emit events with unchanged progress and + // prevent last event from being emitted, because + // it's emitted when `response` is emitted + if (uploaded === lastUploaded || uploaded === uploadBodySize) { + return; + } + + emitter.emit('uploadProgress', { + percent: uploadBodySize ? uploaded / uploadBodySize : 0, + transferred: uploaded, + total: uploadBodySize + }); + }, uploadEventFrequency); + }; + + /* istanbul ignore next: hard to test */ + if (socket.connecting) { + socket.once('connect', onSocketConnect); + } else if (socket.writable) { + // The socket is being reused from pool, + // so the connect event will not be emitted + onSocketConnect(); + } + }); + } +}; diff --git a/node_modules/got/source/request-as-event-emitter.js b/node_modules/got/source/request-as-event-emitter.js new file mode 100644 index 0000000..79586af --- /dev/null +++ b/node_modules/got/source/request-as-event-emitter.js @@ -0,0 +1,312 @@ +'use strict'; +const {URL} = require('url'); // TODO: Use the `URL` global when targeting Node.js 10 +const util = require('util'); +const EventEmitter = require('events'); +const http = require('http'); +const https = require('https'); +const urlLib = require('url'); +const CacheableRequest = require('cacheable-request'); +const toReadableStream = require('to-readable-stream'); +const is = require('@sindresorhus/is'); +const timer = require('@szmarczak/http-timer'); +const timedOut = require('./utils/timed-out'); +const getBodySize = require('./utils/get-body-size'); +const getResponse = require('./get-response'); +const progress = require('./progress'); +const {CacheError, UnsupportedProtocolError, MaxRedirectsError, RequestError, TimeoutError} = require('./errors'); +const urlToOptions = require('./utils/url-to-options'); + +const getMethodRedirectCodes = new Set([300, 301, 302, 303, 304, 305, 307, 308]); +const allMethodRedirectCodes = new Set([300, 303, 307, 308]); + +module.exports = (options, input) => { + const emitter = new EventEmitter(); + const redirects = []; + let currentRequest; + let requestUrl; + let redirectString; + let uploadBodySize; + let retryCount = 0; + let shouldAbort = false; + + const setCookie = options.cookieJar ? util.promisify(options.cookieJar.setCookie.bind(options.cookieJar)) : null; + const getCookieString = options.cookieJar ? util.promisify(options.cookieJar.getCookieString.bind(options.cookieJar)) : null; + const agents = is.object(options.agent) ? options.agent : null; + + const emitError = async error => { + try { + for (const hook of options.hooks.beforeError) { + // eslint-disable-next-line no-await-in-loop + error = await hook(error); + } + + emitter.emit('error', error); + } catch (error2) { + emitter.emit('error', error2); + } + }; + + const get = async options => { + const currentUrl = redirectString || requestUrl; + + if (options.protocol !== 'http:' && options.protocol !== 'https:') { + throw new UnsupportedProtocolError(options); + } + + decodeURI(currentUrl); + + let fn; + if (is.function(options.request)) { + fn = {request: options.request}; + } else { + fn = options.protocol === 'https:' ? https : http; + } + + if (agents) { + const protocolName = options.protocol === 'https:' ? 'https' : 'http'; + options.agent = agents[protocolName] || options.agent; + } + + /* istanbul ignore next: electron.net is broken */ + if (options.useElectronNet && process.versions.electron) { + const r = ({x: require})['yx'.slice(1)]; // Trick webpack + const electron = r('electron'); + fn = electron.net || electron.remote.net; + } + + if (options.cookieJar) { + const cookieString = await getCookieString(currentUrl, {}); + + if (is.nonEmptyString(cookieString)) { + options.headers.cookie = cookieString; + } + } + + let timings; + const handleResponse = async response => { + try { + /* istanbul ignore next: fixes https://github.com/electron/electron/blob/cbb460d47628a7a146adf4419ed48550a98b2923/lib/browser/api/net.js#L59-L65 */ + if (options.useElectronNet) { + response = new Proxy(response, { + get: (target, name) => { + if (name === 'trailers' || name === 'rawTrailers') { + return []; + } + + const value = target[name]; + return is.function(value) ? value.bind(target) : value; + } + }); + } + + const {statusCode} = response; + response.url = currentUrl; + response.requestUrl = requestUrl; + response.retryCount = retryCount; + response.timings = timings; + response.redirectUrls = redirects; + response.request = { + gotOptions: options + }; + + const rawCookies = response.headers['set-cookie']; + if (options.cookieJar && rawCookies) { + await Promise.all(rawCookies.map(rawCookie => setCookie(rawCookie, response.url))); + } + + if (options.followRedirect && 'location' in response.headers) { + if (allMethodRedirectCodes.has(statusCode) || (getMethodRedirectCodes.has(statusCode) && (options.method === 'GET' || options.method === 'HEAD'))) { + response.resume(); // We're being redirected, we don't care about the response. + + if (statusCode === 303) { + // Server responded with "see other", indicating that the resource exists at another location, + // and the client should request it from that location via GET or HEAD. + options.method = 'GET'; + } + + if (redirects.length >= 10) { + throw new MaxRedirectsError(statusCode, redirects, options); + } + + // Handles invalid URLs. See https://github.com/sindresorhus/got/issues/604 + const redirectBuffer = Buffer.from(response.headers.location, 'binary').toString(); + const redirectURL = new URL(redirectBuffer, currentUrl); + redirectString = redirectURL.toString(); + + redirects.push(redirectString); + + const redirectOptions = { + ...options, + ...urlToOptions(redirectURL) + }; + + for (const hook of options.hooks.beforeRedirect) { + // eslint-disable-next-line no-await-in-loop + await hook(redirectOptions); + } + + emitter.emit('redirect', response, redirectOptions); + + await get(redirectOptions); + return; + } + } + + getResponse(response, options, emitter); + } catch (error) { + emitError(error); + } + }; + + const handleRequest = request => { + if (shouldAbort) { + request.once('error', () => {}); + request.abort(); + return; + } + + currentRequest = request; + + request.once('error', error => { + if (request.aborted) { + return; + } + + if (error instanceof timedOut.TimeoutError) { + error = new TimeoutError(error, options); + } else { + error = new RequestError(error, options); + } + + if (emitter.retry(error) === false) { + emitError(error); + } + }); + + timings = timer(request); + + progress.upload(request, emitter, uploadBodySize); + + if (options.gotTimeout) { + timedOut(request, options.gotTimeout, options); + } + + emitter.emit('request', request); + + const uploadComplete = () => { + request.emit('upload-complete'); + }; + + try { + if (is.nodeStream(options.body)) { + options.body.once('end', uploadComplete); + options.body.pipe(request); + options.body = undefined; + } else if (options.body) { + request.end(options.body, uploadComplete); + } else if (input && (options.method === 'POST' || options.method === 'PUT' || options.method === 'PATCH')) { + input.once('end', uploadComplete); + input.pipe(request); + } else { + request.end(uploadComplete); + } + } catch (error) { + emitError(new RequestError(error, options)); + } + }; + + if (options.cache) { + const cacheableRequest = new CacheableRequest(fn.request, options.cache); + const cacheRequest = cacheableRequest(options, handleResponse); + + cacheRequest.once('error', error => { + if (error instanceof CacheableRequest.RequestError) { + emitError(new RequestError(error, options)); + } else { + emitError(new CacheError(error, options)); + } + }); + + cacheRequest.once('request', handleRequest); + } else { + // Catches errors thrown by calling fn.request(...) + try { + handleRequest(fn.request(options, handleResponse)); + } catch (error) { + emitError(new RequestError(error, options)); + } + } + }; + + emitter.retry = error => { + let backoff; + + try { + backoff = options.retry.retries(++retryCount, error); + } catch (error2) { + emitError(error2); + return; + } + + if (backoff) { + const retry = async options => { + try { + for (const hook of options.hooks.beforeRetry) { + // eslint-disable-next-line no-await-in-loop + await hook(options, error, retryCount); + } + + await get(options); + } catch (error) { + emitError(error); + } + }; + + setTimeout(retry, backoff, {...options, forceRefresh: true}); + return true; + } + + return false; + }; + + emitter.abort = () => { + if (currentRequest) { + currentRequest.once('error', () => {}); + currentRequest.abort(); + } else { + shouldAbort = true; + } + }; + + setImmediate(async () => { + try { + // Convert buffer to stream to receive upload progress events (#322) + const {body} = options; + if (is.buffer(body)) { + options.body = toReadableStream(body); + uploadBodySize = body.length; + } else { + uploadBodySize = await getBodySize(options); + } + + if (is.undefined(options.headers['content-length']) && is.undefined(options.headers['transfer-encoding'])) { + if ((uploadBodySize > 0 || options.method === 'PUT') && !is.null(uploadBodySize)) { + options.headers['content-length'] = uploadBodySize; + } + } + + for (const hook of options.hooks.beforeRequest) { + // eslint-disable-next-line no-await-in-loop + await hook(options); + } + + requestUrl = options.href || (new URL(options.path, urlLib.format(options))).toString(); + + await get(options); + } catch (error) { + emitError(error); + } + }); + + return emitter; +}; diff --git a/node_modules/got/source/utils/deep-freeze.js b/node_modules/got/source/utils/deep-freeze.js new file mode 100644 index 0000000..5052b71 --- /dev/null +++ b/node_modules/got/source/utils/deep-freeze.js @@ -0,0 +1,12 @@ +'use strict'; +const is = require('@sindresorhus/is'); + +module.exports = function deepFreeze(object) { + for (const [key, value] of Object.entries(object)) { + if (is.plainObject(value) || is.array(value)) { + deepFreeze(object[key]); + } + } + + return Object.freeze(object); +}; diff --git a/node_modules/got/source/utils/get-body-size.js b/node_modules/got/source/utils/get-body-size.js new file mode 100644 index 0000000..0df5af2 --- /dev/null +++ b/node_modules/got/source/utils/get-body-size.js @@ -0,0 +1,32 @@ +'use strict'; +const fs = require('fs'); +const util = require('util'); +const is = require('@sindresorhus/is'); +const isFormData = require('./is-form-data'); + +module.exports = async options => { + const {body} = options; + + if (options.headers['content-length']) { + return Number(options.headers['content-length']); + } + + if (!body && !options.stream) { + return 0; + } + + if (is.string(body)) { + return Buffer.byteLength(body); + } + + if (isFormData(body)) { + return util.promisify(body.getLength.bind(body))(); + } + + if (body instanceof fs.ReadStream) { + const {size} = await util.promisify(fs.stat)(body.path); + return size; + } + + return null; +}; diff --git a/node_modules/got/source/utils/is-form-data.js b/node_modules/got/source/utils/is-form-data.js new file mode 100644 index 0000000..0033618 --- /dev/null +++ b/node_modules/got/source/utils/is-form-data.js @@ -0,0 +1,4 @@ +'use strict'; +const is = require('@sindresorhus/is'); + +module.exports = body => is.nodeStream(body) && is.function(body.getBoundary); diff --git a/node_modules/got/source/utils/timed-out.js b/node_modules/got/source/utils/timed-out.js new file mode 100644 index 0000000..33611a7 --- /dev/null +++ b/node_modules/got/source/utils/timed-out.js @@ -0,0 +1,160 @@ +'use strict'; +const net = require('net'); + +class TimeoutError extends Error { + constructor(threshold, event) { + super(`Timeout awaiting '${event}' for ${threshold}ms`); + this.name = 'TimeoutError'; + this.code = 'ETIMEDOUT'; + this.event = event; + } +} + +const reentry = Symbol('reentry'); + +const noop = () => {}; + +module.exports = (request, delays, options) => { + /* istanbul ignore next: this makes sure timed-out isn't called twice */ + if (request[reentry]) { + return; + } + + request[reentry] = true; + + let stopNewTimeouts = false; + + const addTimeout = (delay, callback, ...args) => { + // An error had been thrown before. Going further would result in uncaught errors. + // See https://github.com/sindresorhus/got/issues/631#issuecomment-435675051 + if (stopNewTimeouts) { + return noop; + } + + // Event loop order is timers, poll, immediates. + // The timed event may emit during the current tick poll phase, so + // defer calling the handler until the poll phase completes. + let immediate; + const timeout = setTimeout(() => { + immediate = setImmediate(callback, delay, ...args); + /* istanbul ignore next: added in node v9.7.0 */ + if (immediate.unref) { + immediate.unref(); + } + }, delay); + + /* istanbul ignore next: in order to support electron renderer */ + if (timeout.unref) { + timeout.unref(); + } + + const cancel = () => { + clearTimeout(timeout); + clearImmediate(immediate); + }; + + cancelers.push(cancel); + + return cancel; + }; + + const {host, hostname} = options; + const timeoutHandler = (delay, event) => { + request.emit('error', new TimeoutError(delay, event)); + request.once('error', () => {}); // Ignore the `socket hung up` error made by request.abort() + + request.abort(); + }; + + const cancelers = []; + const cancelTimeouts = () => { + stopNewTimeouts = true; + cancelers.forEach(cancelTimeout => cancelTimeout()); + }; + + request.once('error', cancelTimeouts); + request.once('response', response => { + response.once('end', cancelTimeouts); + }); + + if (delays.request !== undefined) { + addTimeout(delays.request, timeoutHandler, 'request'); + } + + if (delays.socket !== undefined) { + const socketTimeoutHandler = () => { + timeoutHandler(delays.socket, 'socket'); + }; + + request.setTimeout(delays.socket, socketTimeoutHandler); + + // `request.setTimeout(0)` causes a memory leak. + // We can just remove the listener and forget about the timer - it's unreffed. + // See https://github.com/sindresorhus/got/issues/690 + cancelers.push(() => request.removeListener('timeout', socketTimeoutHandler)); + } + + if (delays.lookup !== undefined && !request.socketPath && !net.isIP(hostname || host)) { + request.once('socket', socket => { + /* istanbul ignore next: hard to test */ + if (socket.connecting) { + const cancelTimeout = addTimeout(delays.lookup, timeoutHandler, 'lookup'); + socket.once('lookup', cancelTimeout); + } + }); + } + + if (delays.connect !== undefined) { + request.once('socket', socket => { + /* istanbul ignore next: hard to test */ + if (socket.connecting) { + const timeConnect = () => addTimeout(delays.connect, timeoutHandler, 'connect'); + + if (request.socketPath || net.isIP(hostname || host)) { + socket.once('connect', timeConnect()); + } else { + socket.once('lookup', error => { + if (error === null) { + socket.once('connect', timeConnect()); + } + }); + } + } + }); + } + + if (delays.secureConnect !== undefined && options.protocol === 'https:') { + request.once('socket', socket => { + /* istanbul ignore next: hard to test */ + if (socket.connecting) { + socket.once('connect', () => { + const cancelTimeout = addTimeout(delays.secureConnect, timeoutHandler, 'secureConnect'); + socket.once('secureConnect', cancelTimeout); + }); + } + }); + } + + if (delays.send !== undefined) { + request.once('socket', socket => { + const timeRequest = () => addTimeout(delays.send, timeoutHandler, 'send'); + /* istanbul ignore next: hard to test */ + if (socket.connecting) { + socket.once('connect', () => { + request.once('upload-complete', timeRequest()); + }); + } else { + request.once('upload-complete', timeRequest()); + } + }); + } + + if (delays.response !== undefined) { + request.once('upload-complete', () => { + const cancelTimeout = addTimeout(delays.response, timeoutHandler, 'response'); + request.once('response', cancelTimeout); + }); + } +}; + +module.exports.TimeoutError = TimeoutError; diff --git a/node_modules/got/source/utils/url-to-options.js b/node_modules/got/source/utils/url-to-options.js new file mode 100644 index 0000000..848ef30 --- /dev/null +++ b/node_modules/got/source/utils/url-to-options.js @@ -0,0 +1,25 @@ +'use strict'; +const is = require('@sindresorhus/is'); + +module.exports = url => { + const options = { + protocol: url.protocol, + hostname: url.hostname.startsWith('[') ? url.hostname.slice(1, -1) : url.hostname, + hash: url.hash, + search: url.search, + pathname: url.pathname, + href: url.href + }; + + if (is.string(url.port) && url.port.length > 0) { + options.port = Number(url.port); + } + + if (url.username || url.password) { + options.auth = `${url.username}:${url.password}`; + } + + options.path = is.null(url.search) ? url.pathname : `${url.pathname}${url.search}`; + + return options; +}; diff --git a/node_modules/graceful-fs/LICENSE b/node_modules/graceful-fs/LICENSE new file mode 100644 index 0000000..e906a25 --- /dev/null +++ b/node_modules/graceful-fs/LICENSE @@ -0,0 +1,15 @@ +The ISC License + +Copyright (c) 2011-2022 Isaac Z. Schlueter, Ben Noordhuis, and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +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. diff --git a/node_modules/graceful-fs/README.md b/node_modules/graceful-fs/README.md new file mode 100644 index 0000000..82d6e4d --- /dev/null +++ b/node_modules/graceful-fs/README.md @@ -0,0 +1,143 @@ +# graceful-fs + +graceful-fs functions as a drop-in replacement for the fs module, +making various improvements. + +The improvements are meant to normalize behavior across different +platforms and environments, and to make filesystem access more +resilient to errors. + +## Improvements over [fs module](https://nodejs.org/api/fs.html) + +* Queues up `open` and `readdir` calls, and retries them once + something closes if there is an EMFILE error from too many file + descriptors. +* fixes `lchmod` for Node versions prior to 0.6.2. +* implements `fs.lutimes` if possible. Otherwise it becomes a noop. +* ignores `EINVAL` and `EPERM` errors in `chown`, `fchown` or + `lchown` if the user isn't root. +* makes `lchmod` and `lchown` become noops, if not available. +* retries reading a file if `read` results in EAGAIN error. + +On Windows, it retries renaming a file for up to one second if `EACCESS` +or `EPERM` error occurs, likely because antivirus software has locked +the directory. + +## USAGE + +```javascript +// use just like fs +var fs = require('graceful-fs') + +// now go and do stuff with it... +fs.readFile('some-file-or-whatever', (err, data) => { + // Do stuff here. +}) +``` + +## Sync methods + +This module cannot intercept or handle `EMFILE` or `ENFILE` errors from sync +methods. If you use sync methods which open file descriptors then you are +responsible for dealing with any errors. + +This is a known limitation, not a bug. + +## Global Patching + +If you want to patch the global fs module (or any other fs-like +module) you can do this: + +```javascript +// Make sure to read the caveat below. +var realFs = require('fs') +var gracefulFs = require('graceful-fs') +gracefulFs.gracefulify(realFs) +``` + +This should only ever be done at the top-level application layer, in +order to delay on EMFILE errors from any fs-using dependencies. You +should **not** do this in a library, because it can cause unexpected +delays in other parts of the program. + +## Changes + +This module is fairly stable at this point, and used by a lot of +things. That being said, because it implements a subtle behavior +change in a core part of the node API, even modest changes can be +extremely breaking, and the versioning is thus biased towards +bumping the major when in doubt. + +The main change between major versions has been switching between +providing a fully-patched `fs` module vs monkey-patching the node core +builtin, and the approach by which a non-monkey-patched `fs` was +created. + +The goal is to trade `EMFILE` errors for slower fs operations. So, if +you try to open a zillion files, rather than crashing, `open` +operations will be queued up and wait for something else to `close`. + +There are advantages to each approach. Monkey-patching the fs means +that no `EMFILE` errors can possibly occur anywhere in your +application, because everything is using the same core `fs` module, +which is patched. However, it can also obviously cause undesirable +side-effects, especially if the module is loaded multiple times. + +Implementing a separate-but-identical patched `fs` module is more +surgical (and doesn't run the risk of patching multiple times), but +also imposes the challenge of keeping in sync with the core module. + +The current approach loads the `fs` module, and then creates a +lookalike object that has all the same methods, except a few that are +patched. It is safe to use in all versions of Node from 0.8 through +7.0. + +### v4 + +* Do not monkey-patch the fs module. This module may now be used as a + drop-in dep, and users can opt into monkey-patching the fs builtin + if their app requires it. + +### v3 + +* Monkey-patch fs, because the eval approach no longer works on recent + node. +* fixed possible type-error throw if rename fails on windows +* verify that we *never* get EMFILE errors +* Ignore ENOSYS from chmod/chown +* clarify that graceful-fs must be used as a drop-in + +### v2.1.0 + +* Use eval rather than monkey-patching fs. +* readdir: Always sort the results +* win32: requeue a file if error has an OK status + +### v2.0 + +* A return to monkey patching +* wrap process.cwd + +### v1.1 + +* wrap readFile +* Wrap fs.writeFile. +* readdir protection +* Don't clobber the fs builtin +* Handle fs.read EAGAIN errors by trying again +* Expose the curOpen counter +* No-op lchown/lchmod if not implemented +* fs.rename patch only for win32 +* Patch fs.rename to handle AV software on Windows +* Close #4 Chown should not fail on einval or eperm if non-root +* Fix isaacs/fstream#1 Only wrap fs one time +* Fix #3 Start at 1024 max files, then back off on EMFILE +* lutimes that doens't blow up on Linux +* A full on-rewrite using a queue instead of just swallowing the EMFILE error +* Wrap Read/Write streams as well + +### 1.0 + +* Update engines for node 0.6 +* Be lstat-graceful on Windows +* first diff --git a/node_modules/graceful-fs/clone.js b/node_modules/graceful-fs/clone.js new file mode 100644 index 0000000..dff3cc8 --- /dev/null +++ b/node_modules/graceful-fs/clone.js @@ -0,0 +1,23 @@ +'use strict' + +module.exports = clone + +var getPrototypeOf = Object.getPrototypeOf || function (obj) { + return obj.__proto__ +} + +function clone (obj) { + if (obj === null || typeof obj !== 'object') + return obj + + if (obj instanceof Object) + var copy = { __proto__: getPrototypeOf(obj) } + else + var copy = Object.create(null) + + Object.getOwnPropertyNames(obj).forEach(function (key) { + Object.defineProperty(copy, key, Object.getOwnPropertyDescriptor(obj, key)) + }) + + return copy +} diff --git a/node_modules/graceful-fs/graceful-fs.js b/node_modules/graceful-fs/graceful-fs.js new file mode 100644 index 0000000..8d5b89e --- /dev/null +++ b/node_modules/graceful-fs/graceful-fs.js @@ -0,0 +1,448 @@ +var fs = require('fs') +var polyfills = require('./polyfills.js') +var legacy = require('./legacy-streams.js') +var clone = require('./clone.js') + +var util = require('util') + +/* istanbul ignore next - node 0.x polyfill */ +var gracefulQueue +var previousSymbol + +/* istanbul ignore else - node 0.x polyfill */ +if (typeof Symbol === 'function' && typeof Symbol.for === 'function') { + gracefulQueue = Symbol.for('graceful-fs.queue') + // This is used in testing by future versions + previousSymbol = Symbol.for('graceful-fs.previous') +} else { + gracefulQueue = '___graceful-fs.queue' + previousSymbol = '___graceful-fs.previous' +} + +function noop () {} + +function publishQueue(context, queue) { + Object.defineProperty(context, gracefulQueue, { + get: function() { + return queue + } + }) +} + +var debug = noop +if (util.debuglog) + debug = util.debuglog('gfs4') +else if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || '')) + debug = function() { + var m = util.format.apply(util, arguments) + m = 'GFS4: ' + m.split(/\n/).join('\nGFS4: ') + console.error(m) + } + +// Once time initialization +if (!fs[gracefulQueue]) { + // This queue can be shared by multiple loaded instances + var queue = global[gracefulQueue] || [] + publishQueue(fs, queue) + + // Patch fs.close/closeSync to shared queue version, because we need + // to retry() whenever a close happens *anywhere* in the program. + // This is essential when multiple graceful-fs instances are + // in play at the same time. + fs.close = (function (fs$close) { + function close (fd, cb) { + return fs$close.call(fs, fd, function (err) { + // This function uses the graceful-fs shared queue + if (!err) { + resetQueue() + } + + if (typeof cb === 'function') + cb.apply(this, arguments) + }) + } + + Object.defineProperty(close, previousSymbol, { + value: fs$close + }) + return close + })(fs.close) + + fs.closeSync = (function (fs$closeSync) { + function closeSync (fd) { + // This function uses the graceful-fs shared queue + fs$closeSync.apply(fs, arguments) + resetQueue() + } + + Object.defineProperty(closeSync, previousSymbol, { + value: fs$closeSync + }) + return closeSync + })(fs.closeSync) + + if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || '')) { + process.on('exit', function() { + debug(fs[gracefulQueue]) + require('assert').equal(fs[gracefulQueue].length, 0) + }) + } +} + +if (!global[gracefulQueue]) { + publishQueue(global, fs[gracefulQueue]); +} + +module.exports = patch(clone(fs)) +if (process.env.TEST_GRACEFUL_FS_GLOBAL_PATCH && !fs.__patched) { + module.exports = patch(fs) + fs.__patched = true; +} + +function patch (fs) { + // Everything that references the open() function needs to be in here + polyfills(fs) + fs.gracefulify = patch + + fs.createReadStream = createReadStream + fs.createWriteStream = createWriteStream + var fs$readFile = fs.readFile + fs.readFile = readFile + function readFile (path, options, cb) { + if (typeof options === 'function') + cb = options, options = null + + return go$readFile(path, options, cb) + + function go$readFile (path, options, cb, startTime) { + return fs$readFile(path, options, function (err) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([go$readFile, [path, options, cb], err, startTime || Date.now(), Date.now()]) + else { + if (typeof cb === 'function') + cb.apply(this, arguments) + } + }) + } + } + + var fs$writeFile = fs.writeFile + fs.writeFile = writeFile + function writeFile (path, data, options, cb) { + if (typeof options === 'function') + cb = options, options = null + + return go$writeFile(path, data, options, cb) + + function go$writeFile (path, data, options, cb, startTime) { + return fs$writeFile(path, data, options, function (err) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([go$writeFile, [path, data, options, cb], err, startTime || Date.now(), Date.now()]) + else { + if (typeof cb === 'function') + cb.apply(this, arguments) + } + }) + } + } + + var fs$appendFile = fs.appendFile + if (fs$appendFile) + fs.appendFile = appendFile + function appendFile (path, data, options, cb) { + if (typeof options === 'function') + cb = options, options = null + + return go$appendFile(path, data, options, cb) + + function go$appendFile (path, data, options, cb, startTime) { + return fs$appendFile(path, data, options, function (err) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([go$appendFile, [path, data, options, cb], err, startTime || Date.now(), Date.now()]) + else { + if (typeof cb === 'function') + cb.apply(this, arguments) + } + }) + } + } + + var fs$copyFile = fs.copyFile + if (fs$copyFile) + fs.copyFile = copyFile + function copyFile (src, dest, flags, cb) { + if (typeof flags === 'function') { + cb = flags + flags = 0 + } + return go$copyFile(src, dest, flags, cb) + + function go$copyFile (src, dest, flags, cb, startTime) { + return fs$copyFile(src, dest, flags, function (err) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([go$copyFile, [src, dest, flags, cb], err, startTime || Date.now(), Date.now()]) + else { + if (typeof cb === 'function') + cb.apply(this, arguments) + } + }) + } + } + + var fs$readdir = fs.readdir + fs.readdir = readdir + var noReaddirOptionVersions = /^v[0-5]\./ + function readdir (path, options, cb) { + if (typeof options === 'function') + cb = options, options = null + + var go$readdir = noReaddirOptionVersions.test(process.version) + ? function go$readdir (path, options, cb, startTime) { + return fs$readdir(path, fs$readdirCallback( + path, options, cb, startTime + )) + } + : function go$readdir (path, options, cb, startTime) { + return fs$readdir(path, options, fs$readdirCallback( + path, options, cb, startTime + )) + } + + return go$readdir(path, options, cb) + + function fs$readdirCallback (path, options, cb, startTime) { + return function (err, files) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([ + go$readdir, + [path, options, cb], + err, + startTime || Date.now(), + Date.now() + ]) + else { + if (files && files.sort) + files.sort() + + if (typeof cb === 'function') + cb.call(this, err, files) + } + } + } + } + + if (process.version.substr(0, 4) === 'v0.8') { + var legStreams = legacy(fs) + ReadStream = legStreams.ReadStream + WriteStream = legStreams.WriteStream + } + + var fs$ReadStream = fs.ReadStream + if (fs$ReadStream) { + ReadStream.prototype = Object.create(fs$ReadStream.prototype) + ReadStream.prototype.open = ReadStream$open + } + + var fs$WriteStream = fs.WriteStream + if (fs$WriteStream) { + WriteStream.prototype = Object.create(fs$WriteStream.prototype) + WriteStream.prototype.open = WriteStream$open + } + + Object.defineProperty(fs, 'ReadStream', { + get: function () { + return ReadStream + }, + set: function (val) { + ReadStream = val + }, + enumerable: true, + configurable: true + }) + Object.defineProperty(fs, 'WriteStream', { + get: function () { + return WriteStream + }, + set: function (val) { + WriteStream = val + }, + enumerable: true, + configurable: true + }) + + // legacy names + var FileReadStream = ReadStream + Object.defineProperty(fs, 'FileReadStream', { + get: function () { + return FileReadStream + }, + set: function (val) { + FileReadStream = val + }, + enumerable: true, + configurable: true + }) + var FileWriteStream = WriteStream + Object.defineProperty(fs, 'FileWriteStream', { + get: function () { + return FileWriteStream + }, + set: function (val) { + FileWriteStream = val + }, + enumerable: true, + configurable: true + }) + + function ReadStream (path, options) { + if (this instanceof ReadStream) + return fs$ReadStream.apply(this, arguments), this + else + return ReadStream.apply(Object.create(ReadStream.prototype), arguments) + } + + function ReadStream$open () { + var that = this + open(that.path, that.flags, that.mode, function (err, fd) { + if (err) { + if (that.autoClose) + that.destroy() + + that.emit('error', err) + } else { + that.fd = fd + that.emit('open', fd) + that.read() + } + }) + } + + function WriteStream (path, options) { + if (this instanceof WriteStream) + return fs$WriteStream.apply(this, arguments), this + else + return WriteStream.apply(Object.create(WriteStream.prototype), arguments) + } + + function WriteStream$open () { + var that = this + open(that.path, that.flags, that.mode, function (err, fd) { + if (err) { + that.destroy() + that.emit('error', err) + } else { + that.fd = fd + that.emit('open', fd) + } + }) + } + + function createReadStream (path, options) { + return new fs.ReadStream(path, options) + } + + function createWriteStream (path, options) { + return new fs.WriteStream(path, options) + } + + var fs$open = fs.open + fs.open = open + function open (path, flags, mode, cb) { + if (typeof mode === 'function') + cb = mode, mode = null + + return go$open(path, flags, mode, cb) + + function go$open (path, flags, mode, cb, startTime) { + return fs$open(path, flags, mode, function (err, fd) { + if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) + enqueue([go$open, [path, flags, mode, cb], err, startTime || Date.now(), Date.now()]) + else { + if (typeof cb === 'function') + cb.apply(this, arguments) + } + }) + } + } + + return fs +} + +function enqueue (elem) { + debug('ENQUEUE', elem[0].name, elem[1]) + fs[gracefulQueue].push(elem) + retry() +} + +// keep track of the timeout between retry() calls +var retryTimer + +// reset the startTime and lastTime to now +// this resets the start of the 60 second overall timeout as well as the +// delay between attempts so that we'll retry these jobs sooner +function resetQueue () { + var now = Date.now() + for (var i = 0; i < fs[gracefulQueue].length; ++i) { + // entries that are only a length of 2 are from an older version, don't + // bother modifying those since they'll be retried anyway. + if (fs[gracefulQueue][i].length > 2) { + fs[gracefulQueue][i][3] = now // startTime + fs[gracefulQueue][i][4] = now // lastTime + } + } + // call retry to make sure we're actively processing the queue + retry() +} + +function retry () { + // clear the timer and remove it to help prevent unintended concurrency + clearTimeout(retryTimer) + retryTimer = undefined + + if (fs[gracefulQueue].length === 0) + return + + var elem = fs[gracefulQueue].shift() + var fn = elem[0] + var args = elem[1] + // these items may be unset if they were added by an older graceful-fs + var err = elem[2] + var startTime = elem[3] + var lastTime = elem[4] + + // if we don't have a startTime we have no way of knowing if we've waited + // long enough, so go ahead and retry this item now + if (startTime === undefined) { + debug('RETRY', fn.name, args) + fn.apply(null, args) + } else if (Date.now() - startTime >= 60000) { + // it's been more than 60 seconds total, bail now + debug('TIMEOUT', fn.name, args) + var cb = args.pop() + if (typeof cb === 'function') + cb.call(null, err) + } else { + // the amount of time between the last attempt and right now + var sinceAttempt = Date.now() - lastTime + // the amount of time between when we first tried, and when we last tried + // rounded up to at least 1 + var sinceStart = Math.max(lastTime - startTime, 1) + // backoff. wait longer than the total time we've been retrying, but only + // up to a maximum of 100ms + var desiredDelay = Math.min(sinceStart * 1.2, 100) + // it's been long enough since the last retry, do it again + if (sinceAttempt >= desiredDelay) { + debug('RETRY', fn.name, args) + fn.apply(null, args.concat([startTime])) + } else { + // if we can't do this job yet, push it to the end of the queue + // and let the next iteration check again + fs[gracefulQueue].push(elem) + } + } + + // schedule our next run if one isn't already scheduled + if (retryTimer === undefined) { + retryTimer = setTimeout(retry, 0) + } +} diff --git a/node_modules/graceful-fs/legacy-streams.js b/node_modules/graceful-fs/legacy-streams.js new file mode 100644 index 0000000..d617b50 --- /dev/null +++ b/node_modules/graceful-fs/legacy-streams.js @@ -0,0 +1,118 @@ +var Stream = require('stream').Stream + +module.exports = legacy + +function legacy (fs) { + return { + ReadStream: ReadStream, + WriteStream: WriteStream + } + + function ReadStream (path, options) { + if (!(this instanceof ReadStream)) return new ReadStream(path, options); + + Stream.call(this); + + var self = this; + + this.path = path; + this.fd = null; + this.readable = true; + this.paused = false; + + this.flags = 'r'; + this.mode = 438; /*=0666*/ + this.bufferSize = 64 * 1024; + + options = options || {}; + + // Mixin options into this + var keys = Object.keys(options); + for (var index = 0, length = keys.length; index < length; index++) { + var key = keys[index]; + this[key] = options[key]; + } + + if (this.encoding) this.setEncoding(this.encoding); + + if (this.start !== undefined) { + if ('number' !== typeof this.start) { + throw TypeError('start must be a Number'); + } + if (this.end === undefined) { + this.end = Infinity; + } else if ('number' !== typeof this.end) { + throw TypeError('end must be a Number'); + } + + if (this.start > this.end) { + throw new Error('start must be <= end'); + } + + this.pos = this.start; + } + + if (this.fd !== null) { + process.nextTick(function() { + self._read(); + }); + return; + } + + fs.open(this.path, this.flags, this.mode, function (err, fd) { + if (err) { + self.emit('error', err); + self.readable = false; + return; + } + + self.fd = fd; + self.emit('open', fd); + self._read(); + }) + } + + function WriteStream (path, options) { + if (!(this instanceof WriteStream)) return new WriteStream(path, options); + + Stream.call(this); + + this.path = path; + this.fd = null; + this.writable = true; + + this.flags = 'w'; + this.encoding = 'binary'; + this.mode = 438; /*=0666*/ + this.bytesWritten = 0; + + options = options || {}; + + // Mixin options into this + var keys = Object.keys(options); + for (var index = 0, length = keys.length; index < length; index++) { + var key = keys[index]; + this[key] = options[key]; + } + + if (this.start !== undefined) { + if ('number' !== typeof this.start) { + throw TypeError('start must be a Number'); + } + if (this.start < 0) { + throw new Error('start must be >= zero'); + } + + this.pos = this.start; + } + + this.busy = false; + this._queue = []; + + if (this.fd === null) { + this._open = fs.open; + this._queue.push([this._open, this.path, this.flags, this.mode, undefined]); + this.flush(); + } + } +} diff --git a/node_modules/graceful-fs/package.json b/node_modules/graceful-fs/package.json new file mode 100644 index 0000000..3057856 --- /dev/null +++ b/node_modules/graceful-fs/package.json @@ -0,0 +1,50 @@ +{ + "name": "graceful-fs", + "description": "A drop-in replacement for fs, making various improvements.", + "version": "4.2.10", + "repository": { + "type": "git", + "url": "https://github.com/isaacs/node-graceful-fs" + }, + "main": "graceful-fs.js", + "directories": { + "test": "test" + }, + "scripts": { + "preversion": "npm test", + "postversion": "npm publish", + "postpublish": "git push origin --follow-tags", + "test": "nyc --silent node test.js | tap -c -", + "posttest": "nyc report" + }, + "keywords": [ + "fs", + "module", + "reading", + "retry", + "retries", + "queue", + "error", + "errors", + "handling", + "EMFILE", + "EAGAIN", + "EINVAL", + "EPERM", + "EACCESS" + ], + "license": "ISC", + "devDependencies": { + "import-fresh": "^2.0.0", + "mkdirp": "^0.5.0", + "rimraf": "^2.2.8", + "tap": "^12.7.0" + }, + "files": [ + "fs.js", + "graceful-fs.js", + "legacy-streams.js", + "polyfills.js", + "clone.js" + ] +} diff --git a/node_modules/graceful-fs/polyfills.js b/node_modules/graceful-fs/polyfills.js new file mode 100644 index 0000000..46dea36 --- /dev/null +++ b/node_modules/graceful-fs/polyfills.js @@ -0,0 +1,355 @@ +var constants = require('constants') + +var origCwd = process.cwd +var cwd = null + +var platform = process.env.GRACEFUL_FS_PLATFORM || process.platform + +process.cwd = function() { + if (!cwd) + cwd = origCwd.call(process) + return cwd +} +try { + process.cwd() +} catch (er) {} + +// This check is needed until node.js 12 is required +if (typeof process.chdir === 'function') { + var chdir = process.chdir + process.chdir = function (d) { + cwd = null + chdir.call(process, d) + } + if (Object.setPrototypeOf) Object.setPrototypeOf(process.chdir, chdir) +} + +module.exports = patch + +function patch (fs) { + // (re-)implement some things that are known busted or missing. + + // lchmod, broken prior to 0.6.2 + // back-port the fix here. + if (constants.hasOwnProperty('O_SYMLINK') && + process.version.match(/^v0\.6\.[0-2]|^v0\.5\./)) { + patchLchmod(fs) + } + + // lutimes implementation, or no-op + if (!fs.lutimes) { + patchLutimes(fs) + } + + // https://github.com/isaacs/node-graceful-fs/issues/4 + // Chown should not fail on einval or eperm if non-root. + // It should not fail on enosys ever, as this just indicates + // that a fs doesn't support the intended operation. + + fs.chown = chownFix(fs.chown) + fs.fchown = chownFix(fs.fchown) + fs.lchown = chownFix(fs.lchown) + + fs.chmod = chmodFix(fs.chmod) + fs.fchmod = chmodFix(fs.fchmod) + fs.lchmod = chmodFix(fs.lchmod) + + fs.chownSync = chownFixSync(fs.chownSync) + fs.fchownSync = chownFixSync(fs.fchownSync) + fs.lchownSync = chownFixSync(fs.lchownSync) + + fs.chmodSync = chmodFixSync(fs.chmodSync) + fs.fchmodSync = chmodFixSync(fs.fchmodSync) + fs.lchmodSync = chmodFixSync(fs.lchmodSync) + + fs.stat = statFix(fs.stat) + fs.fstat = statFix(fs.fstat) + fs.lstat = statFix(fs.lstat) + + fs.statSync = statFixSync(fs.statSync) + fs.fstatSync = statFixSync(fs.fstatSync) + fs.lstatSync = statFixSync(fs.lstatSync) + + // if lchmod/lchown do not exist, then make them no-ops + if (fs.chmod && !fs.lchmod) { + fs.lchmod = function (path, mode, cb) { + if (cb) process.nextTick(cb) + } + fs.lchmodSync = function () {} + } + if (fs.chown && !fs.lchown) { + fs.lchown = function (path, uid, gid, cb) { + if (cb) process.nextTick(cb) + } + fs.lchownSync = function () {} + } + + // on Windows, A/V software can lock the directory, causing this + // to fail with an EACCES or EPERM if the directory contains newly + // created files. Try again on failure, for up to 60 seconds. + + // Set the timeout this long because some Windows Anti-Virus, such as Parity + // bit9, may lock files for up to a minute, causing npm package install + // failures. Also, take care to yield the scheduler. Windows scheduling gives + // CPU to a busy looping process, which can cause the program causing the lock + // contention to be starved of CPU by node, so the contention doesn't resolve. + if (platform === "win32") { + fs.rename = typeof fs.rename !== 'function' ? fs.rename + : (function (fs$rename) { + function rename (from, to, cb) { + var start = Date.now() + var backoff = 0; + fs$rename(from, to, function CB (er) { + if (er + && (er.code === "EACCES" || er.code === "EPERM") + && Date.now() - start < 60000) { + setTimeout(function() { + fs.stat(to, function (stater, st) { + if (stater && stater.code === "ENOENT") + fs$rename(from, to, CB); + else + cb(er) + }) + }, backoff) + if (backoff < 100) + backoff += 10; + return; + } + if (cb) cb(er) + }) + } + if (Object.setPrototypeOf) Object.setPrototypeOf(rename, fs$rename) + return rename + })(fs.rename) + } + + // if read() returns EAGAIN, then just try it again. + fs.read = typeof fs.read !== 'function' ? fs.read + : (function (fs$read) { + function read (fd, buffer, offset, length, position, callback_) { + var callback + if (callback_ && typeof callback_ === 'function') { + var eagCounter = 0 + callback = function (er, _, __) { + if (er && er.code === 'EAGAIN' && eagCounter < 10) { + eagCounter ++ + return fs$read.call(fs, fd, buffer, offset, length, position, callback) + } + callback_.apply(this, arguments) + } + } + return fs$read.call(fs, fd, buffer, offset, length, position, callback) + } + + // This ensures `util.promisify` works as it does for native `fs.read`. + if (Object.setPrototypeOf) Object.setPrototypeOf(read, fs$read) + return read + })(fs.read) + + fs.readSync = typeof fs.readSync !== 'function' ? fs.readSync + : (function (fs$readSync) { return function (fd, buffer, offset, length, position) { + var eagCounter = 0 + while (true) { + try { + return fs$readSync.call(fs, fd, buffer, offset, length, position) + } catch (er) { + if (er.code === 'EAGAIN' && eagCounter < 10) { + eagCounter ++ + continue + } + throw er + } + } + }})(fs.readSync) + + function patchLchmod (fs) { + fs.lchmod = function (path, mode, callback) { + fs.open( path + , constants.O_WRONLY | constants.O_SYMLINK + , mode + , function (err, fd) { + if (err) { + if (callback) callback(err) + return + } + // prefer to return the chmod error, if one occurs, + // but still try to close, and report closing errors if they occur. + fs.fchmod(fd, mode, function (err) { + fs.close(fd, function(err2) { + if (callback) callback(err || err2) + }) + }) + }) + } + + fs.lchmodSync = function (path, mode) { + var fd = fs.openSync(path, constants.O_WRONLY | constants.O_SYMLINK, mode) + + // prefer to return the chmod error, if one occurs, + // but still try to close, and report closing errors if they occur. + var threw = true + var ret + try { + ret = fs.fchmodSync(fd, mode) + threw = false + } finally { + if (threw) { + try { + fs.closeSync(fd) + } catch (er) {} + } else { + fs.closeSync(fd) + } + } + return ret + } + } + + function patchLutimes (fs) { + if (constants.hasOwnProperty("O_SYMLINK") && fs.futimes) { + fs.lutimes = function (path, at, mt, cb) { + fs.open(path, constants.O_SYMLINK, function (er, fd) { + if (er) { + if (cb) cb(er) + return + } + fs.futimes(fd, at, mt, function (er) { + fs.close(fd, function (er2) { + if (cb) cb(er || er2) + }) + }) + }) + } + + fs.lutimesSync = function (path, at, mt) { + var fd = fs.openSync(path, constants.O_SYMLINK) + var ret + var threw = true + try { + ret = fs.futimesSync(fd, at, mt) + threw = false + } finally { + if (threw) { + try { + fs.closeSync(fd) + } catch (er) {} + } else { + fs.closeSync(fd) + } + } + return ret + } + + } else if (fs.futimes) { + fs.lutimes = function (_a, _b, _c, cb) { if (cb) process.nextTick(cb) } + fs.lutimesSync = function () {} + } + } + + function chmodFix (orig) { + if (!orig) return orig + return function (target, mode, cb) { + return orig.call(fs, target, mode, function (er) { + if (chownErOk(er)) er = null + if (cb) cb.apply(this, arguments) + }) + } + } + + function chmodFixSync (orig) { + if (!orig) return orig + return function (target, mode) { + try { + return orig.call(fs, target, mode) + } catch (er) { + if (!chownErOk(er)) throw er + } + } + } + + + function chownFix (orig) { + if (!orig) return orig + return function (target, uid, gid, cb) { + return orig.call(fs, target, uid, gid, function (er) { + if (chownErOk(er)) er = null + if (cb) cb.apply(this, arguments) + }) + } + } + + function chownFixSync (orig) { + if (!orig) return orig + return function (target, uid, gid) { + try { + return orig.call(fs, target, uid, gid) + } catch (er) { + if (!chownErOk(er)) throw er + } + } + } + + function statFix (orig) { + if (!orig) return orig + // Older versions of Node erroneously returned signed integers for + // uid + gid. + return function (target, options, cb) { + if (typeof options === 'function') { + cb = options + options = null + } + function callback (er, stats) { + if (stats) { + if (stats.uid < 0) stats.uid += 0x100000000 + if (stats.gid < 0) stats.gid += 0x100000000 + } + if (cb) cb.apply(this, arguments) + } + return options ? orig.call(fs, target, options, callback) + : orig.call(fs, target, callback) + } + } + + function statFixSync (orig) { + if (!orig) return orig + // Older versions of Node erroneously returned signed integers for + // uid + gid. + return function (target, options) { + var stats = options ? orig.call(fs, target, options) + : orig.call(fs, target) + if (stats) { + if (stats.uid < 0) stats.uid += 0x100000000 + if (stats.gid < 0) stats.gid += 0x100000000 + } + return stats; + } + } + + // ENOSYS means that the fs doesn't support the op. Just ignore + // that, because it doesn't matter. + // + // if there's no getuid, or if getuid() is something other + // than 0, and the error is EINVAL or EPERM, then just ignore + // it. + // + // This specific case is a silent failure in cp, install, tar, + // and most other unix tools that manage permissions. + // + // When running as root, or if other types of errors are + // encountered, then it's strict. + function chownErOk (er) { + if (!er) + return true + + if (er.code === "ENOSYS") + return true + + var nonroot = !process.getuid || process.getuid() !== 0 + if (nonroot) { + if (er.code === "EINVAL" || er.code === "EPERM") + return true + } + + return false + } +} diff --git a/node_modules/http-cache-semantics/LICENSE b/node_modules/http-cache-semantics/LICENSE new file mode 100644 index 0000000..493d2ea --- /dev/null +++ b/node_modules/http-cache-semantics/LICENSE @@ -0,0 +1,9 @@ +Copyright 2016-2018 Kornel Lesiński + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/node_modules/http-cache-semantics/README.md b/node_modules/http-cache-semantics/README.md new file mode 100644 index 0000000..685aa55 --- /dev/null +++ b/node_modules/http-cache-semantics/README.md @@ -0,0 +1,203 @@ +# Can I cache this? [![Build Status](https://travis-ci.org/kornelski/http-cache-semantics.svg?branch=master)](https://travis-ci.org/kornelski/http-cache-semantics) + +`CachePolicy` tells when responses can be reused from a cache, taking into account [HTTP RFC 7234](http://httpwg.org/specs/rfc7234.html) rules for user agents and shared caches. +It also implements [RFC 5861](https://tools.ietf.org/html/rfc5861), implementing `stale-if-error` and `stale-while-revalidate`. +It's aware of many tricky details such as the `Vary` header, proxy revalidation, and authenticated responses. + +## Usage + +Cacheability of an HTTP response depends on how it was requested, so both `request` and `response` are required to create the policy. + +```js +const policy = new CachePolicy(request, response, options); + +if (!policy.storable()) { + // throw the response away, it's not usable at all + return; +} + +// Cache the data AND the policy object in your cache +// (this is pseudocode, roll your own cache (lru-cache package works)) +letsPretendThisIsSomeCache.set( + request.url, + { policy, response }, + policy.timeToLive() +); +``` + +```js +// And later, when you receive a new request: +const { policy, response } = letsPretendThisIsSomeCache.get(newRequest.url); + +// It's not enough that it exists in the cache, it has to match the new request, too: +if (policy && policy.satisfiesWithoutRevalidation(newRequest)) { + // OK, the previous response can be used to respond to the `newRequest`. + // Response headers have to be updated, e.g. to add Age and remove uncacheable headers. + response.headers = policy.responseHeaders(); + return response; +} +``` + +It may be surprising, but it's not enough for an HTTP response to be [fresh](#yo-fresh) to satisfy a request. It may need to match request headers specified in `Vary`. Even a matching fresh response may still not be usable if the new request restricted cacheability, etc. + +The key method is `satisfiesWithoutRevalidation(newRequest)`, which checks whether the `newRequest` is compatible with the original request and whether all caching conditions are met. + +### Constructor options + +Request and response must have a `headers` property with all header names in lower case. `url`, `status` and `method` are optional (defaults are any URL, status `200`, and `GET` method). + +```js +const request = { + url: '/', + method: 'GET', + headers: { + accept: '*/*', + }, +}; + +const response = { + status: 200, + headers: { + 'cache-control': 'public, max-age=7234', + }, +}; + +const options = { + shared: true, + cacheHeuristic: 0.1, + immutableMinTimeToLive: 24 * 3600 * 1000, // 24h + ignoreCargoCult: false, +}; +``` + +If `options.shared` is `true` (default), then the response is evaluated from a perspective of a shared cache (i.e. `private` is not cacheable and `s-maxage` is respected). If `options.shared` is `false`, then the response is evaluated from a perspective of a single-user cache (i.e. `private` is cacheable and `s-maxage` is ignored). `shared: true` is recommended for HTTP clients. + +`options.cacheHeuristic` is a fraction of response's age that is used as a fallback cache duration. The default is 0.1 (10%), e.g. if a file hasn't been modified for 100 days, it'll be cached for 100\*0.1 = 10 days. + +`options.immutableMinTimeToLive` is a number of milliseconds to assume as the default time to cache responses with `Cache-Control: immutable`. Note that [per RFC](http://httpwg.org/http-extensions/immutable.html) these can become stale, so `max-age` still overrides the default. + +If `options.ignoreCargoCult` is true, common anti-cache directives will be completely ignored if the non-standard `pre-check` and `post-check` directives are present. These two useless directives are most commonly found in bad StackOverflow answers and PHP's "session limiter" defaults. + +### `storable()` + +Returns `true` if the response can be stored in a cache. If it's `false` then you MUST NOT store either the request or the response. + +### `satisfiesWithoutRevalidation(newRequest)` + +This is the most important method. Use this method to check whether the cached response is still fresh in the context of the new request. + +If it returns `true`, then the given `request` matches the original response this cache policy has been created with, and the response can be reused without contacting the server. Note that the old response can't be returned without being updated, see `responseHeaders()`. + +If it returns `false`, then the response may not be matching at all (e.g. it's for a different URL or method), or may require to be refreshed first (see `revalidationHeaders()`). + +### `responseHeaders()` + +Returns updated, filtered set of response headers to return to clients receiving the cached response. This function is necessary, because proxies MUST always remove hop-by-hop headers (such as `TE` and `Connection`) and update response's `Age` to avoid doubling cache time. + +```js +cachedResponse.headers = cachePolicy.responseHeaders(cachedResponse); +``` + +### `timeToLive()` + +Returns approximate time in _milliseconds_ until the response becomes stale (i.e. not fresh). + +After that time (when `timeToLive() <= 0`) the response might not be usable without revalidation. However, there are exceptions, e.g. a client can explicitly allow stale responses, so always check with `satisfiesWithoutRevalidation()`. +`stale-if-error` and `stale-while-revalidate` extend the time to live of the cache, that can still be used if stale. + +### `toObject()`/`fromObject(json)` + +Chances are you'll want to store the `CachePolicy` object along with the cached response. `obj = policy.toObject()` gives a plain JSON-serializable object. `policy = CachePolicy.fromObject(obj)` creates an instance from it. + +### Refreshing stale cache (revalidation) + +When a cached response has expired, it can be made fresh again by making a request to the origin server. The server may respond with status 304 (Not Modified) without sending the response body again, saving bandwidth. + +The following methods help perform the update efficiently and correctly. + +#### `revalidationHeaders(newRequest)` + +Returns updated, filtered set of request headers to send to the origin server to check if the cached response can be reused. These headers allow the origin server to return status 304 indicating the response is still fresh. All headers unrelated to caching are passed through as-is. + +Use this method when updating cache from the origin server. + +```js +updateRequest.headers = cachePolicy.revalidationHeaders(updateRequest); +``` + +#### `revalidatedPolicy(revalidationRequest, revalidationResponse)` + +Use this method to update the cache after receiving a new response from the origin server. It returns an object with two keys: + +- `policy` — A new `CachePolicy` with HTTP headers updated from `revalidationResponse`. You can always replace the old cached `CachePolicy` with the new one. +- `modified` — Boolean indicating whether the response body has changed. + - If `false`, then a valid 304 Not Modified response has been received, and you can reuse the old cached response body. This is also affected by `stale-if-error`. + - If `true`, you should use new response's body (if present), or make another request to the origin server without any conditional headers (i.e. don't use `revalidationHeaders()` this time) to get the new resource. + +```js +// When serving requests from cache: +const { oldPolicy, oldResponse } = letsPretendThisIsSomeCache.get( + newRequest.url +); + +if (!oldPolicy.satisfiesWithoutRevalidation(newRequest)) { + // Change the request to ask the origin server if the cached response can be used + newRequest.headers = oldPolicy.revalidationHeaders(newRequest); + + // Send request to the origin server. The server may respond with status 304 + const newResponse = await makeRequest(newRequest); + + // Create updated policy and combined response from the old and new data + const { policy, modified } = oldPolicy.revalidatedPolicy( + newRequest, + newResponse + ); + const response = modified ? newResponse : oldResponse; + + // Update the cache with the newer/fresher response + letsPretendThisIsSomeCache.set( + newRequest.url, + { policy, response }, + policy.timeToLive() + ); + + // And proceed returning cached response as usual + response.headers = policy.responseHeaders(); + return response; +} +``` + +# Yo, FRESH + +![satisfiesWithoutRevalidation](fresh.jpg) + +## Used by + +- [ImageOptim API](https://imageoptim.com/api), [make-fetch-happen](https://github.com/zkat/make-fetch-happen), [cacheable-request](https://www.npmjs.com/package/cacheable-request) ([got](https://www.npmjs.com/package/got)), [npm/registry-fetch](https://github.com/npm/registry-fetch), [etc.](https://github.com/kornelski/http-cache-semantics/network/dependents) + +## Implemented + +- `Cache-Control` response header with all the quirks. +- `Expires` with check for bad clocks. +- `Pragma` response header. +- `Age` response header. +- `Vary` response header. +- Default cacheability of statuses and methods. +- Requests for stale data. +- Filtering of hop-by-hop headers. +- Basic revalidation request +- `stale-if-error` + +## Unimplemented + +- Merging of range requests, `If-Range` (but correctly supports them as non-cacheable) +- Revalidation of multiple representations + +### Trusting server `Date` + +Per the RFC, the cache should take into account the time between server-supplied `Date` and the time it received the response. The RFC-mandated behavior creates two problems: + + * Servers with incorrectly set timezone may add several hours to cache age (or more, if the clock is completely wrong). + * Even reasonably correct clocks may be off by a couple of seconds, breaking `max-age=1` trick (which is useful for reverse proxies on high-traffic servers). + +Previous versions of this library had an option to ignore the server date if it was "too inaccurate". To support the `max-age=1` trick the library also has to ignore dates that pretty accurate. There's no point of having an option to trust dates that are only a bit inaccurate, so this library won't trust any server dates. `max-age` will be interpreted from the time the response has been received, not from when it has been sent. This will affect only [RFC 1149 networks](https://tools.ietf.org/html/rfc1149). diff --git a/node_modules/http-cache-semantics/index.js b/node_modules/http-cache-semantics/index.js new file mode 100644 index 0000000..4f6c2f3 --- /dev/null +++ b/node_modules/http-cache-semantics/index.js @@ -0,0 +1,673 @@ +'use strict'; +// rfc7231 6.1 +const statusCodeCacheableByDefault = new Set([ + 200, + 203, + 204, + 206, + 300, + 301, + 404, + 405, + 410, + 414, + 501, +]); + +// This implementation does not understand partial responses (206) +const understoodStatuses = new Set([ + 200, + 203, + 204, + 300, + 301, + 302, + 303, + 307, + 308, + 404, + 405, + 410, + 414, + 501, +]); + +const errorStatusCodes = new Set([ + 500, + 502, + 503, + 504, +]); + +const hopByHopHeaders = { + date: true, // included, because we add Age update Date + connection: true, + 'keep-alive': true, + 'proxy-authenticate': true, + 'proxy-authorization': true, + te: true, + trailer: true, + 'transfer-encoding': true, + upgrade: true, +}; + +const excludedFromRevalidationUpdate = { + // Since the old body is reused, it doesn't make sense to change properties of the body + 'content-length': true, + 'content-encoding': true, + 'transfer-encoding': true, + 'content-range': true, +}; + +function toNumberOrZero(s) { + const n = parseInt(s, 10); + return isFinite(n) ? n : 0; +} + +// RFC 5861 +function isErrorResponse(response) { + // consider undefined response as faulty + if(!response) { + return true + } + return errorStatusCodes.has(response.status); +} + +function parseCacheControl(header) { + const cc = {}; + if (!header) return cc; + + // TODO: When there is more than one value present for a given directive (e.g., two Expires header fields, multiple Cache-Control: max-age directives), + // the directive's value is considered invalid. Caches are encouraged to consider responses that have invalid freshness information to be stale + const parts = header.trim().split(/\s*,\s*/); // TODO: lame parsing + for (const part of parts) { + const [k, v] = part.split(/\s*=\s*/, 2); + cc[k] = v === undefined ? true : v.replace(/^"|"$/g, ''); // TODO: lame unquoting + } + + return cc; +} + +function formatCacheControl(cc) { + let parts = []; + for (const k in cc) { + const v = cc[k]; + parts.push(v === true ? k : k + '=' + v); + } + if (!parts.length) { + return undefined; + } + return parts.join(', '); +} + +module.exports = class CachePolicy { + constructor( + req, + res, + { + shared, + cacheHeuristic, + immutableMinTimeToLive, + ignoreCargoCult, + _fromObject, + } = {} + ) { + if (_fromObject) { + this._fromObject(_fromObject); + return; + } + + if (!res || !res.headers) { + throw Error('Response headers missing'); + } + this._assertRequestHasHeaders(req); + + this._responseTime = this.now(); + this._isShared = shared !== false; + this._cacheHeuristic = + undefined !== cacheHeuristic ? cacheHeuristic : 0.1; // 10% matches IE + this._immutableMinTtl = + undefined !== immutableMinTimeToLive + ? immutableMinTimeToLive + : 24 * 3600 * 1000; + + this._status = 'status' in res ? res.status : 200; + this._resHeaders = res.headers; + this._rescc = parseCacheControl(res.headers['cache-control']); + this._method = 'method' in req ? req.method : 'GET'; + this._url = req.url; + this._host = req.headers.host; + this._noAuthorization = !req.headers.authorization; + this._reqHeaders = res.headers.vary ? req.headers : null; // Don't keep all request headers if they won't be used + this._reqcc = parseCacheControl(req.headers['cache-control']); + + // Assume that if someone uses legacy, non-standard uncecessary options they don't understand caching, + // so there's no point stricly adhering to the blindly copy&pasted directives. + if ( + ignoreCargoCult && + 'pre-check' in this._rescc && + 'post-check' in this._rescc + ) { + delete this._rescc['pre-check']; + delete this._rescc['post-check']; + delete this._rescc['no-cache']; + delete this._rescc['no-store']; + delete this._rescc['must-revalidate']; + this._resHeaders = Object.assign({}, this._resHeaders, { + 'cache-control': formatCacheControl(this._rescc), + }); + delete this._resHeaders.expires; + delete this._resHeaders.pragma; + } + + // When the Cache-Control header field is not present in a request, caches MUST consider the no-cache request pragma-directive + // as having the same effect as if "Cache-Control: no-cache" were present (see Section 5.2.1). + if ( + res.headers['cache-control'] == null && + /no-cache/.test(res.headers.pragma) + ) { + this._rescc['no-cache'] = true; + } + } + + now() { + return Date.now(); + } + + storable() { + // The "no-store" request directive indicates that a cache MUST NOT store any part of either this request or any response to it. + return !!( + !this._reqcc['no-store'] && + // A cache MUST NOT store a response to any request, unless: + // The request method is understood by the cache and defined as being cacheable, and + ('GET' === this._method || + 'HEAD' === this._method || + ('POST' === this._method && this._hasExplicitExpiration())) && + // the response status code is understood by the cache, and + understoodStatuses.has(this._status) && + // the "no-store" cache directive does not appear in request or response header fields, and + !this._rescc['no-store'] && + // the "private" response directive does not appear in the response, if the cache is shared, and + (!this._isShared || !this._rescc.private) && + // the Authorization header field does not appear in the request, if the cache is shared, + (!this._isShared || + this._noAuthorization || + this._allowsStoringAuthenticated()) && + // the response either: + // contains an Expires header field, or + (this._resHeaders.expires || + // contains a max-age response directive, or + // contains a s-maxage response directive and the cache is shared, or + // contains a public response directive. + this._rescc['max-age'] || + (this._isShared && this._rescc['s-maxage']) || + this._rescc.public || + // has a status code that is defined as cacheable by default + statusCodeCacheableByDefault.has(this._status)) + ); + } + + _hasExplicitExpiration() { + // 4.2.1 Calculating Freshness Lifetime + return ( + (this._isShared && this._rescc['s-maxage']) || + this._rescc['max-age'] || + this._resHeaders.expires + ); + } + + _assertRequestHasHeaders(req) { + if (!req || !req.headers) { + throw Error('Request headers missing'); + } + } + + satisfiesWithoutRevalidation(req) { + this._assertRequestHasHeaders(req); + + // When presented with a request, a cache MUST NOT reuse a stored response, unless: + // the presented request does not contain the no-cache pragma (Section 5.4), nor the no-cache cache directive, + // unless the stored response is successfully validated (Section 4.3), and + const requestCC = parseCacheControl(req.headers['cache-control']); + if (requestCC['no-cache'] || /no-cache/.test(req.headers.pragma)) { + return false; + } + + if (requestCC['max-age'] && this.age() > requestCC['max-age']) { + return false; + } + + if ( + requestCC['min-fresh'] && + this.timeToLive() < 1000 * requestCC['min-fresh'] + ) { + return false; + } + + // the stored response is either: + // fresh, or allowed to be served stale + if (this.stale()) { + const allowsStale = + requestCC['max-stale'] && + !this._rescc['must-revalidate'] && + (true === requestCC['max-stale'] || + requestCC['max-stale'] > this.age() - this.maxAge()); + if (!allowsStale) { + return false; + } + } + + return this._requestMatches(req, false); + } + + _requestMatches(req, allowHeadMethod) { + // The presented effective request URI and that of the stored response match, and + return ( + (!this._url || this._url === req.url) && + this._host === req.headers.host && + // the request method associated with the stored response allows it to be used for the presented request, and + (!req.method || + this._method === req.method || + (allowHeadMethod && 'HEAD' === req.method)) && + // selecting header fields nominated by the stored response (if any) match those presented, and + this._varyMatches(req) + ); + } + + _allowsStoringAuthenticated() { + // following Cache-Control response directives (Section 5.2.2) have such an effect: must-revalidate, public, and s-maxage. + return ( + this._rescc['must-revalidate'] || + this._rescc.public || + this._rescc['s-maxage'] + ); + } + + _varyMatches(req) { + if (!this._resHeaders.vary) { + return true; + } + + // A Vary header field-value of "*" always fails to match + if (this._resHeaders.vary === '*') { + return false; + } + + const fields = this._resHeaders.vary + .trim() + .toLowerCase() + .split(/\s*,\s*/); + for (const name of fields) { + if (req.headers[name] !== this._reqHeaders[name]) return false; + } + return true; + } + + _copyWithoutHopByHopHeaders(inHeaders) { + const headers = {}; + for (const name in inHeaders) { + if (hopByHopHeaders[name]) continue; + headers[name] = inHeaders[name]; + } + // 9.1. Connection + if (inHeaders.connection) { + const tokens = inHeaders.connection.trim().split(/\s*,\s*/); + for (const name of tokens) { + delete headers[name]; + } + } + if (headers.warning) { + const warnings = headers.warning.split(/,/).filter(warning => { + return !/^\s*1[0-9][0-9]/.test(warning); + }); + if (!warnings.length) { + delete headers.warning; + } else { + headers.warning = warnings.join(',').trim(); + } + } + return headers; + } + + responseHeaders() { + const headers = this._copyWithoutHopByHopHeaders(this._resHeaders); + const age = this.age(); + + // A cache SHOULD generate 113 warning if it heuristically chose a freshness + // lifetime greater than 24 hours and the response's age is greater than 24 hours. + if ( + age > 3600 * 24 && + !this._hasExplicitExpiration() && + this.maxAge() > 3600 * 24 + ) { + headers.warning = + (headers.warning ? `${headers.warning}, ` : '') + + '113 - "rfc7234 5.5.4"'; + } + headers.age = `${Math.round(age)}`; + headers.date = new Date(this.now()).toUTCString(); + return headers; + } + + /** + * Value of the Date response header or current time if Date was invalid + * @return timestamp + */ + date() { + const serverDate = Date.parse(this._resHeaders.date); + if (isFinite(serverDate)) { + return serverDate; + } + return this._responseTime; + } + + /** + * Value of the Age header, in seconds, updated for the current time. + * May be fractional. + * + * @return Number + */ + age() { + let age = this._ageValue(); + + const residentTime = (this.now() - this._responseTime) / 1000; + return age + residentTime; + } + + _ageValue() { + return toNumberOrZero(this._resHeaders.age); + } + + /** + * Value of applicable max-age (or heuristic equivalent) in seconds. This counts since response's `Date`. + * + * For an up-to-date value, see `timeToLive()`. + * + * @return Number + */ + maxAge() { + if (!this.storable() || this._rescc['no-cache']) { + return 0; + } + + // Shared responses with cookies are cacheable according to the RFC, but IMHO it'd be unwise to do so by default + // so this implementation requires explicit opt-in via public header + if ( + this._isShared && + (this._resHeaders['set-cookie'] && + !this._rescc.public && + !this._rescc.immutable) + ) { + return 0; + } + + if (this._resHeaders.vary === '*') { + return 0; + } + + if (this._isShared) { + if (this._rescc['proxy-revalidate']) { + return 0; + } + // if a response includes the s-maxage directive, a shared cache recipient MUST ignore the Expires field. + if (this._rescc['s-maxage']) { + return toNumberOrZero(this._rescc['s-maxage']); + } + } + + // If a response includes a Cache-Control field with the max-age directive, a recipient MUST ignore the Expires field. + if (this._rescc['max-age']) { + return toNumberOrZero(this._rescc['max-age']); + } + + const defaultMinTtl = this._rescc.immutable ? this._immutableMinTtl : 0; + + const serverDate = this.date(); + if (this._resHeaders.expires) { + const expires = Date.parse(this._resHeaders.expires); + // A cache recipient MUST interpret invalid date formats, especially the value "0", as representing a time in the past (i.e., "already expired"). + if (Number.isNaN(expires) || expires < serverDate) { + return 0; + } + return Math.max(defaultMinTtl, (expires - serverDate) / 1000); + } + + if (this._resHeaders['last-modified']) { + const lastModified = Date.parse(this._resHeaders['last-modified']); + if (isFinite(lastModified) && serverDate > lastModified) { + return Math.max( + defaultMinTtl, + ((serverDate - lastModified) / 1000) * this._cacheHeuristic + ); + } + } + + return defaultMinTtl; + } + + timeToLive() { + const age = this.maxAge() - this.age(); + const staleIfErrorAge = age + toNumberOrZero(this._rescc['stale-if-error']); + const staleWhileRevalidateAge = age + toNumberOrZero(this._rescc['stale-while-revalidate']); + return Math.max(0, age, staleIfErrorAge, staleWhileRevalidateAge) * 1000; + } + + stale() { + return this.maxAge() <= this.age(); + } + + _useStaleIfError() { + return this.maxAge() + toNumberOrZero(this._rescc['stale-if-error']) > this.age(); + } + + useStaleWhileRevalidate() { + return this.maxAge() + toNumberOrZero(this._rescc['stale-while-revalidate']) > this.age(); + } + + static fromObject(obj) { + return new this(undefined, undefined, { _fromObject: obj }); + } + + _fromObject(obj) { + if (this._responseTime) throw Error('Reinitialized'); + if (!obj || obj.v !== 1) throw Error('Invalid serialization'); + + this._responseTime = obj.t; + this._isShared = obj.sh; + this._cacheHeuristic = obj.ch; + this._immutableMinTtl = + obj.imm !== undefined ? obj.imm : 24 * 3600 * 1000; + this._status = obj.st; + this._resHeaders = obj.resh; + this._rescc = obj.rescc; + this._method = obj.m; + this._url = obj.u; + this._host = obj.h; + this._noAuthorization = obj.a; + this._reqHeaders = obj.reqh; + this._reqcc = obj.reqcc; + } + + toObject() { + return { + v: 1, + t: this._responseTime, + sh: this._isShared, + ch: this._cacheHeuristic, + imm: this._immutableMinTtl, + st: this._status, + resh: this._resHeaders, + rescc: this._rescc, + m: this._method, + u: this._url, + h: this._host, + a: this._noAuthorization, + reqh: this._reqHeaders, + reqcc: this._reqcc, + }; + } + + /** + * Headers for sending to the origin server to revalidate stale response. + * Allows server to return 304 to allow reuse of the previous response. + * + * Hop by hop headers are always stripped. + * Revalidation headers may be added or removed, depending on request. + */ + revalidationHeaders(incomingReq) { + this._assertRequestHasHeaders(incomingReq); + const headers = this._copyWithoutHopByHopHeaders(incomingReq.headers); + + // This implementation does not understand range requests + delete headers['if-range']; + + if (!this._requestMatches(incomingReq, true) || !this.storable()) { + // revalidation allowed via HEAD + // not for the same resource, or wasn't allowed to be cached anyway + delete headers['if-none-match']; + delete headers['if-modified-since']; + return headers; + } + + /* MUST send that entity-tag in any cache validation request (using If-Match or If-None-Match) if an entity-tag has been provided by the origin server. */ + if (this._resHeaders.etag) { + headers['if-none-match'] = headers['if-none-match'] + ? `${headers['if-none-match']}, ${this._resHeaders.etag}` + : this._resHeaders.etag; + } + + // Clients MAY issue simple (non-subrange) GET requests with either weak validators or strong validators. Clients MUST NOT use weak validators in other forms of request. + const forbidsWeakValidators = + headers['accept-ranges'] || + headers['if-match'] || + headers['if-unmodified-since'] || + (this._method && this._method != 'GET'); + + /* SHOULD send the Last-Modified value in non-subrange cache validation requests (using If-Modified-Since) if only a Last-Modified value has been provided by the origin server. + Note: This implementation does not understand partial responses (206) */ + if (forbidsWeakValidators) { + delete headers['if-modified-since']; + + if (headers['if-none-match']) { + const etags = headers['if-none-match'] + .split(/,/) + .filter(etag => { + return !/^\s*W\//.test(etag); + }); + if (!etags.length) { + delete headers['if-none-match']; + } else { + headers['if-none-match'] = etags.join(',').trim(); + } + } + } else if ( + this._resHeaders['last-modified'] && + !headers['if-modified-since'] + ) { + headers['if-modified-since'] = this._resHeaders['last-modified']; + } + + return headers; + } + + /** + * Creates new CachePolicy with information combined from the previews response, + * and the new revalidation response. + * + * Returns {policy, modified} where modified is a boolean indicating + * whether the response body has been modified, and old cached body can't be used. + * + * @return {Object} {policy: CachePolicy, modified: Boolean} + */ + revalidatedPolicy(request, response) { + this._assertRequestHasHeaders(request); + if(this._useStaleIfError() && isErrorResponse(response)) { // I consider the revalidation request unsuccessful + return { + modified: false, + matches: false, + policy: this, + }; + } + if (!response || !response.headers) { + throw Error('Response headers missing'); + } + + // These aren't going to be supported exactly, since one CachePolicy object + // doesn't know about all the other cached objects. + let matches = false; + if (response.status !== undefined && response.status != 304) { + matches = false; + } else if ( + response.headers.etag && + !/^\s*W\//.test(response.headers.etag) + ) { + // "All of the stored responses with the same strong validator are selected. + // If none of the stored responses contain the same strong validator, + // then the cache MUST NOT use the new response to update any stored responses." + matches = + this._resHeaders.etag && + this._resHeaders.etag.replace(/^\s*W\//, '') === + response.headers.etag; + } else if (this._resHeaders.etag && response.headers.etag) { + // "If the new response contains a weak validator and that validator corresponds + // to one of the cache's stored responses, + // then the most recent of those matching stored responses is selected for update." + matches = + this._resHeaders.etag.replace(/^\s*W\//, '') === + response.headers.etag.replace(/^\s*W\//, ''); + } else if (this._resHeaders['last-modified']) { + matches = + this._resHeaders['last-modified'] === + response.headers['last-modified']; + } else { + // If the new response does not include any form of validator (such as in the case where + // a client generates an If-Modified-Since request from a source other than the Last-Modified + // response header field), and there is only one stored response, and that stored response also + // lacks a validator, then that stored response is selected for update. + if ( + !this._resHeaders.etag && + !this._resHeaders['last-modified'] && + !response.headers.etag && + !response.headers['last-modified'] + ) { + matches = true; + } + } + + if (!matches) { + return { + policy: new this.constructor(request, response), + // Client receiving 304 without body, even if it's invalid/mismatched has no option + // but to reuse a cached body. We don't have a good way to tell clients to do + // error recovery in such case. + modified: response.status != 304, + matches: false, + }; + } + + // use other header fields provided in the 304 (Not Modified) response to replace all instances + // of the corresponding header fields in the stored response. + const headers = {}; + for (const k in this._resHeaders) { + headers[k] = + k in response.headers && !excludedFromRevalidationUpdate[k] + ? response.headers[k] + : this._resHeaders[k]; + } + + const newResponse = Object.assign({}, response, { + status: this._status, + method: this._method, + headers, + }); + return { + policy: new this.constructor(request, newResponse, { + shared: this._isShared, + cacheHeuristic: this._cacheHeuristic, + immutableMinTimeToLive: this._immutableMinTtl, + }), + modified: false, + matches: true, + }; + } +}; diff --git a/node_modules/http-cache-semantics/package.json b/node_modules/http-cache-semantics/package.json new file mode 100644 index 0000000..897798d --- /dev/null +++ b/node_modules/http-cache-semantics/package.json @@ -0,0 +1,24 @@ +{ + "name": "http-cache-semantics", + "version": "4.1.0", + "description": "Parses Cache-Control and other headers. Helps building correct HTTP caches and proxies", + "repository": "https://github.com/kornelski/http-cache-semantics.git", + "main": "index.js", + "scripts": { + "test": "mocha" + }, + "files": [ + "index.js" + ], + "author": "Kornel Lesiński <kornel@geekhood.net> (https://kornel.ski/)", + "license": "BSD-2-Clause", + "devDependencies": { + "eslint": "^5.13.0", + "eslint-plugin-prettier": "^3.0.1", + "husky": "^0.14.3", + "lint-staged": "^8.1.3", + "mocha": "^5.1.0", + "prettier": "^1.14.3", + "prettier-eslint-cli": "^4.7.1" + } +} diff --git a/node_modules/imurmurhash/README.md b/node_modules/imurmurhash/README.md new file mode 100644 index 0000000..f35b20a --- /dev/null +++ b/node_modules/imurmurhash/README.md @@ -0,0 +1,122 @@ +iMurmurHash.js +============== + +An incremental implementation of the MurmurHash3 (32-bit) hashing algorithm for JavaScript based on [Gary Court's implementation](https://github.com/garycourt/murmurhash-js) with [kazuyukitanimura's modifications](https://github.com/kazuyukitanimura/murmurhash-js). + +This version works significantly faster than the non-incremental version if you need to hash many small strings into a single hash, since string concatenation (to build the single string to pass the non-incremental version) is fairly costly. In one case tested, using the incremental version was about 50% faster than concatenating 5-10 strings and then hashing. + +Installation +------------ + +To use iMurmurHash in the browser, [download the latest version](https://raw.github.com/jensyt/imurmurhash-js/master/imurmurhash.min.js) and include it as a script on your site. + +```html +<script type="text/javascript" src="/scripts/imurmurhash.min.js"></script> +<script> +// Your code here, access iMurmurHash using the global object MurmurHash3 +</script> +``` + +--- + +To use iMurmurHash in Node.js, install the module using NPM: + +```bash +npm install imurmurhash +``` + +Then simply include it in your scripts: + +```javascript +MurmurHash3 = require('imurmurhash'); +``` + +Quick Example +------------- + +```javascript +// Create the initial hash +var hashState = MurmurHash3('string'); + +// Incrementally add text +hashState.hash('more strings'); +hashState.hash('even more strings'); + +// All calls can be chained if desired +hashState.hash('and').hash('some').hash('more'); + +// Get a result +hashState.result(); +// returns 0xe4ccfe6b +``` + +Functions +--------- + +### MurmurHash3 ([string], [seed]) +Get a hash state object, optionally initialized with the given _string_ and _seed_. _Seed_ must be a positive integer if provided. Calling this function without the `new` keyword will return a cached state object that has been reset. This is safe to use as long as the object is only used from a single thread and no other hashes are created while operating on this one. If this constraint cannot be met, you can use `new` to create a new state object. For example: + +```javascript +// Use the cached object, calling the function again will return the same +// object (but reset, so the current state would be lost) +hashState = MurmurHash3(); +... + +// Create a new object that can be safely used however you wish. Calling the +// function again will simply return a new state object, and no state loss +// will occur, at the cost of creating more objects. +hashState = new MurmurHash3(); +``` + +Both methods can be mixed however you like if you have different use cases. + +--- + +### MurmurHash3.prototype.hash (string) +Incrementally add _string_ to the hash. This can be called as many times as you want for the hash state object, including after a call to `result()`. Returns `this` so calls can be chained. + +--- + +### MurmurHash3.prototype.result () +Get the result of the hash as a 32-bit positive integer. This performs the tail and finalizer portions of the algorithm, but does not store the result in the state object. This means that it is perfectly safe to get results and then continue adding strings via `hash`. + +```javascript +// Do the whole string at once +MurmurHash3('this is a test string').result(); +// 0x70529328 + +// Do part of the string, get a result, then the other part +var m = MurmurHash3('this is a'); +m.result(); +// 0xbfc4f834 +m.hash(' test string').result(); +// 0x70529328 (same as above) +``` + +--- + +### MurmurHash3.prototype.reset ([seed]) +Reset the state object for reuse, optionally using the given _seed_ (defaults to 0 like the constructor). Returns `this` so calls can be chained. + +--- + +License (MIT) +------------- +Copyright (c) 2013 Gary Court, Jens Taylor + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +the Software, and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS +FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR +COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/imurmurhash/imurmurhash.js b/node_modules/imurmurhash/imurmurhash.js new file mode 100644 index 0000000..e63146a --- /dev/null +++ b/node_modules/imurmurhash/imurmurhash.js @@ -0,0 +1,138 @@ +/** + * @preserve + * JS Implementation of incremental MurmurHash3 (r150) (as of May 10, 2013) + * + * @author <a href="mailto:jensyt@gmail.com">Jens Taylor</a> + * @see http://github.com/homebrewing/brauhaus-diff + * @author <a href="mailto:gary.court@gmail.com">Gary Court</a> + * @see http://github.com/garycourt/murmurhash-js + * @author <a href="mailto:aappleby@gmail.com">Austin Appleby</a> + * @see http://sites.google.com/site/murmurhash/ + */ +(function(){ + var cache; + + // Call this function without `new` to use the cached object (good for + // single-threaded environments), or with `new` to create a new object. + // + // @param {string} key A UTF-16 or ASCII string + // @param {number} seed An optional positive integer + // @return {object} A MurmurHash3 object for incremental hashing + function MurmurHash3(key, seed) { + var m = this instanceof MurmurHash3 ? this : cache; + m.reset(seed) + if (typeof key === 'string' && key.length > 0) { + m.hash(key); + } + + if (m !== this) { + return m; + } + }; + + // Incrementally add a string to this hash + // + // @param {string} key A UTF-16 or ASCII string + // @return {object} this + MurmurHash3.prototype.hash = function(key) { + var h1, k1, i, top, len; + + len = key.length; + this.len += len; + + k1 = this.k1; + i = 0; + switch (this.rem) { + case 0: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) : 0; + case 1: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) << 8 : 0; + case 2: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) << 16 : 0; + case 3: + k1 ^= len > i ? (key.charCodeAt(i) & 0xff) << 24 : 0; + k1 ^= len > i ? (key.charCodeAt(i++) & 0xff00) >> 8 : 0; + } + + this.rem = (len + this.rem) & 3; // & 3 is same as % 4 + len -= this.rem; + if (len > 0) { + h1 = this.h1; + while (1) { + k1 = (k1 * 0x2d51 + (k1 & 0xffff) * 0xcc9e0000) & 0xffffffff; + k1 = (k1 << 15) | (k1 >>> 17); + k1 = (k1 * 0x3593 + (k1 & 0xffff) * 0x1b870000) & 0xffffffff; + + h1 ^= k1; + h1 = (h1 << 13) | (h1 >>> 19); + h1 = (h1 * 5 + 0xe6546b64) & 0xffffffff; + + if (i >= len) { + break; + } + + k1 = ((key.charCodeAt(i++) & 0xffff)) ^ + ((key.charCodeAt(i++) & 0xffff) << 8) ^ + ((key.charCodeAt(i++) & 0xffff) << 16); + top = key.charCodeAt(i++); + k1 ^= ((top & 0xff) << 24) ^ + ((top & 0xff00) >> 8); + } + + k1 = 0; + switch (this.rem) { + case 3: k1 ^= (key.charCodeAt(i + 2) & 0xffff) << 16; + case 2: k1 ^= (key.charCodeAt(i + 1) & 0xffff) << 8; + case 1: k1 ^= (key.charCodeAt(i) & 0xffff); + } + + this.h1 = h1; + } + + this.k1 = k1; + return this; + }; + + // Get the result of this hash + // + // @return {number} The 32-bit hash + MurmurHash3.prototype.result = function() { + var k1, h1; + + k1 = this.k1; + h1 = this.h1; + + if (k1 > 0) { + k1 = (k1 * 0x2d51 + (k1 & 0xffff) * 0xcc9e0000) & 0xffffffff; + k1 = (k1 << 15) | (k1 >>> 17); + k1 = (k1 * 0x3593 + (k1 & 0xffff) * 0x1b870000) & 0xffffffff; + h1 ^= k1; + } + + h1 ^= this.len; + + h1 ^= h1 >>> 16; + h1 = (h1 * 0xca6b + (h1 & 0xffff) * 0x85eb0000) & 0xffffffff; + h1 ^= h1 >>> 13; + h1 = (h1 * 0xae35 + (h1 & 0xffff) * 0xc2b20000) & 0xffffffff; + h1 ^= h1 >>> 16; + + return h1 >>> 0; + }; + + // Reset the hash object for reuse + // + // @param {number} seed An optional positive integer + MurmurHash3.prototype.reset = function(seed) { + this.h1 = typeof seed === 'number' ? seed : 0; + this.rem = this.k1 = this.len = 0; + return this; + }; + + // A cached object to use. This can be safely used if you're in a single- + // threaded environment, otherwise you need to create new hashes to use. + cache = new MurmurHash3(); + + if (typeof(module) != 'undefined') { + module.exports = MurmurHash3; + } else { + this.MurmurHash3 = MurmurHash3; + } +}()); diff --git a/node_modules/imurmurhash/imurmurhash.min.js b/node_modules/imurmurhash/imurmurhash.min.js new file mode 100644 index 0000000..dc0ee88 --- /dev/null +++ b/node_modules/imurmurhash/imurmurhash.min.js @@ -0,0 +1,12 @@ +/** + * @preserve + * JS Implementation of incremental MurmurHash3 (r150) (as of May 10, 2013) + * + * @author <a href="mailto:jensyt@gmail.com">Jens Taylor</a> + * @see http://github.com/homebrewing/brauhaus-diff + * @author <a href="mailto:gary.court@gmail.com">Gary Court</a> + * @see http://github.com/garycourt/murmurhash-js + * @author <a href="mailto:aappleby@gmail.com">Austin Appleby</a> + * @see http://sites.google.com/site/murmurhash/ + */ +!function(){function t(h,r){var s=this instanceof t?this:e;return s.reset(r),"string"==typeof h&&h.length>0&&s.hash(h),s!==this?s:void 0}var e;t.prototype.hash=function(t){var e,h,r,s,i;switch(i=t.length,this.len+=i,h=this.k1,r=0,this.rem){case 0:h^=i>r?65535&t.charCodeAt(r++):0;case 1:h^=i>r?(65535&t.charCodeAt(r++))<<8:0;case 2:h^=i>r?(65535&t.charCodeAt(r++))<<16:0;case 3:h^=i>r?(255&t.charCodeAt(r))<<24:0,h^=i>r?(65280&t.charCodeAt(r++))>>8:0}if(this.rem=3&i+this.rem,i-=this.rem,i>0){for(e=this.h1;;){if(h=4294967295&11601*h+3432906752*(65535&h),h=h<<15|h>>>17,h=4294967295&13715*h+461832192*(65535&h),e^=h,e=e<<13|e>>>19,e=4294967295&5*e+3864292196,r>=i)break;h=65535&t.charCodeAt(r++)^(65535&t.charCodeAt(r++))<<8^(65535&t.charCodeAt(r++))<<16,s=t.charCodeAt(r++),h^=(255&s)<<24^(65280&s)>>8}switch(h=0,this.rem){case 3:h^=(65535&t.charCodeAt(r+2))<<16;case 2:h^=(65535&t.charCodeAt(r+1))<<8;case 1:h^=65535&t.charCodeAt(r)}this.h1=e}return this.k1=h,this},t.prototype.result=function(){var t,e;return t=this.k1,e=this.h1,t>0&&(t=4294967295&11601*t+3432906752*(65535&t),t=t<<15|t>>>17,t=4294967295&13715*t+461832192*(65535&t),e^=t),e^=this.len,e^=e>>>16,e=4294967295&51819*e+2246770688*(65535&e),e^=e>>>13,e=4294967295&44597*e+3266445312*(65535&e),e^=e>>>16,e>>>0},t.prototype.reset=function(t){return this.h1="number"==typeof t?t:0,this.rem=this.k1=this.len=0,this},e=new t,"undefined"!=typeof module?module.exports=t:this.MurmurHash3=t}();
\ No newline at end of file diff --git a/node_modules/imurmurhash/package.json b/node_modules/imurmurhash/package.json new file mode 100644 index 0000000..8a93edb --- /dev/null +++ b/node_modules/imurmurhash/package.json @@ -0,0 +1,40 @@ +{ + "name": "imurmurhash", + "version": "0.1.4", + "description": "An incremental implementation of MurmurHash3", + "homepage": "https://github.com/jensyt/imurmurhash-js", + "main": "imurmurhash.js", + "files": [ + "imurmurhash.js", + "imurmurhash.min.js", + "package.json", + "README.md" + ], + "repository": { + "type": "git", + "url": "https://github.com/jensyt/imurmurhash-js" + }, + "bugs": { + "url": "https://github.com/jensyt/imurmurhash-js/issues" + }, + "keywords": [ + "murmur", + "murmurhash", + "murmurhash3", + "hash", + "incremental" + ], + "author": { + "name": "Jens Taylor", + "email": "jensyt@gmail.com", + "url": "https://github.com/homebrewing" + }, + "license": "MIT", + "dependencies": { + }, + "devDependencies": { + }, + "engines": { + "node": ">=0.8.19" + } +} diff --git a/node_modules/is-obj/index.js b/node_modules/is-obj/index.js new file mode 100644 index 0000000..4d023bc --- /dev/null +++ b/node_modules/is-obj/index.js @@ -0,0 +1,5 @@ +'use strict'; +module.exports = function (x) { + var type = typeof x; + return x !== null && (type === 'object' || type === 'function'); +}; diff --git a/node_modules/is-obj/license b/node_modules/is-obj/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/is-obj/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/is-obj/package.json b/node_modules/is-obj/package.json new file mode 100644 index 0000000..c441d27 --- /dev/null +++ b/node_modules/is-obj/package.json @@ -0,0 +1,33 @@ +{ + "name": "is-obj", + "version": "1.0.1", + "description": "Check if a value is an object", + "license": "MIT", + "repository": "sindresorhus/is-obj", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=0.10.0" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "obj", + "object", + "is", + "check", + "test", + "type" + ], + "devDependencies": { + "ava": "*", + "xo": "*" + } +} diff --git a/node_modules/is-obj/readme.md b/node_modules/is-obj/readme.md new file mode 100644 index 0000000..d311026 --- /dev/null +++ b/node_modules/is-obj/readme.md @@ -0,0 +1,34 @@ +# is-obj [![Build Status](https://travis-ci.org/sindresorhus/is-obj.svg?branch=master)](https://travis-ci.org/sindresorhus/is-obj) + +> Check if a value is an object + +Keep in mind that array, function, regexp, etc, are objects in JavaScript.<br> +See [`is-plain-obj`](https://github.com/sindresorhus/is-plain-obj) if you want to check for plain objects. + + +## Install + +``` +$ npm install --save is-obj +``` + + +## Usage + +```js +const isObj = require('is-obj'); + +isObj({foo: 'bar'}); +//=> true + +isObj([1, 2, 3]); +//=> true + +isObj('foo'); +//=> false +``` + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/json-buffer/.npmignore b/node_modules/json-buffer/.npmignore new file mode 100644 index 0000000..13abef4 --- /dev/null +++ b/node_modules/json-buffer/.npmignore @@ -0,0 +1,3 @@ +node_modules +node_modules/* +npm_debug.log diff --git a/node_modules/json-buffer/.travis.yml b/node_modules/json-buffer/.travis.yml new file mode 100644 index 0000000..244b7e8 --- /dev/null +++ b/node_modules/json-buffer/.travis.yml @@ -0,0 +1,3 @@ +language: node_js +node_js: + - '0.10' diff --git a/node_modules/json-buffer/LICENSE b/node_modules/json-buffer/LICENSE new file mode 100644 index 0000000..b799ec0 --- /dev/null +++ b/node_modules/json-buffer/LICENSE @@ -0,0 +1,22 @@ +Copyright (c) 2013 Dominic Tarr + +Permission is hereby granted, free of charge, +to any person obtaining a copy of this software and +associated documentation files (the "Software"), to +deal in the Software without restriction, including +without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom +the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice +shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR +ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/json-buffer/README.md b/node_modules/json-buffer/README.md new file mode 100644 index 0000000..43857bb --- /dev/null +++ b/node_modules/json-buffer/README.md @@ -0,0 +1,24 @@ +# json-buffer + +JSON functions that can convert buffers! + +[![build status](https://secure.travis-ci.org/dominictarr/json-buffer.png)](http://travis-ci.org/dominictarr/json-buffer) + +[![testling badge](https://ci.testling.com/dominictarr/json-buffer.png)](https://ci.testling.com/dominictarr/json-buffer) + +JSON mangles buffers by converting to an array... +which isn't helpful. json-buffers converts to base64 instead, +and deconverts base64 to a buffer. + +``` js +var JSONB = require('json-buffer') +var Buffer = require('buffer').Buffer + +var str = JSONB.stringify(new Buffer('hello there!')) + +console.log(JSONB.parse(str)) //GET a BUFFER back +``` + +## License + +MIT diff --git a/node_modules/json-buffer/index.js b/node_modules/json-buffer/index.js new file mode 100644 index 0000000..9cafed8 --- /dev/null +++ b/node_modules/json-buffer/index.js @@ -0,0 +1,58 @@ +//TODO: handle reviver/dehydrate function like normal +//and handle indentation, like normal. +//if anyone needs this... please send pull request. + +exports.stringify = function stringify (o) { + if('undefined' == typeof o) return o + + if(o && Buffer.isBuffer(o)) + return JSON.stringify(':base64:' + o.toString('base64')) + + if(o && o.toJSON) + o = o.toJSON() + + if(o && 'object' === typeof o) { + var s = '' + var array = Array.isArray(o) + s = array ? '[' : '{' + var first = true + + for(var k in o) { + var ignore = 'function' == typeof o[k] || (!array && 'undefined' === typeof o[k]) + if(Object.hasOwnProperty.call(o, k) && !ignore) { + if(!first) + s += ',' + first = false + if (array) { + if(o[k] == undefined) + s += 'null' + else + s += stringify(o[k]) + } else if (o[k] !== void(0)) { + s += stringify(k) + ':' + stringify(o[k]) + } + } + } + + s += array ? ']' : '}' + + return s + } else if ('string' === typeof o) { + return JSON.stringify(/^:/.test(o) ? ':' + o : o) + } else if ('undefined' === typeof o) { + return 'null'; + } else + return JSON.stringify(o) +} + +exports.parse = function (s) { + return JSON.parse(s, function (key, value) { + if('string' === typeof value) { + if(/^:base64:/.test(value)) + return new Buffer(value.substring(8), 'base64') + else + return /^:/.test(value) ? value.substring(1) : value + } + return value + }) +} diff --git a/node_modules/json-buffer/package.json b/node_modules/json-buffer/package.json new file mode 100644 index 0000000..035df50 --- /dev/null +++ b/node_modules/json-buffer/package.json @@ -0,0 +1,34 @@ +{ + "name": "json-buffer", + "description": "JSON parse & stringify that supports binary via bops & base64", + "version": "3.0.0", + "homepage": "https://github.com/dominictarr/json-buffer", + "repository": { + "type": "git", + "url": "git://github.com/dominictarr/json-buffer.git" + }, + "devDependencies": { + "tape": "^4.6.3" + }, + "scripts": { + "test": "set -e; for t in test/*.js; do node $t; done" + }, + "author": "Dominic Tarr <dominic.tarr@gmail.com> (http://dominictarr.com)", + "license": "MIT", + "testling": { + "files": "test/*.js", + "browsers": [ + "ie/8..latest", + "firefox/17..latest", + "firefox/nightly", + "chrome/22..latest", + "chrome/canary", + "opera/12..latest", + "opera/next", + "safari/5.1..latest", + "ipad/6.0..latest", + "iphone/6.0..latest", + "android-browser/4.2..latest" + ] + } +} diff --git a/node_modules/json-buffer/test/index.js b/node_modules/json-buffer/test/index.js new file mode 100644 index 0000000..8351804 --- /dev/null +++ b/node_modules/json-buffer/test/index.js @@ -0,0 +1,63 @@ + +var test = require('tape') +var _JSON = require('../') + +function clone (o) { + return JSON.parse(JSON.stringify(o)) +} + +var examples = { + simple: { foo: [], bar: {}, baz: new Buffer('some binary data') }, + just_buffer: new Buffer('JUST A BUFFER'), + all_types: { + string:'hello', + number: 3145, + null: null, + object: {}, + array: [], + boolean: true, + boolean2: false + }, + foo: new Buffer('foo'), + foo2: new Buffer('foo2'), + escape: { + buffer: new Buffer('x'), + string: _JSON.stringify(new Buffer('x')) + }, + escape2: { + buffer: new Buffer('x'), + string: ':base64:'+ new Buffer('x').toString('base64') + }, + undefined: { + empty: undefined, test: true + }, + undefined2: { + first: 1, empty: undefined, test: true + }, + undefinedArray: { + array: [undefined, 1, 'two'] + }, + fn: { + fn: function () {} + }, + undefined: undefined +} + +for(k in examples) +(function (value, k) { + test(k, function (t) { + var s = _JSON.stringify(value) + console.log('parse', s) + if(JSON.stringify(value) !== undefined) { + console.log(s) + var _value = _JSON.parse(s) + t.deepEqual(clone(_value), clone(value)) + } + else + t.equal(s, undefined) + t.end() + }) +})(examples[k], k) + + + diff --git a/node_modules/keyv/LICENSE b/node_modules/keyv/LICENSE new file mode 100644 index 0000000..f27ee9b --- /dev/null +++ b/node_modules/keyv/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2017 Luke Childs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/node_modules/keyv/README.md b/node_modules/keyv/README.md new file mode 100644 index 0000000..2a9287c --- /dev/null +++ b/node_modules/keyv/README.md @@ -0,0 +1,276 @@ +<h1 align="center"> + <img width="250" src="https://rawgit.com/lukechilds/keyv/master/media/logo.svg" alt="keyv"> + <br> + <br> +</h1> + +> Simple key-value storage with support for multiple backends + +[![Build Status](https://travis-ci.org/lukechilds/keyv.svg?branch=master)](https://travis-ci.org/lukechilds/keyv) +[![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv?branch=master) +[![npm](https://img.shields.io/npm/dm/keyv.svg)](https://www.npmjs.com/package/keyv) +[![npm](https://img.shields.io/npm/v/keyv.svg)](https://www.npmjs.com/package/keyv) + +Keyv provides a consistent interface for key-value storage across multiple backends via storage adapters. It supports TTL based expiry, making it suitable as a cache or a persistent key-value store. + +## Features + +There are a few existing modules similar to Keyv, however Keyv is different because it: + +- Isn't bloated +- Has a simple Promise based API +- Suitable as a TTL based cache or persistent key-value store +- [Easily embeddable](#add-cache-support-to-your-module) inside another module +- Works with any storage that implements the [`Map`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map) API +- Handles all JSON types plus `Buffer` +- Supports namespaces +- Wide range of [**efficient, well tested**](#official-storage-adapters) storage adapters +- Connection errors are passed through (db failures won't kill your app) +- Supports the current active LTS version of Node.js or higher + +## Usage + +Install Keyv. + +``` +npm install --save keyv +``` + +By default everything is stored in memory, you can optionally also install a storage adapter. + +``` +npm install --save @keyv/redis +npm install --save @keyv/mongo +npm install --save @keyv/sqlite +npm install --save @keyv/postgres +npm install --save @keyv/mysql +``` + +Create a new Keyv instance, passing your connection string if applicable. Keyv will automatically load the correct storage adapter. + +```js +const Keyv = require('keyv'); + +// One of the following +const keyv = new Keyv(); +const keyv = new Keyv('redis://user:pass@localhost:6379'); +const keyv = new Keyv('mongodb://user:pass@localhost:27017/dbname'); +const keyv = new Keyv('sqlite://path/to/database.sqlite'); +const keyv = new Keyv('postgresql://user:pass@localhost:5432/dbname'); +const keyv = new Keyv('mysql://user:pass@localhost:3306/dbname'); + +// Handle DB connection errors +keyv.on('error', err => console.log('Connection Error', err)); + +await keyv.set('foo', 'expires in 1 second', 1000); // true +await keyv.set('foo', 'never expires'); // true +await keyv.get('foo'); // 'never expires' +await keyv.delete('foo'); // true +await keyv.clear(); // undefined +``` + +### Namespaces + +You can namespace your Keyv instance to avoid key collisions and allow you to clear only a certain namespace while using the same database. + +```js +const users = new Keyv('redis://user:pass@localhost:6379', { namespace: 'users' }); +const cache = new Keyv('redis://user:pass@localhost:6379', { namespace: 'cache' }); + +await users.set('foo', 'users'); // true +await cache.set('foo', 'cache'); // true +await users.get('foo'); // 'users' +await cache.get('foo'); // 'cache' +await users.clear(); // undefined +await users.get('foo'); // undefined +await cache.get('foo'); // 'cache' +``` + +### Custom Serializers + +Keyv uses [`json-buffer`](https://github.com/dominictarr/json-buffer) for data serialization to ensure consistency across different backends. + +You can optionally provide your own serialization functions to support extra data types or to serialize to something other than JSON. + +```js +const keyv = new Keyv({ serialize: JSON.stringify, deserialize: JSON.parse }); +``` + +**Warning:** Using custom serializers means you lose any guarantee of data consistency. You should do extensive testing with your serialisation functions and chosen storage engine. + +## Official Storage Adapters + +The official storage adapters are covered by [over 150 integration tests](https://travis-ci.org/lukechilds/keyv/jobs/260418145) to guarantee consistent behaviour. They are lightweight, efficient wrappers over the DB clients making use of indexes and native TTLs where available. + +Database | Adapter | Native TTL | Status +---|---|---|--- +Redis | [@keyv/redis](https://github.com/lukechilds/keyv-redis) | Yes | [![Build Status](https://travis-ci.org/lukechilds/keyv-redis.svg?branch=master)](https://travis-ci.org/lukechilds/keyv-redis) [![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv-redis/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv-redis?branch=master) +MongoDB | [@keyv/mongo](https://github.com/lukechilds/keyv-mongo) | Yes | [![Build Status](https://travis-ci.org/lukechilds/keyv-mongo.svg?branch=master)](https://travis-ci.org/lukechilds/keyv-mongo) [![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv-mongo/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv-mongo?branch=master) +SQLite | [@keyv/sqlite](https://github.com/lukechilds/keyv-sqlite) | No | [![Build Status](https://travis-ci.org/lukechilds/keyv-sqlite.svg?branch=master)](https://travis-ci.org/lukechilds/keyv-sqlite) [![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv-sqlite/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv-sqlite?branch=master) +PostgreSQL | [@keyv/postgres](https://github.com/lukechilds/keyv-postgres) | No | [![Build Status](https://travis-ci.org/lukechilds/keyv-postgres.svg?branch=master)](https://travis-ci.org/lukechildskeyv-postgreskeyv) [![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv-postgres/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv-postgres?branch=master) +MySQL | [@keyv/mysql](https://github.com/lukechilds/keyv-mysql) | No | [![Build Status](https://travis-ci.org/lukechilds/keyv-mysql.svg?branch=master)](https://travis-ci.org/lukechilds/keyv-mysql) [![Coverage Status](https://coveralls.io/repos/github/lukechilds/keyv-mysql/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/keyv-mysql?branch=master) + +## Third-party Storage Adapters + +You can also use third-party storage adapters or build your own. Keyv will wrap these storage adapters in TTL functionality and handle complex types internally. + +```js +const Keyv = require('keyv'); +const myAdapter = require('./my-storage-adapter'); + +const keyv = new Keyv({ store: myAdapter }); +``` + +Any store that follows the [`Map`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map) api will work. + +```js +new Keyv({ store: new Map() }); +``` + +For example, [`quick-lru`](https://github.com/sindresorhus/quick-lru) is a completely unrelated module that implements the Map API. + +```js +const Keyv = require('keyv'); +const QuickLRU = require('quick-lru'); + +const lru = new QuickLRU({ maxSize: 1000 }); +const keyv = new Keyv({ store: lru }); +``` + +The following are third-party storage adapters compatible with Keyv: + +- [quick-lru](https://github.com/sindresorhus/quick-lru) - Simple "Least Recently Used" (LRU) cache +- [keyv-file](https://github.com/zaaack/keyv-file) - File system storage adapter for Keyv +- [keyv-dynamodb](https://www.npmjs.com/package/keyv-dynamodb) - DynamoDB storage adapter for Keyv + +## Add Cache Support to your Module + +Keyv is designed to be easily embedded into other modules to add cache support. The recommended pattern is to expose a `cache` option in your modules options which is passed through to Keyv. Caching will work in memory by default and users have the option to also install a Keyv storage adapter and pass in a connection string, or any other storage that implements the `Map` API. + +You should also set a namespace for your module so you can safely call `.clear()` without clearing unrelated app data. + +Inside your module: + +```js +class AwesomeModule { + constructor(opts) { + this.cache = new Keyv({ + uri: typeof opts.cache === 'string' && opts.cache, + store: typeof opts.cache !== 'string' && opts.cache, + namespace: 'awesome-module' + }); + } +} +``` + +Now it can be consumed like this: + +```js +const AwesomeModule = require('awesome-module'); + +// Caches stuff in memory by default +const awesomeModule = new AwesomeModule(); + +// After npm install --save keyv-redis +const awesomeModule = new AwesomeModule({ cache: 'redis://localhost' }); + +// Some third-party module that implements the Map API +const awesomeModule = new AwesomeModule({ cache: some3rdPartyStore }); +``` + +## API + +### new Keyv([uri], [options]) + +Returns a new Keyv instance. + +The Keyv instance is also an `EventEmitter` that will emit an `'error'` event if the storage adapter connection fails. + +### uri + +Type: `String`<br> +Default: `undefined` + +The connection string URI. + +Merged into the options object as options.uri. + +### options + +Type: `Object` + +The options object is also passed through to the storage adapter. Check your storage adapter docs for any extra options. + +#### options.namespace + +Type: `String`<br> +Default: `'keyv'` + +Namespace for the current instance. + +#### options.ttl + +Type: `Number`<br> +Default: `undefined` + +Default TTL. Can be overridden by specififying a TTL on `.set()`. + +#### options.serialize + +Type: `Function`<br> +Default: `JSONB.stringify` + +A custom serialization function. + +#### options.deserialize + +Type: `Function`<br> +Default: `JSONB.parse` + +A custom deserialization function. + +#### options.store + +Type: `Storage adapter instance`<br> +Default: `new Map()` + +The storage adapter instance to be used by Keyv. + +#### options.adapter + +Type: `String`<br> +Default: `undefined` + +Specify an adapter to use. e.g `'redis'` or `'mongodb'`. + +### Instance + +Keys must always be strings. Values can be of any type. + +#### .set(key, value, [ttl]) + +Set a value. + +By default keys are persistent. You can set an expiry TTL in milliseconds. + +Returns `true`. + +#### .get(key) + +Returns the value. + +#### .delete(key) + +Deletes an entry. + +Returns `true` if the key existed, `false` if not. + +#### .clear() + +Delete all entries in the current namespace. + +Returns `undefined`. + +## License + +MIT © Luke Childs diff --git a/node_modules/keyv/package.json b/node_modules/keyv/package.json new file mode 100644 index 0000000..00a5531 --- /dev/null +++ b/node_modules/keyv/package.json @@ -0,0 +1,49 @@ +{ + "name": "keyv", + "version": "3.1.0", + "description": "Simple key-value storage with support for multiple backends", + "main": "src/index.js", + "scripts": { + "test": "xo && nyc ava test/keyv.js", + "test:full": "xo && nyc ava --serial", + "coverage": "nyc report --reporter=text-lcov | coveralls" + }, + "xo": { + "extends": "xo-lukechilds" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/lukechilds/keyv.git" + }, + "keywords": [ + "key", + "value", + "store", + "cache", + "ttl" + ], + "author": "Luke Childs <lukechilds123@gmail.com> (http://lukechilds.co.uk)", + "license": "MIT", + "bugs": { + "url": "https://github.com/lukechilds/keyv/issues" + }, + "homepage": "https://github.com/lukechilds/keyv", + "dependencies": { + "json-buffer": "3.0.0" + }, + "devDependencies": { + "ava": "^0.25.0", + "coveralls": "^3.0.0", + "eslint-config-xo-lukechilds": "^1.0.0", + "@keyv/mongo": "*", + "@keyv/mysql": "*", + "@keyv/postgres": "*", + "@keyv/redis": "*", + "@keyv/sqlite": "*", + "@keyv/test-suite": "*", + "nyc": "^11.0.3", + "this": "^1.0.2", + "timekeeper": "^2.0.0", + "xo": "^0.20.1" + } +} diff --git a/node_modules/keyv/src/index.js b/node_modules/keyv/src/index.js new file mode 100644 index 0000000..02af495 --- /dev/null +++ b/node_modules/keyv/src/index.js @@ -0,0 +1,103 @@ +'use strict'; + +const EventEmitter = require('events'); +const JSONB = require('json-buffer'); + +const loadStore = opts => { + const adapters = { + redis: '@keyv/redis', + mongodb: '@keyv/mongo', + mongo: '@keyv/mongo', + sqlite: '@keyv/sqlite', + postgresql: '@keyv/postgres', + postgres: '@keyv/postgres', + mysql: '@keyv/mysql' + }; + if (opts.adapter || opts.uri) { + const adapter = opts.adapter || /^[^:]*/.exec(opts.uri)[0]; + return new (require(adapters[adapter]))(opts); + } + return new Map(); +}; + +class Keyv extends EventEmitter { + constructor(uri, opts) { + super(); + this.opts = Object.assign( + { + namespace: 'keyv', + serialize: JSONB.stringify, + deserialize: JSONB.parse + }, + (typeof uri === 'string') ? { uri } : uri, + opts + ); + + if (!this.opts.store) { + const adapterOpts = Object.assign({}, this.opts); + this.opts.store = loadStore(adapterOpts); + } + + if (typeof this.opts.store.on === 'function') { + this.opts.store.on('error', err => this.emit('error', err)); + } + + this.opts.store.namespace = this.opts.namespace; + } + + _getKeyPrefix(key) { + return `${this.opts.namespace}:${key}`; + } + + get(key) { + key = this._getKeyPrefix(key); + const store = this.opts.store; + return Promise.resolve() + .then(() => store.get(key)) + .then(data => { + data = (typeof data === 'string') ? this.opts.deserialize(data) : data; + if (data === undefined) { + return undefined; + } + if (typeof data.expires === 'number' && Date.now() > data.expires) { + this.delete(key); + return undefined; + } + return data.value; + }); + } + + set(key, value, ttl) { + key = this._getKeyPrefix(key); + if (typeof ttl === 'undefined') { + ttl = this.opts.ttl; + } + if (ttl === 0) { + ttl = undefined; + } + const store = this.opts.store; + + return Promise.resolve() + .then(() => { + const expires = (typeof ttl === 'number') ? (Date.now() + ttl) : null; + value = { value, expires }; + return store.set(key, this.opts.serialize(value), ttl); + }) + .then(() => true); + } + + delete(key) { + key = this._getKeyPrefix(key); + const store = this.opts.store; + return Promise.resolve() + .then(() => store.delete(key)); + } + + clear() { + const store = this.opts.store; + return Promise.resolve() + .then(() => store.clear()); + } +} + +module.exports = Keyv; diff --git a/node_modules/lowercase-keys/index.js b/node_modules/lowercase-keys/index.js new file mode 100644 index 0000000..b8d8898 --- /dev/null +++ b/node_modules/lowercase-keys/index.js @@ -0,0 +1,11 @@ +'use strict'; +module.exports = function (obj) { + var ret = {}; + var keys = Object.keys(Object(obj)); + + for (var i = 0; i < keys.length; i++) { + ret[keys[i].toLowerCase()] = obj[keys[i]]; + } + + return ret; +}; diff --git a/node_modules/lowercase-keys/license b/node_modules/lowercase-keys/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/lowercase-keys/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/lowercase-keys/package.json b/node_modules/lowercase-keys/package.json new file mode 100644 index 0000000..188af70 --- /dev/null +++ b/node_modules/lowercase-keys/package.json @@ -0,0 +1,35 @@ +{ + "name": "lowercase-keys", + "version": "1.0.1", + "description": "Lowercase the keys of an object", + "license": "MIT", + "repository": "sindresorhus/lowercase-keys", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=0.10.0" + }, + "scripts": { + "test": "ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "object", + "assign", + "extend", + "properties", + "lowercase", + "lower-case", + "case", + "keys", + "key" + ], + "devDependencies": { + "ava": "*" + } +} diff --git a/node_modules/lowercase-keys/readme.md b/node_modules/lowercase-keys/readme.md new file mode 100644 index 0000000..dc65770 --- /dev/null +++ b/node_modules/lowercase-keys/readme.md @@ -0,0 +1,33 @@ +# lowercase-keys [![Build Status](https://travis-ci.org/sindresorhus/lowercase-keys.svg?branch=master)](https://travis-ci.org/sindresorhus/lowercase-keys) + +> Lowercase the keys of an object + + +## Install + +``` +$ npm install --save lowercase-keys +``` + + +## Usage + +```js +var lowercaseKeys = require('lowercase-keys'); + +lowercaseKeys({FOO: true, bAr: false}); +//=> {foo: true, bar: false} +``` + + +## API + +### lowercaseKeys(object) + +Lowercases the keys and returns a new object. + + + +## License + +MIT © [Sindre Sorhus](http://sindresorhus.com) diff --git a/node_modules/make-dir/index.js b/node_modules/make-dir/index.js new file mode 100644 index 0000000..1843955 --- /dev/null +++ b/node_modules/make-dir/index.js @@ -0,0 +1,85 @@ +'use strict'; +const fs = require('fs'); +const path = require('path'); +const pify = require('pify'); + +const defaults = { + mode: 0o777 & (~process.umask()), + fs +}; + +// https://github.com/nodejs/node/issues/8987 +// https://github.com/libuv/libuv/pull/1088 +const checkPath = pth => { + if (process.platform === 'win32') { + const pathHasInvalidWinCharacters = /[<>:"|?*]/.test(pth.replace(path.parse(pth).root, '')); + + if (pathHasInvalidWinCharacters) { + const err = new Error(`Path contains invalid characters: ${pth}`); + err.code = 'EINVAL'; + throw err; + } + } +}; + +module.exports = (input, opts) => Promise.resolve().then(() => { + checkPath(input); + opts = Object.assign({}, defaults, opts); + + const mkdir = pify(opts.fs.mkdir); + const stat = pify(opts.fs.stat); + + const make = pth => { + return mkdir(pth, opts.mode) + .then(() => pth) + .catch(err => { + if (err.code === 'ENOENT') { + if (err.message.includes('null bytes') || path.dirname(pth) === pth) { + throw err; + } + + return make(path.dirname(pth)).then(() => make(pth)); + } + + return stat(pth) + .then(stats => stats.isDirectory() ? pth : Promise.reject()) + .catch(() => { + throw err; + }); + }); + }; + + return make(path.resolve(input)); +}); + +module.exports.sync = (input, opts) => { + checkPath(input); + opts = Object.assign({}, defaults, opts); + + const make = pth => { + try { + opts.fs.mkdirSync(pth, opts.mode); + } catch (err) { + if (err.code === 'ENOENT') { + if (err.message.includes('null bytes') || path.dirname(pth) === pth) { + throw err; + } + + make(path.dirname(pth)); + return make(pth); + } + + try { + if (!opts.fs.statSync(pth).isDirectory()) { + throw new Error('The path is not a directory'); + } + } catch (_) { + throw err; + } + } + + return pth; + }; + + return make(path.resolve(input)); +}; diff --git a/node_modules/make-dir/license b/node_modules/make-dir/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/make-dir/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/make-dir/package.json b/node_modules/make-dir/package.json new file mode 100644 index 0000000..ec907a7 --- /dev/null +++ b/node_modules/make-dir/package.json @@ -0,0 +1,54 @@ +{ + "name": "make-dir", + "version": "1.3.0", + "description": "Make a directory and its parents if needed - Think `mkdir -p`", + "license": "MIT", + "repository": "sindresorhus/make-dir", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && nyc ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "mkdir", + "mkdirp", + "make", + "directories", + "dir", + "dirs", + "folders", + "directory", + "folder", + "path", + "parent", + "parents", + "intermediate", + "recursively", + "recursive", + "create", + "fs", + "filesystem", + "file-system" + ], + "dependencies": { + "pify": "^3.0.0" + }, + "devDependencies": { + "ava": "*", + "codecov": "^3.0.0", + "graceful-fs": "^4.1.11", + "nyc": "^11.3.0", + "path-type": "^3.0.0", + "tempy": "^0.2.1", + "xo": "^0.20.0" + } +} diff --git a/node_modules/make-dir/readme.md b/node_modules/make-dir/readme.md new file mode 100644 index 0000000..8a32bf4 --- /dev/null +++ b/node_modules/make-dir/readme.md @@ -0,0 +1,116 @@ +# make-dir [![Build Status: macOS & Linux](https://travis-ci.org/sindresorhus/make-dir.svg?branch=master)](https://travis-ci.org/sindresorhus/make-dir) [![Build status: Windows](https://ci.appveyor.com/api/projects/status/e0vtt8y600w91gcs/branch/master?svg=true)](https://ci.appveyor.com/project/sindresorhus/make-dir/branch/master) [![codecov](https://codecov.io/gh/sindresorhus/make-dir/branch/master/graph/badge.svg)](https://codecov.io/gh/sindresorhus/make-dir) + +> Make a directory and its parents if needed - Think `mkdir -p` + + +## Advantages over [`mkdirp`](https://github.com/substack/node-mkdirp) + +- Promise API *(Async/await ready!)* +- Fixes many `mkdirp` issues: [#96](https://github.com/substack/node-mkdirp/pull/96) [#70](https://github.com/substack/node-mkdirp/issues/70) [#66](https://github.com/substack/node-mkdirp/issues/66) +- 100% test coverage +- CI-tested on macOS, Linux, and Windows +- Actively maintained +- Doesn't bundle a CLI + + +## Install + +``` +$ npm install make-dir +``` + + +## Usage + +``` +$ pwd +/Users/sindresorhus/fun +$ tree +. +``` + +```js +const makeDir = require('make-dir'); + +makeDir('unicorn/rainbow/cake').then(path => { + console.log(path); + //=> '/Users/sindresorhus/fun/unicorn/rainbow/cake' +}); +``` + +``` +$ tree +. +└── unicorn + └── rainbow + └── cake +``` + +Multiple directories: + +```js +const makeDir = require('make-dir'); + +Promise.all([ + makeDir('unicorn/rainbow') + makeDir('foo/bar') +]).then(paths => { + console.log(paths); + /* + [ + '/Users/sindresorhus/fun/unicorn/rainbow', + '/Users/sindresorhus/fun/foo/bar' + ] + */ +}); +``` + + +## API + +### makeDir(path, [options]) + +Returns a `Promise` for the path to the created directory. + +### makeDir.sync(path, [options]) + +Returns the path to the created directory. + +#### path + +Type: `string` + +Directory to create. + +#### options + +Type: `Object` + +##### mode + +Type: `integer`<br> +Default: `0o777 & (~process.umask())` + +Directory [permissions](https://x-team.com/blog/file-system-permissions-umask-node-js/). + +##### fs + +Type: `Object`<br> +Default: `require('fs')` + +Use a custom `fs` implementation. For example [`graceful-fs`](https://github.com/isaacs/node-graceful-fs). + + +## Related + +- [make-dir-cli](https://github.com/sindresorhus/make-dir-cli) - CLI for this module +- [del](https://github.com/sindresorhus/del) - Delete files and directories +- [globby](https://github.com/sindresorhus/globby) - User-friendly glob matching +- [cpy](https://github.com/sindresorhus/cpy) - Copy files +- [cpy-cli](https://github.com/sindresorhus/cpy-cli) - Copy files on the command-line +- [move-file](https://github.com/sindresorhus/move-file) - Move a file + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/mimic-response/index.js b/node_modules/mimic-response/index.js new file mode 100644 index 0000000..d5e33be --- /dev/null +++ b/node_modules/mimic-response/index.js @@ -0,0 +1,32 @@ +'use strict'; + +// We define these manually to ensure they're always copied +// even if they would move up the prototype chain +// https://nodejs.org/api/http.html#http_class_http_incomingmessage +const knownProps = [ + 'destroy', + 'setTimeout', + 'socket', + 'headers', + 'trailers', + 'rawHeaders', + 'statusCode', + 'httpVersion', + 'httpVersionMinor', + 'httpVersionMajor', + 'rawTrailers', + 'statusMessage' +]; + +module.exports = (fromStream, toStream) => { + const fromProps = new Set(Object.keys(fromStream).concat(knownProps)); + + for (const prop of fromProps) { + // Don't overwrite existing properties + if (prop in toStream) { + continue; + } + + toStream[prop] = typeof fromStream[prop] === 'function' ? fromStream[prop].bind(fromStream) : fromStream[prop]; + } +}; diff --git a/node_modules/mimic-response/license b/node_modules/mimic-response/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/mimic-response/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/mimic-response/package.json b/node_modules/mimic-response/package.json new file mode 100644 index 0000000..689cb61 --- /dev/null +++ b/node_modules/mimic-response/package.json @@ -0,0 +1,37 @@ +{ + "name": "mimic-response", + "version": "1.0.1", + "description": "Mimic a Node.js HTTP response stream", + "license": "MIT", + "repository": "sindresorhus/mimic-response", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "mimic", + "response", + "stream", + "http", + "https", + "request", + "get", + "core" + ], + "devDependencies": { + "ava": "*", + "create-test-server": "^0.1.0", + "pify": "^3.0.0", + "xo": "*" + } +} diff --git a/node_modules/mimic-response/readme.md b/node_modules/mimic-response/readme.md new file mode 100644 index 0000000..e07ec66 --- /dev/null +++ b/node_modules/mimic-response/readme.md @@ -0,0 +1,54 @@ +# mimic-response [![Build Status](https://travis-ci.org/sindresorhus/mimic-response.svg?branch=master)](https://travis-ci.org/sindresorhus/mimic-response) + +> Mimic a [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage) + + +## Install + +``` +$ npm install mimic-response +``` + + +## Usage + +```js +const stream = require('stream'); +const mimicResponse = require('mimic-response'); + +const responseStream = getHttpResponseStream(); +const myStream = new stream.PassThrough(); + +mimicResponse(responseStream, myStream); + +console.log(myStream.statusCode); +//=> 200 +``` + + +## API + +### mimicResponse(from, to) + +#### from + +Type: `Stream` + +[Node.js HTTP response stream.](https://nodejs.org/api/http.html#http_class_http_incomingmessage) + +#### to + +Type: `Stream` + +Any stream. + + +## Related + +- [mimic-fn](https://github.com/sindresorhus/mimic-fn) - Make a function mimic another one +- [clone-response](https://github.com/lukechilds/clone-response) - Clone a Node.js response stream + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/normalize-url/index.d.ts b/node_modules/normalize-url/index.d.ts new file mode 100644 index 0000000..7e332f2 --- /dev/null +++ b/node_modules/normalize-url/index.d.ts @@ -0,0 +1,216 @@ +declare namespace normalizeUrl { + interface Options { + /** + @default 'http:' + */ + readonly defaultProtocol?: string; + + /** + Prepends `defaultProtocol` to the URL if it's protocol-relative. + + @default true + + @example + ``` + normalizeUrl('//sindresorhus.com:80/'); + //=> 'http://sindresorhus.com' + + normalizeUrl('//sindresorhus.com:80/', {normalizeProtocol: false}); + //=> '//sindresorhus.com' + ``` + */ + readonly normalizeProtocol?: boolean; + + /** + Normalizes `https:` URLs to `http:`. + + @default false + + @example + ``` + normalizeUrl('https://sindresorhus.com:80/'); + //=> 'https://sindresorhus.com' + + normalizeUrl('https://sindresorhus.com:80/', {forceHttp: true}); + //=> 'http://sindresorhus.com' + ``` + */ + readonly forceHttp?: boolean; + + /** + Normalizes `http:` URLs to `https:`. + + This option can't be used with the `forceHttp` option at the same time. + + @default false + + @example + ``` + normalizeUrl('https://sindresorhus.com:80/'); + //=> 'https://sindresorhus.com' + + normalizeUrl('http://sindresorhus.com:80/', {forceHttps: true}); + //=> 'https://sindresorhus.com' + ``` + */ + readonly forceHttps?: boolean; + + /** + Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of a URL. + + @default true + + @example + ``` + normalizeUrl('user:password@sindresorhus.com'); + //=> 'https://sindresorhus.com' + + normalizeUrl('user:password@sindresorhus.com', {stripAuthentication: false}); + //=> 'https://user:password@sindresorhus.com' + ``` + */ + readonly stripAuthentication?: boolean; + + /** + Removes hash from the URL. + + @default false + + @example + ``` + normalizeUrl('sindresorhus.com/about.html#contact'); + //=> 'http://sindresorhus.com/about.html#contact' + + normalizeUrl('sindresorhus.com/about.html#contact', {stripHash: true}); + //=> 'http://sindresorhus.com/about.html' + ``` + */ + readonly stripHash?: boolean; + + /** + Removes HTTP(S) protocol from an URL `http://sindresorhus.com` → `sindresorhus.com`. + + @default false + + @example + ``` + normalizeUrl('https://sindresorhus.com'); + //=> 'https://sindresorhus.com' + + normalizeUrl('sindresorhus.com', {stripProtocol: true}); + //=> 'sindresorhus.com' + ``` + */ + readonly stripProtocol?: boolean; + + /** + Removes `www.` from the URL. + + @default true + + @example + ``` + normalizeUrl('http://www.sindresorhus.com'); + //=> 'http://sindresorhus.com' + + normalizeUrl('http://www.sindresorhus.com', {stripWWW: false}); + //=> 'http://www.sindresorhus.com' + ``` + */ + readonly stripWWW?: boolean; + + /** + Removes query parameters that matches any of the provided strings or regexes. + + @default [/^utm_\w+/i] + + @example + ``` + normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', { + removeQueryParameters: ['ref'] + }); + //=> 'http://sindresorhus.com/?foo=bar' + ``` + */ + readonly removeQueryParameters?: ReadonlyArray<RegExp | string>; + + /** + Removes trailing slash. + + __Note__: Trailing slash is always removed if the URL doesn't have a pathname. + + @default true + + @example + ``` + normalizeUrl('http://sindresorhus.com/redirect/'); + //=> 'http://sindresorhus.com/redirect' + + normalizeUrl('http://sindresorhus.com/redirect/', {removeTrailingSlash: false}); + //=> 'http://sindresorhus.com/redirect/' + + normalizeUrl('http://sindresorhus.com/', {removeTrailingSlash: false}); + //=> 'http://sindresorhus.com' + ``` + */ + readonly removeTrailingSlash?: boolean; + + /** + Removes the default directory index file from path that matches any of the provided strings or regexes. + When `true`, the regex `/^index\.[a-z]+$/` is used. + + @default false + + @example + ``` + normalizeUrl('www.sindresorhus.com/foo/default.php', { + removeDirectoryIndex: [/^default\.[a-z]+$/] + }); + //=> 'http://sindresorhus.com/foo' + ``` + */ + readonly removeDirectoryIndex?: ReadonlyArray<RegExp | string>; + + /** + Sorts the query parameters alphabetically by key. + + @default true + + @example + ``` + normalizeUrl('www.sindresorhus.com?b=two&a=one&c=three', { + sortQueryParameters: false + }); + //=> 'http://sindresorhus.com/?b=two&a=one&c=three' + ``` + */ + readonly sortQueryParameters?: boolean; + } +} + +declare const normalizeUrl: { + /** + [Normalize](https://en.wikipedia.org/wiki/URL_normalization) a URL. + + @param url - URL to normalize, including [data URL](https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs). + + @example + ``` + import normalizeUrl = require('normalize-url'); + + normalizeUrl('sindresorhus.com'); + //=> 'http://sindresorhus.com' + + normalizeUrl('HTTP://xn--xample-hva.com:80/?b=bar&a=foo'); + //=> 'http://êxample.com/?a=foo&b=bar' + ``` + */ + (url: string, options?: normalizeUrl.Options): string; + + // TODO: Remove this for the next major release, refactor the whole definition to: + // declare function normalizeUrl(url: string, options?: normalizeUrl.Options): string; + // export = normalizeUrl; + default: typeof normalizeUrl; +}; + +export = normalizeUrl; diff --git a/node_modules/normalize-url/index.js b/node_modules/normalize-url/index.js new file mode 100644 index 0000000..2ab7f57 --- /dev/null +++ b/node_modules/normalize-url/index.js @@ -0,0 +1,221 @@ +'use strict'; +// TODO: Use the `URL` global when targeting Node.js 10 +const URLParser = typeof URL === 'undefined' ? require('url').URL : URL; + +// https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs +const DATA_URL_DEFAULT_MIME_TYPE = 'text/plain'; +const DATA_URL_DEFAULT_CHARSET = 'us-ascii'; + +const testParameter = (name, filters) => { + return filters.some(filter => filter instanceof RegExp ? filter.test(name) : filter === name); +}; + +const normalizeDataURL = (urlString, {stripHash}) => { + const parts = urlString.match(/^data:([^,]*?),([^#]*?)(?:#(.*))?$/); + + if (!parts) { + throw new Error(`Invalid URL: ${urlString}`); + } + + const mediaType = parts[1].split(';'); + const body = parts[2]; + const hash = stripHash ? '' : parts[3]; + + let base64 = false; + + if (mediaType[mediaType.length - 1] === 'base64') { + mediaType.pop(); + base64 = true; + } + + // Lowercase MIME type + const mimeType = (mediaType.shift() || '').toLowerCase(); + const attributes = mediaType + .map(attribute => { + let [key, value = ''] = attribute.split('=').map(string => string.trim()); + + // Lowercase `charset` + if (key === 'charset') { + value = value.toLowerCase(); + + if (value === DATA_URL_DEFAULT_CHARSET) { + return ''; + } + } + + return `${key}${value ? `=${value}` : ''}`; + }) + .filter(Boolean); + + const normalizedMediaType = [ + ...attributes + ]; + + if (base64) { + normalizedMediaType.push('base64'); + } + + if (normalizedMediaType.length !== 0 || (mimeType && mimeType !== DATA_URL_DEFAULT_MIME_TYPE)) { + normalizedMediaType.unshift(mimeType); + } + + return `data:${normalizedMediaType.join(';')},${base64 ? body.trim() : body}${hash ? `#${hash}` : ''}`; +}; + +const normalizeUrl = (urlString, options) => { + options = { + defaultProtocol: 'http:', + normalizeProtocol: true, + forceHttp: false, + forceHttps: false, + stripAuthentication: true, + stripHash: false, + stripWWW: true, + removeQueryParameters: [/^utm_\w+/i], + removeTrailingSlash: true, + removeDirectoryIndex: false, + sortQueryParameters: true, + ...options + }; + + // TODO: Remove this at some point in the future + if (Reflect.has(options, 'normalizeHttps')) { + throw new Error('options.normalizeHttps is renamed to options.forceHttp'); + } + + if (Reflect.has(options, 'normalizeHttp')) { + throw new Error('options.normalizeHttp is renamed to options.forceHttps'); + } + + if (Reflect.has(options, 'stripFragment')) { + throw new Error('options.stripFragment is renamed to options.stripHash'); + } + + urlString = urlString.trim(); + + // Data URL + if (/^data:/i.test(urlString)) { + return normalizeDataURL(urlString, options); + } + + const hasRelativeProtocol = urlString.startsWith('//'); + const isRelativeUrl = !hasRelativeProtocol && /^\.*\//.test(urlString); + + // Prepend protocol + if (!isRelativeUrl) { + urlString = urlString.replace(/^(?!(?:\w+:)?\/\/)|^\/\//, options.defaultProtocol); + } + + const urlObj = new URLParser(urlString); + + if (options.forceHttp && options.forceHttps) { + throw new Error('The `forceHttp` and `forceHttps` options cannot be used together'); + } + + if (options.forceHttp && urlObj.protocol === 'https:') { + urlObj.protocol = 'http:'; + } + + if (options.forceHttps && urlObj.protocol === 'http:') { + urlObj.protocol = 'https:'; + } + + // Remove auth + if (options.stripAuthentication) { + urlObj.username = ''; + urlObj.password = ''; + } + + // Remove hash + if (options.stripHash) { + urlObj.hash = ''; + } + + // Remove duplicate slashes if not preceded by a protocol + if (urlObj.pathname) { + // TODO: Use the following instead when targeting Node.js 10 + // `urlObj.pathname = urlObj.pathname.replace(/(?<!https?:)\/{2,}/g, '/');` + urlObj.pathname = urlObj.pathname.replace(/((?!:).|^)\/{2,}/g, (_, p1) => { + if (/^(?!\/)/g.test(p1)) { + return `${p1}/`; + } + + return '/'; + }); + } + + // Decode URI octets + if (urlObj.pathname) { + urlObj.pathname = decodeURI(urlObj.pathname); + } + + // Remove directory index + if (options.removeDirectoryIndex === true) { + options.removeDirectoryIndex = [/^index\.[a-z]+$/]; + } + + if (Array.isArray(options.removeDirectoryIndex) && options.removeDirectoryIndex.length > 0) { + let pathComponents = urlObj.pathname.split('/'); + const lastComponent = pathComponents[pathComponents.length - 1]; + + if (testParameter(lastComponent, options.removeDirectoryIndex)) { + pathComponents = pathComponents.slice(0, pathComponents.length - 1); + urlObj.pathname = pathComponents.slice(1).join('/') + '/'; + } + } + + if (urlObj.hostname) { + // Remove trailing dot + urlObj.hostname = urlObj.hostname.replace(/\.$/, ''); + + // Remove `www.` + if (options.stripWWW && /^www\.([a-z\-\d]{2,63})\.([a-z.]{2,5})$/.test(urlObj.hostname)) { + // Each label should be max 63 at length (min: 2). + // The extension should be max 5 at length (min: 2). + // Source: https://en.wikipedia.org/wiki/Hostname#Restrictions_on_valid_host_names + urlObj.hostname = urlObj.hostname.replace(/^www\./, ''); + } + } + + // Remove query unwanted parameters + if (Array.isArray(options.removeQueryParameters)) { + for (const key of [...urlObj.searchParams.keys()]) { + if (testParameter(key, options.removeQueryParameters)) { + urlObj.searchParams.delete(key); + } + } + } + + // Sort query parameters + if (options.sortQueryParameters) { + urlObj.searchParams.sort(); + } + + if (options.removeTrailingSlash) { + urlObj.pathname = urlObj.pathname.replace(/\/$/, ''); + } + + // Take advantage of many of the Node `url` normalizations + urlString = urlObj.toString(); + + // Remove ending `/` + if ((options.removeTrailingSlash || urlObj.pathname === '/') && urlObj.hash === '') { + urlString = urlString.replace(/\/$/, ''); + } + + // Restore relative protocol, if applicable + if (hasRelativeProtocol && !options.normalizeProtocol) { + urlString = urlString.replace(/^http:\/\//, '//'); + } + + // Remove http/https + if (options.stripProtocol) { + urlString = urlString.replace(/^(?:https?:)?\/\//, ''); + } + + return urlString; +}; + +module.exports = normalizeUrl; +// TODO: Remove this for the next major release +module.exports.default = normalizeUrl; diff --git a/node_modules/normalize-url/license b/node_modules/normalize-url/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/normalize-url/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/normalize-url/package.json b/node_modules/normalize-url/package.json new file mode 100644 index 0000000..b0d59e0 --- /dev/null +++ b/node_modules/normalize-url/package.json @@ -0,0 +1,44 @@ +{ + "name": "normalize-url", + "version": "4.5.1", + "description": "Normalize a URL", + "license": "MIT", + "repository": "sindresorhus/normalize-url", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=8" + }, + "scripts": { + "test": "xo && nyc ava && tsd" + }, + "files": [ + "index.js", + "index.d.ts" + ], + "keywords": [ + "normalize", + "url", + "uri", + "address", + "string", + "normalization", + "normalisation", + "query", + "querystring", + "simplify", + "strip", + "trim", + "canonical" + ], + "devDependencies": { + "ava": "^2.4.0", + "coveralls": "^3.0.6", + "nyc": "^14.1.1", + "tsd": "^0.8.0", + "xo": "^0.24.0" + } +} diff --git a/node_modules/normalize-url/readme.md b/node_modules/normalize-url/readme.md new file mode 100644 index 0000000..a851fdd --- /dev/null +++ b/node_modules/normalize-url/readme.md @@ -0,0 +1,232 @@ +# normalize-url [![Build Status](https://travis-ci.org/sindresorhus/normalize-url.svg?branch=master)](https://travis-ci.org/sindresorhus/normalize-url) [![Coverage Status](https://coveralls.io/repos/github/sindresorhus/normalize-url/badge.svg?branch=master)](https://coveralls.io/github/sindresorhus/normalize-url?branch=master) + +> [Normalize](https://en.wikipedia.org/wiki/URL_normalization) a URL + +Useful when you need to display, store, deduplicate, sort, compare, etc, URLs. + + +## Install + +``` +$ npm install normalize-url +``` + + +## Usage + +```js +const normalizeUrl = require('normalize-url'); + +normalizeUrl('sindresorhus.com'); +//=> 'http://sindresorhus.com' + +normalizeUrl('HTTP://xn--xample-hva.com:80/?b=bar&a=foo'); +//=> 'http://êxample.com/?a=foo&b=bar' +``` + + +## API + +### normalizeUrl(url, options?) + +#### url + +Type: `string` + +URL to normalize, including [data URL](https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs). + +#### options + +Type: `object` + +##### defaultProtocol + +Type: `string`<br> +Default: `http:` + +##### normalizeProtocol + +Type: `boolean`<br> +Default: `true` + +Prepend `defaultProtocol` to the URL if it's protocol-relative. + +```js +normalizeUrl('//sindresorhus.com:80/'); +//=> 'http://sindresorhus.com' + +normalizeUrl('//sindresorhus.com:80/', {normalizeProtocol: false}); +//=> '//sindresorhus.com' +``` + +##### forceHttp + +Type: `boolean`<br> +Default: `false` + +Normalize `https:` to `http:`. + +```js +normalizeUrl('https://sindresorhus.com:80/'); +//=> 'https://sindresorhus.com' + +normalizeUrl('https://sindresorhus.com:80/', {forceHttp: true}); +//=> 'http://sindresorhus.com' +``` + +##### forceHttps + +Type: `boolean`<br> +Default: `false` + +Normalize `http:` to `https:`. + +```js +normalizeUrl('https://sindresorhus.com:80/'); +//=> 'https://sindresorhus.com' + +normalizeUrl('http://sindresorhus.com:80/', {forceHttps: true}); +//=> 'https://sindresorhus.com' +``` + +This option can't be used with the `forceHttp` option at the same time. + +##### stripAuthentication + +Type: `boolean`<br> +Default: `true` + +Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of the URL. + +```js +normalizeUrl('user:password@sindresorhus.com'); +//=> 'https://sindresorhus.com' + +normalizeUrl('user:password@sindresorhus.com', {stripAuthentication: false}); +//=> 'https://user:password@sindresorhus.com' +``` + +##### stripHash + +Type: `boolean`<br> +Default: `false` + +Strip the hash part of the URL. + +```js +normalizeUrl('sindresorhus.com/about.html#contact'); +//=> 'http://sindresorhus.com/about.html#contact' + +normalizeUrl('sindresorhus.com/about.html#contact', {stripHash: true}); +//=> 'http://sindresorhus.com/about.html' +``` + +##### stripProtocol + +Type: `boolean`<br> +Default: `false` + +Remove HTTP(S) protocol from the URL: `http://sindresorhus.com` → `sindresorhus.com`. + +```js +normalizeUrl('https://sindresorhus.com'); +//=> 'https://sindresorhus.com' + +normalizeUrl('sindresorhus.com', {stripProtocol: true}); +//=> 'sindresorhus.com' +``` + +##### stripWWW + +Type: `boolean`<br> +Default: `true` + +Remove `www.` from the URL. + +```js +normalizeUrl('http://www.sindresorhus.com'); +//=> 'http://sindresorhus.com' + +normalizeUrl('http://www.sindresorhus.com', {stripWWW: false}); +//=> 'http://www.sindresorhus.com' +``` + +##### removeQueryParameters + +Type: `Array<RegExp | string>`<br> +Default: `[/^utm_\w+/i]` + +Remove query parameters that matches any of the provided strings or regexes. + +```js +normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', { + removeQueryParameters: ['ref'] +}); +//=> 'http://sindresorhus.com/?foo=bar' +``` + +##### removeTrailingSlash + +Type: `boolean`<br> +Default: `true` + +Remove trailing slash. + +**Note:** Trailing slash is always removed if the URL doesn't have a pathname. + +```js +normalizeUrl('http://sindresorhus.com/redirect/'); +//=> 'http://sindresorhus.com/redirect' + +normalizeUrl('http://sindresorhus.com/redirect/', {removeTrailingSlash: false}); +//=> 'http://sindresorhus.com/redirect/' + +normalizeUrl('http://sindresorhus.com/', {removeTrailingSlash: false}); +//=> 'http://sindresorhus.com' +``` + +##### removeDirectoryIndex + +Type: `boolean | Array<RegExp | string>`<br> +Default: `false` + +Removes the default directory index file from path that matches any of the provided strings or regexes. When `true`, the regex `/^index\.[a-z]+$/` is used. + +```js +normalizeUrl('www.sindresorhus.com/foo/default.php', { + removeDirectoryIndex: [/^default\.[a-z]+$/] +}); +//=> 'http://sindresorhus.com/foo' +``` + +##### sortQueryParameters + +Type: `boolean`<br> +Default: `true` + +Sorts the query parameters alphabetically by key. + +```js +normalizeUrl('www.sindresorhus.com?b=two&a=one&c=three', { + sortQueryParameters: false +}); +//=> 'http://sindresorhus.com/?b=two&a=one&c=three' +``` + + +## Related + +- [compare-urls](https://github.com/sindresorhus/compare-urls) - Compare URLs by first normalizing them + + +--- + +<div align="center"> + <b> + <a href="https://tidelift.com/subscription/pkg/npm-normalize-url?utm_source=npm-normalize-url&utm_medium=referral&utm_campaign=readme">Get professional support for this package with a Tidelift subscription</a> + </b> + <br> + <sub> + Tidelift helps make open source sustainable for maintainers while giving companies<br>assurances about security, maintenance, and licensing for their dependencies. + </sub> +</div> diff --git a/node_modules/once/LICENSE b/node_modules/once/LICENSE new file mode 100644 index 0000000..19129e3 --- /dev/null +++ b/node_modules/once/LICENSE @@ -0,0 +1,15 @@ +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +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. diff --git a/node_modules/once/README.md b/node_modules/once/README.md new file mode 100644 index 0000000..1f1ffca --- /dev/null +++ b/node_modules/once/README.md @@ -0,0 +1,79 @@ +# once + +Only call a function once. + +## usage + +```javascript +var once = require('once') + +function load (file, cb) { + cb = once(cb) + loader.load('file') + loader.once('load', cb) + loader.once('error', cb) +} +``` + +Or add to the Function.prototype in a responsible way: + +```javascript +// only has to be done once +require('once').proto() + +function load (file, cb) { + cb = cb.once() + loader.load('file') + loader.once('load', cb) + loader.once('error', cb) +} +``` + +Ironically, the prototype feature makes this module twice as +complicated as necessary. + +To check whether you function has been called, use `fn.called`. Once the +function is called for the first time the return value of the original +function is saved in `fn.value` and subsequent calls will continue to +return this value. + +```javascript +var once = require('once') + +function load (cb) { + cb = once(cb) + var stream = createStream() + stream.once('data', cb) + stream.once('end', function () { + if (!cb.called) cb(new Error('not found')) + }) +} +``` + +## `once.strict(func)` + +Throw an error if the function is called twice. + +Some functions are expected to be called only once. Using `once` for them would +potentially hide logical errors. + +In the example below, the `greet` function has to call the callback only once: + +```javascript +function greet (name, cb) { + // return is missing from the if statement + // when no name is passed, the callback is called twice + if (!name) cb('Hello anonymous') + cb('Hello ' + name) +} + +function log (msg) { + console.log(msg) +} + +// this will print 'Hello anonymous' but the logical error will be missed +greet(null, once(msg)) + +// once.strict will print 'Hello anonymous' and throw an error when the callback will be called the second time +greet(null, once.strict(msg)) +``` diff --git a/node_modules/once/once.js b/node_modules/once/once.js new file mode 100644 index 0000000..2354067 --- /dev/null +++ b/node_modules/once/once.js @@ -0,0 +1,42 @@ +var wrappy = require('wrappy') +module.exports = wrappy(once) +module.exports.strict = wrappy(onceStrict) + +once.proto = once(function () { + Object.defineProperty(Function.prototype, 'once', { + value: function () { + return once(this) + }, + configurable: true + }) + + Object.defineProperty(Function.prototype, 'onceStrict', { + value: function () { + return onceStrict(this) + }, + configurable: true + }) +}) + +function once (fn) { + var f = function () { + if (f.called) return f.value + f.called = true + return f.value = fn.apply(this, arguments) + } + f.called = false + return f +} + +function onceStrict (fn) { + var f = function () { + if (f.called) + throw new Error(f.onceError) + f.called = true + return f.value = fn.apply(this, arguments) + } + var name = fn.name || 'Function wrapped with `once`' + f.onceError = name + " shouldn't be called more than once" + f.called = false + return f +} diff --git a/node_modules/once/package.json b/node_modules/once/package.json new file mode 100644 index 0000000..16815b2 --- /dev/null +++ b/node_modules/once/package.json @@ -0,0 +1,33 @@ +{ + "name": "once", + "version": "1.4.0", + "description": "Run a function exactly one time", + "main": "once.js", + "directories": { + "test": "test" + }, + "dependencies": { + "wrappy": "1" + }, + "devDependencies": { + "tap": "^7.0.1" + }, + "scripts": { + "test": "tap test/*.js" + }, + "files": [ + "once.js" + ], + "repository": { + "type": "git", + "url": "git://github.com/isaacs/once" + }, + "keywords": [ + "once", + "function", + "one", + "single" + ], + "author": "Isaac Z. Schlueter <i@izs.me> (http://blog.izs.me/)", + "license": "ISC" +} diff --git a/node_modules/p-cancelable/index.d.ts b/node_modules/p-cancelable/index.d.ts new file mode 100644 index 0000000..316d636 --- /dev/null +++ b/node_modules/p-cancelable/index.d.ts @@ -0,0 +1,168 @@ +/** + * Accepts a function that is called when the promise is canceled. + * + * You're not required to call this function. You can call this function multiple times to add multiple cancel handlers. + */ +export interface OnCancelFunction { + (cancelHandler: () => void): void; + shouldReject: boolean; +} + +declare class PCancelable<ValueType> extends Promise<ValueType> { + /** + * Convenience method to make your promise-returning or async function cancelable. + * + * @param fn - A promise-returning function. The function you specify will have `onCancel` appended to its parameters. + * + * @example + * + * import PCancelable from 'p-cancelable'; + * + * const fn = PCancelable.fn((input, onCancel) => { + * const job = new Job(); + * + * onCancel(() => { + * job.cleanup(); + * }); + * + * return job.start(); //=> Promise + * }); + * + * const cancelablePromise = fn('input'); //=> PCancelable + * + * // … + * + * cancelablePromise.cancel(); + */ + static fn<ReturnType>( + userFn: (onCancel: OnCancelFunction) => PromiseLike<ReturnType> + ): () => PCancelable<ReturnType>; + static fn<Agument1Type, ReturnType>( + userFn: ( + argument1: Agument1Type, + onCancel: OnCancelFunction + ) => PromiseLike<ReturnType> + ): (argument1: Agument1Type) => PCancelable<ReturnType>; + static fn<Agument1Type, Agument2Type, ReturnType>( + userFn: ( + argument1: Agument1Type, + argument2: Agument2Type, + onCancel: OnCancelFunction + ) => PromiseLike<ReturnType> + ): ( + argument1: Agument1Type, + argument2: Agument2Type + ) => PCancelable<ReturnType>; + static fn<Agument1Type, Agument2Type, Agument3Type, ReturnType>( + userFn: ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type, + onCancel: OnCancelFunction + ) => PromiseLike<ReturnType> + ): ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type + ) => PCancelable<ReturnType>; + static fn<Agument1Type, Agument2Type, Agument3Type, Agument4Type, ReturnType>( + userFn: ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type, + argument4: Agument4Type, + onCancel: OnCancelFunction + ) => PromiseLike<ReturnType> + ): ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type, + argument4: Agument4Type + ) => PCancelable<ReturnType>; + static fn< + Agument1Type, + Agument2Type, + Agument3Type, + Agument4Type, + Agument5Type, + ReturnType + >( + userFn: ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type, + argument4: Agument4Type, + argument5: Agument5Type, + onCancel: OnCancelFunction + ) => PromiseLike<ReturnType> + ): ( + argument1: Agument1Type, + argument2: Agument2Type, + argument3: Agument3Type, + argument4: Agument4Type, + argument5: Agument5Type + ) => PCancelable<ReturnType>; + static fn<ReturnType>( + userFn: (...arguments: unknown[]) => PromiseLike<ReturnType> + ): (...arguments: unknown[]) => PCancelable<ReturnType>; + + /** + * Create a promise that can be canceled. + * + * Can be constructed in the same was as a [`Promise` constructor](https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Promise), but with an appended `onCancel` parameter in `executor`. `PCancelable` is a subclass of `Promise`. + * + * Cancelling will reject the promise with `CancelError`. To avoid that, set `onCancel.shouldReject` to `false`. + * + * @example + * + * import PCancelable from 'p-cancelable'; + * + * const cancelablePromise = new PCancelable((resolve, reject, onCancel) => { + * const job = new Job(); + * + * onCancel.shouldReject = false; + * onCancel(() => { + * job.stop(); + * }); + * + * job.on('finish', resolve); + * }); + * + * cancelablePromise.cancel(); // Doesn't throw an error + */ + constructor( + executor: ( + resolve: (value?: ValueType | PromiseLike<ValueType>) => void, + reject: (reason?: unknown) => void, + onCancel: OnCancelFunction + ) => void + ); + + /** + * Whether the promise is canceled. + */ + readonly isCanceled: boolean; + + /** + * Cancel the promise and optionally provide a reason. + * + * The cancellation is synchronous. Calling it after the promise has settled or multiple times does nothing. + * + * @param reason - The cancellation reason to reject the promise with. + */ + cancel(reason?: string): void; +} + +export default PCancelable; + +/** + * Rejection reason when `.cancel()` is called. + * + * It includes a `.isCanceled` property for convenience. + */ +export class CancelError extends Error { + readonly name: 'CancelError'; + readonly isCanceled: true; + + constructor(reason?: string); +} diff --git a/node_modules/p-cancelable/index.js b/node_modules/p-cancelable/index.js new file mode 100644 index 0000000..26bd42e --- /dev/null +++ b/node_modules/p-cancelable/index.js @@ -0,0 +1,103 @@ +'use strict'; + +class CancelError extends Error { + constructor(reason) { + super(reason || 'Promise was canceled'); + this.name = 'CancelError'; + } + + get isCanceled() { + return true; + } +} + +class PCancelable { + static fn(userFn) { + return (...args) => { + return new PCancelable((resolve, reject, onCancel) => { + args.push(onCancel); + userFn(...args).then(resolve, reject); + }); + }; + } + + constructor(executor) { + this._cancelHandlers = []; + this._isPending = true; + this._isCanceled = false; + this._rejectOnCancel = true; + + this._promise = new Promise((resolve, reject) => { + this._reject = reject; + + const onResolve = value => { + this._isPending = false; + resolve(value); + }; + + const onReject = error => { + this._isPending = false; + reject(error); + }; + + const onCancel = handler => { + this._cancelHandlers.push(handler); + }; + + Object.defineProperties(onCancel, { + shouldReject: { + get: () => this._rejectOnCancel, + set: bool => { + this._rejectOnCancel = bool; + } + } + }); + + return executor(onResolve, onReject, onCancel); + }); + } + + then(onFulfilled, onRejected) { + return this._promise.then(onFulfilled, onRejected); + } + + catch(onRejected) { + return this._promise.catch(onRejected); + } + + finally(onFinally) { + return this._promise.finally(onFinally); + } + + cancel(reason) { + if (!this._isPending || this._isCanceled) { + return; + } + + if (this._cancelHandlers.length > 0) { + try { + for (const handler of this._cancelHandlers) { + handler(); + } + } catch (error) { + this._reject(error); + } + } + + this._isCanceled = true; + if (this._rejectOnCancel) { + this._reject(new CancelError(reason)); + } + } + + get isCanceled() { + return this._isCanceled; + } +} + +Object.setPrototypeOf(PCancelable.prototype, Promise.prototype); + +module.exports = PCancelable; +module.exports.default = PCancelable; + +module.exports.CancelError = CancelError; diff --git a/node_modules/p-cancelable/license b/node_modules/p-cancelable/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/p-cancelable/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/p-cancelable/package.json b/node_modules/p-cancelable/package.json new file mode 100644 index 0000000..fa3a6c9 --- /dev/null +++ b/node_modules/p-cancelable/package.json @@ -0,0 +1,49 @@ +{ + "name": "p-cancelable", + "version": "1.1.0", + "description": "Create a promise that can be canceled", + "license": "MIT", + "repository": "sindresorhus/p-cancelable", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=6" + }, + "scripts": { + "test": "xo && ava && tsd-check" + }, + "files": [ + "index.js", + "index.d.ts" + ], + "keywords": [ + "promise", + "cancelable", + "cancel", + "canceled", + "canceling", + "cancellable", + "cancellation", + "abort", + "abortable", + "aborting", + "cleanup", + "task", + "token", + "async", + "function", + "await", + "promises", + "bluebird" + ], + "devDependencies": { + "ava": "^1.3.1", + "delay": "^4.1.0", + "promise.prototype.finally": "^3.1.0", + "tsd-check": "^0.3.0", + "xo": "^0.24.0" + } +} diff --git a/node_modules/p-cancelable/readme.md b/node_modules/p-cancelable/readme.md new file mode 100644 index 0000000..b66e96a --- /dev/null +++ b/node_modules/p-cancelable/readme.md @@ -0,0 +1,155 @@ +# p-cancelable [![Build Status](https://travis-ci.org/sindresorhus/p-cancelable.svg?branch=master)](https://travis-ci.org/sindresorhus/p-cancelable) + +> Create a promise that can be canceled + +Useful for animation, loading resources, long-running async computations, async iteration, etc. + + +## Install + +``` +$ npm install p-cancelable +``` + + +## Usage + +```js +const PCancelable = require('p-cancelable'); + +const cancelablePromise = new PCancelable((resolve, reject, onCancel) => { + const worker = new SomeLongRunningOperation(); + + onCancel(() => { + worker.close(); + }); + + worker.on('finish', resolve); + worker.on('error', reject); +}); + +(async () => { + try { + console.log('Operation finished successfully:', await cancelablePromise); + } catch (error) { + if (cancelablePromise.isCanceled) { + // Handle the cancelation here + console.log('Operation was canceled'); + return; + } + + throw error; + } +})(); + +// Cancel the operation after 10 seconds +setTimeout(() => { + cancelablePromise.cancel('Unicorn has changed its color'); +}, 10000); +``` + + +## API + +### new PCancelable(executor) + +Same as the [`Promise` constructor](https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Promise), but with an appended `onCancel` parameter in `executor`.<br> +Cancelling will reject the promise with `PCancelable.CancelError`. To avoid that, set `onCancel.shouldReject` to `false`. + +```js +const PCancelable = require('p-cancelable'); + +const cancelablePromise = new PCancelable((resolve, reject, onCancel) => { + const job = new Job(); + + onCancel.shouldReject = false; + onCancel(() => { + job.stop(); + }); + + job.on('finish', resolve); +}); + +cancelablePromise.cancel(); // Doesn't throw an error +``` + +`PCancelable` is a subclass of `Promise`. + +#### onCanceled(fn) + +Type: `Function` + +Accepts a function that is called when the promise is canceled. + +You're not required to call this function. You can call this function multiple times to add multiple cancel handlers. + +### PCancelable#cancel([reason]) + +Type: `Function` + +Cancel the promise and optionally provide a reason. + +The cancellation is synchronous. Calling it after the promise has settled or multiple times does nothing. + +### PCancelable#isCanceled + +Type: `boolean` + +Whether the promise is canceled. + +### PCancelable.CancelError + +Type: `Error` + +Rejection reason when `.cancel()` is called. + +It includes a `.isCanceled` property for convenience. + +### PCancelable.fn(fn) + +Convenience method to make your promise-returning or async function cancelable. + +The function you specify will have `onCancel` appended to its parameters. + +```js +const PCancelable = require('p-cancelable'); + +const fn = PCancelable.fn((input, onCancel) => { + const job = new Job(); + + onCancel(() => { + job.cleanup(); + }); + + return job.start(); //=> Promise +}); + +const cancelablePromise = fn('input'); //=> PCancelable + +// … + +cancelablePromise.cancel(); +``` + + +## FAQ + +### Cancelable vs. Cancellable + +[In American English, the verb cancel is usually inflected canceled and canceling—with one l.](http://grammarist.com/spelling/cancel/)<br>Both a [browser API](https://developer.mozilla.org/en-US/docs/Web/API/Event/cancelable) and the [Cancelable Promises proposal](https://github.com/tc39/proposal-cancelable-promises) use this spelling. + +### What about the official [Cancelable Promises proposal](https://github.com/tc39/proposal-cancelable-promises)? + +~~It's still an early draft and I don't really like its current direction. It complicates everything and will require deep changes in the ecosystem to adapt to it. And the way you have to use cancel tokens is verbose and convoluted. I much prefer the more pragmatic and less invasive approach in this module.~~ The proposal was withdrawn. + + +## Related + +- [p-progress](https://github.com/sindresorhus/p-progress) - Create a promise that reports progress +- [p-lazy](https://github.com/sindresorhus/p-lazy) - Create a lazy promise that defers execution until `.then()` or `.catch()` is called +- [More…](https://github.com/sindresorhus/promise-fun) + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/pify/index.js b/node_modules/pify/index.js new file mode 100644 index 0000000..1dee43a --- /dev/null +++ b/node_modules/pify/index.js @@ -0,0 +1,84 @@ +'use strict'; + +const processFn = (fn, opts) => function () { + const P = opts.promiseModule; + const args = new Array(arguments.length); + + for (let i = 0; i < arguments.length; i++) { + args[i] = arguments[i]; + } + + return new P((resolve, reject) => { + if (opts.errorFirst) { + args.push(function (err, result) { + if (opts.multiArgs) { + const results = new Array(arguments.length - 1); + + for (let i = 1; i < arguments.length; i++) { + results[i - 1] = arguments[i]; + } + + if (err) { + results.unshift(err); + reject(results); + } else { + resolve(results); + } + } else if (err) { + reject(err); + } else { + resolve(result); + } + }); + } else { + args.push(function (result) { + if (opts.multiArgs) { + const results = new Array(arguments.length - 1); + + for (let i = 0; i < arguments.length; i++) { + results[i] = arguments[i]; + } + + resolve(results); + } else { + resolve(result); + } + }); + } + + fn.apply(this, args); + }); +}; + +module.exports = (obj, opts) => { + opts = Object.assign({ + exclude: [/.+(Sync|Stream)$/], + errorFirst: true, + promiseModule: Promise + }, opts); + + const filter = key => { + const match = pattern => typeof pattern === 'string' ? key === pattern : pattern.test(key); + return opts.include ? opts.include.some(match) : !opts.exclude.some(match); + }; + + let ret; + if (typeof obj === 'function') { + ret = function () { + if (opts.excludeMain) { + return obj.apply(this, arguments); + } + + return processFn(obj, opts).apply(this, arguments); + }; + } else { + ret = Object.create(Object.getPrototypeOf(obj)); + } + + for (const key in obj) { // eslint-disable-line guard-for-in + const x = obj[key]; + ret[key] = typeof x === 'function' && filter(key) ? processFn(x, opts) : x; + } + + return ret; +}; diff --git a/node_modules/pify/license b/node_modules/pify/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/pify/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/pify/package.json b/node_modules/pify/package.json new file mode 100644 index 0000000..468d857 --- /dev/null +++ b/node_modules/pify/package.json @@ -0,0 +1,51 @@ +{ + "name": "pify", + "version": "3.0.0", + "description": "Promisify a callback-style function", + "license": "MIT", + "repository": "sindresorhus/pify", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava && npm run optimization-test", + "optimization-test": "node --allow-natives-syntax optimization-test.js" + }, + "files": [ + "index.js" + ], + "keywords": [ + "promise", + "promises", + "promisify", + "all", + "denodify", + "denodeify", + "callback", + "cb", + "node", + "then", + "thenify", + "convert", + "transform", + "wrap", + "wrapper", + "bind", + "to", + "async", + "await", + "es2015", + "bluebird" + ], + "devDependencies": { + "ava": "*", + "pinkie-promise": "^2.0.0", + "v8-natives": "^1.0.0", + "xo": "*" + } +} diff --git a/node_modules/pify/readme.md b/node_modules/pify/readme.md new file mode 100644 index 0000000..376ca4e --- /dev/null +++ b/node_modules/pify/readme.md @@ -0,0 +1,131 @@ +# pify [![Build Status](https://travis-ci.org/sindresorhus/pify.svg?branch=master)](https://travis-ci.org/sindresorhus/pify) + +> Promisify a callback-style function + + +## Install + +``` +$ npm install --save pify +``` + + +## Usage + +```js +const fs = require('fs'); +const pify = require('pify'); + +// Promisify a single function +pify(fs.readFile)('package.json', 'utf8').then(data => { + console.log(JSON.parse(data).name); + //=> 'pify' +}); + +// Promisify all methods in a module +pify(fs).readFile('package.json', 'utf8').then(data => { + console.log(JSON.parse(data).name); + //=> 'pify' +}); +``` + + +## API + +### pify(input, [options]) + +Returns a `Promise` wrapped version of the supplied function or module. + +#### input + +Type: `Function` `Object` + +Callback-style function or module whose methods you want to promisify. + +#### options + +##### multiArgs + +Type: `boolean`<br> +Default: `false` + +By default, the promisified function will only return the second argument from the callback, which works fine for most APIs. This option can be useful for modules like `request` that return multiple arguments. Turning this on will make it return an array of all arguments from the callback, excluding the error argument, instead of just the second argument. This also applies to rejections, where it returns an array of all the callback arguments, including the error. + +```js +const request = require('request'); +const pify = require('pify'); + +pify(request, {multiArgs: true})('https://sindresorhus.com').then(result => { + const [httpResponse, body] = result; +}); +``` + +##### include + +Type: `string[]` `RegExp[]` + +Methods in a module to promisify. Remaining methods will be left untouched. + +##### exclude + +Type: `string[]` `RegExp[]`<br> +Default: `[/.+(Sync|Stream)$/]` + +Methods in a module **not** to promisify. Methods with names ending with `'Sync'` are excluded by default. + +##### excludeMain + +Type: `boolean`<br> +Default: `false` + +If given module is a function itself, it will be promisified. Turn this option on if you want to promisify only methods of the module. + +```js +const pify = require('pify'); + +function fn() { + return true; +} + +fn.method = (data, callback) => { + setImmediate(() => { + callback(null, data); + }); +}; + +// Promisify methods but not `fn()` +const promiseFn = pify(fn, {excludeMain: true}); + +if (promiseFn()) { + promiseFn.method('hi').then(data => { + console.log(data); + }); +} +``` + +##### errorFirst + +Type: `boolean`<br> +Default: `true` + +Whether the callback has an error as the first argument. You'll want to set this to `false` if you're dealing with an API that doesn't have an error as the first argument, like `fs.exists()`, some browser APIs, Chrome Extension APIs, etc. + +##### promiseModule + +Type: `Function` + +Custom promise module to use instead of the native one. + +Check out [`pinkie-promise`](https://github.com/floatdrop/pinkie-promise) if you need a tiny promise polyfill. + + +## Related + +- [p-event](https://github.com/sindresorhus/p-event) - Promisify an event by waiting for it to be emitted +- [p-map](https://github.com/sindresorhus/p-map) - Map over promises concurrently +- [More…](https://github.com/sindresorhus/promise-fun) + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/prepend-http/index.js b/node_modules/prepend-http/index.js new file mode 100644 index 0000000..82b3a6b --- /dev/null +++ b/node_modules/prepend-http/index.js @@ -0,0 +1,15 @@ +'use strict'; +module.exports = (url, opts) => { + if (typeof url !== 'string') { + throw new TypeError(`Expected \`url\` to be of type \`string\`, got \`${typeof url}\``); + } + + url = url.trim(); + opts = Object.assign({https: false}, opts); + + if (/^\.*\/|^(?!localhost)\w+:/.test(url)) { + return url; + } + + return url.replace(/^(?!(?:\w+:)?\/\/)/, opts.https ? 'https://' : 'http://'); +}; diff --git a/node_modules/prepend-http/license b/node_modules/prepend-http/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/prepend-http/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/prepend-http/package.json b/node_modules/prepend-http/package.json new file mode 100644 index 0000000..cbfac02 --- /dev/null +++ b/node_modules/prepend-http/package.json @@ -0,0 +1,35 @@ +{ + "name": "prepend-http", + "version": "2.0.0", + "description": "Prepend `http://` to humanized URLs like todomvc.com and localhost", + "license": "MIT", + "repository": "sindresorhus/prepend-http", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "prepend", + "protocol", + "scheme", + "url", + "uri", + "http", + "https", + "humanized" + ], + "devDependencies": { + "ava": "*", + "xo": "*" + } +} diff --git a/node_modules/prepend-http/readme.md b/node_modules/prepend-http/readme.md new file mode 100644 index 0000000..55d640d --- /dev/null +++ b/node_modules/prepend-http/readme.md @@ -0,0 +1,56 @@ +# prepend-http [![Build Status](https://travis-ci.org/sindresorhus/prepend-http.svg?branch=master)](https://travis-ci.org/sindresorhus/prepend-http) + +> Prepend `http://` to humanized URLs like `todomvc.com` and `localhost` + + +## Install + +``` +$ npm install prepend-http +``` + + +## Usage + +```js +const prependHttp = require('prepend-http'); + +prependHttp('todomvc.com'); +//=> 'http://todomvc.com' + +prependHttp('localhost'); +//=> 'http://localhost' + +prependHttp('http://todomvc.com'); +//=> 'http://todomvc.com' + +prependHttp('todomvc.com', {https: true}); +//=> 'https://todomvc.com' +``` + + +## API + +### prependHttp(url, [options]) + +#### url + +Type: `string` + +URL to prepend `http://` on. + +#### options + +Type: `Object` + +##### https + +Type: `boolean`<br> +Default: `false` + +Prepend `https://` instead of `http://`. + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/proxy-check/README.md b/node_modules/proxy-check/README.md new file mode 100644 index 0000000..29bd28a --- /dev/null +++ b/node_modules/proxy-check/README.md @@ -0,0 +1,21 @@ +# Check proxy for NodeJS + +```javascript +const proxy_check = require('proxy-check'); + +const proxy = { + host: '54.82.74.24', + port: 5557, + proxyAuth: 'y0adXjeO:pAzAHCr4' +}; +// or +// const proxy = 'y0adXjeO:pAzAHCr4@54.82.74.24:5557'; + +proxy_check(proxy).then(r => { + console.log(r); // true +}).catch(e => { + console.error(e); // ECONNRESET +}); +``` + +#### Install your simple proxy-server: https://github.com/zamanuhina/install-proxy-one-line diff --git a/node_modules/proxy-check/index.js b/node_modules/proxy-check/index.js new file mode 100644 index 0000000..efb6991 --- /dev/null +++ b/node_modules/proxy-check/index.js @@ -0,0 +1,87 @@ +const http = require('http'); + +const errors = [ + 'Bad proxy string', + 'Proxy offline' +]; + +const proxy_check = p => { + + return new Promise((resolve, reject) => { + + let proxy = { + host: '', + port: 0, + proxyAuth: '' + }; + + if (typeof p === 'object') { + if (Array.isArray(p)) { + if (typeof p[0] === 'object') { + proxy = p[0]; + } else if (typeof p === 'string') { + p = p[0]; + } else { + return reject(errors[0]); + } + } else { + proxy = p; + } + } + + if (typeof p === 'string') { + if (p.indexOf('@') + 1) { + proxy.proxyAuth = p.split('@')[0]; + const host_port = p.split('@')[1]; + if (host_port.indexOf(':') + 1) { + proxy.host = host_port.split(':')[0]; + proxy.port = host_port.split(':')[1]; + } + } else { + if (p.indexOf(':') + 1) { + proxy.host = p.split(':')[0]; + proxy.port = p.split(':')[1]; + } + } + } + + const proxy_options = { + method: 'CONNECT', + path: 'www.google.com:443', + timeout: 1000, + agent: false + }; + + if (proxy.host) { + proxy_options.host = proxy.host; + } + if (proxy.port) { + proxy_options.port = proxy.port; + } + if (proxy.proxyAuth) { + proxy_options.headers = { + 'Proxy-Authorization': 'Basic ' + Buffer.from(proxy.proxyAuth).toString('base64') + }; + } + + const req = http.request(proxy_options); + req.on('connect', res => { + req.destroy(); + if (res.statusCode === 200) { + return resolve(true); + } else { + return reject(errors[1]); + } + }); + req.on('timeout', () => { + req.destroy(); + }); + req.on('error', err => { + return reject((err && err.code) || errors[1]); + }); + req.end(); + + }); +} + +module.exports = proxy_check; diff --git a/node_modules/proxy-check/package.json b/node_modules/proxy-check/package.json new file mode 100644 index 0000000..b38e0cc --- /dev/null +++ b/node_modules/proxy-check/package.json @@ -0,0 +1,22 @@ +{ + "name": "proxy-check", + "version": "1.0.8", + "description": "Check proxy for NodeJS", + "main": "index.js", + "repository": { + "type": "git", + "url": "https://github.com/zamanuhina/proxy-check.git" + }, + "publishConfig": { + "registry": "https://registry.npmjs.org/" + }, + "keywords": [ + "proxy", + "proxy-check" + ], + "license": "MIT", + "bugs": { + "url": "https://github.com/zamanuhina/proxy-check/issues" + }, + "homepage": "https://github.com/zamanuhina/proxy-check#readme" +} diff --git a/node_modules/pump/.travis.yml b/node_modules/pump/.travis.yml new file mode 100644 index 0000000..17f9433 --- /dev/null +++ b/node_modules/pump/.travis.yml @@ -0,0 +1,5 @@ +language: node_js +node_js: + - "0.10" + +script: "npm test" diff --git a/node_modules/pump/LICENSE b/node_modules/pump/LICENSE new file mode 100644 index 0000000..757562e --- /dev/null +++ b/node_modules/pump/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2014 Mathias Buus + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE.
\ No newline at end of file diff --git a/node_modules/pump/README.md b/node_modules/pump/README.md new file mode 100644 index 0000000..4c81471 --- /dev/null +++ b/node_modules/pump/README.md @@ -0,0 +1,65 @@ +# pump + +pump is a small node module that pipes streams together and destroys all of them if one of them closes. + +``` +npm install pump +``` + +[![build status](http://img.shields.io/travis/mafintosh/pump.svg?style=flat)](http://travis-ci.org/mafintosh/pump) + +## What problem does it solve? + +When using standard `source.pipe(dest)` source will _not_ be destroyed if dest emits close or an error. +You are also not able to provide a callback to tell when then pipe has finished. + +pump does these two things for you + +## Usage + +Simply pass the streams you want to pipe together to pump and add an optional callback + +``` js +var pump = require('pump') +var fs = require('fs') + +var source = fs.createReadStream('/dev/random') +var dest = fs.createWriteStream('/dev/null') + +pump(source, dest, function(err) { + console.log('pipe finished', err) +}) + +setTimeout(function() { + dest.destroy() // when dest is closed pump will destroy source +}, 1000) +``` + +You can use pump to pipe more than two streams together as well + +``` js +var transform = someTransformStream() + +pump(source, transform, anotherTransform, dest, function(err) { + console.log('pipe finished', err) +}) +``` + +If `source`, `transform`, `anotherTransform` or `dest` closes all of them will be destroyed. + +Similarly to `stream.pipe()`, `pump()` returns the last stream passed in, so you can do: + +``` +return pump(s1, s2) // returns s2 +``` + +If you want to return a stream that combines *both* s1 and s2 to a single stream use +[pumpify](https://github.com/mafintosh/pumpify) instead. + +## License + +MIT + +## Related + +`pump` is part of the [mississippi stream utility collection](https://github.com/maxogden/mississippi) which includes more useful stream modules similar to this one. diff --git a/node_modules/pump/index.js b/node_modules/pump/index.js new file mode 100644 index 0000000..c15059f --- /dev/null +++ b/node_modules/pump/index.js @@ -0,0 +1,82 @@ +var once = require('once') +var eos = require('end-of-stream') +var fs = require('fs') // we only need fs to get the ReadStream and WriteStream prototypes + +var noop = function () {} +var ancient = /^v?\.0/.test(process.version) + +var isFn = function (fn) { + return typeof fn === 'function' +} + +var isFS = function (stream) { + if (!ancient) return false // newer node version do not need to care about fs is a special way + if (!fs) return false // browser + return (stream instanceof (fs.ReadStream || noop) || stream instanceof (fs.WriteStream || noop)) && isFn(stream.close) +} + +var isRequest = function (stream) { + return stream.setHeader && isFn(stream.abort) +} + +var destroyer = function (stream, reading, writing, callback) { + callback = once(callback) + + var closed = false + stream.on('close', function () { + closed = true + }) + + eos(stream, {readable: reading, writable: writing}, function (err) { + if (err) return callback(err) + closed = true + callback() + }) + + var destroyed = false + return function (err) { + if (closed) return + if (destroyed) return + destroyed = true + + if (isFS(stream)) return stream.close(noop) // use close for fs streams to avoid fd leaks + if (isRequest(stream)) return stream.abort() // request.destroy just do .end - .abort is what we want + + if (isFn(stream.destroy)) return stream.destroy() + + callback(err || new Error('stream was destroyed')) + } +} + +var call = function (fn) { + fn() +} + +var pipe = function (from, to) { + return from.pipe(to) +} + +var pump = function () { + var streams = Array.prototype.slice.call(arguments) + var callback = isFn(streams[streams.length - 1] || noop) && streams.pop() || noop + + if (Array.isArray(streams[0])) streams = streams[0] + if (streams.length < 2) throw new Error('pump requires two streams per minimum') + + var error + var destroys = streams.map(function (stream, i) { + var reading = i < streams.length - 1 + var writing = i > 0 + return destroyer(stream, reading, writing, function (err) { + if (!error) error = err + if (err) destroys.forEach(call) + if (reading) return + destroys.forEach(call) + callback(error) + }) + }) + + return streams.reduce(pipe) +} + +module.exports = pump diff --git a/node_modules/pump/package.json b/node_modules/pump/package.json new file mode 100644 index 0000000..0b838f9 --- /dev/null +++ b/node_modules/pump/package.json @@ -0,0 +1,24 @@ +{ + "name": "pump", + "version": "3.0.0", + "repository": "git://github.com/mafintosh/pump.git", + "license": "MIT", + "description": "pipe streams together and close all of them if one of them closes", + "browser": { + "fs": false + }, + "keywords": [ + "streams", + "pipe", + "destroy", + "callback" + ], + "author": "Mathias Buus Madsen <mathiasbuus@gmail.com>", + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + }, + "scripts": { + "test": "node test-browser.js && node test-node.js" + } +} diff --git a/node_modules/pump/test-browser.js b/node_modules/pump/test-browser.js new file mode 100644 index 0000000..9a06c8a --- /dev/null +++ b/node_modules/pump/test-browser.js @@ -0,0 +1,66 @@ +var stream = require('stream') +var pump = require('./index') + +var rs = new stream.Readable() +var ws = new stream.Writable() + +rs._read = function (size) { + this.push(Buffer(size).fill('abc')) +} + +ws._write = function (chunk, encoding, cb) { + setTimeout(function () { + cb() + }, 100) +} + +var toHex = function () { + var reverse = new (require('stream').Transform)() + + reverse._transform = function (chunk, enc, callback) { + reverse.push(chunk.toString('hex')) + callback() + } + + return reverse +} + +var wsClosed = false +var rsClosed = false +var callbackCalled = false + +var check = function () { + if (wsClosed && rsClosed && callbackCalled) { + console.log('test-browser.js passes') + clearTimeout(timeout) + } +} + +ws.on('finish', function () { + wsClosed = true + check() +}) + +rs.on('end', function () { + rsClosed = true + check() +}) + +var res = pump(rs, toHex(), toHex(), toHex(), ws, function () { + callbackCalled = true + check() +}) + +if (res !== ws) { + throw new Error('should return last stream') +} + +setTimeout(function () { + rs.push(null) + rs.emit('close') +}, 1000) + +var timeout = setTimeout(function () { + check() + throw new Error('timeout') +}, 5000) diff --git a/node_modules/pump/test-node.js b/node_modules/pump/test-node.js new file mode 100644 index 0000000..561251a --- /dev/null +++ b/node_modules/pump/test-node.js @@ -0,0 +1,53 @@ +var pump = require('./index') + +var rs = require('fs').createReadStream('/dev/random') +var ws = require('fs').createWriteStream('/dev/null') + +var toHex = function () { + var reverse = new (require('stream').Transform)() + + reverse._transform = function (chunk, enc, callback) { + reverse.push(chunk.toString('hex')) + callback() + } + + return reverse +} + +var wsClosed = false +var rsClosed = false +var callbackCalled = false + +var check = function () { + if (wsClosed && rsClosed && callbackCalled) { + console.log('test-node.js passes') + clearTimeout(timeout) + } +} + +ws.on('close', function () { + wsClosed = true + check() +}) + +rs.on('close', function () { + rsClosed = true + check() +}) + +var res = pump(rs, toHex(), toHex(), toHex(), ws, function () { + callbackCalled = true + check() +}) + +if (res !== ws) { + throw new Error('should return last stream') +} + +setTimeout(function () { + rs.destroy() +}, 1000) + +var timeout = setTimeout(function () { + throw new Error('timeout') +}, 5000) diff --git a/node_modules/responselike/LICENSE b/node_modules/responselike/LICENSE new file mode 100644 index 0000000..8829a00 --- /dev/null +++ b/node_modules/responselike/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2017 Luke Childs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/responselike/README.md b/node_modules/responselike/README.md new file mode 100644 index 0000000..6361931 --- /dev/null +++ b/node_modules/responselike/README.md @@ -0,0 +1,77 @@ +# responselike + +> A response-like object for mocking a Node.js HTTP response stream + +[![Build Status](https://travis-ci.org/lukechilds/responselike.svg?branch=master)](https://travis-ci.org/lukechilds/responselike) +[![Coverage Status](https://coveralls.io/repos/github/lukechilds/responselike/badge.svg?branch=master)](https://coveralls.io/github/lukechilds/responselike?branch=master) +[![npm](https://img.shields.io/npm/dm/responselike.svg)](https://www.npmjs.com/package/responselike) +[![npm](https://img.shields.io/npm/v/responselike.svg)](https://www.npmjs.com/package/responselike) + +Returns a streamable response object similar to a [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage). Useful for formatting cached responses so they can be consumed by code expecting a real response. + +## Install + +```shell +npm install --save responselike +``` + +Or if you're just using for testing you'll want: + +```shell +npm install --save-dev responselike +``` + +## Usage + +```js +const Response = require('responselike'); + +const response = new Response(200, { foo: 'bar' }, Buffer.from('Hi!'), 'https://example.com'); + +response.statusCode; +// 200 +response.headers; +// { foo: 'bar' } +response.body; +// <Buffer 48 69 21> +response.url; +// 'https://example.com' + +response.pipe(process.stdout); +// Hi! +``` + + +## API + +### new Response(statusCode, headers, body, url) + +Returns a streamable response object similar to a [Node.js HTTP response stream](https://nodejs.org/api/http.html#http_class_http_incomingmessage). + +#### statusCode + +Type: `number` + +HTTP response status code. + +#### headers + +Type: `object` + +HTTP headers object. Keys will be automatically lowercased. + +#### body + +Type: `buffer` + +A Buffer containing the response body. The Buffer contents will be streamable but is also exposed directly as `response.body`. + +#### url + +Type: `string` + +Request URL string. + +## License + +MIT © Luke Childs diff --git a/node_modules/responselike/package.json b/node_modules/responselike/package.json new file mode 100644 index 0000000..520c8a1 --- /dev/null +++ b/node_modules/responselike/package.json @@ -0,0 +1,38 @@ +{ + "name": "responselike", + "version": "1.0.2", + "description": "A response-like object for mocking a Node.js HTTP response stream", + "main": "src/index.js", + "scripts": { + "test": "xo && nyc ava", + "coverage": "nyc report --reporter=text-lcov | coveralls" + }, + "xo": { + "extends": "xo-lukechilds" + }, + "keywords": [ + "http", + "https", + "response", + "mock", + "request", + "responselike" + ], + "repository": { + "type": "git", + "url": "https://github.com/lukechilds/responselike.git" + }, + "author": "lukechilds", + "license": "MIT", + "devDependencies": { + "ava": "^0.22.0", + "coveralls": "^2.13.1", + "eslint-config-xo-lukechilds": "^1.0.0", + "get-stream": "^3.0.0", + "nyc": "^11.1.0", + "xo": "^0.19.0" + }, + "dependencies": { + "lowercase-keys": "^1.0.0" + } +} diff --git a/node_modules/responselike/src/index.js b/node_modules/responselike/src/index.js new file mode 100644 index 0000000..b17b481 --- /dev/null +++ b/node_modules/responselike/src/index.js @@ -0,0 +1,34 @@ +'use strict'; + +const Readable = require('stream').Readable; +const lowercaseKeys = require('lowercase-keys'); + +class Response extends Readable { + constructor(statusCode, headers, body, url) { + if (typeof statusCode !== 'number') { + throw new TypeError('Argument `statusCode` should be a number'); + } + if (typeof headers !== 'object') { + throw new TypeError('Argument `headers` should be an object'); + } + if (!(body instanceof Buffer)) { + throw new TypeError('Argument `body` should be a buffer'); + } + if (typeof url !== 'string') { + throw new TypeError('Argument `url` should be a string'); + } + + super(); + this.statusCode = statusCode; + this.headers = lowercaseKeys(headers); + this.body = body; + this.url = url; + } + + _read() { + this.push(this.body); + this.push(null); + } +} + +module.exports = Response; diff --git a/node_modules/signal-exit/LICENSE.txt b/node_modules/signal-exit/LICENSE.txt new file mode 100644 index 0000000..eead04a --- /dev/null +++ b/node_modules/signal-exit/LICENSE.txt @@ -0,0 +1,16 @@ +The ISC License + +Copyright (c) 2015, Contributors + +Permission to use, copy, modify, and/or distribute this software +for any purpose with or without fee is hereby granted, provided +that the above copyright notice and this permission notice +appear in all copies. + +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. diff --git a/node_modules/signal-exit/README.md b/node_modules/signal-exit/README.md new file mode 100644 index 0000000..f9c7c00 --- /dev/null +++ b/node_modules/signal-exit/README.md @@ -0,0 +1,39 @@ +# signal-exit + +[![Build Status](https://travis-ci.org/tapjs/signal-exit.png)](https://travis-ci.org/tapjs/signal-exit) +[![Coverage](https://coveralls.io/repos/tapjs/signal-exit/badge.svg?branch=master)](https://coveralls.io/r/tapjs/signal-exit?branch=master) +[![NPM version](https://img.shields.io/npm/v/signal-exit.svg)](https://www.npmjs.com/package/signal-exit) +[![Standard Version](https://img.shields.io/badge/release-standard%20version-brightgreen.svg)](https://github.com/conventional-changelog/standard-version) + +When you want to fire an event no matter how a process exits: + +* reaching the end of execution. +* explicitly having `process.exit(code)` called. +* having `process.kill(pid, sig)` called. +* receiving a fatal signal from outside the process + +Use `signal-exit`. + +```js +var onExit = require('signal-exit') + +onExit(function (code, signal) { + console.log('process exited!') +}) +``` + +## API + +`var remove = onExit(function (code, signal) {}, options)` + +The return value of the function is a function that will remove the +handler. + +Note that the function *only* fires for signals if the signal would +cause the process to exit. That is, there are no other listeners, and +it is a fatal signal. + +## Options + +* `alwaysLast`: Run this handler after any other signal or exit + handlers. This causes `process.emit` to be monkeypatched. diff --git a/node_modules/signal-exit/index.js b/node_modules/signal-exit/index.js new file mode 100644 index 0000000..93703f3 --- /dev/null +++ b/node_modules/signal-exit/index.js @@ -0,0 +1,202 @@ +// Note: since nyc uses this module to output coverage, any lines +// that are in the direct sync flow of nyc's outputCoverage are +// ignored, since we can never get coverage for them. +// grab a reference to node's real process object right away +var process = global.process + +const processOk = function (process) { + return process && + typeof process === 'object' && + typeof process.removeListener === 'function' && + typeof process.emit === 'function' && + typeof process.reallyExit === 'function' && + typeof process.listeners === 'function' && + typeof process.kill === 'function' && + typeof process.pid === 'number' && + typeof process.on === 'function' +} + +// some kind of non-node environment, just no-op +/* istanbul ignore if */ +if (!processOk(process)) { + module.exports = function () { + return function () {} + } +} else { + var assert = require('assert') + var signals = require('./signals.js') + var isWin = /^win/i.test(process.platform) + + var EE = require('events') + /* istanbul ignore if */ + if (typeof EE !== 'function') { + EE = EE.EventEmitter + } + + var emitter + if (process.__signal_exit_emitter__) { + emitter = process.__signal_exit_emitter__ + } else { + emitter = process.__signal_exit_emitter__ = new EE() + emitter.count = 0 + emitter.emitted = {} + } + + // Because this emitter is a global, we have to check to see if a + // previous version of this library failed to enable infinite listeners. + // I know what you're about to say. But literally everything about + // signal-exit is a compromise with evil. Get used to it. + if (!emitter.infinite) { + emitter.setMaxListeners(Infinity) + emitter.infinite = true + } + + module.exports = function (cb, opts) { + /* istanbul ignore if */ + if (!processOk(global.process)) { + return function () {} + } + assert.equal(typeof cb, 'function', 'a callback must be provided for exit handler') + + if (loaded === false) { + load() + } + + var ev = 'exit' + if (opts && opts.alwaysLast) { + ev = 'afterexit' + } + + var remove = function () { + emitter.removeListener(ev, cb) + if (emitter.listeners('exit').length === 0 && + emitter.listeners('afterexit').length === 0) { + unload() + } + } + emitter.on(ev, cb) + + return remove + } + + var unload = function unload () { + if (!loaded || !processOk(global.process)) { + return + } + loaded = false + + signals.forEach(function (sig) { + try { + process.removeListener(sig, sigListeners[sig]) + } catch (er) {} + }) + process.emit = originalProcessEmit + process.reallyExit = originalProcessReallyExit + emitter.count -= 1 + } + module.exports.unload = unload + + var emit = function emit (event, code, signal) { + /* istanbul ignore if */ + if (emitter.emitted[event]) { + return + } + emitter.emitted[event] = true + emitter.emit(event, code, signal) + } + + // { <signal>: <listener fn>, ... } + var sigListeners = {} + signals.forEach(function (sig) { + sigListeners[sig] = function listener () { + /* istanbul ignore if */ + if (!processOk(global.process)) { + return + } + // If there are no other listeners, an exit is coming! + // Simplest way: remove us and then re-send the signal. + // We know that this will kill the process, so we can + // safely emit now. + var listeners = process.listeners(sig) + if (listeners.length === emitter.count) { + unload() + emit('exit', null, sig) + /* istanbul ignore next */ + emit('afterexit', null, sig) + /* istanbul ignore next */ + if (isWin && sig === 'SIGHUP') { + // "SIGHUP" throws an `ENOSYS` error on Windows, + // so use a supported signal instead + sig = 'SIGINT' + } + /* istanbul ignore next */ + process.kill(process.pid, sig) + } + } + }) + + module.exports.signals = function () { + return signals + } + + var loaded = false + + var load = function load () { + if (loaded || !processOk(global.process)) { + return + } + loaded = true + + // This is the number of onSignalExit's that are in play. + // It's important so that we can count the correct number of + // listeners on signals, and don't wait for the other one to + // handle it instead of us. + emitter.count += 1 + + signals = signals.filter(function (sig) { + try { + process.on(sig, sigListeners[sig]) + return true + } catch (er) { + return false + } + }) + + process.emit = processEmit + process.reallyExit = processReallyExit + } + module.exports.load = load + + var originalProcessReallyExit = process.reallyExit + var processReallyExit = function processReallyExit (code) { + /* istanbul ignore if */ + if (!processOk(global.process)) { + return + } + process.exitCode = code || /* istanbul ignore next */ 0 + emit('exit', process.exitCode, null) + /* istanbul ignore next */ + emit('afterexit', process.exitCode, null) + /* istanbul ignore next */ + originalProcessReallyExit.call(process, process.exitCode) + } + + var originalProcessEmit = process.emit + var processEmit = function processEmit (ev, arg) { + if (ev === 'exit' && processOk(global.process)) { + /* istanbul ignore else */ + if (arg !== undefined) { + process.exitCode = arg + } + var ret = originalProcessEmit.apply(this, arguments) + /* istanbul ignore next */ + emit('exit', process.exitCode, null) + /* istanbul ignore next */ + emit('afterexit', process.exitCode, null) + /* istanbul ignore next */ + return ret + } else { + return originalProcessEmit.apply(this, arguments) + } + } +} diff --git a/node_modules/signal-exit/package.json b/node_modules/signal-exit/package.json new file mode 100644 index 0000000..e1a0031 --- /dev/null +++ b/node_modules/signal-exit/package.json @@ -0,0 +1,38 @@ +{ + "name": "signal-exit", + "version": "3.0.7", + "description": "when you want to fire an event no matter how a process exits.", + "main": "index.js", + "scripts": { + "test": "tap", + "snap": "tap", + "preversion": "npm test", + "postversion": "npm publish", + "prepublishOnly": "git push origin --follow-tags" + }, + "files": [ + "index.js", + "signals.js" + ], + "repository": { + "type": "git", + "url": "https://github.com/tapjs/signal-exit.git" + }, + "keywords": [ + "signal", + "exit" + ], + "author": "Ben Coe <ben@npmjs.com>", + "license": "ISC", + "bugs": { + "url": "https://github.com/tapjs/signal-exit/issues" + }, + "homepage": "https://github.com/tapjs/signal-exit", + "devDependencies": { + "chai": "^3.5.0", + "coveralls": "^3.1.1", + "nyc": "^15.1.0", + "standard-version": "^9.3.1", + "tap": "^15.1.1" + } +} diff --git a/node_modules/signal-exit/signals.js b/node_modules/signal-exit/signals.js new file mode 100644 index 0000000..3bd67a8 --- /dev/null +++ b/node_modules/signal-exit/signals.js @@ -0,0 +1,53 @@ +// This is not the set of all possible signals. +// +// It IS, however, the set of all signals that trigger +// an exit on either Linux or BSD systems. Linux is a +// superset of the signal names supported on BSD, and +// the unknown signals just fail to register, so we can +// catch that easily enough. +// +// Don't bother with SIGKILL. It's uncatchable, which +// means that we can't fire any callbacks anyway. +// +// If a user does happen to register a handler on a non- +// fatal signal like SIGWINCH or something, and then +// exit, it'll end up firing `process.emit('exit')`, so +// the handler will be fired anyway. +// +// SIGBUS, SIGFPE, SIGSEGV and SIGILL, when not raised +// artificially, inherently leave the process in a +// state from which it is not safe to try and enter JS +// listeners. +module.exports = [ + 'SIGABRT', + 'SIGALRM', + 'SIGHUP', + 'SIGINT', + 'SIGTERM' +] + +if (process.platform !== 'win32') { + module.exports.push( + 'SIGVTALRM', + 'SIGXCPU', + 'SIGXFSZ', + 'SIGUSR2', + 'SIGTRAP', + 'SIGSYS', + 'SIGQUIT', + 'SIGIOT' + // should detect profiler and enable/disable accordingly. + // see #21 + // 'SIGPROF' + ) +} + +if (process.platform === 'linux') { + module.exports.push( + 'SIGIO', + 'SIGPOLL', + 'SIGPWR', + 'SIGSTKFLT', + 'SIGUNUSED' + ) +} diff --git a/node_modules/to-readable-stream/index.js b/node_modules/to-readable-stream/index.js new file mode 100644 index 0000000..554bfa5 --- /dev/null +++ b/node_modules/to-readable-stream/index.js @@ -0,0 +1,11 @@ +'use strict'; +const {Readable} = require('stream'); + +module.exports = input => ( + new Readable({ + read() { + this.push(input); + this.push(null); + } + }) +); diff --git a/node_modules/to-readable-stream/license b/node_modules/to-readable-stream/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/to-readable-stream/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/to-readable-stream/package.json b/node_modules/to-readable-stream/package.json new file mode 100644 index 0000000..c475a92 --- /dev/null +++ b/node_modules/to-readable-stream/package.json @@ -0,0 +1,40 @@ +{ + "name": "to-readable-stream", + "version": "1.0.0", + "description": "Convert a string/Buffer/Uint8Array to a readable stream", + "license": "MIT", + "repository": "sindresorhus/to-readable-stream", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=6" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "stream", + "readablestream", + "string", + "buffer", + "uint8array", + "from", + "into", + "to", + "transform", + "convert", + "readable", + "pull" + ], + "devDependencies": { + "ava": "*", + "get-stream": "^3.0.0", + "xo": "*" + } +} diff --git a/node_modules/to-readable-stream/readme.md b/node_modules/to-readable-stream/readme.md new file mode 100644 index 0000000..fc207c5 --- /dev/null +++ b/node_modules/to-readable-stream/readme.md @@ -0,0 +1,42 @@ +# to-readable-stream [![Build Status](https://travis-ci.org/sindresorhus/to-readable-stream.svg?branch=master)](https://travis-ci.org/sindresorhus/to-readable-stream) + +> Convert a string/Buffer/Uint8Array to a [readable stream](https://nodejs.org/api/stream.html#stream_readable_streams) + + +## Install + +``` +$ npm install to-readable-stream +``` + + +## Usage + +```js +const toReadableStream = require('to-readable-stream'); + +toReadableStream('🦄🌈').pipe(process.stdout); +``` + + +## API + +### toReadableStream(input) + +Returns a [`stream.Readable`](https://nodejs.org/api/stream.html#stream_readable_streams). + +#### input + +Type: `string` `Buffer` `Uint8Array` + +Value to convert to a stream. + + +## Related + +- [into-stream](https://github.com/sindresorhus/into-stream) - More advanced version of this module + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/translatte/LICENSE.txt b/node_modules/translatte/LICENSE.txt new file mode 100755 index 0000000..1f6d321 --- /dev/null +++ b/node_modules/translatte/LICENSE.txt @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2019, ExtensionsApp <extensionsapp@gmail.com> + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE.
\ No newline at end of file diff --git a/node_modules/translatte/README.md b/node_modules/translatte/README.md new file mode 100755 index 0000000..03e4290 --- /dev/null +++ b/node_modules/translatte/README.md @@ -0,0 +1,200 @@ +# A free and unlimited translate for NodeJS. + +<p align="center"><img src="https://raw.githubusercontent.com/extensionsapp/translatte/master/translatte_md.png" alt="TRANSLATTE, npm package translate for NodeJS" title="TRANSLATTE, npm package translate for NodeJS"></p> + +### Installation +``` +npm i translatte +``` + +### Usage + +Translate string to German: + +```javascript +const translatte = require('translatte'); + +translatte('Do you speak Russian?', {to: 'de'}).then(res => { + console.log(res.text); +}).catch(err => { + console.error(err); +}); +// Ihr sprecht auf Russisch? +``` + +Translate string to English using proxy: + +```javascript +const translatte = require('translatte'); + +translatte('Вы говорите по-русски?', { + from: 'ru', + to: 'en', + agents: [ + 'Mozilla/5.0 (Windows NT 10.0; ...', + 'Mozilla/4.0 (Windows NT 10.0; ...', + 'Mozilla/5.0 (Windows NT 10.0; ...' + ], + proxies: [ + 'LOGIN:PASSWORD@192.0.2.100:12345', + 'LOGIN:PASSWORD@192.0.2.200:54321' + ] +}).then(res => { + console.log(res); +}).catch(err => { + console.error(err); +}); +// { text: 'Do you speak Russian?', +// from: { +// language: { +// didYouMean: false, +// iso: 'ru' +// }, +// text: { +// autoCorrected: false, +// value: '', +// didYouMean: false +// } +// }, +// raw: '' } +``` + +## API + +### translatte(text, options) + +#### text + +Type: `string` + +The text to be translated. + +#### options + +Type: `object` + +##### from + +Type: `string` Default: `auto` + +The `text` language. Must be `auto` or one of the codes/names (not case sensitive) contained in [languages.js](https://github.com/extensionsapp/translatte/blob/master/languages.js). + +##### to + +Type: `string` Default: `en` + +The language in which the text should be translated. Must be one of the codes/names (not case sensitive) contained in [languages.js](https://github.com/extensionsapp/translatte/blob/master/languages.js). + +##### raw + +Type: `boolean` Default: `false` + +If `true`, the returned object will have a `raw` property with the raw response (`string`) from Google Translate. + +##### agents + +Type: `array` Default: `[]` + +An `array` of strings specifying the user-agent `['Mozilla/5.0 ...', 'Mozilla/4.0 ...']`. One random result will be selected. + +##### proxies + +Type: `array` Default: `[]` + +An `array` of strings `LOGIN:PASSWORD@IP:PORT` specifying the proxies `['LOGIN:PASSWORD@192.0.2.100:12345', 'LOGIN:PASSWORD@192.0.2.200:54321']`. One random result will be selected. + +##### tld + +Type: `string` Default: `com` + +TLD for Google translate host to be used in API calls: `https://translate.google.[tld]` + +##### client + +Type: `string` Default: `t` + +Query parameter client used in API calls. Can be `t|gtx`. + +#### priority + +Type: `array` Default: `['google_free']` + +Array of priority services. + +#### services + +Type: `object` Default: `{"google_free": true}` + +Objects in order of priority, if one of the services does not perform the translation, it proceeds to the next. + +**Supported services:** +- `{"google_free": true}` + - <a href="https://translate.google.com/" target="_blank">Google Translate</a>, this service works by default. It is completely free and has no limits. +- `{"google_v3": {"project-id": "XXX", "token": "YYY"}}` + - <a href="https://cloud.google.com/translate/docs/quickstart-client-libraries-v3" target="_blank">Google Cloud</a>, requires registration and credit card details. 500,000 characters per month are issued free of charge, then $20 for every million characters. +- `{"microsoft_v3": {"key": "XXX", "location": "global"}}` + - <a href="https://azure.microsoft.com/en-us/pricing/details/cognitive-services/translator-text-api/" target="_blank">Microsoft Azure</a>, requires registration and credit card details. Free of charge 2,000,000 characters per month, then $10 for every million characters. +- `{"yandex_v1": {"key": "XXX"}}` + - <a href="https://translate.yandex.ru/developers/keys" target="_blank">Yandex Translate</a>, requires registration. Free of charge 10,000,000 characters per month. +- `{"yandex_v2": {"key": "XXX"}}` + - <a href="https://cloud.yandex.ru/docs/translate/" target="_blank">Yandex Cloud</a>, requires registration and credit card details. $15 for every million characters. + +### Returns an `object`: + +- `text` *(string)* – The translated text. +- `from` *(object)* + - `language` *(object)* + - `didYouMean` *(boolean)* - `true` if the API suggest a correction in the source language + - `iso` *(string)* - The [code of the language](https://github.com/extensionsapp/translatte/blob/master/languages.js) that the API has recognized in the `text` + - `text` *(object)* + - `autoCorrected` *(boolean)* – `true` if the API has auto corrected the `text` + - `value` *(string)* – The auto corrected `text` or the `text` with suggested corrections + - `didYouMean` *(boolean)* – `true` if the API has suggested corrections to the `text` +- `raw` *(string)* - If `options.raw` is true, the raw response from Google Translate servers. Otherwise, `''`. +- `proxy` *(string)* – The proxy that were used in the request. +- `agent` *(string)* – The agent that were used in the request. +- `service` *(object)* – The service that were used in the request. + +Note that `res.from.text` will only be returned if `from.text.autoCorrected` or `from.text.didYouMean` equals to `true`. In this case, it will have the corrections delimited with brackets (`[ ]`): + +``` js +translate('I spea Dutch').then(res => { + console.log(res.from.text.value); + //=> I [speak] Dutch +}).catch(err => { + console.error(err); +}); +``` +Otherwise, it will be an empty `string` (`''`). + +### Errors an `object`: + +Errors in the name of each `services`. + +```json +{ + "google_free": "Could not get token from google", + "google_v3": "Response code 403 (Forbidden)", + "microsoft_v3": "Response code 403 (Forbidden)", + "yandex_v1": "Response code 403 (Forbidden)", + "yandex_v2": "Response code 403 (Forbidden)" +} +``` + +If the proxy server `LOGIN:PASSWORD@192.0.2.100:12345` is inactive. + +```json +{ + "google_free": "LOGIN:PASSWORD@192.0.2.100:12345" +} +``` + +If the error is not related to `services`. + +```json +{ + "message": "The language «foo» is not supported" +} +``` + +**2020 ExtensionsApp**
\ No newline at end of file diff --git a/node_modules/translatte/index.js b/node_modules/translatte/index.js new file mode 100755 index 0000000..16083db --- /dev/null +++ b/node_modules/translatte/index.js @@ -0,0 +1,406 @@ +const querystring = require('querystring'); +const languages = require('./languages'); +const proxy_check = require('proxy-check'); +const tunnel = require('tunnel'); +const token = require('./token'); +const got = require('got'); + +const translatte = async (text, opts) => { + opts = opts || {}; + opts = JSON.parse(JSON.stringify(opts)); + + let result = { + text: '', + raw: '', + from: { + language: { + didYouMean: false, + iso: '' + }, + text: { + autoCorrected: false, + value: '', + didYouMean: false + } + }, + proxy: '', + agent: '', + service: {google_free: true} + }; + + let errors = [ + 'The language «[lang]» is not supported', + 'Text must not exceed 5000 bytes', + 'The server returned an empty response', + 'Could not get token from google', + 'Text translation request failed' + ]; + + if (opts.from && !languages.isSupported(opts.from)) { + return Promise.reject({message: errors[0].replace('[lang]', opts.from)}); + } + + if (opts.to && !languages.isSupported(opts.to)) { + return Promise.reject({message: errors[0].replace('[lang]', opts.to)}); + } + + let bytes = languages.utf8Length(text); + opts.client = opts.client || 't'; + opts.tld = opts.tld || 'com'; + opts.from = languages.getCode(opts.from || 'auto'); + opts.to = languages.getCode(opts.to || 'en'); + opts.services = opts.services || {google_free: true}; + let services = Object.keys(opts.services); + + opts.priority = opts.priority + ? typeof opts.priority === 'string' + ? [opts.priority] + : opts.priority.filter(p => services.indexOf(p) + 1) + : services; + + if (opts.priority.length > 1) { + let all_index = opts.priority.length - 1; + let err_services = {}; + return opts.priority.reduce((p, priority, index) => { + return p.then(prev => { + return new Promise((resolve, reject) => { + if (prev) return resolve(prev); + translatte(text, {...opts, priority}).then(t => { + if (!t || !t.text) { + err_services[priority] = errors[2]; + return all_index === index + ? reject(err_services) + : resolve(); + } + return resolve(t); + }).catch(e => { + err_services[priority] = typeof e === 'object' && (e[priority] || e.message) + ? e[priority] || e.message + : e; + return all_index === index + ? reject(err_services) + : resolve(); + }); + }); + }); + }, Promise.resolve()); + } + + let priority = opts.priority[0]; + + if (bytes > 5000) { + let chars = Math.ceil(text.length / Math.ceil(bytes / 4700)) + 100; + let plain = ' ' + text + ' '; + let texts = []; + let j = 0; + ['.', ',', ' '].forEach(separator => { + if (!plain) return; + let split = plain.split(separator); + for (let i = 0, l = split.length; i < l; i++) { + if (!texts[j]) texts[j] = []; + if ((texts[j].join(separator) + split[i]).length < chars) { + texts[j].push(split[i]); + plain = split.slice(i+1).join(separator); + } else { + if (!texts[j].length) break; + texts[j].push(''); + texts[++j] = []; + if ((texts[j].join(separator) + split[i]).length < chars) { + texts[j].push(split[i]); + plain = split.slice(i+1).join(separator); + } else { + break; + } + } + } + texts = texts.map(function (t) { + if (!t) return; + if (typeof t === 'object') { + return t.join(separator).trim(); + } else if (typeof t === 'string') { + return t.trim(); + } + }).filter(Boolean); + }); + if (!texts || !texts.length) return Promise.reject({[priority]: errors[1]}); + return texts.reduce((p, item) => { + return p.then(prev => { + return new Promise((resolve, reject) => { + setTimeout(() => { + translatte(item, opts).then(t => { + if (!t || !t.text) return reject(errors[2]); + t.text = prev && prev.text ? prev.text + ' ' + t.text : t.text; + return resolve(t); + }).catch(e => reject(e)); + }, 1000); + }); + }); + }, Promise.resolve()); + } + + if (priority === 'google_v3') { + if (Array.isArray(opts.services['google_v3'])) { + opts.services['google_v3'] = opts + .services['google_v3'][Math.floor(Math.random() * opts + .services['google_v3'].length)]; + } + result.service = {google_v3: opts.services['google_v3']}; + let url = 'https://translation.googleapis.com/v3beta1/projects/' + + opts.services['google_v3']['project-id'] + '/locations/global:translateText'; + try { + const {body} = await got(url, { + method: 'POST', + headers: { + 'Authorization': 'Bearer ' + opts.services['google_v3']['token'], + 'Content-type': 'application/json' + }, + body: { + source_language_code: opts.from, + target_language_code: opts.to, + contents: [text] + }, + json: true, + timeout: 10000, + retry: 0 + }); + for (const translation of body.translations) { + result.text += result.text + ? ' ' + translation.translations.translatedText + : translation.translations.translatedText; + } + } catch (e) { + return Promise.reject({google_v3: e.message || e}); + } + return Promise.resolve(result); + } + + if (priority === 'microsoft_v3') { + if (!opts.services['microsoft_v3']) return Promise.resolve(result); + if (Array.isArray(opts.services['microsoft_v3'])) { + opts.services['microsoft_v3'] = opts + .services['microsoft_v3'][Math.floor(Math.random() * opts + .services['microsoft_v3'].length)]; + } + result.service = {microsoft_v3: opts.services['microsoft_v3']}; + let url = 'https://api.cognitive.microsofttranslator.com/translate?' + + querystring.stringify({ + 'api-version': '3.0', + from: opts.from === 'auto' ? '' : opts.from, + to: opts.to + }); + try { + const {body} = await got(url, { + method: 'POST', + headers: { + 'Ocp-Apim-Subscription-Key': opts.services['microsoft_v3']['key'], + 'Ocp-Apim-Subscription-Region': opts.services['microsoft_v3']['location'] + ? opts.services['microsoft_v3']['location'].replace(/[^a-z]/ig, '').toLowerCase() + : 'global', + 'Content-type': 'application/json' + }, + body: [{text}], + json: true, + timeout: 10000, + retry: 0 + }); + for (const translation of body) { + if (translation.detectedLanguage && translation.detectedLanguage.language) { + result.from.language.iso = translation.detectedLanguage.language; + } + result.text += result.text + ? ' ' + translation.translations[0].text + : translation.translations[0].text; + } + } catch (e) { + return Promise.reject({microsoft_v3: e.message || e}); + } + return Promise.resolve(result); + } + + if (priority === 'yandex_v1') { + if (!opts.services['yandex_v1']) return Promise.resolve(result); + if (Array.isArray(opts.services['yandex_v1'])) { + opts.services['yandex_v1'] = opts + .services['yandex_v1'][Math.floor(Math.random() * opts + .services['yandex_v1'].length)]; + } + result.service = {yandex_v1: opts.services['yandex_v1']}; + let url = 'https://translate.yandex.net/api/v1.5/tr.json/translate?' + + querystring.stringify({ + key: opts.services['yandex_v1']['key'], + lang: opts.from && opts.from !== 'auto' + ? opts.from + '-' + opts.to + : opts.to, + text: text + }); + try { + const {body} = await got(url, {json: true, timeout: 10000, retry: 0}); + for (const translation of body.text) { + result.text += result.text + ? ' ' + translation + : translation; + } + } catch (e) { + return Promise.reject({yandex_v1: e.message || e}); + } + return Promise.resolve(result); + } + + if (priority === 'yandex_v2') { + if (!opts.services['yandex_v2']) return Promise.resolve(result); + if (Array.isArray(opts.services['yandex_v2'])) { + opts.services['yandex_v2'] = opts + .services['yandex_v2'][Math.floor(Math.random() * opts + .services['yandex_v2'].length)]; + } + result.service = {yandex_v2: opts.services['yandex_v2']}; + let url = 'https://translate.api.cloud.yandex.net/translate/v2/translate'; + try { + const {body} = await got(url, { + method: 'POST', + headers: { + 'Authorization': 'Api-Key ' + opts.services['yandex_v2']['key'], + 'Content-type': 'application/json' + }, + body: { + sourceLanguageCode: opts.from, + targetLanguageCode: opts.to, + texts: [text] + }, + json: true, + timeout: 10000, + retry: 0 + }); + for (const translation of body.translations) { + result.text += result.text + ? ' ' + translation.text + : translation.text; + } + } catch (e) { + return Promise.reject({yandex_v2: e.message || e}); + } + return Promise.resolve(result); + } + + let proxy = {}; + let translate = {}; + + opts.agents = opts.agents + ? typeof opts.agents === 'string' + ? opts.agents.split(',').map(p => p.trim()) + : opts.agents + : []; + opts.proxies = opts.proxies + ? typeof opts.proxies === 'string' + ? opts.proxies.split(',').map(p => p.trim()) + : opts.proxies + : []; + + if (opts.agents.length) { + let a = opts.agents[Math.floor(Math.random() * opts.agents.length)]; + result.agent = a; + opts.headers = { + 'User-Agent': a + }; + } + if (opts.proxies.length) { + let p = opts.proxies[Math.floor(Math.random() * opts.proxies.length)]; + result.proxy = p; + if (p.indexOf('@') + 1) { + proxy.proxyAuth = p.split('@')[0]; + proxy.host = (p.split('@')[1]).split(':')[0]; + proxy.port = (p.split('@')[1]).split(':')[1]; + } else { + proxy.host = p.split(':')[0]; + proxy.port = p.split(':')[1]; + } + } + + opts.proxy = proxy.host + ? opts.headers + ? {agent: tunnel.httpsOverHttp({proxy, headers: opts.headers})} + : {agent: tunnel.httpsOverHttp({proxy})} + : {}; + + const translate_string = () => { + return new Promise(async (resolve, reject) => { + let t = await token.get(text, opts); + + if (!t) return reject({google_free: errors[3]}); + + let url = 'https://translate.google.' + opts.tld + '/translate_a/single?' + + querystring.stringify({ + [t.name]: t.value, + client: opts.client, + sl: opts.from, + tl: opts.to, + hl: opts.to, + dt: ['at', 'bd', 'ex', 'ld', 'md', 'qca', 'rw', 'rm', 'ss', 't'], + ie: 'UTF-8', + oe: 'UTF-8', + otf: 1, + ssel: 0, + tsel: 0, + kc: 7, + q: text + }); + + try { + translate = await got(url, {...opts.proxy, json: true, timeout: 10000, headers: opts.headers, retry: 0}); + } catch (e) { + return reject({google_free: errors[4]}); + } + + result.raw = opts.raw + ? JSON.stringify(translate.body) + : ''; + + let body = translate.body; + + body[0].forEach(obj => { + if (obj[0]) { + result.text += obj[0]; + } + }); + + if (body[2] === body[8][0][0]) { + result.from.language.iso = body[2]; + } else { + result.from.language.didYouMean = true; + result.from.language.iso = body[8][0][0]; + } + + if (body[7] && body[7][0]) { + let str = body[7][0]; + + str = str.replace(/<b><i>/g, '['); + str = str.replace(/<\/i><\/b>/g, ']'); + + result.from.text.value = str; + + if (body[7][5] === true) { + result.from.text.autoCorrected = true; + } else { + result.from.text.didYouMean = true; + } + } + + return result.text + ? resolve(result) + : reject({google_free: errors[2]}); + }); + }; + + if (opts && opts.proxy && opts.proxy.agent) { + return proxy_check(result.proxy).then(() => { + return translate_string(); + }).catch(() => { + return Promise.reject({google_free: result.proxy}); + }); + } else { + return translate_string(); + } +}; + +module.exports = translatte; +module.exports.languages = languages;
\ No newline at end of file diff --git a/node_modules/translatte/languages.js b/node_modules/translatte/languages.js new file mode 100755 index 0000000..083714e --- /dev/null +++ b/node_modules/translatte/languages.js @@ -0,0 +1,187 @@ +/** + * + * Generated from https://translate.google.com + * + * The languages that Google Translate supports (as of 5/15/16) alongside with their ISO 639-1 codes + * See https://en.wikipedia.org/wiki/List_of_ISO_639-1_codes + */ + +var langs = { + 'auto': 'Automatic', + 'af': 'Afrikaans', + 'sq': 'Albanian', + 'am': 'Amharic', + 'ar': 'Arabic', + 'hy': 'Armenian', + 'az': 'Azerbaijani', + 'eu': 'Basque', + 'be': 'Belarusian', + 'bn': 'Bengali', + 'bs': 'Bosnian', + 'bg': 'Bulgarian', + 'ca': 'Catalan', + 'ceb': 'Cebuano', + 'ny': 'Chichewa', + 'zh': 'Chinese (Simplified)', + 'zh-cn': 'Chinese (Simplified)', + 'zh-tw': 'Chinese (Traditional)', + 'co': 'Corsican', + 'hr': 'Croatian', + 'cs': 'Czech', + 'da': 'Danish', + 'nl': 'Dutch', + 'en': 'English', + 'eo': 'Esperanto', + 'et': 'Estonian', + 'tl': 'Filipino', + 'fi': 'Finnish', + 'fr': 'French', + 'fy': 'Frisian', + 'gl': 'Galician', + 'ka': 'Georgian', + 'de': 'German', + 'el': 'Greek', + 'gu': 'Gujarati', + 'ht': 'Haitian Creole', + 'ha': 'Hausa', + 'haw': 'Hawaiian', + 'he': 'Hebrew', + 'iw': 'Hebrew', + 'hi': 'Hindi', + 'hmn': 'Hmong', + 'hu': 'Hungarian', + 'is': 'Icelandic', + 'ig': 'Igbo', + 'id': 'Indonesian', + 'ga': 'Irish', + 'it': 'Italian', + 'ja': 'Japanese', + 'jw': 'Javanese', + 'kn': 'Kannada', + 'kk': 'Kazakh', + 'km': 'Khmer', + 'ko': 'Korean', + 'ku': 'Kurdish (Kurmanji)', + 'ky': 'Kyrgyz', + 'lo': 'Lao', + 'la': 'Latin', + 'lv': 'Latvian', + 'lt': 'Lithuanian', + 'lb': 'Luxembourgish', + 'mk': 'Macedonian', + 'mg': 'Malagasy', + 'ms': 'Malay', + 'ml': 'Malayalam', + 'mt': 'Maltese', + 'mi': 'Maori', + 'mr': 'Marathi', + 'mn': 'Mongolian', + 'my': 'Myanmar (Burmese)', + 'ne': 'Nepali', + 'no': 'Norwegian', + 'ps': 'Pashto', + 'fa': 'Persian', + 'pl': 'Polish', + 'pt': 'Portuguese', + 'pa': 'Punjabi', + 'ro': 'Romanian', + 'ru': 'Russian', + 'sm': 'Samoan', + 'gd': 'Scots Gaelic', + 'sr': 'Serbian', + 'st': 'Sesotho', + 'sn': 'Shona', + 'sd': 'Sindhi', + 'si': 'Sinhala', + 'sk': 'Slovak', + 'sl': 'Slovenian', + 'so': 'Somali', + 'es': 'Spanish', + 'su': 'Sundanese', + 'sw': 'Swahili', + 'sv': 'Swedish', + 'tg': 'Tajik', + 'ta': 'Tamil', + 'te': 'Telugu', + 'th': 'Thai', + 'tr': 'Turkish', + 'uk': 'Ukrainian', + 'ur': 'Urdu', + 'uz': 'Uzbek', + 'vi': 'Vietnamese', + 'cy': 'Welsh', + 'xh': 'Xhosa', + 'yi': 'Yiddish', + 'yo': 'Yoruba', + 'zu': 'Zulu' +}; +/** + * Returns the ISO 639-1 code of the desiredLang – if it is supported by Google Translate + * @param {string} desiredLang – the name or the code of the desired language + * @returns {string|boolean} The ISO 639-1 code of the language or false if the language is not supported + */ +function getCode(desiredLang) { + if (!desiredLang) { + return false; + } + desiredLang = desiredLang.toLowerCase(); + + if (langs[desiredLang]) { + return desiredLang; + } + + var keys = Object.keys(langs).filter(function (key) { + if (typeof langs[key] !== 'string') { + return false; + } + + return langs[key].toLowerCase() === desiredLang; + }); + + return keys[0] || false; +} + +/** + * Returns true if the desiredLang is supported by Google Translate and false otherwise + * @param desiredLang – the ISO 639-1 code or the name of the desired language + * @returns {boolean} + */ +function isSupported(desiredLang) { + return Boolean(getCode(desiredLang)); +} + +/** + * Returns utf8 length + * @param str – string + * @returns {number} + */ +function utf8Length(str) { + var utf8 = []; + for (var i = 0; i < str.length; i++) { + var charcode = str.charCodeAt(i); + if (charcode < 0x80) utf8.push(charcode); + else if (charcode < 0x800) { + utf8.push(0xc0 | (charcode >> 6), + 0x80 | (charcode & 0x3f)); + } else if (charcode < 0xd800 || charcode >= 0xe000) { + utf8.push(0xe0 | (charcode >> 12), + 0x80 | ((charcode >> 6) & 0x3f), + 0x80 | (charcode & 0x3f)); + } + else { + i++; + charcode = 0x10000 + (((charcode & 0x3ff) << 10) + | (str.charCodeAt(i) & 0x3ff)); + utf8.push(0xf0 | (charcode >> 18), + 0x80 | ((charcode >> 12) & 0x3f), + 0x80 | ((charcode >> 6) & 0x3f), + 0x80 | (charcode & 0x3f)); + } + } + return utf8.length; +} + +module.exports = langs; +module.exports.isSupported = isSupported; +module.exports.getCode = getCode; +module.exports.utf8Length = utf8Length;
\ No newline at end of file diff --git a/node_modules/translatte/logo.png b/node_modules/translatte/logo.png Binary files differnew file mode 100755 index 0000000..9a13d88 --- /dev/null +++ b/node_modules/translatte/logo.png diff --git a/node_modules/translatte/package.json b/node_modules/translatte/package.json new file mode 100755 index 0000000..96ea209 --- /dev/null +++ b/node_modules/translatte/package.json @@ -0,0 +1,47 @@ +{ + "name": "translatte", + "version": "3.0.1", + "description": "A free and unlimited translate for NodeJS", + "main": "index.js", + "repository": { + "type": "git", + "url": "https://github.com/extensionsapp/translatte.git" + }, + "keywords": [ + "translate", + "translator", + "google", + "google translate", + "api", + "free", + "language", + "proxy", + "translatte", + "microsoft", + "azure", + "microsoft azure", + "microsoft translate", + "azure translate", + "google cloud", + "google cloud translate", + "yandex", + "yandex cloud", + "yandex translate", + "yandex cloud translate" + ], + "author": { + "name": "ExtensionsApp", + "email": "extensionsapp@gmail.com" + }, + "license": "MIT", + "bugs": { + "url": "https://github.com/extensionsapp/translatte/issues" + }, + "homepage": "https://github.com/extensionsapp/translatte#readme", + "dependencies": { + "tunnel": "0.0.6", + "configstore": "4.0.0", + "proxy-check": "1.0.8", + "got": "9.6.0" + } +} diff --git a/node_modules/translatte/token.js b/node_modules/translatte/token.js new file mode 100755 index 0000000..71f360b --- /dev/null +++ b/node_modules/translatte/token.js @@ -0,0 +1,120 @@ +/** + * Last update: 2018/11/24 + * https://translate.google.com/translate/releases/twsfe_w_20160620_RC00/r/js/desktop_module_main.js + * + * Everything between 'BEGIN' and 'END' was copied from the url above. + */ + +var got = require('got'); +var Configstore = require('configstore'); + +/* eslint-disable */ +// BEGIN + +function sM(a) { + var b; + if (null !== yr) + b = yr; + else { + b = wr(String.fromCharCode(84)); + var c = wr(String.fromCharCode(75)); + b = [b(), b()]; + b[1] = c(); + b = (yr = window[b.join(c())] || "") || "" + } + var d = wr(String.fromCharCode(116)) + , c = wr(String.fromCharCode(107)) + , d = [d(), d()]; + d[1] = c(); + c = "&" + d.join("") + "="; + d = b.split("."); + b = Number(d[0]) || 0; + for (var e = [], f = 0, g = 0; g < a.length; g++) { + var l = a.charCodeAt(g); + 128 > l ? e[f++] = l : (2048 > l ? e[f++] = l >> 6 | 192 : (55296 === (l & 64512) && g + 1 < a.length && 56320 === (a.charCodeAt(g + 1) & 64512) ? (l = 65536 + ((l & 1023) << 10) + (a.charCodeAt(++g) & 1023), + e[f++] = l >> 18 | 240, + e[f++] = l >> 12 & 63 | 128) : e[f++] = l >> 12 | 224, + e[f++] = l >> 6 & 63 | 128), + e[f++] = l & 63 | 128) + } + a = b; + for (f = 0; f < e.length; f++) + a += e[f], + a = xr(a, "+-a^+6"); + a = xr(a, "+-3^+b+-f"); + a ^= Number(d[1]) || 0; + 0 > a && (a = (a & 2147483647) + 2147483648); + a %= 1E6; + return c + (a.toString() + "." + (a ^ b)) +} + +var yr = null; +var wr = function (a) { + return function () { + return a + } +} + , xr = function (a, b) { + for (var c = 0; c < b.length - 2; c += 3) { + var d = b.charAt(c + 2) + , d = "a" <= d ? d.charCodeAt(0) - 87 : Number(d) + , d = "+" === b.charAt(c + 1) ? a >>> d : a << d; + a = "+" === b.charAt(c) ? a + d & 4294967295 : a ^ d + } + return a +}; + +// END +/* eslint-enable */ + +var config = new Configstore('google-translate-api'); + +var window = { + TKK: config.get('TKK') || '422854.923862967' +}; + +function updateTKK(opts) { + opts = opts || {tld: 'com', proxy: {}, headers: {}}; + return new Promise(function (resolve, reject) { + var now = Math.floor(Date.now() / 3600000); + + if (Number(window.TKK.split('.')[0]) === now) { + resolve(); + } else { + got('https://translate.google.' + opts.tld, {...opts.proxy, headers: opts.headers, timeout: 2000, retry: 0}).then(function (res) { + var code = res.body.match(/TKK='.*?';/g); + + if (code) { + eval(code[0]); + /* eslint-disable no-undef */ + if (typeof TKK !== 'undefined') { + window.TKK = TKK; + config.set('TKK', TKK); + } + /* eslint-enable no-undef */ + } + + /** + * Note: If the regex or the eval fail, there is no need to worry. The server will accept + * relatively old seeds. + */ + + resolve(); + }).catch(function () { + reject(); + }); + } + }); +} + +function get(text, opts) { + return updateTKK(opts).then(function () { + var tk = sM(text); + tk = tk.replace('&tk=', ''); + return {name: 'tk', value: tk}; + }).catch(function () { + return null; + }); +} + +module.exports.get = get;
\ No newline at end of file diff --git a/node_modules/translatte/translatte_lg.png b/node_modules/translatte/translatte_lg.png Binary files differnew file mode 100755 index 0000000..a544465 --- /dev/null +++ b/node_modules/translatte/translatte_lg.png diff --git a/node_modules/translatte/translatte_md.png b/node_modules/translatte/translatte_md.png Binary files differnew file mode 100755 index 0000000..c166c39 --- /dev/null +++ b/node_modules/translatte/translatte_md.png diff --git a/node_modules/tunnel/.idea/encodings.xml b/node_modules/tunnel/.idea/encodings.xml new file mode 100644 index 0000000..97626ba --- /dev/null +++ b/node_modules/tunnel/.idea/encodings.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="Encoding"> + <file url="PROJECT" charset="UTF-8" /> + </component> +</project>
\ No newline at end of file diff --git a/node_modules/tunnel/.idea/modules.xml b/node_modules/tunnel/.idea/modules.xml new file mode 100644 index 0000000..27bf888 --- /dev/null +++ b/node_modules/tunnel/.idea/modules.xml @@ -0,0 +1,8 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="ProjectModuleManager"> + <modules> + <module fileurl="file://$PROJECT_DIR$/.idea/node-tunnel.iml" filepath="$PROJECT_DIR$/.idea/node-tunnel.iml" /> + </modules> + </component> +</project>
\ No newline at end of file diff --git a/node_modules/tunnel/.idea/node-tunnel.iml b/node_modules/tunnel/.idea/node-tunnel.iml new file mode 100644 index 0000000..24643cc --- /dev/null +++ b/node_modules/tunnel/.idea/node-tunnel.iml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<module type="WEB_MODULE" version="4"> + <component name="NewModuleRootManager"> + <content url="file://$MODULE_DIR$"> + <excludeFolder url="file://$MODULE_DIR$/.tmp" /> + <excludeFolder url="file://$MODULE_DIR$/temp" /> + <excludeFolder url="file://$MODULE_DIR$/tmp" /> + </content> + <orderEntry type="inheritedJdk" /> + <orderEntry type="sourceFolder" forTests="false" /> + </component> +</module>
\ No newline at end of file diff --git a/node_modules/tunnel/.idea/vcs.xml b/node_modules/tunnel/.idea/vcs.xml new file mode 100644 index 0000000..94a25f7 --- /dev/null +++ b/node_modules/tunnel/.idea/vcs.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="VcsDirectoryMappings"> + <mapping directory="$PROJECT_DIR$" vcs="Git" /> + </component> +</project>
\ No newline at end of file diff --git a/node_modules/tunnel/.idea/workspace.xml b/node_modules/tunnel/.idea/workspace.xml new file mode 100644 index 0000000..1a318c8 --- /dev/null +++ b/node_modules/tunnel/.idea/workspace.xml @@ -0,0 +1,797 @@ +<?xml version="1.0" encoding="UTF-8"?> +<project version="4"> + <component name="ChangeListManager"> + <list default="true" id="3caed8aa-31ae-4b3d-ad18-6f9796663516" name="Default" comment=""> + <change type="MODIFICATION" beforePath="$PROJECT_DIR$/.travis.yml" afterPath="$PROJECT_DIR$/.travis.yml" /> + <change type="MODIFICATION" beforePath="$PROJECT_DIR$/CHANGELOG.md" afterPath="$PROJECT_DIR$/CHANGELOG.md" /> + </list> + <ignored path="$PROJECT_DIR$/.tmp/" /> + <ignored path="$PROJECT_DIR$/temp/" /> + <ignored path="$PROJECT_DIR$/tmp/" /> + <option name="EXCLUDED_CONVERTED_TO_IGNORED" value="true" /> + <option name="TRACKING_ENABLED" value="true" /> + <option name="SHOW_DIALOG" value="false" /> + <option name="HIGHLIGHT_CONFLICTS" value="true" /> + <option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" /> + <option name="LAST_RESOLUTION" value="IGNORE" /> + </component> + <component name="FileEditorManager"> + <leaf SIDE_TABS_SIZE_LIMIT_KEY="300"> + <file leaf-file-name="package.json" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/package.json"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="34"> + <caret line="2" column="19" lean-forward="false" selection-start-line="2" selection-start-column="19" selection-end-line="2" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="README.md" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/README.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="2312"> + <caret line="136" column="67" lean-forward="false" selection-start-line="136" selection-start-column="67" selection-end-line="136" selection-end-column="67" /> + <folding> + <marker date="1497272379133" expanded="true" signature="590:646" ph="{...}" /> + <marker date="1497272379133" expanded="true" signature="601:644" ph="{"host": 'localhost'...}" /> + <marker date="1497272379133" expanded="true" signature="674:737" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="884:1330" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="964:1328" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1103:1192" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1290:1324" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="1357:1419" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="1514:2209" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="1540:1623" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1842:2207" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1981:2070" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2168:2202" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="2237:2300" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="2395:3180" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="2475:3178" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="2615:2704" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2802:2836" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="3207:3269" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="3366:4398" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="3392:3475" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="3694:4396" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="3834:3923" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="4021:4055" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="4426:4489" ph="{"host": 'example.com'...}" /> + </folding> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name=".travis.yml" pinned="false" current-in-tab="true"> + <entry file="file://$PROJECT_DIR$/.travis.yml"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="102"> + <caret line="6" column="0" lean-forward="true" selection-start-line="6" selection-start-column="0" selection-end-line="6" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="tunnel.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/lib/tunnel.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="697"> + <caret line="41" column="19" lean-forward="false" selection-start-line="41" selection-start-column="19" selection-end-line="41" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="http-over-http-error.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="935"> + <caret line="55" column="26" lean-forward="true" selection-start-line="55" selection-start-column="26" selection-end-line="55" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="http-over-http-error2.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error2.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1207"> + <caret line="71" column="0" lean-forward="false" selection-start-line="71" selection-start-column="0" selection-end-line="71" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="https-over-http.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/test/https-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1479"> + <caret line="87" column="0" lean-forward="false" selection-start-line="87" selection-start-column="0" selection-end-line="87" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="https-over-https.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/test/https-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="http-over-http.js" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/test/http-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1088"> + <caret line="64" column="26" lean-forward="true" selection-start-line="64" selection-start-column="26" selection-end-line="64" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + </file> + <file leaf-file-name="CHANGELOG.md" pinned="false" current-in-tab="false"> + <entry file="file://$PROJECT_DIR$/CHANGELOG.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="102"> + <caret line="6" column="0" lean-forward="false" selection-start-line="6" selection-start-column="0" selection-end-line="6" selection-end-column="0" /> + <folding /> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + </file> + </leaf> + </component> + <component name="FileTemplateManagerImpl"> + <option name="RECENT_TEMPLATES"> + <list> + <option value="JavaScript File" /> + </list> + </option> + </component> + <component name="FindInProjectRecents"> + <findStrings> + <find>max</find> + <find>onconne</find> + </findStrings> + </component> + <component name="Git.Settings"> + <option name="RECENT_GIT_ROOT_PATH" value="$PROJECT_DIR$" /> + </component> + <component name="IdeDocumentHistory"> + <option name="CHANGED_PATHS"> + <list> + <option value="$PROJECT_DIR$/test/http-over-http-error.js" /> + <option value="$PROJECT_DIR$/README.md" /> + <option value="$PROJECT_DIR$/package.json" /> + <option value="$PROJECT_DIR$/test/http-over-http-error2.js" /> + <option value="$PROJECT_DIR$/test/https-over-http-localaddress.js" /> + <option value="$PROJECT_DIR$/test/https-over-http.js" /> + <option value="$PROJECT_DIR$/lib/tunnel.js" /> + <option value="$PROJECT_DIR$/CHANGELOG.md" /> + <option value="$PROJECT_DIR$/.travis.yml" /> + </list> + </option> + </component> + <component name="JsBuildToolGruntFileManager" detection-done="true" sorting="DEFINITION_ORDER" /> + <component name="JsBuildToolPackageJson" detection-done="true" sorting="DEFINITION_ORDER"> + <package-json value="$PROJECT_DIR$/package.json" /> + </component> + <component name="JsFlowSettings"> + <service-enabled>false</service-enabled> + <exe-path /> + <annotation-enable>false</annotation-enable> + <other-services-enabled>false</other-services-enabled> + <auto-save>true</auto-save> + </component> + <component name="JsGulpfileManager"> + <detection-done>true</detection-done> + <sorting>DEFINITION_ORDER</sorting> + </component> + <component name="NodeModulesDirectoryManager"> + <handled-path value="$PROJECT_DIR$/node_modules" /> + </component> + <component name="ProjectFrameBounds"> + <option name="x" value="785" /> + <option name="y" value="40" /> + <option name="width" value="1788" /> + <option name="height" value="1407" /> + </component> + <component name="ProjectView"> + <navigator currentView="ProjectPane" proportions="" version="1"> + <flattenPackages /> + <showMembers /> + <showModules /> + <showLibraryContents /> + <hideEmptyPackages /> + <abbreviatePackageNames /> + <autoscrollToSource /> + <autoscrollFromSource ProjectPane="true" /> + <sortByType /> + <manualOrder /> + <foldersAlwaysOnTop value="true" /> + </navigator> + <panes> + <pane id="Scope" /> + <pane id="Scratches" /> + <pane id="ProjectPane"> + <subPane> + <expand> + <path> + <item name="node-tunnel" type="b2602c69:ProjectViewProjectNode" /> + <item name="node-tunnel" type="462c0819:PsiDirectoryNode" /> + </path> + <path> + <item name="node-tunnel" type="b2602c69:ProjectViewProjectNode" /> + <item name="node-tunnel" type="462c0819:PsiDirectoryNode" /> + <item name="lib" type="462c0819:PsiDirectoryNode" /> + </path> + <path> + <item name="node-tunnel" type="b2602c69:ProjectViewProjectNode" /> + <item name="node-tunnel" type="462c0819:PsiDirectoryNode" /> + <item name="test" type="462c0819:PsiDirectoryNode" /> + </path> + </expand> + <select /> + </subPane> + </pane> + </panes> + </component> + <component name="PropertiesComponent"> + <property name="WebServerToolWindowFactoryState" value="false" /> + <property name="last_opened_file_path" value="$PROJECT_DIR$" /> + <property name="HbShouldOpenHtmlAsHb" value="" /> + <property name="nodejs_interpreter_path" value="$PROJECT_DIR$/../../nvmw/v6.10.3/node" /> + </component> + <component name="RecentsManager"> + <key name="CopyFile.RECENT_KEYS"> + <recent name="C:\Users\koichik\git\koichik\node-tunnel\test" /> + </key> + </component> + <component name="RunDashboard"> + <option name="ruleStates"> + <list> + <RuleState> + <option name="name" value="ConfigurationTypeDashboardGroupingRule" /> + </RuleState> + <RuleState> + <option name="name" value="StatusDashboardGroupingRule" /> + </RuleState> + </list> + </option> + </component> + <component name="RunManager"> + <configuration default="true" type="js.build_tools.gulp" factoryName="Gulp.js"> + <node-interpreter>project</node-interpreter> + <node-options /> + <gulpfile /> + <tasks /> + <arguments /> + <envs /> + </configuration> + <configuration default="true" type="DartCommandLineRunConfigurationType" factoryName="Dart Command Line Application"> + <method /> + </configuration> + <configuration default="true" type="DartTestRunConfigurationType" factoryName="Dart Test"> + <method /> + </configuration> + <configuration default="true" type="JavaScriptTestRunnerJest" factoryName="Jest"> + <node-interpreter value="project" /> + <working-dir value="" /> + <envs /> + <scope-kind value="ALL" /> + <method /> + </configuration> + <configuration default="true" type="JavaScriptTestRunnerKarma" factoryName="Karma"> + <config-file value="" /> + <node-interpreter value="project" /> + <envs /> + <method /> + </configuration> + <configuration default="true" type="JavaScriptTestRunnerProtractor" factoryName="Protractor"> + <config-file value="" /> + <node-interpreter value="project" /> + <envs /> + <method /> + </configuration> + <configuration default="true" type="JavascriptDebugType" factoryName="JavaScript Debug"> + <method /> + </configuration> + <configuration default="true" type="NodeJSConfigurationType" factoryName="Node.js" path-to-node="project" working-dir=""> + <method /> + </configuration> + <configuration default="true" type="cucumber.js" factoryName="Cucumber.js"> + <option name="cucumberJsArguments" value="" /> + <option name="executablePath" /> + <option name="filePath" /> + <method /> + </configuration> + <configuration default="true" type="js.build_tools.npm" factoryName="npm"> + <command value="run" /> + <scripts /> + <node-interpreter value="project" /> + <envs /> + <method /> + </configuration> + <configuration default="true" type="mocha-javascript-test-runner" factoryName="Mocha"> + <node-interpreter>project</node-interpreter> + <node-options /> + <working-directory /> + <pass-parent-env>true</pass-parent-env> + <envs /> + <ui /> + <extra-mocha-options /> + <test-kind>DIRECTORY</test-kind> + <test-directory /> + <recursive>false</recursive> + <method /> + </configuration> + </component> + <component name="ShelveChangesManager" show_recycled="false"> + <option name="remove_strategy" value="false" /> + </component> + <component name="SvnConfiguration"> + <configuration /> + </component> + <component name="TaskManager"> + <task active="true" id="Default" summary="Default task"> + <changelist id="3caed8aa-31ae-4b3d-ad18-6f9796663516" name="Default" comment="" /> + <created>1497256565348</created> + <option name="number" value="Default" /> + <option name="presentableId" value="Default" /> + <updated>1497256565348</updated> + <workItem from="1497256566573" duration="8794000" /> + <workItem from="1497272051717" duration="2328000" /> + <workItem from="1536577850117" duration="8708000" /> + <workItem from="1536636907096" duration="739000" /> + </task> + <servers /> + </component> + <component name="TimeTrackingManager"> + <option name="totallyTimeSpent" value="20569000" /> + </component> + <component name="ToolWindowManager"> + <frame x="785" y="40" width="1788" height="1407" extended-state="0" /> + <editor active="true" /> + <layout> + <window_info id="Project" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="0" side_tool="false" content_ui="combo" /> + <window_info id="TODO" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="6" side_tool="false" content_ui="tabs" /> + <window_info id="SvgViewer" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" /> + <window_info id="Event Log" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="7" side_tool="true" content_ui="tabs" /> + <window_info id="Run" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="2" side_tool="false" content_ui="tabs" /> + <window_info id="Version Control" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.32967034" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" /> + <window_info id="npm" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="2" side_tool="true" content_ui="tabs" /> + <window_info id="Structure" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" /> + <window_info id="Terminal" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" /> + <window_info id="Debug" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" /> + <window_info id="Favorites" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="2" side_tool="true" content_ui="tabs" /> + <window_info id="Cvs" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="4" side_tool="false" content_ui="tabs" /> + <window_info id="Message" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="0" side_tool="false" content_ui="tabs" /> + <window_info id="Commander" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="0" side_tool="false" content_ui="tabs" /> + <window_info id="Inspection" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="5" side_tool="false" content_ui="tabs" /> + <window_info id="Hierarchy" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="2" side_tool="false" content_ui="combo" /> + <window_info id="Find" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" /> + <window_info id="Ant Build" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" /> + </layout> + </component> + <component name="TypeScriptGeneratedFilesManager"> + <option name="version" value="1" /> + </component> + <component name="VcsContentAnnotationSettings"> + <option name="myLimit" value="2678400000" /> + </component> + <component name="XDebuggerManager"> + <breakpoint-manager /> + <watches-manager /> + </component> + <component name="editorHistoryManager"> + <entry file="file://$PROJECT_DIR$/package.json"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="34"> + <caret line="2" column="19" lean-forward="false" selection-start-line="2" selection-start-column="19" selection-end-line="2" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/README.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="2312"> + <caret line="136" column="67" lean-forward="false" selection-start-line="136" selection-start-column="67" selection-end-line="136" selection-end-column="67" /> + <folding> + <marker date="1497272379133" expanded="true" signature="590:646" ph="{...}" /> + <marker date="1497272379133" expanded="true" signature="601:644" ph="{"host": 'localhost'...}" /> + <marker date="1497272379133" expanded="true" signature="674:737" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="884:1330" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="964:1328" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1103:1192" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1290:1324" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="1357:1419" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="1514:2209" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="1540:1623" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1842:2207" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1981:2070" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2168:2202" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="2237:2300" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="2395:3180" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="2475:3178" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="2615:2704" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2802:2836" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="3207:3269" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="3366:4398" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="3392:3475" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="3694:4396" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="3834:3923" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="4021:4055" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="4426:4489" ph="{"host": 'example.com'...}" /> + </folding> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/.travis.yml"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="102"> + <caret line="6" column="0" lean-forward="true" selection-start-line="6" selection-start-column="0" selection-end-line="6" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="935"> + <caret line="55" column="26" lean-forward="true" selection-start-line="55" selection-start-column="26" selection-end-line="55" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error2.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1207"> + <caret line="71" column="0" lean-forward="false" selection-start-line="71" selection-start-column="0" selection-end-line="71" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1479"> + <caret line="87" column="0" lean-forward="false" selection-start-line="87" selection-start-column="0" selection-end-line="87" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1088"> + <caret line="64" column="26" lean-forward="true" selection-start-line="64" selection-start-column="26" selection-end-line="64" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/lib/tunnel.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="697"> + <caret line="41" column="19" lean-forward="false" selection-start-line="41" selection-start-column="19" selection-end-line="41" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/package.json"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="34"> + <caret line="2" column="19" lean-forward="false" selection-start-line="2" selection-start-column="19" selection-end-line="2" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/README.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="2312"> + <caret line="136" column="67" lean-forward="false" selection-start-line="136" selection-start-column="67" selection-end-line="136" selection-end-column="67" /> + <folding> + <marker date="1497272379133" expanded="true" signature="590:646" ph="{...}" /> + <marker date="1497272379133" expanded="true" signature="601:644" ph="{"host": 'localhost'...}" /> + <marker date="1497272379133" expanded="true" signature="674:737" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="884:1330" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="964:1328" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1103:1192" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1290:1324" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="1357:1419" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="1514:2209" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="1540:1623" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1842:2207" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1981:2070" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2168:2202" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="2237:2300" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="2395:3180" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="2475:3178" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="2615:2704" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2802:2836" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="3207:3269" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="3366:4398" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="3392:3475" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="3694:4396" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="3834:3923" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="4021:4055" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="4426:4489" ph="{"host": 'example.com'...}" /> + </folding> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/lib/tunnel.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="2550"> + <caret line="150" column="0" lean-forward="false" selection-start-line="150" selection-start-column="0" selection-end-line="150" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/CHANGELOG.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="51"> + <caret line="3" column="21" lean-forward="false" selection-start-line="3" selection-start-column="21" selection-end-line="3" selection-end-column="21" /> + <folding /> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/.travis.yml"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="119"> + <caret line="7" column="0" lean-forward="true" selection-start-line="7" selection-start-column="0" selection-end-line="7" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/package.json"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/README.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding> + <marker date="1497272379133" expanded="true" signature="590:646" ph="{...}" /> + <marker date="1497272379133" expanded="true" signature="601:644" ph="{"host": 'localhost'...}" /> + <marker date="1497272379133" expanded="true" signature="674:737" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="884:1330" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="964:1328" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1103:1192" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1290:1324" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="1357:1419" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="1514:2209" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="1540:1623" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1842:2207" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1981:2070" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2168:2202" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="2237:2300" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="2395:3180" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="2475:3178" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="2615:2704" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2802:2836" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="3207:3269" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="3366:4398" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="3392:3475" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="3694:4396" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="3834:3923" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="4021:4055" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="4426:4489" ph="{"host": 'example.com'...}" /> + </folding> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/.travis.yml"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/lib/tunnel.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="2550"> + <caret line="150" column="0" lean-forward="false" selection-start-line="150" selection-start-column="0" selection-end-line="150" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-https-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="136"> + <caret line="8" column="0" lean-forward="false" selection-start-line="7" selection-start-column="0" selection-end-line="8" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1309"> + <caret line="77" column="0" lean-forward="false" selection-start-line="77" selection-start-column="0" selection-end-line="77" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-https-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/README.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="2312"> + <caret line="136" column="67" lean-forward="false" selection-start-line="136" selection-start-column="67" selection-end-line="136" selection-end-column="67" /> + <folding> + <marker date="1497272379133" expanded="true" signature="590:646" ph="{...}" /> + <marker date="1497272379133" expanded="true" signature="601:644" ph="{"host": 'localhost'...}" /> + <marker date="1497272379133" expanded="true" signature="674:737" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="884:1330" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="964:1328" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1103:1192" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1290:1324" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="1357:1419" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="1514:2209" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="1540:1623" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="1842:2207" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="1981:2070" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2168:2202" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="2237:2300" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="2395:3180" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="2475:3178" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="2615:2704" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="2802:2836" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="3207:3269" ph="{"host": 'example.com'...}" /> + <marker date="1497272379133" expanded="true" signature="3366:4398" ph="{"maxSockets": poolSize...}" /> + <marker date="1497272379133" expanded="true" signature="3392:3475" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="3694:4396" ph="{"host": proxyHost...}" /> + <marker date="1497272379133" expanded="true" signature="3834:3923" ph="//..." /> + <marker date="1497272379133" expanded="true" signature="4021:4055" ph="{"User-Agent": 'Node'...}" /> + <marker date="1497272379133" expanded="true" signature="4426:4489" ph="{"host": 'example.com'...}" /> + </folding> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/package.json"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="34"> + <caret line="2" column="19" lean-forward="false" selection-start-line="2" selection-start-column="19" selection-end-line="2" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="935"> + <caret line="55" column="26" lean-forward="true" selection-start-line="55" selection-start-column="26" selection-end-line="55" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http-error2.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1207"> + <caret line="71" column="0" lean-forward="false" selection-start-line="71" selection-start-column="0" selection-end-line="71" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-http-localaddress.js" /> + <entry file="file://$PROJECT_DIR$/test/https-over-https.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="0"> + <caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/http-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1088"> + <caret line="64" column="26" lean-forward="true" selection-start-line="64" selection-start-column="26" selection-end-line="64" selection-end-column="26" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/test/https-over-http.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="1479"> + <caret line="87" column="0" lean-forward="false" selection-start-line="87" selection-start-column="0" selection-end-line="87" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/lib/tunnel.js"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="697"> + <caret line="41" column="19" lean-forward="false" selection-start-line="41" selection-start-column="19" selection-end-line="41" selection-end-column="19" /> + <folding /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/CHANGELOG.md"> + <provider selected="true" editor-type-id="split-provider[text-editor;markdown-preview-editor]"> + <state split_layout="SPLIT"> + <first_editor relative-caret-position="102"> + <caret line="6" column="0" lean-forward="false" selection-start-line="6" selection-start-column="0" selection-end-line="6" selection-end-column="0" /> + <folding /> + </first_editor> + <second_editor /> + </state> + </provider> + </entry> + <entry file="file://$PROJECT_DIR$/.travis.yml"> + <provider selected="true" editor-type-id="text-editor"> + <state relative-caret-position="102"> + <caret line="6" column="0" lean-forward="true" selection-start-line="6" selection-start-column="0" selection-end-line="6" selection-end-column="0" /> + <folding /> + </state> + </provider> + </entry> + </component> +</project>
\ No newline at end of file diff --git a/node_modules/tunnel/.travis.yml b/node_modules/tunnel/.travis.yml new file mode 100644 index 0000000..cb6e182 --- /dev/null +++ b/node_modules/tunnel/.travis.yml @@ -0,0 +1,6 @@ +language: node_js +node_js: + - "4" + - "6" + - "8" + - "10" diff --git a/node_modules/tunnel/CHANGELOG.md b/node_modules/tunnel/CHANGELOG.md new file mode 100644 index 0000000..baf6b18 --- /dev/null +++ b/node_modules/tunnel/CHANGELOG.md @@ -0,0 +1,22 @@ +# Changelog + + - 0.0.6 (2018/09/11) + - Fix `localAddress` not working (#25) + - Fix `Host:` header for CONNECT method by @tmurakam (#29, #30) + - Fix default port for https (#32) + - Fix error handling when the proxy send illegal response body (#33) + + - 0.0.5 (2017/06/12) + - Fix socket leak. + + - 0.0.4 (2016/01/23) + - supported Node v0.12 or later. + + - 0.0.3 (2014/01/20) + - fixed package.json + + - 0.0.1 (2012/02/18) + - supported Node v0.6.x (0.6.11 or later). + + - 0.0.0 (2012/02/11) + - first release. diff --git a/node_modules/tunnel/LICENSE b/node_modules/tunnel/LICENSE new file mode 100644 index 0000000..8b8a895 --- /dev/null +++ b/node_modules/tunnel/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2012 Koichi Kobayashi + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/tunnel/README.md b/node_modules/tunnel/README.md new file mode 100644 index 0000000..f54bca5 --- /dev/null +++ b/node_modules/tunnel/README.md @@ -0,0 +1,185 @@ +# node-tunnel - HTTP/HTTPS Agents for tunneling proxies + +[![Build Status](https://img.shields.io/travis/koichik/node-tunnel.svg?style=flat)](https://travis-ci.org/koichik/node-tunnel) +[![Dependency Status](http://img.shields.io/david/koichik/node-tunnel.svg?style=flat)](https://david-dm.org/koichik/node-tunnel#info=dependencies) +[![DevDependency Status](http://img.shields.io/david/dev/koichik/node-tunnel.svg?style=flat)](https://david-dm.org/koichik/node-tunnel#info=devDependencies) + +## Example + +```javascript +var tunnel = require('tunnel'); + +var tunnelingAgent = tunnel.httpsOverHttp({ + proxy: { + host: 'localhost', + port: 3128 + } +}); + +var req = https.request({ + host: 'example.com', + port: 443, + agent: tunnelingAgent +}); +``` + +## Installation + + $ npm install tunnel + +## Usages + +### HTTP over HTTP tunneling + +```javascript +var tunnelingAgent = tunnel.httpOverHttp({ + maxSockets: poolSize, // Defaults to http.Agent.defaultMaxSockets + + proxy: { // Proxy settings + host: proxyHost, // Defaults to 'localhost' + port: proxyPort, // Defaults to 80 + localAddress: localAddress, // Local interface if necessary + + // Basic authorization for proxy server if necessary + proxyAuth: 'user:password', + + // Header fields for proxy server if necessary + headers: { + 'User-Agent': 'Node' + } + } +}); + +var req = http.request({ + host: 'example.com', + port: 80, + agent: tunnelingAgent +}); +``` + +### HTTPS over HTTP tunneling + +```javascript +var tunnelingAgent = tunnel.httpsOverHttp({ + maxSockets: poolSize, // Defaults to http.Agent.defaultMaxSockets + + // CA for origin server if necessary + ca: [ fs.readFileSync('origin-server-ca.pem')], + + // Client certification for origin server if necessary + key: fs.readFileSync('origin-server-key.pem'), + cert: fs.readFileSync('origin-server-cert.pem'), + + proxy: { // Proxy settings + host: proxyHost, // Defaults to 'localhost' + port: proxyPort, // Defaults to 80 + localAddress: localAddress, // Local interface if necessary + + // Basic authorization for proxy server if necessary + proxyAuth: 'user:password', + + // Header fields for proxy server if necessary + headers: { + 'User-Agent': 'Node' + }, + } +}); + +var req = https.request({ + host: 'example.com', + port: 443, + agent: tunnelingAgent +}); +``` + +### HTTP over HTTPS tunneling + +```javascript +var tunnelingAgent = tunnel.httpOverHttps({ + maxSockets: poolSize, // Defaults to http.Agent.defaultMaxSockets + + proxy: { // Proxy settings + host: proxyHost, // Defaults to 'localhost' + port: proxyPort, // Defaults to 443 + localAddress: localAddress, // Local interface if necessary + + // Basic authorization for proxy server if necessary + proxyAuth: 'user:password', + + // Header fields for proxy server if necessary + headers: { + 'User-Agent': 'Node' + }, + + // CA for proxy server if necessary + ca: [ fs.readFileSync('origin-server-ca.pem')], + + // Server name for verification if necessary + servername: 'example.com', + + // Client certification for proxy server if necessary + key: fs.readFileSync('origin-server-key.pem'), + cert: fs.readFileSync('origin-server-cert.pem'), + } +}); + +var req = http.request({ + host: 'example.com', + port: 80, + agent: tunnelingAgent +}); +``` + +### HTTPS over HTTPS tunneling + +```javascript +var tunnelingAgent = tunnel.httpsOverHttps({ + maxSockets: poolSize, // Defaults to http.Agent.defaultMaxSockets + + // CA for origin server if necessary + ca: [ fs.readFileSync('origin-server-ca.pem')], + + // Client certification for origin server if necessary + key: fs.readFileSync('origin-server-key.pem'), + cert: fs.readFileSync('origin-server-cert.pem'), + + proxy: { // Proxy settings + host: proxyHost, // Defaults to 'localhost' + port: proxyPort, // Defaults to 443 + localAddress: localAddress, // Local interface if necessary + + // Basic authorization for proxy server if necessary + proxyAuth: 'user:password', + + // Header fields for proxy server if necessary + headers: { + 'User-Agent': 'Node' + } + + // CA for proxy server if necessary + ca: [ fs.readFileSync('origin-server-ca.pem')], + + // Server name for verification if necessary + servername: 'example.com', + + // Client certification for proxy server if necessary + key: fs.readFileSync('origin-server-key.pem'), + cert: fs.readFileSync('origin-server-cert.pem'), + } +}); + +var req = https.request({ + host: 'example.com', + port: 443, + agent: tunnelingAgent +}); +``` + +## CONTRIBUTORS +* [Aleksis Brezas (abresas)](https://github.com/abresas) +* [Jackson Tian (JacksonTian)](https://github.com/JacksonTian) +* [Dmitry Sorin (1999)](https://github.com/1999) + +## License + +Licensed under the [MIT](https://github.com/koichik/node-tunnel/blob/master/LICENSE) license. diff --git a/node_modules/tunnel/index.js b/node_modules/tunnel/index.js new file mode 100644 index 0000000..2947757 --- /dev/null +++ b/node_modules/tunnel/index.js @@ -0,0 +1 @@ +module.exports = require('./lib/tunnel'); diff --git a/node_modules/tunnel/lib/tunnel.js b/node_modules/tunnel/lib/tunnel.js new file mode 100644 index 0000000..10cc382 --- /dev/null +++ b/node_modules/tunnel/lib/tunnel.js @@ -0,0 +1,264 @@ +'use strict'; + +var net = require('net'); +var tls = require('tls'); +var http = require('http'); +var https = require('https'); +var events = require('events'); +var assert = require('assert'); +var util = require('util'); + + +exports.httpOverHttp = httpOverHttp; +exports.httpsOverHttp = httpsOverHttp; +exports.httpOverHttps = httpOverHttps; +exports.httpsOverHttps = httpsOverHttps; + + +function httpOverHttp(options) { + var agent = new TunnelingAgent(options); + agent.request = http.request; + return agent; +} + +function httpsOverHttp(options) { + var agent = new TunnelingAgent(options); + agent.request = http.request; + agent.createSocket = createSecureSocket; + agent.defaultPort = 443; + return agent; +} + +function httpOverHttps(options) { + var agent = new TunnelingAgent(options); + agent.request = https.request; + return agent; +} + +function httpsOverHttps(options) { + var agent = new TunnelingAgent(options); + agent.request = https.request; + agent.createSocket = createSecureSocket; + agent.defaultPort = 443; + return agent; +} + + +function TunnelingAgent(options) { + var self = this; + self.options = options || {}; + self.proxyOptions = self.options.proxy || {}; + self.maxSockets = self.options.maxSockets || http.Agent.defaultMaxSockets; + self.requests = []; + self.sockets = []; + + self.on('free', function onFree(socket, host, port, localAddress) { + var options = toOptions(host, port, localAddress); + for (var i = 0, len = self.requests.length; i < len; ++i) { + var pending = self.requests[i]; + if (pending.host === options.host && pending.port === options.port) { + // Detect the request to connect same origin server, + // reuse the connection. + self.requests.splice(i, 1); + pending.request.onSocket(socket); + return; + } + } + socket.destroy(); + self.removeSocket(socket); + }); +} +util.inherits(TunnelingAgent, events.EventEmitter); + +TunnelingAgent.prototype.addRequest = function addRequest(req, host, port, localAddress) { + var self = this; + var options = mergeOptions({request: req}, self.options, toOptions(host, port, localAddress)); + + if (self.sockets.length >= this.maxSockets) { + // We are over limit so we'll add it to the queue. + self.requests.push(options); + return; + } + + // If we are under maxSockets create a new one. + self.createSocket(options, function(socket) { + socket.on('free', onFree); + socket.on('close', onCloseOrRemove); + socket.on('agentRemove', onCloseOrRemove); + req.onSocket(socket); + + function onFree() { + self.emit('free', socket, options); + } + + function onCloseOrRemove(err) { + self.removeSocket(socket); + socket.removeListener('free', onFree); + socket.removeListener('close', onCloseOrRemove); + socket.removeListener('agentRemove', onCloseOrRemove); + } + }); +}; + +TunnelingAgent.prototype.createSocket = function createSocket(options, cb) { + var self = this; + var placeholder = {}; + self.sockets.push(placeholder); + + var connectOptions = mergeOptions({}, self.proxyOptions, { + method: 'CONNECT', + path: options.host + ':' + options.port, + agent: false, + headers: { + host: options.host + ':' + options.port + } + }); + if (options.localAddress) { + connectOptions.localAddress = options.localAddress; + } + if (connectOptions.proxyAuth) { + connectOptions.headers = connectOptions.headers || {}; + connectOptions.headers['Proxy-Authorization'] = 'Basic ' + + new Buffer(connectOptions.proxyAuth).toString('base64'); + } + + debug('making CONNECT request'); + var connectReq = self.request(connectOptions); + connectReq.useChunkedEncodingByDefault = false; // for v0.6 + connectReq.once('response', onResponse); // for v0.6 + connectReq.once('upgrade', onUpgrade); // for v0.6 + connectReq.once('connect', onConnect); // for v0.7 or later + connectReq.once('error', onError); + connectReq.end(); + + function onResponse(res) { + // Very hacky. This is necessary to avoid http-parser leaks. + res.upgrade = true; + } + + function onUpgrade(res, socket, head) { + // Hacky. + process.nextTick(function() { + onConnect(res, socket, head); + }); + } + + function onConnect(res, socket, head) { + connectReq.removeAllListeners(); + socket.removeAllListeners(); + + if (res.statusCode !== 200) { + debug('tunneling socket could not be established, statusCode=%d', + res.statusCode); + socket.destroy(); + var error = new Error('tunneling socket could not be established, ' + + 'statusCode=' + res.statusCode); + error.code = 'ECONNRESET'; + options.request.emit('error', error); + self.removeSocket(placeholder); + return; + } + if (head.length > 0) { + debug('got illegal response body from proxy'); + socket.destroy(); + var error = new Error('got illegal response body from proxy'); + error.code = 'ECONNRESET'; + options.request.emit('error', error); + self.removeSocket(placeholder); + return; + } + debug('tunneling connection has established'); + self.sockets[self.sockets.indexOf(placeholder)] = socket; + return cb(socket); + } + + function onError(cause) { + connectReq.removeAllListeners(); + + debug('tunneling socket could not be established, cause=%s\n', + cause.message, cause.stack); + var error = new Error('tunneling socket could not be established, ' + + 'cause=' + cause.message); + error.code = 'ECONNRESET'; + options.request.emit('error', error); + self.removeSocket(placeholder); + } +}; + +TunnelingAgent.prototype.removeSocket = function removeSocket(socket) { + var pos = this.sockets.indexOf(socket) + if (pos === -1) { + return; + } + this.sockets.splice(pos, 1); + + var pending = this.requests.shift(); + if (pending) { + // If we have pending requests and a socket gets closed a new one + // needs to be created to take over in the pool for the one that closed. + this.createSocket(pending, function(socket) { + pending.request.onSocket(socket); + }); + } +}; + +function createSecureSocket(options, cb) { + var self = this; + TunnelingAgent.prototype.createSocket.call(self, options, function(socket) { + var hostHeader = options.request.getHeader('host'); + var tlsOptions = mergeOptions({}, self.options, { + socket: socket, + servername: hostHeader ? hostHeader.replace(/:.*$/, '') : options.host + }); + + // 0 is dummy port for v0.6 + var secureSocket = tls.connect(0, tlsOptions); + self.sockets[self.sockets.indexOf(socket)] = secureSocket; + cb(secureSocket); + }); +} + + +function toOptions(host, port, localAddress) { + if (typeof host === 'string') { // since v0.10 + return { + host: host, + port: port, + localAddress: localAddress + }; + } + return host; // for v0.11 or later +} + +function mergeOptions(target) { + for (var i = 1, len = arguments.length; i < len; ++i) { + var overrides = arguments[i]; + if (typeof overrides === 'object') { + var keys = Object.keys(overrides); + for (var j = 0, keyLen = keys.length; j < keyLen; ++j) { + var k = keys[j]; + if (overrides[k] !== undefined) { + target[k] = overrides[k]; + } + } + } + } + return target; +} + + +var debug; +if (process.env.NODE_DEBUG && /\btunnel\b/.test(process.env.NODE_DEBUG)) { + debug = function() { + var args = Array.prototype.slice.call(arguments); + if (typeof args[0] === 'string') { + args[0] = 'TUNNEL: ' + args[0]; + } else { + args.unshift('TUNNEL:'); + } + console.error.apply(console, args); + } +} else { + debug = function() {}; +} +exports.debug = debug; // for test diff --git a/node_modules/tunnel/package.json b/node_modules/tunnel/package.json new file mode 100644 index 0000000..bcd7b95 --- /dev/null +++ b/node_modules/tunnel/package.json @@ -0,0 +1,34 @@ +{ + "name": "tunnel", + "version": "0.0.6", + "description": "Node HTTP/HTTPS Agents for tunneling proxies", + "keywords": [ + "http", + "https", + "agent", + "proxy", + "tunnel" + ], + "homepage": "https://github.com/koichik/node-tunnel/", + "bugs": "https://github.com/koichik/node-tunnel/issues", + "license": "MIT", + "author": "Koichi Kobayashi <koichik@improvement.jp>", + "main": "./index.js", + "directories": { + "lib": "./lib" + }, + "repository": { + "type": "git", + "url": "https://github.com/koichik/node-tunnel.git" + }, + "scripts": { + "test": "mocha" + }, + "devDependencies": { + "mocha": "^5.2.0", + "should": "^13.2.3" + }, + "engines": { + "node": ">=0.6.11 <=0.7.0 || >=0.7.3" + } +} diff --git a/node_modules/unique-string/index.js b/node_modules/unique-string/index.js new file mode 100644 index 0000000..5bc7787 --- /dev/null +++ b/node_modules/unique-string/index.js @@ -0,0 +1,4 @@ +'use strict'; +const cryptoRandomString = require('crypto-random-string'); + +module.exports = () => cryptoRandomString(32); diff --git a/node_modules/unique-string/license b/node_modules/unique-string/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/unique-string/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/unique-string/package.json b/node_modules/unique-string/package.json new file mode 100644 index 0000000..b12954a --- /dev/null +++ b/node_modules/unique-string/package.json @@ -0,0 +1,44 @@ +{ + "name": "unique-string", + "version": "1.0.0", + "description": "Generate a unique random string", + "license": "MIT", + "repository": "sindresorhus/unique-string", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "unique", + "string", + "random", + "uniq", + "str", + "rand", + "text", + "id", + "identifier", + "slug", + "hex" + ], + "dependencies": { + "crypto-random-string": "^1.0.0" + }, + "devDependencies": { + "ava": "*", + "xo": "*" + }, + "xo": { + "esnext": true + } +} diff --git a/node_modules/unique-string/readme.md b/node_modules/unique-string/readme.md new file mode 100644 index 0000000..5d5ac97 --- /dev/null +++ b/node_modules/unique-string/readme.md @@ -0,0 +1,32 @@ +# unique-string [![Build Status](https://travis-ci.org/sindresorhus/unique-string.svg?branch=master)](https://travis-ci.org/sindresorhus/unique-string) + +> Generate a unique random string + + +## Install + +``` +$ npm install --save unique-string +``` + + +## Usage + +```js +const uniqueString = require('unique-string'); + +uniqueString(); +//=> 'b4de2a49c8ffa3fbee04446f045483b2' +``` + + +## API + +### uniqueString() + +Returns a 32 character unique string. Matches the length of MD5, which is [unique enough](http://stackoverflow.com/a/2444336/64949) for non-crypto purposes. + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/url-parse-lax/index.js b/node_modules/url-parse-lax/index.js new file mode 100644 index 0000000..5c62a58 --- /dev/null +++ b/node_modules/url-parse-lax/index.js @@ -0,0 +1,12 @@ +'use strict'; +const url = require('url'); +const prependHttp = require('prepend-http'); + +module.exports = (input, options) => { + if (typeof input !== 'string') { + throw new TypeError(`Expected \`url\` to be of type \`string\`, got \`${typeof input}\` instead.`); + } + + const finalUrl = prependHttp(input, Object.assign({https: true}, options)); + return url.parse(finalUrl); +}; diff --git a/node_modules/url-parse-lax/license b/node_modules/url-parse-lax/license new file mode 100644 index 0000000..e7af2f7 --- /dev/null +++ b/node_modules/url-parse-lax/license @@ -0,0 +1,9 @@ +MIT License + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/node_modules/url-parse-lax/package.json b/node_modules/url-parse-lax/package.json new file mode 100644 index 0000000..b3c58f9 --- /dev/null +++ b/node_modules/url-parse-lax/package.json @@ -0,0 +1,42 @@ +{ + "name": "url-parse-lax", + "version": "3.0.0", + "description": "Lax url.parse() with support for protocol-less URLs & IPs", + "license": "MIT", + "repository": "sindresorhus/url-parse-lax", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "url", + "uri", + "parse", + "parser", + "loose", + "lax", + "protocol", + "less", + "protocol-less", + "ip", + "ipv4", + "ipv6" + ], + "dependencies": { + "prepend-http": "^2.0.0" + }, + "devDependencies": { + "ava": "*", + "xo": "*" + } +} diff --git a/node_modules/url-parse-lax/readme.md b/node_modules/url-parse-lax/readme.md new file mode 100644 index 0000000..be0d437 --- /dev/null +++ b/node_modules/url-parse-lax/readme.md @@ -0,0 +1,127 @@ +# url-parse-lax [![Build Status](https://travis-ci.org/sindresorhus/url-parse-lax.svg?branch=master)](https://travis-ci.org/sindresorhus/url-parse-lax) + +> Lax [`url.parse()`](https://nodejs.org/docs/latest/api/url.html#url_url_parse_urlstr_parsequerystring_slashesdenotehost) with support for protocol-less URLs & IPs + + +## Install + +``` +$ npm install url-parse-lax +``` + + +## Usage + +```js +const urlParseLax = require('url-parse-lax'); + +urlParseLax('sindresorhus.com'); +/* +{ + protocol: 'https:', + slashes: true, + auth: null, + host: 'sindresorhus.com', + port: null, + hostname: 'sindresorhus.com', + hash: null, + search: null, + query: null, + pathname: '/', + path: '/', + href: 'https://sindresorhus.com/' +} +*/ + +urlParseLax('[2001:db8::]:8000'); +/* +{ + protocol: null, + slashes: true, + auth: null, + host: '[2001:db8::]:8000', + port: '8000', + hostname: '2001:db8::', + hash: null, + search: null, + query: null, + pathname: '/', + path: '/', + href: 'http://[2001:db8::]:8000/' +} +*/ +``` + +And with the built-in `url.parse()`: + +```js +const url = require('url'); + +url.parse('sindresorhus.com'); +/* +{ + protocol: null, + slashes: null, + auth: null, + host: null, + port: null, + hostname: null, + hash: null, + search: null, + query: null, + pathname: 'sindresorhus', + path: 'sindresorhus', + href: 'sindresorhus' +} +*/ + +url.parse('[2001:db8::]:8000'); +/* +{ + protocol: null, + slashes: null, + auth: null, + host: null, + port: null, + hostname: null, + hash: null, + search: null, + query: null, + pathname: '[2001:db8::]:8000', + path: '[2001:db8::]:8000', + href: '[2001:db8::]:8000' +} +*/ +``` + + +## API + +### urlParseLax(url, [options]) + +#### url + +Type: `string` + +URL to parse. + +#### options + +Type: `Object` + +##### https + +Type: `boolean`<br> +Default: `true` + +Prepend `https://` instead of `http://` to protocol-less URLs. + + +## Related + +- [url-format-lax](https://github.com/sindresorhus/url-format-lax) - Lax `url.format()` that formats a hostname and port into IPv6-compatible socket form of `hostname:port` + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/node_modules/wrappy/LICENSE b/node_modules/wrappy/LICENSE new file mode 100644 index 0000000..19129e3 --- /dev/null +++ b/node_modules/wrappy/LICENSE @@ -0,0 +1,15 @@ +The ISC License + +Copyright (c) Isaac Z. Schlueter and Contributors + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +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. diff --git a/node_modules/wrappy/README.md b/node_modules/wrappy/README.md new file mode 100644 index 0000000..98eab25 --- /dev/null +++ b/node_modules/wrappy/README.md @@ -0,0 +1,36 @@ +# wrappy + +Callback wrapping utility + +## USAGE + +```javascript +var wrappy = require("wrappy") + +// var wrapper = wrappy(wrapperFunction) + +// make sure a cb is called only once +// See also: http://npm.im/once for this specific use case +var once = wrappy(function (cb) { + var called = false + return function () { + if (called) return + called = true + return cb.apply(this, arguments) + } +}) + +function printBoo () { + console.log('boo') +} +// has some rando property +printBoo.iAmBooPrinter = true + +var onlyPrintOnce = once(printBoo) + +onlyPrintOnce() // prints 'boo' +onlyPrintOnce() // does nothing + +// random property is retained! +assert.equal(onlyPrintOnce.iAmBooPrinter, true) +``` diff --git a/node_modules/wrappy/package.json b/node_modules/wrappy/package.json new file mode 100644 index 0000000..1307520 --- /dev/null +++ b/node_modules/wrappy/package.json @@ -0,0 +1,29 @@ +{ + "name": "wrappy", + "version": "1.0.2", + "description": "Callback wrapping utility", + "main": "wrappy.js", + "files": [ + "wrappy.js" + ], + "directories": { + "test": "test" + }, + "dependencies": {}, + "devDependencies": { + "tap": "^2.3.1" + }, + "scripts": { + "test": "tap --coverage test/*.js" + }, + "repository": { + "type": "git", + "url": "https://github.com/npm/wrappy" + }, + "author": "Isaac Z. Schlueter <i@izs.me> (http://blog.izs.me/)", + "license": "ISC", + "bugs": { + "url": "https://github.com/npm/wrappy/issues" + }, + "homepage": "https://github.com/npm/wrappy" +} diff --git a/node_modules/wrappy/wrappy.js b/node_modules/wrappy/wrappy.js new file mode 100644 index 0000000..bb7e7d6 --- /dev/null +++ b/node_modules/wrappy/wrappy.js @@ -0,0 +1,33 @@ +// Returns a wrapper function that returns a wrapped callback +// The wrapper function should do some stuff, and return a +// presumably different callback function. +// This makes sure that own properties are retained, so that +// decorations and such are not lost along the way. +module.exports = wrappy +function wrappy (fn, cb) { + if (fn && cb) return wrappy(fn)(cb) + + if (typeof fn !== 'function') + throw new TypeError('need wrapper function') + + Object.keys(fn).forEach(function (k) { + wrapper[k] = fn[k] + }) + + return wrapper + + function wrapper() { + var args = new Array(arguments.length) + for (var i = 0; i < args.length; i++) { + args[i] = arguments[i] + } + var ret = fn.apply(this, args) + var cb = args[args.length-1] + if (typeof ret === 'function' && ret !== cb) { + Object.keys(cb).forEach(function (k) { + ret[k] = cb[k] + }) + } + return ret + } +} diff --git a/node_modules/write-file-atomic/CHANGELOG.md b/node_modules/write-file-atomic/CHANGELOG.md new file mode 100644 index 0000000..920ae2c --- /dev/null +++ b/node_modules/write-file-atomic/CHANGELOG.md @@ -0,0 +1,25 @@ +# 2.4.3 + +* Ignore errors raised by `fs.closeSync` when cleaning up after a write + error. + +# 2.4.2 + +* A pair of patches to fix some fd leaks. We would leak fds with sync use + when errors occured and with async use any time fsync was not in use. (#34) + +# 2.4.1 + +* Fix a bug where `signal-exit` instances would be leaked. This was fixed when addressing #35. + +# 2.4.0 + +## Features + +* Allow chown and mode options to be set to false to disable the defaulting behavior. (#20) +* Support passing encoding strings in options slot for compat with Node.js API. (#31) +* Add support for running inside of worker threads (#37) + +## Fixes + +* Remove unneeded call when returning success (#36) diff --git a/node_modules/write-file-atomic/LICENSE b/node_modules/write-file-atomic/LICENSE new file mode 100644 index 0000000..95e65a7 --- /dev/null +++ b/node_modules/write-file-atomic/LICENSE @@ -0,0 +1,6 @@ +Copyright (c) 2015, Rebecca Turner + +Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted, provided that the above copyright notice and this permission notice appear in all copies. + +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. + diff --git a/node_modules/write-file-atomic/README.md b/node_modules/write-file-atomic/README.md new file mode 100644 index 0000000..ca28e99 --- /dev/null +++ b/node_modules/write-file-atomic/README.md @@ -0,0 +1,56 @@ +write-file-atomic +----------------- + +This is an extension for node's `fs.writeFile` that makes its operation +atomic and allows you set ownership (uid/gid of the file). + +### var writeFileAtomic = require('write-file-atomic')<br>writeFileAtomic(filename, data, [options], callback) + +* filename **String** +* data **String** | **Buffer** +* options **Object** | **String** + * chown **Object** default, uid & gid of existing file, if any + * uid **Number** + * gid **Number** + * encoding **String** | **Null** default = 'utf8' + * fsync **Boolean** default = true + * mode **Number** default, from existing file, if any + * Promise **Object** default = native Promise object +* callback **Function** + +Atomically and asynchronously writes data to a file, replacing the file if it already +exists. data can be a string or a buffer. + +The file is initially named `filename + "." + murmurhex(__filename, process.pid, ++invocations)`. +Note that `require('worker_threads').threadId` is used in addition to `process.pid` if running inside of a worker thread. +If writeFile completes successfully then, if passed the **chown** option it will change +the ownership of the file. Finally it renames the file back to the filename you specified. If +it encounters errors at any of these steps it will attempt to unlink the temporary file and then +pass the error back to the caller. +If multiple writes are concurrently issued to the same file, the write operations are put into a queue and serialized in the order they were called, using Promises. Native promises are used by default, but you can inject your own promise-like object with the **Promise** option. Writes to different files are still executed in parallel. + +If provided, the **chown** option requires both **uid** and **gid** properties or else +you'll get an error. If **chown** is not specified it will default to using +the owner of the previous file. To prevent chown from being ran you can +also pass `false`, in which case the file will be created with the current user's credentials. + +If **mode** is not specified, it will default to using the permissions from +an existing file, if any. Expicitly setting this to `false` remove this default, resulting +in a file created with the system default permissions. + +If options is a String, it's assumed to be the **encoding** option. The **encoding** option is ignored if **data** is a buffer. It defaults to 'utf8'. + +If the **fsync** option is **false**, writeFile will skip the final fsync call. + +Example: + +```javascript +writeFileAtomic('message.txt', 'Hello Node', {chown:{uid:100,gid:50}}, function (err) { + if (err) throw err; + console.log('It\'s saved!'); +}); +``` + +### var writeFileAtomicSync = require('write-file-atomic').sync<br>writeFileAtomicSync(filename, data, [options]) + +The synchronous version of **writeFileAtomic**. diff --git a/node_modules/write-file-atomic/index.js b/node_modules/write-file-atomic/index.js new file mode 100644 index 0000000..64ae987 --- /dev/null +++ b/node_modules/write-file-atomic/index.js @@ -0,0 +1,238 @@ +'use strict' +module.exports = writeFile +module.exports.sync = writeFileSync +module.exports._getTmpname = getTmpname // for testing +module.exports._cleanupOnExit = cleanupOnExit + +var fs = require('graceful-fs') +var MurmurHash3 = require('imurmurhash') +var onExit = require('signal-exit') +var path = require('path') +var activeFiles = {} + +// if we run inside of a worker_thread, `process.pid` is not unique +/* istanbul ignore next */ +var threadId = (function getId () { + try { + var workerThreads = require('worker_threads') + + /// if we are in main thread, this is set to `0` + return workerThreads.threadId + } catch (e) { + // worker_threads are not available, fallback to 0 + return 0 + } +})() + +var invocations = 0 +function getTmpname (filename) { + return filename + '.' + + MurmurHash3(__filename) + .hash(String(process.pid)) + .hash(String(threadId)) + .hash(String(++invocations)) + .result() +} + +function cleanupOnExit (tmpfile) { + return function () { + try { + fs.unlinkSync(typeof tmpfile === 'function' ? tmpfile() : tmpfile) + } catch (_) {} + } +} + +function writeFile (filename, data, options, callback) { + if (options) { + if (options instanceof Function) { + callback = options + options = {} + } else if (typeof options === 'string') { + options = { encoding: options } + } + } else { + options = {} + } + + var Promise = options.Promise || global.Promise + var truename + var fd + var tmpfile + /* istanbul ignore next -- The closure only gets called when onExit triggers */ + var removeOnExitHandler = onExit(cleanupOnExit(() => tmpfile)) + var absoluteName = path.resolve(filename) + + new Promise(function serializeSameFile (resolve) { + // make a queue if it doesn't already exist + if (!activeFiles[absoluteName]) activeFiles[absoluteName] = [] + + activeFiles[absoluteName].push(resolve) // add this job to the queue + if (activeFiles[absoluteName].length === 1) resolve() // kick off the first one + }).then(function getRealPath () { + return new Promise(function (resolve) { + fs.realpath(filename, function (_, realname) { + truename = realname || filename + tmpfile = getTmpname(truename) + resolve() + }) + }) + }).then(function stat () { + return new Promise(function stat (resolve) { + if (options.mode && options.chown) resolve() + else { + // Either mode or chown is not explicitly set + // Default behavior is to copy it from original file + fs.stat(truename, function (err, stats) { + if (err || !stats) resolve() + else { + options = Object.assign({}, options) + + if (options.mode == null) { + options.mode = stats.mode + } + if (options.chown == null && process.getuid) { + options.chown = { uid: stats.uid, gid: stats.gid } + } + resolve() + } + }) + } + }) + }).then(function thenWriteFile () { + return new Promise(function (resolve, reject) { + fs.open(tmpfile, 'w', options.mode, function (err, _fd) { + fd = _fd + if (err) reject(err) + else resolve() + }) + }) + }).then(function write () { + return new Promise(function (resolve, reject) { + if (Buffer.isBuffer(data)) { + fs.write(fd, data, 0, data.length, 0, function (err) { + if (err) reject(err) + else resolve() + }) + } else if (data != null) { + fs.write(fd, String(data), 0, String(options.encoding || 'utf8'), function (err) { + if (err) reject(err) + else resolve() + }) + } else resolve() + }) + }).then(function syncAndClose () { + return new Promise(function (resolve, reject) { + if (options.fsync !== false) { + fs.fsync(fd, function (err) { + if (err) fs.close(fd, () => reject(err)) + else fs.close(fd, resolve) + }) + } else { + fs.close(fd, resolve) + } + }) + }).then(function chown () { + fd = null + if (options.chown) { + return new Promise(function (resolve, reject) { + fs.chown(tmpfile, options.chown.uid, options.chown.gid, function (err) { + if (err) reject(err) + else resolve() + }) + }) + } + }).then(function chmod () { + if (options.mode) { + return new Promise(function (resolve, reject) { + fs.chmod(tmpfile, options.mode, function (err) { + if (err) reject(err) + else resolve() + }) + }) + } + }).then(function rename () { + return new Promise(function (resolve, reject) { + fs.rename(tmpfile, truename, function (err) { + if (err) reject(err) + else resolve() + }) + }) + }).then(function success () { + removeOnExitHandler() + callback() + }, function fail (err) { + return new Promise(resolve => { + return fd ? fs.close(fd, resolve) : resolve() + }).then(() => { + removeOnExitHandler() + fs.unlink(tmpfile, function () { + callback(err) + }) + }) + }).then(function checkQueue () { + activeFiles[absoluteName].shift() // remove the element added by serializeSameFile + if (activeFiles[absoluteName].length > 0) { + activeFiles[absoluteName][0]() // start next job if one is pending + } else delete activeFiles[absoluteName] + }) +} + +function writeFileSync (filename, data, options) { + if (typeof options === 'string') options = { encoding: options } + else if (!options) options = {} + try { + filename = fs.realpathSync(filename) + } catch (ex) { + // it's ok, it'll happen on a not yet existing file + } + var tmpfile = getTmpname(filename) + + if (!options.mode || !options.chown) { + // Either mode or chown is not explicitly set + // Default behavior is to copy it from original file + try { + var stats = fs.statSync(filename) + options = Object.assign({}, options) + if (!options.mode) { + options.mode = stats.mode + } + if (!options.chown && process.getuid) { + options.chown = { uid: stats.uid, gid: stats.gid } + } + } catch (ex) { + // ignore stat errors + } + } + + var fd + var cleanup = cleanupOnExit(tmpfile) + var removeOnExitHandler = onExit(cleanup) + + try { + fd = fs.openSync(tmpfile, 'w', options.mode) + if (Buffer.isBuffer(data)) { + fs.writeSync(fd, data, 0, data.length, 0) + } else if (data != null) { + fs.writeSync(fd, String(data), 0, String(options.encoding || 'utf8')) + } + if (options.fsync !== false) { + fs.fsyncSync(fd) + } + fs.closeSync(fd) + if (options.chown) fs.chownSync(tmpfile, options.chown.uid, options.chown.gid) + if (options.mode) fs.chmodSync(tmpfile, options.mode) + fs.renameSync(tmpfile, filename) + removeOnExitHandler() + } catch (err) { + if (fd) { + try { + fs.closeSync(fd) + } catch (ex) { + // ignore close errors at this stage, error may have closed fd already. + } + } + removeOnExitHandler() + cleanup() + throw err + } +} diff --git a/node_modules/write-file-atomic/package.json b/node_modules/write-file-atomic/package.json new file mode 100644 index 0000000..bbb0fa2 --- /dev/null +++ b/node_modules/write-file-atomic/package.json @@ -0,0 +1,41 @@ +{ + "name": "write-file-atomic", + "version": "2.4.3", + "description": "Write files in an atomic fashion w/configurable ownership", + "main": "index.js", + "scripts": { + "test": "standard && tap --100 test/*.js", + "preversion": "npm test", + "postversion": "npm publish", + "postpublish": "git push origin --follow-tags" + }, + "repository": { + "type": "git", + "url": "git@github.com:iarna/write-file-atomic.git" + }, + "keywords": [ + "writeFile", + "atomic" + ], + "author": "Rebecca Turner <me@re-becca.org> (http://re-becca.org)", + "license": "ISC", + "bugs": { + "url": "https://github.com/iarna/write-file-atomic/issues" + }, + "homepage": "https://github.com/iarna/write-file-atomic", + "dependencies": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + }, + "devDependencies": { + "mkdirp": "^0.5.1", + "require-inject": "^1.4.0", + "rimraf": "^2.5.4", + "standard": "^12.0.1", + "tap": "^12.1.3" + }, + "files": [ + "index.js" + ] +} diff --git a/node_modules/xdg-basedir/index.js b/node_modules/xdg-basedir/index.js new file mode 100644 index 0000000..f5aa176 --- /dev/null +++ b/node_modules/xdg-basedir/index.js @@ -0,0 +1,28 @@ +'use strict'; +const os = require('os'); +const path = require('path'); + +const home = os.homedir(); +const env = process.env; + +exports.data = env.XDG_DATA_HOME || + (home ? path.join(home, '.local', 'share') : null); + +exports.config = env.XDG_CONFIG_HOME || + (home ? path.join(home, '.config') : null); + +exports.cache = env.XDG_CACHE_HOME || (home ? path.join(home, '.cache') : null); + +exports.runtime = env.XDG_RUNTIME_DIR || null; + +exports.dataDirs = (env.XDG_DATA_DIRS || '/usr/local/share/:/usr/share/').split(':'); + +if (exports.data) { + exports.dataDirs.unshift(exports.data); +} + +exports.configDirs = (env.XDG_CONFIG_DIRS || '/etc/xdg').split(':'); + +if (exports.config) { + exports.configDirs.unshift(exports.config); +} diff --git a/node_modules/xdg-basedir/license b/node_modules/xdg-basedir/license new file mode 100644 index 0000000..654d0bf --- /dev/null +++ b/node_modules/xdg-basedir/license @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (sindresorhus.com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/node_modules/xdg-basedir/package.json b/node_modules/xdg-basedir/package.json new file mode 100644 index 0000000..08bfa8c --- /dev/null +++ b/node_modules/xdg-basedir/package.json @@ -0,0 +1,40 @@ +{ + "name": "xdg-basedir", + "version": "3.0.0", + "description": "Get XDG Base Directory paths", + "license": "MIT", + "repository": "sindresorhus/xdg-basedir", + "author": { + "name": "Sindre Sorhus", + "email": "sindresorhus@gmail.com", + "url": "sindresorhus.com" + }, + "engines": { + "node": ">=4" + }, + "scripts": { + "test": "xo && ava" + }, + "files": [ + "index.js" + ], + "keywords": [ + "xdg", + "base", + "directory", + "dir", + "basedir", + "path", + "data", + "config", + "cache", + "linux", + "unix", + "spec" + ], + "devDependencies": { + "ava": "*", + "require-uncached": "^1.0.2", + "xo": "*" + } +} diff --git a/node_modules/xdg-basedir/readme.md b/node_modules/xdg-basedir/readme.md new file mode 100644 index 0000000..61f8c16 --- /dev/null +++ b/node_modules/xdg-basedir/readme.md @@ -0,0 +1,60 @@ +# xdg-basedir [![Build Status](https://travis-ci.org/sindresorhus/xdg-basedir.svg?branch=master)](https://travis-ci.org/sindresorhus/xdg-basedir) + +> Get [XDG Base Directory](https://specifications.freedesktop.org/basedir-spec/basedir-spec-latest.html) paths + + +## Install + +``` +$ npm install --save xdg-basedir +``` + + +## Usage + +```js +const xdgBasedir = require('xdg-basedir'); + +xdgBasedir.data; +//=> '/home/sindresorhus/.local/share' + +xdgBasedir.config; +//=> '/home/sindresorhus/.config' + +xdgBasedir.dataDirs +//=> ['/home/sindresorhus/.local/share', '/usr/local/share/', '/usr/share/'] +``` + + +## API + +The properties `.data`, `.config`, `.cache`, `.runtime` will return `null` in the uncommon case that both the XDG environment variable is not set and the users home directory can't be found. You need to handle this case. A common solution is to [fall back to a temp directory](https://github.com/yeoman/configstore/blob/b82690fc401318ad18dcd7d151a0003a4898a314/index.js#L15). + +### .data + +Directory for user specific data files. + +### .config + +Directory for user specific configuration files. + +### .cache + +Directory for user specific non-essential data files. + +### .runtime + +Directory for user-specific non-essential runtime files and other file objects (such as sockets, named pipes, etc). + +### .dataDirs + +Preference-ordered array of base directories to search for data files in addition to `.data`. + +### .configDirs + +Preference-ordered array of base directories to search for configuration files in addition to `.config`. + + +## License + +MIT © [Sindre Sorhus](https://sindresorhus.com) diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..1aae732 --- /dev/null +++ b/package-lock.json @@ -0,0 +1,717 @@ +{ + "name": "voicer", + "version": "1.0.0", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "name": "voicer", + "version": "1.0.0", + "license": "MIT", + "dependencies": { + "axios": "^0.26.1", + "translatte": "^3.0.1" + } + }, + "node_modules/@sindresorhus/is": { + "version": "0.14.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", + "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==", + "engines": { + "node": ">=6" + } + }, + "node_modules/@szmarczak/http-timer": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", + "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", + "dependencies": { + "defer-to-connect": "^1.0.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/axios": { + "version": "0.26.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.26.1.tgz", + "integrity": "sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==", + "dependencies": { + "follow-redirects": "^1.14.8" + } + }, + "node_modules/cacheable-request": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", + "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", + "dependencies": { + "clone-response": "^1.0.2", + "get-stream": "^5.1.0", + "http-cache-semantics": "^4.0.0", + "keyv": "^3.0.0", + "lowercase-keys": "^2.0.0", + "normalize-url": "^4.1.0", + "responselike": "^1.0.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/cacheable-request/node_modules/get-stream": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz", + "integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==", + "dependencies": { + "pump": "^3.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cacheable-request/node_modules/lowercase-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", + "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==", + "engines": { + "node": ">=8" + } + }, + "node_modules/clone-response": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", + "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "dependencies": { + "mimic-response": "^1.0.0" + } + }, + "node_modules/configstore": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-4.0.0.tgz", + "integrity": "sha512-CmquAXFBocrzaSM8mtGPMM/HiWmyIpr4CcJl/rgY2uCObZ/S7cKU0silxslqJejl+t/T9HS8E0PUNQD81JGUEQ==", + "dependencies": { + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/crypto-random-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", + "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", + "engines": { + "node": ">=4" + } + }, + "node_modules/decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", + "dependencies": { + "mimic-response": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/defer-to-connect": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", + "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==" + }, + "node_modules/dot-prop": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.1.tgz", + "integrity": "sha512-l0p4+mIuJIua0mhxGoh4a+iNL9bmeK5DvnSVQa6T0OhrVmaEa1XScX5Etc673FePCJOArq/4Pa2cLGODUWTPOQ==", + "dependencies": { + "is-obj": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/follow-redirects": { + "version": "1.14.9", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.9.tgz", + "integrity": "sha512-MQDfihBQYMcyy5dhRDJUHcw7lb2Pv/TuE6xP1vyraLukNDHKbDxDNaOE3NbCAdKQApno+GPRyo1YAp89yCjK4w==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/get-stream": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", + "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", + "dependencies": { + "pump": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/got": { + "version": "9.6.0", + "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", + "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", + "dependencies": { + "@sindresorhus/is": "^0.14.0", + "@szmarczak/http-timer": "^1.1.2", + "cacheable-request": "^6.0.0", + "decompress-response": "^3.3.0", + "duplexer3": "^0.1.4", + "get-stream": "^4.1.0", + "lowercase-keys": "^1.0.1", + "mimic-response": "^1.0.1", + "p-cancelable": "^1.0.0", + "to-readable-stream": "^1.0.0", + "url-parse-lax": "^3.0.0" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.10", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==" + }, + "node_modules/http-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==" + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/is-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", + "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/json-buffer": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", + "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" + }, + "node_modules/keyv": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", + "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", + "dependencies": { + "json-buffer": "3.0.0" + } + }, + "node_modules/lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/make-dir": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "dependencies": { + "pify": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==", + "engines": { + "node": ">=4" + } + }, + "node_modules/normalize-url": { + "version": "4.5.1", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", + "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==", + "engines": { + "node": ">=8" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/p-cancelable": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", + "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", + "engines": { + "node": ">=6" + } + }, + "node_modules/pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "engines": { + "node": ">=4" + } + }, + "node_modules/prepend-http": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", + "engines": { + "node": ">=4" + } + }, + "node_modules/proxy-check": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/proxy-check/-/proxy-check-1.0.8.tgz", + "integrity": "sha512-gooLamKpgl6wi3tJuVpDC7KL3+xSwstUIatyrknMSLaznc+n/cpEiO2HwIAcU30VLExafchmzTpFOgHr8of0wA==" + }, + "node_modules/pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/responselike": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", + "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "dependencies": { + "lowercase-keys": "^1.0.0" + } + }, + "node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==" + }, + "node_modules/to-readable-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", + "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==", + "engines": { + "node": ">=6" + } + }, + "node_modules/translatte": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/translatte/-/translatte-3.0.1.tgz", + "integrity": "sha512-OP41nm4dS1ctRmDDXfgJGK7tAtq2yJe0QCOaRBQjBM+kS4ak4dhWrbL8Mf8p7TFzWJAdV+TLZ1oiYEW3gpWGJg==", + "dependencies": { + "configstore": "4.0.0", + "got": "9.6.0", + "proxy-check": "1.0.8", + "tunnel": "0.0.6" + } + }, + "node_modules/tunnel": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz", + "integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==", + "engines": { + "node": ">=0.6.11 <=0.7.0 || >=0.7.3" + } + }, + "node_modules/unique-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", + "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "dependencies": { + "crypto-random-string": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/url-parse-lax": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", + "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "dependencies": { + "prepend-http": "^2.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" + }, + "node_modules/write-file-atomic": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", + "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", + "dependencies": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + } + }, + "node_modules/xdg-basedir": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", + "integrity": "sha1-SWsswQnsqNus/i3HK2A8F8WHCtQ=", + "engines": { + "node": ">=4" + } + } + }, + "dependencies": { + "@sindresorhus/is": { + "version": "0.14.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", + "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==" + }, + "@szmarczak/http-timer": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", + "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", + "requires": { + "defer-to-connect": "^1.0.1" + } + }, + "axios": { + "version": "0.26.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.26.1.tgz", + "integrity": "sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==", + "requires": { + "follow-redirects": "^1.14.8" + } + }, + "cacheable-request": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", + "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", + "requires": { + "clone-response": "^1.0.2", + "get-stream": "^5.1.0", + "http-cache-semantics": "^4.0.0", + "keyv": "^3.0.0", + "lowercase-keys": "^2.0.0", + "normalize-url": "^4.1.0", + "responselike": "^1.0.2" + }, + "dependencies": { + "get-stream": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz", + "integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==", + "requires": { + "pump": "^3.0.0" + } + }, + "lowercase-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", + "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==" + } + } + }, + "clone-response": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", + "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "requires": { + "mimic-response": "^1.0.0" + } + }, + "configstore": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-4.0.0.tgz", + "integrity": "sha512-CmquAXFBocrzaSM8mtGPMM/HiWmyIpr4CcJl/rgY2uCObZ/S7cKU0silxslqJejl+t/T9HS8E0PUNQD81JGUEQ==", + "requires": { + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" + } + }, + "crypto-random-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", + "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=" + }, + "decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", + "requires": { + "mimic-response": "^1.0.0" + } + }, + "defer-to-connect": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", + "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==" + }, + "dot-prop": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.1.tgz", + "integrity": "sha512-l0p4+mIuJIua0mhxGoh4a+iNL9bmeK5DvnSVQa6T0OhrVmaEa1XScX5Etc673FePCJOArq/4Pa2cLGODUWTPOQ==", + "requires": { + "is-obj": "^1.0.0" + } + }, + "duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" + }, + "end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "requires": { + "once": "^1.4.0" + } + }, + "follow-redirects": { + "version": "1.14.9", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.9.tgz", + "integrity": "sha512-MQDfihBQYMcyy5dhRDJUHcw7lb2Pv/TuE6xP1vyraLukNDHKbDxDNaOE3NbCAdKQApno+GPRyo1YAp89yCjK4w==" + }, + "get-stream": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", + "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", + "requires": { + "pump": "^3.0.0" + } + }, + "got": { + "version": "9.6.0", + "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", + "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", + "requires": { + "@sindresorhus/is": "^0.14.0", + "@szmarczak/http-timer": "^1.1.2", + "cacheable-request": "^6.0.0", + "decompress-response": "^3.3.0", + "duplexer3": "^0.1.4", + "get-stream": "^4.1.0", + "lowercase-keys": "^1.0.1", + "mimic-response": "^1.0.1", + "p-cancelable": "^1.0.0", + "to-readable-stream": "^1.0.0", + "url-parse-lax": "^3.0.0" + } + }, + "graceful-fs": { + "version": "4.2.10", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==" + }, + "http-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==" + }, + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=" + }, + "is-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", + "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=" + }, + "json-buffer": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", + "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" + }, + "keyv": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", + "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", + "requires": { + "json-buffer": "3.0.0" + } + }, + "lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==" + }, + "make-dir": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "requires": { + "pify": "^3.0.0" + } + }, + "mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" + }, + "normalize-url": { + "version": "4.5.1", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", + "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==" + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "requires": { + "wrappy": "1" + } + }, + "p-cancelable": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", + "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==" + }, + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" + }, + "prepend-http": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" + }, + "proxy-check": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/proxy-check/-/proxy-check-1.0.8.tgz", + "integrity": "sha512-gooLamKpgl6wi3tJuVpDC7KL3+xSwstUIatyrknMSLaznc+n/cpEiO2HwIAcU30VLExafchmzTpFOgHr8of0wA==" + }, + "pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "responselike": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", + "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "requires": { + "lowercase-keys": "^1.0.0" + } + }, + "signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==" + }, + "to-readable-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", + "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==" + }, + "translatte": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/translatte/-/translatte-3.0.1.tgz", + "integrity": "sha512-OP41nm4dS1ctRmDDXfgJGK7tAtq2yJe0QCOaRBQjBM+kS4ak4dhWrbL8Mf8p7TFzWJAdV+TLZ1oiYEW3gpWGJg==", + "requires": { + "configstore": "4.0.0", + "got": "9.6.0", + "proxy-check": "1.0.8", + "tunnel": "0.0.6" + } + }, + "tunnel": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz", + "integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==" + }, + "unique-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", + "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "requires": { + "crypto-random-string": "^1.0.0" + } + }, + "url-parse-lax": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", + "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "requires": { + "prepend-http": "^2.0.0" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" + }, + "write-file-atomic": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", + "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", + "requires": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + } + }, + "xdg-basedir": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", + "integrity": "sha1-SWsswQnsqNus/i3HK2A8F8WHCtQ=" + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..494f3c9 --- /dev/null +++ b/package.json @@ -0,0 +1,15 @@ +{ + "name": "voicer", + "version": "1.0.0", + "description": "", + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "author": "Minteck", + "license": "MIT", + "dependencies": { + "axios": "^0.26.1", + "translatte": "^3.0.1" + } +} diff --git a/prefixes.json b/prefixes.json new file mode 100644 index 0000000..d17acf3 --- /dev/null +++ b/prefixes.json @@ -0,0 +1,50 @@ +[ + "dix machin", + "dis machin", + "dis hum machin", + "guy marchand", + "guy machin", + "dis hum hum", + "petit machin", + "hum hum", + "dit machin", + "guy marchand", + "dis marchand", + "dit hum hum", + "dis ma chambre", + "dit hum", + "dis ma chance", + "dix hum", + "dix ma chance", + "dis hum", + "dit ma chance", + "dit hum", + "dis ma chance", + "dim hum", + "dim ma chance", + "dimanche", + "bon dix machin", + "bon dis machin", + "bon dis hum machin", + "bon guy marchand", + "bon guy machin", + "bon dis hum hum", + "bon petit machin", + "bon hum hum", + "bon dit machin", + "bon guy marchand", + "bon dis marchand", + "bon dit hum hum", + "bon dis ma chambre", + "bon dit hum", + "bon dis ma chance", + "bon dix hum", + "bon dix ma chance", + "bon dis hum", + "bon dit ma chance", + "bon dit hum", + "bon dis ma chance", + "bon dim hum", + "bon dim ma chance", + "bon dimanche" +]
\ No newline at end of file diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..9c9b692 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,17 @@ +certifi==2021.10.8 +cffi==1.15.0 +chardet==3.0.4 +h11==0.9.0 +h2==3.2.0 +hpack==3.0.0 +hstspreload==2021.12.1 +httpcore==0.9.1 +httpx==0.13.3 +hyperframe==5.2.0 +idna==2.10 +PyAudio==0.2.11 +pycparser==2.21 +rfc3986==1.5.0 +sniffio==1.2.0 +sounddevice==0.4.4 +vosk==0.3.32 diff --git a/sounds/.DS_Store b/sounds/.DS_Store Binary files differnew file mode 100644 index 0000000..5008ddf --- /dev/null +++ b/sounds/.DS_Store diff --git a/sounds/ignored.wav b/sounds/ignored.wav Binary files differnew file mode 100644 index 0000000..aba111b --- /dev/null +++ b/sounds/ignored.wav diff --git a/sounds/load.wav b/sounds/load.wav Binary files differnew file mode 100644 index 0000000..efb3cc1 --- /dev/null +++ b/sounds/load.wav diff --git a/sounds/ready.wav b/sounds/ready.wav Binary files differnew file mode 100644 index 0000000..b30e63e --- /dev/null +++ b/sounds/ready.wav diff --git a/sounds/start.wav b/sounds/start.wav Binary files differnew file mode 100644 index 0000000..06417ec --- /dev/null +++ b/sounds/start.wav diff --git a/sounds/stop.wav b/sounds/stop.wav Binary files differnew file mode 100644 index 0000000..d26cd63 --- /dev/null +++ b/sounds/stop.wav diff --git a/weatherconditions.json b/weatherconditions.json new file mode 100644 index 0000000..069c663 --- /dev/null +++ b/weatherconditions.json @@ -0,0 +1 @@ +[{"code":1000,"day":"Sunny","night":"Clear","icon":113,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"مشمس","night_text":"صافي"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"সূর্যোজ্জ্বল","night_text":"পরিষ্কার"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слънчево","night_text":"Ясно"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"晴天","night_text":"晴朗"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"晴天","night_text":"晴朗"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slunečno","night_text":"Jasno"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Zonnig","night_text":"Helder"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Aurinkoinen","night_text":"Pilvetön"},{"lang_name":"French","lang_iso":"fr","day_text":"Ensoleillé","night_text":"Clair"},{"lang_name":"German","lang_iso":"de","day_text":"Sonnig","night_text":"Klar"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ηλιόλουστη/ο","night_text":"Αίθριος"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"धूप वाला","night_text":"साफ"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Napos idő","night_text":"Felhőtlen"},{"lang_name":"Italian","lang_iso":"it","day_text":"Soleggiato","night_text":"Sereno"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"晴れ","night_text":"快晴"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Srengenge Sumunar","night_text":"Resik"},{"lang_name":"Korean","lang_iso":"ko","day_text":"맑음","night_text":"화창함"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"晴天","night_text":"晴朗"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"लख्ख","night_text":"स्वच्छ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Słonecznie","night_text":"Bezchmurnie"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Sol","night_text":"Céu limpo"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਧੁੱਪਦਾਰ","night_text":"ਸਾਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Soare","night_text":"Senin"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Солнечно","night_text":"Ясно"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Sunčano","night_text":"Vedro"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"හිරු එළිය සහිත","night_text":"පැහැදිලි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slnečno","night_text":"Jasno"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Soleado","night_text":"Despejado"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Soligt","night_text":"Klart"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"வெயில்","night_text":"தெளிவு"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఎండకాయడం","night_text":"స్పష్టంగా ఉండటం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Güneşli","night_text":"Açık"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Сонячно","night_text":"Ясно"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"دھوپ والا","night_text":"شفاف"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Nhiều nắng","night_text":"Trời quang"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"贴金","night_text":"贴起好"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有阳光","night_text":"晴朗"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"晴天","night_text":"晴朗"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kuyashisa","night_text":"Licwathile"}]},{"code":1003,"day":"Partly Cloudy","night":"Partly Cloudy","icon":116,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"غائم جزئياً","night_text":"غائم جزئياً"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"অংশত মেঘলা","night_text":"অংশত মেঘলা"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Частична облачност","night_text":"Частична облачност"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"局部多云","night_text":"局部多云"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"局部多雲","night_text":"局部多雲"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Částečně oblačno","night_text":"Částečně oblačno"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Gedeeltelijk bewolkt","night_text":"Gedeeltelijk bewolkt"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Puolipilvinen","night_text":"Puolipilvinen"},{"lang_name":"French","lang_iso":"fr","day_text":"Partiellement nuageux","night_text":"Partiellement nuageux"},{"lang_name":"German","lang_iso":"de","day_text":"leicht bewölkt","night_text":"leicht bewölkt"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους συννεφιά","night_text":"Κατά τόπους συννεφιά"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्के बादल","night_text":"हल्के बादल"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Részben felhős","night_text":"Részben felhős"},{"lang_name":"Italian","lang_iso":"it","day_text":"Parzialmente nuvoloso","night_text":"Parzialmente nuvoloso"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により曇り","night_text":"所により曇り"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Mendhung sebagian","night_text":"Mendhung sebagian"},{"lang_name":"Korean","lang_iso":"ko","day_text":"대체로 맑음","night_text":"대체로 맑음"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"局部多云","night_text":"局部多云"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अंशत: ढगाळ","night_text":"अंशत: ढगाळ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Częściowe zachmurzenie","night_text":"Częściowe zachmurzenie"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Parcialmente nublado","night_text":"Parcialmente nublado"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਥੋੜ੍ਹਾਂ ਬੱਦਲਵਾਈ","night_text":"ਥੋੜ੍ਹਾਂ ਬੱਦਲਵਾਈ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Parțial noros","night_text":"Parțial noros"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Переменная облачность","night_text":"Переменная облачность"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Delimično oblačno","night_text":"Delimično oblačno"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"අඩ වශයෙන් වළාකුළු සහිත","night_text":"අඩ වශයෙන් වළාකුළු සහිත"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Čiastočne oblačno","night_text":"Čiastočne oblačno"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Parcialmente nublado","night_text":"Parcialmente nublado"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Växlande molnighet","night_text":"Växlande molnighet"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"கொஞ்சம் மேகமூட்டம்","night_text":"கொஞ்சம் மேகமூட்டம்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"పాక్షికంగా మేఘావృతం","night_text":"పాక్షికంగా మేఘావృతం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Parçalı Bulutlu","night_text":"Parçalı Bulutlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невелика хмарність","night_text":"Невелика хмарність"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"تھوڑے بادلوں والا","night_text":"تھوڑے بادلوں والا"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Có Mây","night_text":"Có Mây"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部兜云","night_text":"撅部兜云"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"局部多云","night_text":"局部多云"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"局部多雲","night_text":"局部多雲"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Lithe gqwa gqwa ngamafu","night_text":"Lithe gqwa gqwa ngamafu"}]},{"code":1006,"day":"Cloudy","night":"Cloudy","icon":119,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"غائم","night_text":"غائم"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মেঘলা","night_text":"মেঘলা"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Облачно","night_text":"Облачно"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"多云","night_text":"多云"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"多雲","night_text":"多雲"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Oblačno","night_text":"Oblačno"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Bewolkt","night_text":"Bewolkt"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Pilvinen","night_text":"Pilvinen"},{"lang_name":"French","lang_iso":"fr","day_text":"Nuageux","night_text":"Nuageux"},{"lang_name":"German","lang_iso":"de","day_text":"bewölkt","night_text":"bewölkt"},{"lang_name":"Greek","lang_iso":"el","day_text":"Συννεφιά","night_text":"Συννεφιά"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बादलों से भरा","night_text":"बादलों से भरा"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Felhős","night_text":"Felhős"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nuvoloso","night_text":"Nuvoloso"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"曇り","night_text":"曇り"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Mendhung","night_text":"Mendhung"},{"lang_name":"Korean","lang_iso":"ko","day_text":"구름 낀","night_text":"구름 낀"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"多云","night_text":"多云"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"ढगाळ","night_text":"ढगाळ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Zachmurzenie","night_text":"Zachmurzenie"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Nublado","night_text":"Nublado"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬੱਦਲਵਾਈ","night_text":"ਬੱਦਲਵਾਈ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Noros","night_text":"Noros"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Облачно","night_text":"Облачно"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Oblačno","night_text":"Oblačno"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"වළාකුළු සහිත","night_text":"වළාකුළු සහිත"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Oblačno","night_text":"Oblačno"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nublado","night_text":"Nublado"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Molnigt","night_text":"Molnigt"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மேகமூட்டம்","night_text":"மேகமூட்டம்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మేఘావృతం","night_text":"మేఘావృతం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bulutlu","night_text":"Bulutlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Хмарно","night_text":"Хмарно"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"بادلوں والا","night_text":"بادلوں والا"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Nhiều mây","night_text":"Nhiều mây"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"兜云","night_text":"兜云"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"多云","night_text":"多云"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"多雲","night_text":"多雲"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Linamafu","night_text":"Linamafu"}]},{"code":1009,"day":"Overcast","night":"Overcast","icon":122,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ملبَد بالغيوم","night_text":"ملبَد بالغيوم"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মেঘাচ্ছন্ন","night_text":"মেঘাচ্ছন্ন"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Плътна облачност","night_text":"Плътна облачност"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"阴天","night_text":"阴天"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"陰天","night_text":"陰天"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Zataženo","night_text":"Zataženo"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Geheel bewolkt","night_text":"Geheel bewolkt"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Täysin pilvinen","night_text":"Täysin pilvinen"},{"lang_name":"French","lang_iso":"fr","day_text":"Couvert","night_text":"Couvert"},{"lang_name":"German","lang_iso":"de","day_text":"bedeckt","night_text":"bedeckt"},{"lang_name":"Greek","lang_iso":"el","day_text":"Νεφελώδης","night_text":"Νεφελώδης"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बादलों से घिरा","night_text":"बादलों से घिरा"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Borús","night_text":"Borús"},{"lang_name":"Italian","lang_iso":"it","day_text":"Coperto","night_text":"Coperto"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"本曇り","night_text":"本曇り"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Mendhung peteng","night_text":"Mendhung peteng"},{"lang_name":"Korean","lang_iso":"ko","day_text":"흐린","night_text":"흐린"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"阴天","night_text":"阴天"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मेघाच्छादित","night_text":"मेघाच्छादित"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Pochmurno","night_text":"Pochmurno"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Encoberto","night_text":"Encoberto"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਘਿਰਿਆ ਹੋਇਆ","night_text":"ਘਿਰਿਆ ਹੋਇਆ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Cer acoperit","night_text":"Cer acoperit"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Пасмурно","night_text":"Пасмурно"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Naoblačenje","night_text":"Naoblačenje"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"වළාකුලින් අඳුරු වූ","night_text":"වළාකුලින් අඳුරු වූ"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Zamračené","night_text":"Zamračené"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Cielo cubierto","night_text":"Cielo cubierto"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Mulet","night_text":"Mulet"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மேகம்சூழ்ந்தது","night_text":"மேகம்சூழ்ந்தது"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మబ్బుకమ్ము","night_text":"మబ్బుకమ్ము"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Çok bulutlu","night_text":"Çok bulutlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Суцільна хмарність","night_text":"Суцільна хмарність"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"بدلی چھا جانا","night_text":"بدلی چھا جانا"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"U ám","night_text":"U ám"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"兜云","night_text":"兜云"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"阴天","night_text":"阴天"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"陰天","night_text":"陰天"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Liguqubele","night_text":"Liguqubele"}]},{"code":1030,"day":"Mist","night":"Mist","icon":143,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"سديم","night_text":"سديم"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা কুয়াশা","night_text":"হাল্কা কুয়াশা"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Лека мъгла","night_text":"Лека мъгла"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"薄雾","night_text":"薄雾"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"薄霧","night_text":"薄霧"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Opar","night_text":"Opar"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Mist","night_text":"Mist"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Sumuinen","night_text":"Sumuinen"},{"lang_name":"French","lang_iso":"fr","day_text":"Brume","night_text":"Brume"},{"lang_name":"German","lang_iso":"de","day_text":"leichter Nebel","night_text":"leichter Nebel"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ομίχλη","night_text":"Ομίχλη"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"कोहरा","night_text":"कोहरा"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Gyenge köd","night_text":"Gyenge köd"},{"lang_name":"Italian","lang_iso":"it","day_text":"Foschia","night_text":"Foschia"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"もや","night_text":"もや"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Pedhut","night_text":"Pedhut"},{"lang_name":"Korean","lang_iso":"ko","day_text":"안개","night_text":"안개"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"薄雾","night_text":"薄雾"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"धुके","night_text":"धुके"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Zamglenie","night_text":"Zamglenie"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Neblina","night_text":"Neblina"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕੋਹਰਾ","night_text":"ਕੋਹਰਾ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ceață","night_text":"Ceață"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Дымка","night_text":"Дымка"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Sumaglica","night_text":"Sumaglica"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මීදුම","night_text":"මීදුම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Opar","night_text":"Opar"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Neblina","night_text":"Neblina"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Fuktdis","night_text":"Fuktdis"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பனிமூட்டம்","night_text":"பனிமூட்டம்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"పొగమంచు","night_text":"పొగమంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Sisli","night_text":"Sisli"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Туман","night_text":"Туман"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"کہر","night_text":"کہر"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Sương mù","night_text":"Sương mù"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠波吴","night_text":"悠波吴"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有薄雾","night_text":"有薄雾"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"薄霧","night_text":"薄霧"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kunenkungu","night_text":"Kunenkungu"}]},{"code":1063,"day":"Patchy rain nearby","night":"Patchy rain nearby","icon":176,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار متفاوتة قريبة","night_text":"أمطار متفاوتة قريبة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত বৃষ্টিপাত","night_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Дъждове на отделни места в околността","night_text":"Дъждове на отделни места в околността"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"周边有零星小雨","night_text":"周边有零星小雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"週边有零星小雨","night_text":"週边有零星小雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy blízký déšť","night_text":"Místy blízký déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke regen in de omgeving","night_text":"Plaatselijke regen in de omgeving"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanaista sadetta lähellä","night_text":"Hajanaista sadetta lähellä"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie éparse à proximité","night_text":"Pluie éparse à proximité"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise Regenfall","night_text":"stellenweise Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους βροχή σε κοντινή απόσταση","night_text":"Κατά τόπους βροχή σε κοντινή απόσταση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"आसपास अलग-अलग इलाकों में वारिश","night_text":"आसपास अलग-अलग इलाकों में वारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A közelben eső","night_text":"A közelben eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia a tratti nelle vicinanze","night_text":"Pioggia a tratti nelle vicinanze"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"近くで所により雨","night_text":"近くで所により雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan ora rata ing sacedhake","night_text":"Udan ora rata ing sacedhake"},{"lang_name":"Korean","lang_iso":"ko","day_text":"근처 곳곳에 비","night_text":"근처 곳곳에 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"周边有零星小雨","night_text":"周边有零星小雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"आजूबाजूला अनियमित पाऊस","night_text":"आजूबाजूला अनियमित पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe opady deszczu w pobliżu","night_text":"Miejscowe opady deszczu w pobliżu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Possibilidade de chuva irregular","night_text":"Possibilidade de chuva irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਮੀਂਹ","night_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi pe porţiuni în apropiere","night_text":"Ploi pe porţiuni în apropiere"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами дождь","night_text":"Местами дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimična kiša","night_text":"Mestimična kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ආසන්නයේ තැනින් තැන වැසි","night_text":"ආසන්නයේ තැනින් තැන වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami blízky dážď","night_text":"Miestami blízky dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvia moderada a intervalos","night_text":"Lluvia moderada a intervalos"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med regn i närheten","night_text":"Områden med regn i närheten"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"அருகில் சீரில்லாத மழை","night_text":"அருகில் சீரில்லாத மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా దగ్గరల్లో వర్షం","night_text":"చెదురుమదురుగా దగ్గరల్లో వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz yağmur yağışlı","night_text":"Bölgesel düzensiz yağmur yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями дощ","night_text":"Місцями дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"قریب میں جہاں تہاں بارش","night_text":"قریب میں جہاں تہاں بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa lả tả gần đó","night_text":"Mưa lả tả gần đó"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"无尽撅部落鱼","night_text":"无尽撅部落鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"附近有零星雨","night_text":"附近有零星雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"週边有零星小雨","night_text":"週边有零星小雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kunezihlamvana zemvula lapha nalapha eduze","night_text":"Kunezihlamvana zemvula lapha nalapha eduze"}]},{"code":1066,"day":"Patchy snow nearby","night":"Patchy snow nearby","icon":179,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج متفاوتة قريبة","night_text":"ثلوج متفاوتة قريبة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত তুষারপাত","night_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Снеговалежи на отделни места в околността","night_text":"Снеговалежи на отделни места в околността"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"周边有零星小雪","night_text":"周边有零星小雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"週边有零星小雪","night_text":"週边有零星小雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy blízké sněžení","night_text":"Místy blízké sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke sneeuw in de omgeving","night_text":"Plaatselijke sneeuw in de omgeving"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanaista lumisadetta lähellä","night_text":"Hajanaista lumisadetta lähellä"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige éparse à proximité","night_text":"Neige éparse à proximité"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise Schneefall","night_text":"stellenweise Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους χιονόπτωση σε κοντινή απόσταση","night_text":"Κατά τόπους χιονόπτωση σε κοντινή απόσταση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"आसपास अलग-अलग इलाकों में हिमपात","night_text":"आसपास अलग-अलग इलाकों में हिमपात"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A közelben foltokban havazás","night_text":"A közelben foltokban havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve a tratti nelle vicinanze","night_text":"Neve a tratti nelle vicinanze"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"近くで所により雪","night_text":"近くで所により雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju ora rata ing sacedhake","night_text":"Udan salju ora rata ing sacedhake"},{"lang_name":"Korean","lang_iso":"ko","day_text":"근처 곳곳에 눈","night_text":"근처 곳곳에 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"周边有零星小雪","night_text":"周边有零星小雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"आजूबाजूला अनियमित बर्फ","night_text":"आजूबाजूला अनियमित बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe opady śniegu w pobliżu","night_text":"Miejscowe opady śniegu w pobliżu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Possibilidade de neve irregular","night_text":"Possibilidade de neve irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ","night_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori pe porţiuni în apropiere","night_text":"Ninsori pe porţiuni în apropiere"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами снег","night_text":"Местами снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimične snežne padavine","night_text":"Mestimične snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ආසන්නයේ තැනින් තැන හිම","night_text":"ආසන්නයේ තැනින් තැන හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami blízke sneženie","night_text":"Miestami blízke sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nieve moderada a intervalos en las aproximaciones","night_text":"Nieve moderada a intervalos en las aproximaciones"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med snö i närheten","night_text":"Områden med snö i närheten"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"அருகில் சீரில்லாத பனிமழை","night_text":"அருகில் சீரில்லாத பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా దగ్గరల్లో మంచు","night_text":"చెదురుమదురుగా దగ్గరల్లో మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz kar yağışlı","night_text":"Bölgesel düzensiz kar yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями сніг","night_text":"Місцями сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"قریب میں جہاں تہاں برفباری","night_text":"قریب میں جہاں تہاں برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết rơi lả tả gần đó","night_text":"Tuyết rơi lả tả gần đó"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"无尽撅部落削","night_text":"无尽撅部落削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"附近有零星雪","night_text":"附近有零星雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"週边有零星小雪","night_text":"週边有零星小雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Liyakhithika lapha nalapha eduze","night_text":"Liyakhithika lapha nalapha eduze"}]},{"code":1069,"day":"Patchy sleet nearby","night":"Patchy sleet nearby","icon":182,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"صقيع متفاوت قريب","night_text":"صقيع متفاوت قريب"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত বৃষ্টি সহ তুষারপাত","night_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত বৃষ্টি সহ তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Суграшици на отделни места в околността","night_text":"Суграшици на отделни места в околността"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"周边有零星小雨夹雪","night_text":"周边有零星小雨夹雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"週边有零星小雨夾雪","night_text":"週边有零星小雨夾雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy blízký déšť se sněhem","night_text":"Místy blízký déšť se sněhem"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke natte sneeuw in de omgeving","night_text":"Plaatselijke natte sneeuw in de omgeving"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanaista räntäsadetta lähellä","night_text":"Hajanaista räntäsadetta lähellä"},{"lang_name":"French","lang_iso":"fr","day_text":"Grésil épars à proximité","night_text":"Grésil épars à proximité"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise Eisregen","night_text":"stellenweise Eisregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους χιονόνερο σε κοντινή απόσταση","night_text":"Κατά τόπους χιονόνερο σε κοντινή απόσταση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"आसपास ओलों के साथ मामूली बारिश","night_text":"आसपास ओलों के साथ मामूली बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A közelben foltokban dara","night_text":"A közelben foltokban dara"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nevischio a tratti nelle vicinanze","night_text":"Nevischio a tratti nelle vicinanze"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"近くで所によりみぞれ","night_text":"近くで所によりみぞれ"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan es lan salju ing sacedhake","night_text":"Udan es lan salju ing sacedhake"},{"lang_name":"Korean","lang_iso":"ko","day_text":"근처 곳곳에 진눈깨비","night_text":"근처 곳곳에 진눈깨비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"周边有零星小雨夹雪","night_text":"周边有零星小雨夹雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"आजूबाजूला अनियमित गारांचा पाऊस","night_text":"आजूबाजूला अनियमित गारांचा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe opady śniegu z deszczem w pobliżu","night_text":"Miejscowe opady śniegu z deszczem w pobliżu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Possibilidade de neve molhada irregular","night_text":"Possibilidade de neve molhada irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ ਵਾਲਾ ਮੀਂਹ","night_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ ਵਾਲਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Lapoviță pe porţiuni în apropiere","night_text":"Lapoviță pe porţiuni în apropiere"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами дождь со снегом","night_text":"Местами дождь со снегом"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimična susnežica","night_text":"Mestimična susnežica"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ආසන්නයේ තැනින් තැන හිම වැස්ස","night_text":"ආසන්නයේ තැනින් තැන හිම වැස්ස"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami blízky dážď so snehom","night_text":"Miestami blízky dážď so snehom"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Aguanieve moderada a intervalos en las aproximaciones","night_text":"Aguanieve moderada a intervalos en las aproximaciones"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med snöblandat regn i närheten","night_text":"Områden med snöblandat regn i närheten"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"அருகில் சீரில்லாத ஆலங்கட்டி மழை","night_text":"அருகில் சீரில்லாத ஆலங்கட்டி மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా దగ్గరల్లో వడగండ్ల వాన","night_text":"చెదురుమదురుగా దగ్గరల్లో వడగండ్ల వాన"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz karla karışık yağmurlu","night_text":"Bölgesel düzensiz karla karışık yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями мокрий сніг","night_text":"Місцями мокрий сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"قریب میں جہاں تہاں ژالہ باری","night_text":"قریب میں جہاں تہاں ژالہ باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa tuyết lả tả gần đó","night_text":"Mưa tuyết lả tả gần đó"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"无尽撅部鱼假削","night_text":"无尽撅部鱼假削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"附近有零星雨夹雪","night_text":"附近有零星雨夹雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"週边有零星小雨夾雪","night_text":"週边有零星小雨夾雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kunesichotho esihambisana nomoya lapha nalapha","night_text":"Kunesichotho esihambisana nomoya lapha nalapha"}]},{"code":1072,"day":"Patchy freezing drizzle nearby","night":"Patchy freezing drizzle nearby","icon":185,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"رذاذ متجمِد متفاوت قريب","night_text":"رذاذ متجمِد متفاوت قريب"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত","night_text":"পার্শ্ববর্তী এলাকায় অনিয়মিত গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Преохладени ръмежи на отделни места в околността","night_text":"Преохладени ръмежи на отделни места в околността"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"周边有有零星小冻雾雨","night_text":"周边有有零星小冻雾雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"週边有零星小凍霧雨","night_text":"週边有零星小凍霧雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy blízké mrznoucí mrholení","night_text":"Místy blízké mrznoucí mrholení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke onderkoelde motregen in de omgeving","night_text":"Plaatselijke onderkoelde motregen in de omgeving"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanaista jäätävää sadetta lähellä","night_text":"Hajanaista jäätävää sadetta lähellä"},{"lang_name":"French","lang_iso":"fr","day_text":"Bruine verglaçante éparse à proximité","night_text":"Bruine verglaçante éparse à proximité"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise gefrierender Nieselregen","night_text":"stellenweise gefrierender Nieselregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους παγωμένο ψιλόβροχο σε κοντινή απόσταση","night_text":"Κατά τόπους παγωμένο ψιλόβροχο σε κοντινή απόσταση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"आसपास अलग-अलग इलाकों में जमा देने वाली बौछार","night_text":"आसपास अलग-अलग इलाकों में जमा देने वाली बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A közelben foltokban szemerkélő fagyos eső","night_text":"A közelben foltokban szemerkélő fagyos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioviggine congelantesi a tratti nelle vicinanze","night_text":"Pioviggine congelantesi a tratti nelle vicinanze"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"近くで所により着氷性の霧雨","night_text":"近くで所により着氷性の霧雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Grimis atis ora rata ing sacedhake","night_text":"Grimis atis ora rata ing sacedhake"},{"lang_name":"Korean","lang_iso":"ko","day_text":"근처 곳곳에 동결 이슬비","night_text":"근처 곳곳에 동결 이슬비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"周边有有零星小冻雾雨","night_text":"周边有有零星小冻雾雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"आजूबाजूला अनियमित गारठवणारी रिपरिप","night_text":"आजूबाजूला अनियमित गारठवणारी रिपरिप"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe wystąpienie mroźnej mżawki w pobliżu","night_text":"Miejscowe wystąpienie mroźnej mżawki w pobliżu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Possibilidade de chuvisco gelado irregular","night_text":"Possibilidade de chuvisco gelado irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ ਵਾਲੀ ਥੋੜ੍ਹੀ ਕਿਣ-ਮਿਣ","night_text":"ਨੇੜੇ ਕਿਤੇ-ਕਿਤੇ ਬਰਫ ਵਾਲੀ ਥੋੜ੍ਹੀ ਕਿਣ-ਮਿਣ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Burniță şi polei pe porţiuni în apropiere","night_text":"Burniță şi polei pe porţiuni în apropiere"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами замерзающая морось","night_text":"Местами замерзающая морось"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično kiša koja se ledi pri zemlji","night_text":"Mestimično kiša koja se ledi pri zemlji"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ආසන්නයේ තැනින් තැන ඉතා ශීතල මිදෙන තරමේ සිහින් පොද","night_text":"ආසන්නයේ තැනින් තැන ඉතා ශීතල මිදෙන තරමේ සිහින් පොද"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami blízke mrznúce mrholenie","night_text":"Miestami blízke mrznúce mrholenie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Llovizna helada a intervalos en las aproximaciones","night_text":"Llovizna helada a intervalos en las aproximaciones"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med underkylt duggregn i närheten","night_text":"Områden med underkylt duggregn i närheten"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"அருகில் சீரில்லாத உறையவைக்கும் மழைத்தூறல்","night_text":"அருகில் சீரில்லாத உறையவைக்கும் மழைத்தூறல்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా దగ్గరల్లో ఘనీభవన చినుకులు","night_text":"చెదురుమదురుగా దగ్గరల్లో ఘనీభవన చినుకులు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz donmuş çisenti","night_text":"Bölgesel düzensiz donmuş çisenti"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями паморозь","night_text":"Місцями паморозь"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"قریب میں جہاں تہاں یخ بستہ پھوہار","night_text":"قریب میں جہاں تہاں یخ بستہ پھوہار"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa phùn băng giá lả tả gần đó","night_text":"Mưa phùn băng giá lả tả gần đó"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"无尽撅部董鱼","night_text":"无尽撅部董鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"附近有冰冻零星小雨","night_text":"附近有冰冻零星小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"週边有零星小凍霧雨","night_text":"週边有零星小凍霧雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kunokukhiza okubandayo eduze lapha nalapha","night_text":"Kunokukhiza okubandayo eduze lapha nalapha"}]},{"code":1087,"day":"Thundery outbreaks in nearby","night":"Thundery outbreaks in nearby","icon":200,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"عواصف رعديَة في المناطق المجاورة","night_text":"عواصف رعديَة في المناطق المجاورة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"পার্শ্ববর্তী এলাকায় বজ্রবিদ্যুতপূর্ণ ঝড়বৃষ্টি","night_text":"পার্শ্ববর্তী এলাকায় বজ্রবিদ্যুতপূর্ণ ঝড়বৃষ্টি"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Прояви на гръмотевици в околността","night_text":"Прояви на гръмотевици в околността"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"周边有雷雨","night_text":"周边有雷雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"週边有雷雨","night_text":"週边有雷雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"V okolí možnosti vzniku bouřek","night_text":"V okolí možnosti vzniku bouřek"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Onweersbuien in de omgeving","night_text":"Onweersbuien in de omgeving"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Ukkospuuskia lähellä","night_text":"Ukkospuuskia lähellä"},{"lang_name":"French","lang_iso":"fr","day_text":"Foyers orageux à proximité","night_text":"Foyers orageux à proximité"},{"lang_name":"German","lang_iso":"de","day_text":"gewittrige Niederschläge","night_text":"gewittrige Niederschläge"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ξέσπασματα καταιγίδας σε κοντινή","night_text":"Ξέσπασματα καταιγίδας σε κοντινή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"आसपास गरज के साथ बारिश","night_text":"आसपास गरज के साथ बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A közelben hirtelen vihar","night_text":"A közelben hirtelen vihar"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni temporalesche nelle vicinanze","night_text":"Precipitazioni temporalesche nelle vicinanze"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"近くで雷の発生","night_text":"近くで雷の発生"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan angin nganggo thathit ing sacedhake","night_text":"Udan angin nganggo thathit ing sacedhake"},{"lang_name":"Korean","lang_iso":"ko","day_text":"근처에 천둥 발생","night_text":"근처에 천둥 발생"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"周边有雷雨","night_text":"周边有雷雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"आजूबाजूला मेघगर्जनेसह उद्रेक","night_text":"आजूबाजूला मेघगर्जनेसह उद्रेक"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Gwałtowne grzmienia w pobliżu","night_text":"Gwałtowne grzmienia w pobliżu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Possibilidade de trovoada","night_text":"Possibilidade de trovoada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਨੇੜੇ ਗਰਜ ਵਾਲੇ ਭਾਂਬੜ","night_text":"ਨੇੜੇ ਗਰਜ ਵਾਲੇ ਭਾਂਬੜ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Tunete în apropiere","night_text":"Tunete în apropiere"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами грозы","night_text":"Местами грозы"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično lokalno nevreme s grmljavinom","night_text":"Mestimično lokalno nevreme s grmljavinom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ආසන්නයේ ගිගුරුම් සහිත වැසි","night_text":"ආසන්නයේ ගිගුරුම් සහිත වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"V okolí možnosti vzniku búrok","night_text":"V okolí možnosti vzniku búrok"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Cielos tormentosos en las aproximaciones","night_text":"Cielos tormentosos en las aproximaciones"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Åska i närheten","night_text":"Åska i närheten"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"அருகில் இடி மின்னல்கள்","night_text":"அருகில் இடி மின்னல்கள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"దగ్గరల్లో పిడుగు పడటం","night_text":"దగ్గరల్లో పిడుగు పడటం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz gök gürültülü yağmurlu","night_text":"Bölgesel düzensiz gök gürültülü yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями грози","night_text":"Місцями грози"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"قریب میں طوفان برق و باراں","night_text":"قریب میں طوفان برق و باراں"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Các cơn giông tố nổi lên gần đó","night_text":"Các cơn giông tố nổi lên gần đó"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"礼八四无尽贴气无好","night_text":"礼八四无尽贴气无好"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"附近有雷暴","night_text":"附近有雷暴"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"週边有雷雨","night_text":"週边有雷雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Kunokuduma kwezulu eduze","night_text":"Kunokuduma kwezulu eduze"}]},{"code":1114,"day":"Blowing snow","night":"Blowing snow","icon":227,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"هبَات من الثلوج","night_text":"هبَات من الثلوج"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"তুষারঝড়","night_text":"তুষারঝড়"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Навяващ сняг","night_text":"Навяващ сняг"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"飞雪","night_text":"飞雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"飛雪","night_text":"飛雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Vítr se sněžením","night_text":"Vítr se sněžením"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Driftsneeuw","night_text":"Driftsneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Lumipuuska","night_text":"Lumipuuska"},{"lang_name":"French","lang_iso":"fr","day_text":"Rafales de neige","night_text":"Rafales de neige"},{"lang_name":"German","lang_iso":"de","day_text":"Schneeverwehungen","night_text":"Schneeverwehungen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Φυσάει χιόνι","night_text":"Φυσάει χιόνι"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"ब्लोइंग स्नो","night_text":"ब्लोइंग स्नो"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Hófúvás","night_text":"Hófúvás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Turbinio di neve","night_text":"Turbinio di neve"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"吹雪","night_text":"吹雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Angin salju","night_text":"Angin salju"},{"lang_name":"Korean","lang_iso":"ko","day_text":"날리는 눈","night_text":"날리는 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"飞雪","night_text":"飞雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"उधळणारा \tबर्फ","night_text":"उधळणारा \tबर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Wiatr ze śniegiem","night_text":"Wiatr ze śniegiem"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Rajadas de vento com neve","night_text":"Rajadas de vento com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਉੱਡ ਰਹੀ ਬਰਫ","night_text":"ਉੱਡ ਰਹੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsoare viscolită","night_text":"Ninsoare viscolită"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Поземок","night_text":"Поземок"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Sneg nošen vetrom","night_text":"Sneg nošen vetrom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සුළඟට ගසා ගෙන යන හිම","night_text":"සුළඟට ගසා ගෙන යන හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Vietor so snežením","night_text":"Vietor so snežením"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Chubascos de nieve","night_text":"Chubascos de nieve"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Högt snödrev","night_text":"Högt snödrev"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பலத்த பனிமழை","night_text":"பலத்த பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మంచు వెదజల్లడం","night_text":"మంచు వెదజల్లడం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Tipi","night_text":"Tipi"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Низова хуртовина","night_text":"Низова хуртовина"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جھکڑ کے ساتھ برف باری","night_text":"جھکڑ کے ساتھ برف باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết thổi mạnh","night_text":"Tuyết thổi mạnh"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"次削","night_text":"次削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"飞雪","night_text":"飞雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"飛雪","night_text":"飛雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika okunomoya","night_text":"Ukukhithika okunomoya"}]},{"code":1117,"day":"Blizzard","night":"Blizzard","icon":230,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"عاصفة ثلجيَة","night_text":"عاصفة ثلجيَة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"ভয়ঙ্কর ও প্রবল তুষারঝড়","night_text":"ভয়ঙ্কর ও প্রবল তুষারঝড়"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Снежна буря","night_text":"Снежна буря"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"暴风雪","night_text":"暴风雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"暴風雪","night_text":"暴風雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Sněhová bouře","night_text":"Sněhová bouře"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Sneeuwstorm","night_text":"Sneeuwstorm"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Lumimyrsky","night_text":"Lumimyrsky"},{"lang_name":"French","lang_iso":"fr","day_text":"Blizzard","night_text":"Blizzard"},{"lang_name":"German","lang_iso":"de","day_text":"Schneesturm","night_text":"Schneesturm"},{"lang_name":"Greek","lang_iso":"el","day_text":"Χιονοθύελλα","night_text":"Χιονοθύελλα"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बर्फानी तूफान","night_text":"बर्फानी तूफान"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Hóvihar","night_text":"Hóvihar"},{"lang_name":"Italian","lang_iso":"it","day_text":"Blizzard","night_text":"Blizzard"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"猛吹雪","night_text":"猛吹雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan angin salju","night_text":"Udan angin salju"},{"lang_name":"Korean","lang_iso":"ko","day_text":"눈보라","night_text":"눈보라"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"暴风雪","night_text":"暴风雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हिमवादळ","night_text":"हिमवादळ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Śnieżyca","night_text":"Śnieżyca"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Nevasca","night_text":"Nevasca"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫੀਲਾ ਤੂਫਾਨ","night_text":"ਬਰਫੀਲਾ ਤੂਫਾਨ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Viscol","night_text":"Viscol"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Метель","night_text":"Метель"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Snežna mećava","night_text":"Snežna mećava"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"හිම කුණාටුව","night_text":"හිම කුණාටුව"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Snehová búrka","night_text":"Snehová búrka"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ventisca","night_text":"Ventisca"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Häftig snöstorm","night_text":"Häftig snöstorm"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பனிச் சூறாவளி","night_text":"பனிச் சூறாவளி"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మంచు తుఫాను","night_text":"మంచు తుఫాను"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Kar fırtınası","night_text":"Kar fırtınası"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Заметіль","night_text":"Заметіль"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"برف باری کا طوفان","night_text":"برف باری کا طوفان"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Trận bão tuyết","night_text":"Trận bão tuyết"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"保风削","night_text":"保风削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"暴风雪","night_text":"暴风雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"暴風雪","night_text":"暴風雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esinamandla","night_text":"Isichotho esinamandla"}]},{"code":1135,"day":"Fog","night":"Fog","icon":248,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ضباب","night_text":"ضباب"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"কুয়াশা","night_text":"কুয়াশা"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Тежка мъгла","night_text":"Тежка мъгла"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"雾","night_text":"雾"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"霧","night_text":"霧"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mlha","night_text":"Mlha"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Mist","night_text":"Mist"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Sumu","night_text":"Sumu"},{"lang_name":"French","lang_iso":"fr","day_text":"Brouillard","night_text":"Brouillard"},{"lang_name":"German","lang_iso":"de","day_text":"Nebel","night_text":"Nebel"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ομίχλη","night_text":"Ομίχλη"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"धुंध","night_text":"धुंध"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Köd","night_text":"Köd"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nebbia","night_text":"Nebbia"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"霧","night_text":"霧"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Pedhut Lelimengan","night_text":"Pedhut Lelimengan"},{"lang_name":"Korean","lang_iso":"ko","day_text":"안개","night_text":"안개"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"雾","night_text":"雾"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"धुके","night_text":"धुके"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Mgła","night_text":"Mgła"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Nevoeiro","night_text":"Nevoeiro"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਧੁੰਦ","night_text":"ਧੁੰਦ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ceață densă","night_text":"Ceață densă"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Туман","night_text":"Туман"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Magla","night_text":"Magla"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ඝන මීදුම","night_text":"ඝන මීදුම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Hmla","night_text":"Hmla"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Niebla moderada","night_text":"Niebla moderada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Dimma","night_text":"Dimma"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மூடுபனி","night_text":"மூடுபனி"},{"lang_name":"Telugu","lang_iso":"te","day_text":"పొగమంచు","night_text":"పొగమంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Puslu","night_text":"Puslu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Туман","night_text":"Туман"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"دھند","night_text":"دھند"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Sương mù","night_text":"Sương mù"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠吴","night_text":"悠吴"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有雾","night_text":"有雾"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"霧","night_text":"霧"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Inkungu","night_text":"Inkungu"}]},{"code":1147,"day":"Freezing fog","night":"Freezing fog","icon":260,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ضباب متجمِد","night_text":"ضباب متجمِد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হিম শীতল কুয়াশা","night_text":"হিম শীতল কুয়াশা"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Преохладена мъгла","night_text":"Преохладена мъгла"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"冻雾","night_text":"冻雾"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"凍霧","night_text":"凍霧"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mrznoucí mlha","night_text":"Mrznoucí mlha"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Aanvriezende mist","night_text":"Aanvriezende mist"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Jäätävä sumu","night_text":"Jäätävä sumu"},{"lang_name":"French","lang_iso":"fr","day_text":"Brouillard givrant","night_text":"Brouillard givrant"},{"lang_name":"German","lang_iso":"de","day_text":"Eisnebel","night_text":"Eisnebel"},{"lang_name":"Greek","lang_iso":"el","day_text":"Παγωμένη ομίχλη","night_text":"Παγωμένη ομίχλη"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"जमा देने वाली धुंध","night_text":"जमा देने वाली धुंध"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Jeges köd","night_text":"Jeges köd"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nebbia congelantesi","night_text":"Nebbia congelantesi"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"着氷性の霧","night_text":"着氷性の霧"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Pedhut Atis Lelimengan","night_text":"Pedhut Atis Lelimengan"},{"lang_name":"Korean","lang_iso":"ko","day_text":"동결 안개","night_text":"동결 안개"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"冻雾","night_text":"冻雾"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"गारठवणारे धुके","night_text":"गारठवणारे धुके"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Mroźna mgła","night_text":"Mroźna mgła"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Nevoeiro gelado","night_text":"Nevoeiro gelado"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲੀ ਧੁੰਦ","night_text":"ਬਰਫ ਵਾਲੀ ਧੁੰਦ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Chiciură","night_text":"Chiciură"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Переохлажденный туман","night_text":"Переохлажденный туман"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Magla koja se ledi","night_text":"Magla koja se ledi"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"අධික ශීතල මිදෙන තරමේ ඝන මීදුම","night_text":"අධික ශීතල මිදෙන තරමේ ඝන මීදුම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mrznúca hmla","night_text":"Mrznúca hmla"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Niebla helada","night_text":"Niebla helada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Dimfrost","night_text":"Dimfrost"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"உறையவைக்கும் மூடுபனி","night_text":"உறையவைக்கும் மூடுபனி"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఘనీభవన పొగమంచు","night_text":"ఘనీభవన పొగమంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Dondurucu sis","night_text":"Dondurucu sis"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Туман з памороззю","night_text":"Туман з памороззю"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جمادینے والی دھند","night_text":"جمادینے والی دھند"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Sương mù băng giá","night_text":"Sương mù băng giá"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠东吴","night_text":"悠东吴"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"冰冻雾","night_text":"冰冻雾"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"凍霧","night_text":"凍霧"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Inkungu enamakhaza","night_text":"Inkungu enamakhaza"}]},{"code":1150,"day":"Patchy light drizzle","night":"Patchy light drizzle","icon":263,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"رذاذ خفيف متفاوت","night_text":"رذاذ خفيف متفاوت"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এক পশলা হাল্কা গুড়ি গুড়ি বৃষ্টিপাত","night_text":"এক পশলা হাল্কা গুড়ি গুড়ি বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Леки превалявания на отделни места","night_text":"Леки превалявания на отделни места"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"零星细雨","night_text":"零星细雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"片狀細雨","night_text":"片狀細雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy slabé mrholení","night_text":"Místy slabé mrholení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke lichte motregen","night_text":"Plaatselijke lichte motregen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanainen kevyt tihkusade","night_text":"Hajanainen kevyt tihkusade"},{"lang_name":"French","lang_iso":"fr","day_text":"Bruine légère éparse","night_text":"Bruine légère éparse"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise Nieselregen","night_text":"stellenweise Nieselregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ελαφρό ψιλόβροχο","night_text":"Κατά τόπους ελαφρό ψιλόβροχο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में मामूली सी बौछार","night_text":"अलग-अलग इलाकों में मामूली सी बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban enyhe szemerkélő eső","night_text":"Foltokban enyhe szemerkélő eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioviggine debole a tratti","night_text":"Pioviggine debole a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により霧雨","night_text":"所により霧雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Grimis ora rata","night_text":"Grimis ora rata"},{"lang_name":"Korean","lang_iso":"ko","day_text":"곳곳에 가벼운 이슬비","night_text":"곳곳에 가벼운 이슬비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"零星细雨","night_text":"零星细雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अनियमित हलकीशी रिपरिप","night_text":"अनियमित हलकीशी रिपरिप"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe wystąpienie lekkiej mżawki","night_text":"Miejscowe wystąpienie lekkiej mżawki"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuvisco irregular","night_text":"Chuvisco irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਕਿਣ-ਮਿਣ","night_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਕਿਣ-ਮਿਣ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Burniță uşoară pe porțiuni","night_text":"Burniță uşoară pe porțiuni"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами слабая морось","night_text":"Местами слабая морось"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično slaba sitna kiša","night_text":"Mestimično slaba sitna kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තැනින් තැන සැහැල්ලු සිරි පොද","night_text":"තැනින් තැන සැහැල්ලු සිරි පොද"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami slabé mrholenie","night_text":"Miestami slabé mrholenie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Llovizna a intervalos","night_text":"Llovizna a intervalos"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med lätt duggregn","night_text":"Områden med lätt duggregn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"சீரில்லாத இலேசான மழைத்தூறல்","night_text":"சீரில்லாத இலேசான மழைத்தூறல்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా తేలికపాటి జల్లు","night_text":"చెదురుమదురుగా తేలికపాటి జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel düzensiz hafif çisenti","night_text":"Bölgesel düzensiz hafif çisenti"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями невеликий дощ","night_text":"Місцями невеликий дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جہاں تہاں ہلکی بوندا باندی","night_text":"جہاں تہاں ہلکی بوندا باندی"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa phùn nhẹ lả tả","night_text":"Mưa phùn nhẹ lả tả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部悠肖鱼","night_text":"撅部悠肖鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"零星小雨","night_text":"零星小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"零星細雨","night_text":"零星細雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhiza okuncane lapha nalapha","night_text":"Ukukhiza okuncane lapha nalapha"}]},{"code":1153,"day":"Light drizzle","night":"Light drizzle","icon":266,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"رذاذ خفيف متفاوت","night_text":"رذاذ خفيف متفاوت"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা গুড়ি গুড়ি বৃষ্টিপাত","night_text":"হাল্কা গুড়ি গুড়ি বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Леки превалявания","night_text":"Леки превалявания"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"细雨","night_text":"细雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"細雨","night_text":"細雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé mrholení","night_text":"Slabé mrholení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte motregen","night_text":"Lichte motregen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt tihkusade","night_text":"Kevyt tihkusade"},{"lang_name":"French","lang_iso":"fr","day_text":"Bruine légère","night_text":"Bruine légère"},{"lang_name":"German","lang_iso":"de","day_text":"Nieselregen","night_text":"Nieselregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ελαφρό ψιλόβροχο","night_text":"Ελαφρό ψιλόβροχο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की बौछार","night_text":"हल्की बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe szemerkélő eső","night_text":"Enyhe szemerkélő eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioviggine debole","night_text":"Pioviggine debole"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"霧雨","night_text":"霧雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Grimis ora deres","night_text":"Grimis ora deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 이슬비","night_text":"가벼운 이슬비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"细雨","night_text":"细雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलकीशी रिपरिप","night_text":"हलकीशी रिपरिप"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekka mżawka","night_text":"Lekka mżawka"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuvisco","night_text":"Chuvisco"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਹਲਕੀ ਕਿਣ-ਮਿਣ","night_text":"ਹਲਕੀ ਕਿਣ-ਮਿਣ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Burniță uşoară","night_text":"Burniță uşoară"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Слабая морось","night_text":"Слабая морось"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Sitna kiša","night_text":"Sitna kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු සිරි පොද","night_text":"සැහැල්ලු සිරි පොද"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé mrholenie","night_text":"Slabé mrholenie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Llovizna","night_text":"Llovizna"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt duggregn","night_text":"Lätt duggregn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான மழைத்தூறல்","night_text":"இலேசான மழைத்தூறல்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి జల్లు","night_text":"తేలికపాటి జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif çisenti","night_text":"Hafif çisenti"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликий дощ","night_text":"Невеликий дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی بوندا باندی","night_text":"ہلکی بوندا باندی"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa phùn nhẹ","night_text":"Mưa phùn nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"卯猫鱼","night_text":"卯猫鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小雨","night_text":"小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"細雨","night_text":"細雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhiza okuncane","night_text":"Ukukhiza okuncane"}]},{"code":1168,"day":"Freezing drizzle","night":"Freezing drizzle","icon":281,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"رذاذ متجمِد","night_text":"رذاذ متجمِد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত","night_text":"হাল্কা গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Преохладени ръмежи","night_text":"Преохладени ръмежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"冻雾雨","night_text":"冻雾雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"凍霧雨","night_text":"凍霧雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mrznoucí mrholení","night_text":"Mrznoucí mrholení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Onderkoelde motregen","night_text":"Onderkoelde motregen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Jäätävä tihkusade","night_text":"Jäätävä tihkusade"},{"lang_name":"French","lang_iso":"fr","day_text":"Bruine verglaçante","night_text":"Bruine verglaçante"},{"lang_name":"German","lang_iso":"de","day_text":"gefrierender Nieselregen","night_text":"gefrierender Nieselregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Παγωμένο ψιλόβροχο","night_text":"Παγωμένο ψιλόβροχο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"जमा देने वाली बौछार","night_text":"जमा देने वाली बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Fagyos szemerkélő eső","night_text":"Fagyos szemerkélő eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioviggine congelantesi","night_text":"Pioviggine congelantesi"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"着氷性の霧雨","night_text":"着氷性の霧雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Grimis atis","night_text":"Grimis atis"},{"lang_name":"Korean","lang_iso":"ko","day_text":"동결 이슬비","night_text":"동결 이슬비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"冻雾雨","night_text":"冻雾雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"गारठवणारी रिपरिप","night_text":"गारठवणारी रिपरिप"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Mroźna mżawka","night_text":"Mroźna mżawka"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuvisco gelado","night_text":"Chuvisco gelado"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲੀ ਕਿਣ-ਮਿਣ","night_text":"ਬਰਫ ਵਾਲੀ ਕਿਣ-ਮਿਣ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Burniță înghețată","night_text":"Burniță înghețată"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Замерзающая морось","night_text":"Замерзающая морось"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Sitna kiša koja se ledi","night_text":"Sitna kiša koja se ledi"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මිදෙන තරමට ශීතල සිරි පොද","night_text":"මිදෙන තරමට ශීතල සිරි පොද"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mrznúce mrholenie","night_text":"Mrznúce mrholenie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Llovizna helada","night_text":"Llovizna helada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Underkylt duggregn","night_text":"Underkylt duggregn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"உறையவைக்கும் மழைத்தூறல்","night_text":"உறையவைக்கும் மழைத்தூறல்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఘనీభవన జల్లు","night_text":"ఘనీభవన జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Dondurucu çisenti","night_text":"Dondurucu çisenti"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Ожеледиця","night_text":"Ожеледиця"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جمادینے والی پھوار","night_text":"جمادینے والی پھوار"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa phùn băng giá","night_text":"Mưa phùn băng giá"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"董鱼","night_text":"董鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"冰冻小雨","night_text":"冰冻小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"凍霧雨","night_text":"凍霧雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhiza okunamakhaza","night_text":"Ukukhiza okunamakhaza"}]},{"code":1171,"day":"Heavy freezing drizzle","night":"Heavy freezing drizzle","icon":284,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"رذاذ متجمِد شديد","night_text":"رذاذ متجمِد شديد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"ভারী গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত","night_text":"ভারী গুড়ি গুড়ি হিম শীতল বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Силни преохладени ръмежи","night_text":"Силни преохладени ръмежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"大冻雾雨","night_text":"大冻雾雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"大凍霧雨","night_text":"大凍霧雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Silné mrznoucí mrholení","night_text":"Silné mrznoucí mrholení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Zware onderkoelde motregen","night_text":"Zware onderkoelde motregen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Rankka jäätävä tihkusade","night_text":"Rankka jäätävä tihkusade"},{"lang_name":"French","lang_iso":"fr","day_text":"Forte bruine verglaçante","night_text":"Forte bruine verglaçante"},{"lang_name":"German","lang_iso":"de","day_text":"starker Nieselregen","night_text":"starker Nieselregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ισχυρό παγωμένο ψιλόβροχο","night_text":"Ισχυρό παγωμένο ψιλόβροχο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बेहद जमा देने वाली बौछार","night_text":"बेहद जमा देने वाली बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Heves szemerkélő fagyos eső","night_text":"Heves szemerkélő fagyos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioviggine congelantesi forte","night_text":"Pioviggine congelantesi forte"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"強い着氷性の霧雨","night_text":"強い着氷性の霧雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Grimis deres atis","night_text":"Grimis deres atis"},{"lang_name":"Korean","lang_iso":"ko","day_text":"심한 동결 이슬비","night_text":"심한 동결 이슬비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"大冻雾雨","night_text":"大冻雾雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"जोरदार गारठवणारी रिपरिप","night_text":"जोरदार गारठवणारी रिपरिप"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Ciężka, mroźna mżawka","night_text":"Ciężka, mroźna mżawka"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuvisco forte gelado","night_text":"Chuvisco forte gelado"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲੀ ਤੇਜ਼ ਕਿਣ-ਮਿਣ","night_text":"ਬਰਫ ਵਾਲੀ ਤੇਜ਼ ਕਿਣ-ਮਿਣ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Burniță înghețată în cantităţi însemnate","night_text":"Burniță înghețată în cantităţi însemnate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Сильная замерзающая морось","night_text":"Сильная замерзающая морось"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Jaka sitna kiša koja se ledi","night_text":"Jaka sitna kiša koja se ledi"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"දැඩි මිදෙන තරමට ශීතල සිරි පොද","night_text":"දැඩි මිදෙන තරමට ශීතල සිරි පොද"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Silné mrznúce mrholenie","night_text":"Silné mrznúce mrholenie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Fuerte llovizna helada","night_text":"Fuerte llovizna helada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Tungt underkylt duggregn","night_text":"Tungt underkylt duggregn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"கனமான உறையவைக்கும் மழைத்தூறல்","night_text":"கனமான உறையவைக்கும் மழைத்தூறல்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"భారీ ఘనీభవన జల్లు","night_text":"భారీ ఘనీభవన జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Yoğun dondurucu çisenti","night_text":"Yoğun dondurucu çisenti"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Сильна ожеледиця","night_text":"Сильна ожеледиця"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جمادینے والی شدید بونداباندی","night_text":"جمادینے والی شدید بونداباندی"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa phùn nặng băng giá","night_text":"Mưa phùn nặng băng giá"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"较拐董鱼","night_text":"较拐董鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"大冰冻小雨","night_text":"大冰冻小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"大凍霧雨","night_text":"大凍霧雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhiza okunamandla okunamakhaza","night_text":"Ukukhiza okunamandla okunamakhaza"}]},{"code":1180,"day":"Patchy light rain","night":"Patchy light rain","icon":293,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار خفيفة متفاوتة","night_text":"أمطار خفيفة متفاوتة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এক পশলা হাল্কা বৃষ্টিপাত","night_text":"এক পশলা হাল্কা বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби дъждове на отделни места","night_text":"Слаби дъждове на отделни места"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"片状小雨","night_text":"片状小雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"片狀小雨","night_text":"片狀小雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy slabý déšť","night_text":"Místy slabý déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke lichte regen","night_text":"Plaatselijke lichte regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanainen kevyt sade","night_text":"Hajanainen kevyt sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie légère éparse","night_text":"Pluie légère éparse"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise leichter Regenfall","night_text":"stellenweise leichter Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ασθενής βροχή","night_text":"Κατά τόπους ασθενής βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में हल्की बौछार","night_text":"अलग-अलग इलाकों में हल्की बौछार"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban enyhe eső","night_text":"Foltokban enyhe eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia debole a tratti","night_text":"Pioggia debole a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により弱い雨","night_text":"所により弱い雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan ora deres ora rata","night_text":"Udan ora deres ora rata"},{"lang_name":"Korean","lang_iso":"ko","day_text":"곳곳에 가벼운 비","night_text":"곳곳에 가벼운 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"片状小雨","night_text":"片状小雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अनियमित हलकासा पाऊस","night_text":"अनियमित हलकासा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe opady lekkiego deszczu","night_text":"Miejscowe opady lekkiego deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca irregular","night_text":"Chuva fraca irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕਾ ਮੀਂਹ","night_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi uşoare pe alocuri","night_text":"Ploi uşoare pe alocuri"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами небольшой дождь","night_text":"Местами небольшой дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično slaba kiša","night_text":"Mestimično slaba kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තැනින් තැන සැහැල්ලු වැසි","night_text":"තැනින් තැන සැහැල්ලු වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami slabý dážď","night_text":"Miestami slabý dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvias ligeras a intervalos","night_text":"Lluvias ligeras a intervalos"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med lätt regn","night_text":"Områden med lätt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"சீரில்லாத இலேசான மழை","night_text":"சீரில்லாத இலேசான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా తేలికపాటి వర్షం","night_text":"చెదురుమదురుగా తేలికపాటి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Düzensiz hafif yağmurlu","night_text":"Düzensiz hafif yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями мряка","night_text":"Місцями мряка"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جہاں تہاں ہلکی بارش","night_text":"جہاں تہاں ہلکی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa nhẹ lả tả","night_text":"Mưa nhẹ lả tả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部肖鱼","night_text":"撅部肖鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"零星小雨","night_text":"零星小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"片狀小雨","night_text":"片狀小雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Izihlamvana zemvula lapha nalapha","night_text":"Izihlamvana zemvula lapha nalapha"}]},{"code":1183,"day":"Light rain","night":"Light rain","icon":296,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار خفيفة","night_text":"أمطار خفيفة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা বৃষ্টিপাত","night_text":"হাল্কা বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби дъждове","night_text":"Слаби дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"小雨","night_text":"小雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"小雨","night_text":"小雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabý déšť","night_text":"Slabý déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte regen","night_text":"Lichte regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt sade","night_text":"Kevyt sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie légère","night_text":"Pluie légère"},{"lang_name":"German","lang_iso":"de","day_text":"leichter Regenfall","night_text":"leichter Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής βροχή","night_text":"Ασθενής βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की बारिश","night_text":"हल्की बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe eső","night_text":"Enyhe eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia debole","night_text":"Pioggia debole"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"弱い雨","night_text":"弱い雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan ora deres","night_text":"Udan ora deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 비","night_text":"가벼운 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"小雨","night_text":"小雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलकासा पाऊस","night_text":"हलकासा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekki deszcz","night_text":"Lekki deszcz"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca","night_text":"Chuva fraca"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਹਲਕਾ ਮੀਂਹ","night_text":"ਹਲਕਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi uşoare","night_text":"Ploi uşoare"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой дождь","night_text":"Небольшой дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slaba kiša","night_text":"Slaba kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු වැසි","night_text":"සැහැල්ලු වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabý dážď","night_text":"Slabý dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeras lluvias","night_text":"Ligeras lluvias"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt regn","night_text":"Lätt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான மழை","night_text":"இலேசான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి వర్షం","night_text":"తేలికపాటి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif yağmurlu","night_text":"Hafif yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Мряка","night_text":"Мряка"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی بارش","night_text":"ہلکی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa nhẹ","night_text":"Mưa nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"肖鱼","night_text":"肖鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小雨","night_text":"小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"零星小雨","night_text":"零星小雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engamathe ezimpukane","night_text":"Imvula engamathe ezimpukane"}]},{"code":1186,"day":"Moderate rain at times","night":"Moderate rain at times","icon":299,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار معتدلة أحياناً","night_text":"أمطار معتدلة أحياناً"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝে মাঝে মাঝারি বৃষ্টিপাত","night_text":"মাঝে মাঝে মাঝারি বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени прекъснати дъждове","night_text":"Умерени прекъснати дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"偶尔有中雨","night_text":"偶尔有中雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"偶爾有中雨","night_text":"偶爾有中雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Občasný mírný déšť","night_text":"Občasný mírný déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Nu en dan normale regen","night_text":"Nu en dan normale regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Ajoittainen keskivoimakas sade","night_text":"Ajoittainen keskivoimakas sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie modérée par moments","night_text":"Pluie modérée par moments"},{"lang_name":"German","lang_iso":"de","day_text":"zuweilen mäßiger Regenfall","night_text":"zuweilen mäßiger Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια βροχή κατά περιόδους","night_text":"Μέτρια βροχή κατά περιόδους"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अक्सर सामान्य बारिश","night_text":"अक्सर सामान्य बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Időnként mérsékelt eső","night_text":"Időnként mérsékelt eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia moderata a tratti","night_text":"Pioggia moderata a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"時々穏やかな雨","night_text":"時々穏やかな雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Kadhang udan rada deres","night_text":"Kadhang udan rada deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"때때로 보통 비","night_text":"때때로 보통 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"偶尔有中雨","night_text":"偶尔有中雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"कधीतरी मध्यम पाऊस","night_text":"कधीतरी मध्यम पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, średnie opady deszczu","night_text":"Przejściowe, średnie opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Períodos de chuva moderada","night_text":"Períodos de chuva moderada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਵਾਰ-ਵਾਰ ਦਰਮਿਆਨਾ ਮੀਂਹ","night_text":"ਵਾਰ-ਵਾਰ ਦਰਮਿਆਨਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi moderate uneori","night_text":"Ploi moderate uneori"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Временами умеренный дождь","night_text":"Временами умеренный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Povremeno umerena kiša","night_text":"Povremeno umerena kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"යම් අවස්ථාවලදී මධ්යස්ථ වැසි","night_text":"යම් අවස්ථාවලදී මධ්යස්ථ වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Občasný mierny dážď","night_text":"Občasný mierny dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Periodos de lluvia moderada","night_text":"Periodos de lluvia moderada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt regn då och då","night_text":"Måttligt regn då och då"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"விட்டுவிட்டு மிதமான மழை","night_text":"விட்டுவிட்டு மிதமான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"పలుసమయాల్లో ఒక మాదిరి వర్షం","night_text":"పలుసమయాల్లో ఒక మాదిరి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Ara ara orta kuvvetli yağmurlu","night_text":"Ara ara orta kuvvetli yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Час від часу помірний дощ","night_text":"Час від часу помірний дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"کبھی کبھار معتدل بارش","night_text":"کبھی کبھار معتدل بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Thỉnh thoảng mưa vừa","night_text":"Thỉnh thoảng mưa vừa"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"有咯晨光中鱼","night_text":"有咯晨光中鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有时有中雨","night_text":"有时有中雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"偶爾有中雨","night_text":"偶爾有中雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula nje engatheni ngezikhathi ezithile","night_text":"Imvula nje engatheni ngezikhathi ezithile"}]},{"code":1189,"day":"Moderate rain","night":"Moderate rain","icon":302,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار معتدلة","night_text":"أمطار معتدلة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝারি বৃষ্টিপাত","night_text":"মাঝারি বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени дъждове","night_text":"Умерени дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中雨","night_text":"中雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中雨","night_text":"中雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírný déšť","night_text":"Mírný déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale regen","night_text":"Normale regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas sade","night_text":"Keskivoimakas sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie modérée","night_text":"Pluie modérée"},{"lang_name":"German","lang_iso":"de","day_text":"mäßiger Regenfall","night_text":"mäßiger Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια βροχή","night_text":"Μέτρια βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य बारिश","night_text":"सामान्य बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt eső","night_text":"Mérsékelt eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia moderata","night_text":"Pioggia moderata"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかな雨","night_text":"穏やかな雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan rada deres","night_text":"Udan rada deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 비","night_text":"보통 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中雨","night_text":"中雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम पाऊस","night_text":"मध्यम पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie opady deszczu","night_text":"Średnie opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva moderada","night_text":"Chuva moderada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਦਰਮਿਆਨਾ ਮੀਂਹ","night_text":"ਦਰਮਿਆਨਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi moderate","night_text":"Ploi moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный дождь","night_text":"Умеренный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerena kiša","night_text":"Umerena kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ වැසි","night_text":"මධ්යස්ථ වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierny dážď","night_text":"Mierny dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvia moderada","night_text":"Lluvia moderada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt regn","night_text":"Måttligt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான மழை","night_text":"மிதமான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఒక మాదిరి వర్షం","night_text":"ఒక మాదిరి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli yağmurlu","night_text":"Orta kuvvetli yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний дощ","night_text":"Помірний дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل بارش","night_text":"معتدل بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa vừa","night_text":"Mưa vừa"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中鱼","night_text":"中鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中雨","night_text":"中雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中雨","night_text":"中雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engatheni","night_text":"Imvula engatheni"}]},{"code":1192,"day":"Heavy rain at times","night":"Heavy rain at times","icon":305,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار شديدة أحياناً","night_text":"أمطار شديدة أحياناً"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝে মাঝে ভারী বৃষ্টিপাত","night_text":"মাঝে মাঝে ভারী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Силни прекъснати дъждове","night_text":"Силни прекъснати дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"偶尔有大雨","night_text":"偶尔有大雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"偶爾有大雨","night_text":"偶爾有大雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Občasný silný déšť","night_text":"Občasný silný déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Nu en dan zware regen","night_text":"Nu en dan zware regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Ajoittainen rankka sade","night_text":"Ajoittainen rankka sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie forte par moments","night_text":"Pluie forte par moments"},{"lang_name":"German","lang_iso":"de","day_text":"zeitweise starker Regenfall","night_text":"zeitweise starker Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ισχυρή βροχή κατά περιόδους","night_text":"Ισχυρή βροχή κατά περιόδους"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अक्सर जोरदार बारिश","night_text":"अक्सर जोरदार बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Időnként heves eső","night_text":"Időnként heves eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia forte a tratti","night_text":"Pioggia forte a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"時々大雨","night_text":"時々大雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Kadhang udan deres","night_text":"Kadhang udan deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"때때로 폭우","night_text":"때때로 폭우"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"偶尔有大雨","night_text":"偶尔有大雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"कधीतरी जोरदार पाऊस","night_text":"कधीतरी जोरदार पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, ciężkie opady deszczu","night_text":"Przejściowe, ciężkie opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Períodos de chuva forte","night_text":"Períodos de chuva forte"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਸਮੇ-ਸਮੇਂ ਤੇ ਤੇਜ਼ ਮੀਂਹ","night_text":"ਸਮੇ-ਸਮੇਂ ਤੇ ਤੇਜ਼ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploaie torențială uneori","night_text":"Ploaie torențială uneori"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Временами сильный дождь","night_text":"Временами сильный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Povremeno jaka kiša","night_text":"Povremeno jaka kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"යම් අවස්ථාවලදී තද වැසි","night_text":"යම් අවස්ථාවලදී තද වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Občasný silný dážď","night_text":"Občasný silný dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Periodos de fuertes lluvias","night_text":"Periodos de fuertes lluvias"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Tungt regn då och då","night_text":"Tungt regn då och då"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"விட்டுவிட்டு கனமான மழை","night_text":"விட்டுவிட்டு கனமான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"పలుసమయాల్లో భారీ వర్షం","night_text":"పలుసమయాల్లో భారీ వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Ara ara şiddetli yağmurlu","night_text":"Ara ara şiddetli yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Час від часу сильний дощ","night_text":"Час від часу сильний дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"کبھی کبھار تیز بارش","night_text":"کبھی کبھار تیز بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Thỉnh thoảng mưa nặng hạt","night_text":"Thỉnh thoảng mưa nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"有咯晨光达鱼","night_text":"有咯晨光达鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有时有大雨","night_text":"有时有大雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"偶爾有大雨","night_text":"偶爾有大雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula enamandla ngezikhathi ezithile","night_text":"Imvula enamandla ngezikhathi ezithile"}]},{"code":1195,"day":"Heavy rain","night":"Heavy rain","icon":308,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار شديدة","night_text":"أمطار شديدة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"ভারী বৃষ্টিপাত","night_text":"ভারী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Силни дъждове","night_text":"Силни дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"大雨","night_text":"大雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"大雨","night_text":"大雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Silný déšť","night_text":"Silný déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Zware regen","night_text":"Zware regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Rankka sade","night_text":"Rankka sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie forte","night_text":"Pluie forte"},{"lang_name":"German","lang_iso":"de","day_text":"starker Regenfall","night_text":"starker Regenfall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ισχυρή βροχή","night_text":"Ισχυρή βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"जोरदार बारिश","night_text":"जोरदार बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Heves eső","night_text":"Heves eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia forte","night_text":"Pioggia forte"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"大雨","night_text":"大雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan deres","night_text":"Udan deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"폭우","night_text":"폭우"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"大雨","night_text":"大雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"जोरदार पाऊस","night_text":"जोरदार पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Ciężkie opady deszczu","night_text":"Ciężkie opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva forte","night_text":"Chuva forte"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਤੇਜ਼ ਮੀਂਹ","night_text":"ਤੇਜ਼ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploaie torențială","night_text":"Ploaie torențială"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Сильный дождь","night_text":"Сильный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Jaka kiša","night_text":"Jaka kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තද වැසි","night_text":"තද වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Silný dážď","night_text":"Silný dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Fuertes lluvias","night_text":"Fuertes lluvias"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Tungt regn","night_text":"Tungt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"கனமான மழை","night_text":"கனமான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"భారీ వర్షం","night_text":"భారీ వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Şiddetli yağmurlu","night_text":"Şiddetli yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Сильний дощ","night_text":"Сильний дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"تیز بارش","night_text":"تیز بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rơi nặng hạt","night_text":"Mưa rơi nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"达鱼","night_text":"达鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"大雨","night_text":"大雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"大雨","night_text":"大雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula enamandla","night_text":"Imvula enamandla"}]},{"code":1198,"day":"Light freezing rain","night":"Light freezing rain","icon":311,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار متجمِدة خفيفة","night_text":"أمطار متجمِدة خفيفة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা হিম শীতল বৃষ্টিপাত","night_text":"হাল্কা হিম শীতল বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби преохладени дъждове","night_text":"Слаби преохладени дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"微冻雨","night_text":"微冻雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"微凍雨","night_text":"微凍雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabý mrznoucí déšť","night_text":"Slabý mrznoucí déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte onderkoelde regen","night_text":"Lichte onderkoelde regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt jäätävä sade","night_text":"Kevyt jäätävä sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie verglaçante légère","night_text":"Pluie verglaçante légère"},{"lang_name":"German","lang_iso":"de","day_text":"leichter Eisregen","night_text":"leichter Eisregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής παγωμένη βροχή","night_text":"Ασθενής παγωμένη βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की जमा देने वाली बारिश","night_text":"हल्की जमा देने वाली बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe fagyos eső","night_text":"Enyhe fagyos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia congelantesi debole","night_text":"Pioggia congelantesi debole"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"着氷性の弱い雨","night_text":"着氷性の弱い雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan atis rada deres","night_text":"Udan atis rada deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"약간의 동결 비","night_text":"약간의 동결 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"微冻雨","night_text":"微冻雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलकासा गारठवणारा पाऊस","night_text":"हलकासा गारठवणारा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekkie opady mroźnego deszczu","night_text":"Lekkie opady mroźnego deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca e gelada","night_text":"Chuva fraca e gelada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਹਲਕਾ ਬਰਫ ਵਾਲਾ ਮੀਂਹ","night_text":"ਹਲਕਾ ਬਰਫ ਵਾਲਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploaie înghețată în cantităţi mici","night_text":"Ploaie înghețată în cantităţi mici"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Слабый переохлажденный дождь","night_text":"Слабый переохлажденный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slaba ledena kiša","night_text":"Slaba ledena kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු මිදෙන තරමට ශීතල වැසි","night_text":"සැහැල්ලු මිදෙන තරමට ශීතල වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabý mrznúci dážď","night_text":"Slabý mrznúci dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeras lluvias heladas","night_text":"Ligeras lluvias heladas"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt underkylt regn","night_text":"Lätt underkylt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான உறையவைக்கும் மழை","night_text":"இலேசான உறையவைக்கும் மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి ఘనీభవన వర్షం","night_text":"తేలికపాటి ఘనీభవన వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif dondurucu yağmurlu","night_text":"Hafif dondurucu yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликий дощ та ожеледиця","night_text":"Невеликий дощ та ожеледиця"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی جمادینے والی بارش","night_text":"ہلکی جمادینے والی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa giá rét nhẹ","night_text":"Mưa giá rét nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"轻董鱼","night_text":"轻董鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"冰冻小雨","night_text":"冰冻小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"微凍雨","night_text":"微凍雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engenamandla kodwa ebandayo","night_text":"Imvula engenamandla kodwa ebandayo"}]},{"code":1201,"day":"Moderate or heavy freezing rain","night":"Moderate or heavy freezing rain","icon":314,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار متجمِدة معتدلة أو شديدة","night_text":"أمطار متجمِدة معتدلة أو شديدة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝারি বা ভারী হিম শীতল বৃষ্টিপাত","night_text":"মাঝারি বা ভারী হিম শীতল বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени или силни преохладени дъждове","night_text":"Умерени или силни преохладени дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中度或大冻雨","night_text":"中度或大冻雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中度或大凍雨","night_text":"中度或大凍雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírný nebo silný mrznoucí déšť","night_text":"Mírný nebo silný mrznoucí déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware onderkoelde regen","night_text":"Normale of zware onderkoelde regen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas tai rankka jäätävä sade","night_text":"Keskivoimakas tai rankka jäätävä sade"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie verglaçante modérée à forte","night_text":"Pluie verglaçante modérée à forte"},{"lang_name":"German","lang_iso":"de","day_text":"mäßiger bis starker Eisregen","night_text":"mäßiger bis starker Eisregen"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή παγωμένη βροχή","night_text":"Μέτρια ή ισχυρή παγωμένη βροχή"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"जमा देने वाली सामान्य या जोरदार बारिश","night_text":"जमा देने वाली सामान्य या जोरदार बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves fagyos eső","night_text":"Mérsékelt, vagy heves fagyos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia congelantesi moderata o forte","night_text":"Pioggia congelantesi moderata o forte"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"着氷性の穏やかな雨または大雨","night_text":"着氷性の穏やかな雨または大雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan Rada Deres utawa Udan Deres Atis","night_text":"Udan Rada Deres utawa Udan Deres Atis"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 또는 심한 동결 비","night_text":"보통 또는 심한 동결 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中度或大冻雨","night_text":"中度或大冻雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम किंवा जोरदार गारठवणारा पाऊस","night_text":"मध्यम किंवा जोरदार गारठवणारा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie lub ciężkie opady mroźnego deszczu","night_text":"Średnie lub ciężkie opady mroźnego deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva gelada moderada ou forte","night_text":"Chuva gelada moderada ou forte"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲਾ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ","night_text":"ਬਰਫ ਵਾਲਾ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploaie înghețată în cantităţi mari şi moderate","night_text":"Ploaie înghețată în cantităţi mari şi moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный или сильный переохлажденный дождь","night_text":"Умеренный или сильный переохлажденный дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerena ili jaka ledena kiša","night_text":"Umerena ili jaka ledena kiša"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හෝ තද මිදෙන තරමට ශීතල වැසි","night_text":"මධ්යස්ථ හෝ තද මිදෙන තරමට ශීතල වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierny alebo silný mrznúci dážď","night_text":"Mierny alebo silný mrznúci dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvias heladas fuertes o moderadas","night_text":"Lluvias heladas fuertes o moderadas"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt eller tungt underkylt regn","night_text":"Måttligt eller tungt underkylt regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான அல்லது கனமான உறையவைக்கும் மழை","night_text":"மிதமான அல்லது கனமான உறையவைக்கும் மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం లేదా భారీ ఘనీభవన వర్షం","night_text":"మధ్యస్థం లేదా భారీ ఘనీభవన వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya Şiddetli dondurucu yağmurlu","night_text":"Orta kuvvetli veya Şiddetli dondurucu yağmurlu"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний або сильний дощ та ожеледиця","night_text":"Помірний або сильний дощ та ожеледиця"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل یا تیز جمادینے والی بارش","night_text":"معتدل یا تیز جمادینے والی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa giá rét Vừa hoặc Nặng Hạt","night_text":"Mưa giá rét Vừa hoặc Nặng Hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到大董鱼","night_text":"中到大董鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大冰冻雨","night_text":"中到大冰冻雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中度或大凍雨","night_text":"中度或大凍雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula ebandayo enamandla noma engatheni","night_text":"Imvula ebandayo enamandla noma engatheni"}]},{"code":1204,"day":"Light sleet","night":"Light sleet","icon":317,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"صقيع خفيف","night_text":"صقيع خفيف"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা বৃষ্টি সহ তুষারপাত","night_text":"হাল্কা বৃষ্টি সহ তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаба суграшица","night_text":"Слаба суграшица"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"微雨夹雪","night_text":"微雨夹雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"微雨夾雪","night_text":"微雨夾雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabý déšť se sněhem","night_text":"Slabý déšť se sněhem"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte natte sneeuw","night_text":"Lichte natte sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt räntäsade","night_text":"Kevyt räntäsade"},{"lang_name":"French","lang_iso":"fr","day_text":"Léger grésil","night_text":"Léger grésil"},{"lang_name":"German","lang_iso":"de","day_text":"leichte Graupelschauer","night_text":"leichte Graupelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενές χιονόνερο","night_text":"Ασθενές χιονόνερο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की ओलावृष्टि","night_text":"हल्की ओलावृष्टि"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe ólmos eső","night_text":"Enyhe ólmos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nevischio debole","night_text":"Nevischio debole"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"軽いみぞれ","night_text":"軽いみぞれ"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan es lan salju ora deres","night_text":"Udan es lan salju ora deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 진눈깨비","night_text":"가벼운 진눈깨비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"微雨夹雪","night_text":"微雨夹雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलकासा गारांचा पाऊस","night_text":"हलकासा गारांचा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekkie opady śniegu z deszczem","night_text":"Lekkie opady śniegu z deszczem"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca com neve","night_text":"Chuva fraca com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲਾ ਹਲਕਾ ਮੀਂਹ","night_text":"ਬਰਫ ਵਾਲਾ ਹਲਕਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Lapoviță în cantităţi mici","night_text":"Lapoviță în cantităţi mici"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой дождь со снегом","night_text":"Небольшой дождь со снегом"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slaba susnežica","night_text":"Slaba susnežica"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු හිමවැස්ස","night_text":"සැහැල්ලු හිමවැස්ස"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabý dážď so snehom","night_text":"Slabý dážď so snehom"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeras precipitaciones de aguanieve","night_text":"Ligeras precipitaciones de aguanieve"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt snöblandat regn","night_text":"Lätt snöblandat regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான ஆலங்கட்டி மழை","night_text":"இலேசான ஆலங்கட்டி மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి వడగండ్లు","night_text":"తేలికపాటి వడగండ్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif karla karışık yağmur","night_text":"Hafif karla karışık yağmur"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликий дощ зі снігом","night_text":"Невеликий дощ зі снігом"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی ژالہ باری","night_text":"ہلکی ژالہ باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa tuyết nhẹ","night_text":"Mưa tuyết nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"小咯鱼假削","night_text":"小咯鱼假削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小雨夹雪","night_text":"小雨夹雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"微雨夾雪","night_text":"微雨夾雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esingenamandla esihambisana nomoya","night_text":"Isichotho esingenamandla esihambisana nomoya"}]},{"code":1207,"day":"Moderate or heavy sleet","night":"Moderate or heavy sleet","icon":320,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"صقيع معتدل أو شديد","night_text":"صقيع معتدل أو شديد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝারি বা ভারী বৃষ্টি সহ তুষারপাত","night_text":"মাঝারি বা ভারী বৃষ্টি সহ তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерена или силна суграшица","night_text":"Умерена или силна суграшица"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中度或大雨夹雪","night_text":"中度或大雨夹雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中度或大雨夾雪","night_text":"中度或大雨夾雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírný nebo silný déšť se sněhem","night_text":"Mírný nebo silný déšť se sněhem"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware natte sneeuw","night_text":"Normale of zware natte sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas tai rankka räntäsade","night_text":"Keskivoimakas tai rankka räntäsade"},{"lang_name":"French","lang_iso":"fr","day_text":"Grésil modéré à fort","night_text":"Grésil modéré à fort"},{"lang_name":"German","lang_iso":"de","day_text":"mäßige bis starke Graupelschauer","night_text":"mäßige bis starke Graupelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτριο ή ισχυρό χιονόνερο","night_text":"Μέτριο ή ισχυρό χιονόνερο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य या जोरदार ओलावृष्टि","night_text":"सामान्य या जोरदार ओलावृष्टि"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves ólmos eső","night_text":"Mérsékelt, vagy heves ólmos eső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Nevischio moderato o forte","night_text":"Nevischio moderato o forte"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかなまたは強いみぞれ","night_text":"穏やかなまたは強いみぞれ"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan es lan salju rada deres utawa deres","night_text":"Udan es lan salju rada deres utawa deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"중간 또는 무거운 진눈깨비","night_text":"중간 또는 무거운 진눈깨비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中度或大雨夹雪","night_text":"中度或大雨夹雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम किंवा जोरदार गारांचा पाऊस","night_text":"मध्यम किंवा जोरदार गारांचा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie lub ciężkie opady śniegu z deszczem","night_text":"Średnie lub ciężkie opady śniegu z deszczem"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva forte ou moderada com neve","night_text":"Chuva forte ou moderada com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲਾ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ","night_text":"ਬਰਫ ਵਾਲਾ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Lapoviță în cantităţi mari şi moderate","night_text":"Lapoviță în cantităţi mari şi moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный или сильный дождь со снегом","night_text":"Умеренный или сильный дождь со снегом"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerena ili jaka susnežica","night_text":"Umerena ili jaka susnežica"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හෝ තද හිම වැස්ස","night_text":"මධ්යස්ථ හෝ තද හිම වැස්ස"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierny alebo silný dážď so snehom","night_text":"Mierny alebo silný dážď so snehom"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Aguanieve fuerte o moderada","night_text":"Aguanieve fuerte o moderada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt eller tungt snöblandat regn","night_text":"Måttligt eller tungt snöblandat regn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான அல்லது கனமான ஆலங்கட்டி மழை","night_text":"மிதமான அல்லது கனமான ஆலங்கட்டி மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం నుంచి భారీ వడగండ్లు","night_text":"మధ్యస్థం నుంచి భారీ వడగండ్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya şiddetli karla karışık yağmur","night_text":"Orta kuvvetli veya şiddetli karla karışık yağmur"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний або сильний дощ зі снігом","night_text":"Помірний або сильний дощ зі снігом"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل یا شدید ژالہ باری","night_text":"معتدل یا شدید ژالہ باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa tuyết vừa hoặc nặng hạt","night_text":"Mưa tuyết vừa hoặc nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到大鱼假削","night_text":"中到大鱼假削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大雨夹雪","night_text":"中到大雨夹雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中度或大雨夾雪","night_text":"中度或大雨夾雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esingatheni esihambisana nomoya noma esinamandla","night_text":"Isichotho esingatheni esihambisana nomoya noma esinamandla"}]},{"code":1210,"day":"Patchy light snow","night":"Patchy light snow","icon":323,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج خفيفة متفاوتة","night_text":"ثلوج خفيفة متفاوتة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"অনিয়মিত হাল্কা তুষারপাত","night_text":"অনিয়মিত হাল্কা তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби снеговалежи на отделни места","night_text":"Слаби снеговалежи на отделни места"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"零星小雪","night_text":"零星小雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"片狀小雪","night_text":"片狀小雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy slabé sněžení","night_text":"Místy slabé sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke lichte sneeuw","night_text":"Plaatselijke lichte sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanainen kevyt lumisade","night_text":"Hajanainen kevyt lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige légère éparse","night_text":"Neige légère éparse"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise leichter Schneefall","night_text":"stellenweise leichter Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ασθενής χιονόπτωση","night_text":"Κατά τόπους ασθενής χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में हल्की बर्फबारी","night_text":"अलग-अलग इलाकों में हल्की बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban enyhe havazás","night_text":"Foltokban enyhe havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve debole a tratti","night_text":"Neve debole a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により小雪","night_text":"所により小雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju ora deres ora rata","night_text":"Udan salju ora deres ora rata"},{"lang_name":"Korean","lang_iso":"ko","day_text":"곳곳에 가벼운 눈","night_text":"곳곳에 가벼운 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"零星小雪","night_text":"零星小雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अनियमित हलकेसे बर्फ","night_text":"अनियमित हलकेसे बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, lekkie opady śniegu","night_text":"Miejscowe, lekkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Queda de neve irregular e fraca","night_text":"Queda de neve irregular e fraca"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਬਰਫ","night_text":"ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi mici pe alocuri","night_text":"Ninsori în cantităţi mici pe alocuri"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами небольшой снег","night_text":"Местами небольшой снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično slab sneg","night_text":"Mestimično slab sneg"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තැනින් තැන සැහැල්ලු හිම","night_text":"තැනින් තැන සැහැල්ලු හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami slabé sneženie","night_text":"Miestami slabé sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nevadas ligeras a intervalos","night_text":"Nevadas ligeras a intervalos"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med lätt snöfall","night_text":"Områden med lätt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"சீரில்லாத இலேசான பனிமழை","night_text":"சீரில்லாத இலேசான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా తేలికపాటి మంచు","night_text":"చెదురుమదురుగా తేలికపాటి మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Düzensiz hafif karlı","night_text":"Düzensiz hafif karlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями невеликий сніг","night_text":"Місцями невеликий сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جہاں تہاں ہلکی برفباری","night_text":"جہاں تہاں ہلکی برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết nhẹ lả tả","night_text":"Tuyết nhẹ lả tả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部肖削","night_text":"撅部肖削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"零星小雪","night_text":"零星小雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"片狀小雪","night_text":"片狀小雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika kancane lapha nalapha","night_text":"Ukukhithika kancane lapha nalapha"}]},{"code":1213,"day":"Light snow","night":"Light snow","icon":326,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج خفيفة","night_text":"ثلوج خفيفة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা তুষারপাত","night_text":"হাল্কা তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби снеговалежи","night_text":"Слаби снеговалежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"小雪","night_text":"小雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"小雪","night_text":"小雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé sněžení","night_text":"Slabé sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte sneeuw","night_text":"Lichte sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt lumisade","night_text":"Kevyt lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige légère","night_text":"Neige légère"},{"lang_name":"German","lang_iso":"de","day_text":"leichter Schneefall","night_text":"leichter Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής χιονόπτωση","night_text":"Ασθενής χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की बर्फबारी","night_text":"हल्की बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe havazás","night_text":"Enyhe havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve debole","night_text":"Neve debole"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"小雪","night_text":"小雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju ora deres","night_text":"Udan salju ora deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 눈","night_text":"가벼운 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"小雪","night_text":"小雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलकेसे बर्फ","night_text":"हलकेसे बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekkie opady śniegu","night_text":"Lekkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Queda de neve fraca","night_text":"Queda de neve fraca"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਹਲਕੀ ਬਰਫ","night_text":"ਹਲਕੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi mici","night_text":"Ninsori în cantităţi mici"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой снег","night_text":"Небольшой снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slabe snežne padavine","night_text":"Slabe snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු හිම","night_text":"සැහැල්ලු හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé sneženie","night_text":"Slabé sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nevadas ligeras","night_text":"Nevadas ligeras"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt snöfall","night_text":"Lätt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான பனிமழை","night_text":"இலேசான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి మంచు","night_text":"తేలికపాటి మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif karlı","night_text":"Hafif karlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликий сніг","night_text":"Невеликий сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی برفباری","night_text":"ہلکی برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết nhẹ","night_text":"Tuyết nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"肖削","night_text":"肖削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小雪","night_text":"小雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"小雪","night_text":"小雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika kancane","night_text":"Ukukhithika kancane"}]},{"code":1216,"day":"Patchy moderate snow","night":"Patchy moderate snow","icon":329,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج معتدلة متفاوتة","night_text":"ثلوج معتدلة متفاوتة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"অনিয়মিত মাঝারি তুষারপাত","night_text":"অনিয়মিত মাঝারি তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени снеговалежи на отделни места","night_text":"Умерени снеговалежи на отделни места"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"零星中雪","night_text":"零星中雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"片狀中雪","night_text":"片狀中雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy mírné sněžení","night_text":"Místy mírné sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke normale sneeuw","night_text":"Plaatselijke normale sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Hajanainen keskivoimakas lumisade","night_text":"Hajanainen keskivoimakas lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige modérée éparse","night_text":"Neige modérée éparse"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise mäßiger Schneefall","night_text":"stellenweise mäßiger Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους μέτρια χιονόπτωση","night_text":"Κατά τόπους μέτρια χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में सामान्य बर्फबारी","night_text":"अलग-अलग इलाकों में सामान्य बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban mérsékelt havazás","night_text":"Foltokban mérsékelt havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve moderata a tratti","night_text":"Neve moderata a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により穏やかな雪","night_text":"所により穏やかな雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju rada deres ora rata","night_text":"Udan salju rada deres ora rata"},{"lang_name":"Korean","lang_iso":"ko","day_text":"곳곳에 적당한 눈","night_text":"곳곳에 적당한 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"零星中雪","night_text":"零星中雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अनियमित मध्यम बर्फ","night_text":"अनियमित मध्यम बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, średnie opady śniegu","night_text":"Miejscowe, średnie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Queda de neve moderada e irregular","night_text":"Queda de neve moderada e irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕਿਤੇ-ਕਿਤੇ ਦਰਮਿਆਨੀ ਬਰਫ","night_text":"ਕਿਤੇ-ਕਿਤੇ ਦਰਮਿਆਨੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori moderate pe alocuri","night_text":"Ninsori moderate pe alocuri"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами умеренный снег","night_text":"Местами умеренный снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično umeren sneg","night_text":"Mestimično umeren sneg"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තැනින් තැන මධ්යස්ථ හිම","night_text":"තැනින් තැන මධ්යස්ථ හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami mierne sneženie","night_text":"Miestami mierne sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nieve moderada a intervalos","night_text":"Nieve moderada a intervalos"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med måttligt snöfall","night_text":"Områden med måttligt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"சீரில்லாத மிதமான பனிமழை","night_text":"சீரில்லாத மிதமான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా ఒక మాదిరి మంచు","night_text":"చెదురుమదురుగా ఒక మాదిరి మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Düzensiz orta kuvvetli karlı","night_text":"Düzensiz orta kuvvetli karlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями помірний сніг","night_text":"Місцями помірний сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جہاں تہاں معتدل برفباری","night_text":"جہاں تہاں معتدل برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết vừa lả tả","night_text":"Tuyết vừa lả tả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部中削","night_text":"撅部中削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"零星中雪","night_text":"零星中雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"片狀中雪","night_text":"片狀中雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika okungatheni lapha nalapha","night_text":"Ukukhithika okungatheni lapha nalapha"}]},{"code":1219,"day":"Moderate snow","night":"Moderate snow","icon":332,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج معتدلة","night_text":"ثلوج معتدلة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝারি তুষারপাত","night_text":"মাঝারি তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени снеговалежи","night_text":"Умерени снеговалежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中雪","night_text":"中雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中雪","night_text":"中雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírné sněžení","night_text":"Mírné sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale sneeuw","night_text":"Normale sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas lumisade","night_text":"Keskivoimakas lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige modérée","night_text":"Neige modérée"},{"lang_name":"German","lang_iso":"de","day_text":"mäßiger Schneefall","night_text":"mäßiger Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια χιονόπτωση","night_text":"Μέτρια χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य बर्फबारी","night_text":"सामान्य बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt havazás","night_text":"Mérsékelt havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve moderata","night_text":"Neve moderata"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかな雪","night_text":"穏やかな雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju rada deres","night_text":"Udan salju rada deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 눈","night_text":"보통 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中雪","night_text":"中雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम बर्फ","night_text":"मध्यम बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie opady śniegu","night_text":"Średnie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Queda de neve moderada","night_text":"Queda de neve moderada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਦਰਮਿਆਨੀ ਬਰਫ","night_text":"ਦਰਮਿਆਨੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori moderate","night_text":"Ninsori moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный снег","night_text":"Умеренный снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerene snežne padavine","night_text":"Umerene snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හිම","night_text":"මධ්යස්ථ හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierne sneženie","night_text":"Mierne sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nieve moderada","night_text":"Nieve moderada"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt snöfall","night_text":"Måttligt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான பனிமழை","night_text":"மிதமான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఒక మాదిరి మంచు","night_text":"ఒక మాదిరి మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli karlı","night_text":"Orta kuvvetli karlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний сніг","night_text":"Помірний сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل برفباری","night_text":"معتدل برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết vừa","night_text":"Tuyết vừa"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中削","night_text":"中削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中雪","night_text":"中雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中雪","night_text":"中雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika okungatheni","night_text":"Ukukhithika okungatheni"}]},{"code":1222,"day":"Patchy heavy snow","night":"Patchy heavy snow","icon":335,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج شديدة متفاوتة","night_text":"ثلوج شديدة متفاوتة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"অনিয়মিত ভারী তুষারপাত","night_text":"অনিয়মিত ভারী তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Силни снеговалежи на отделни места","night_text":"Силни снеговалежи на отделни места"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"零星大雪","night_text":"零星大雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"片狀大雪","night_text":"片狀大雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Místy silné sněžení","night_text":"Místy silné sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke zware sneeuw","night_text":"Plaatselijke zware sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Ajoittainen rankka lumisade","night_text":"Ajoittainen rankka lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige forte éparse","night_text":"Neige forte éparse"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise starker Schneefall","night_text":"stellenweise starker Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ισχυρή χιονόπτωση","night_text":"Κατά τόπους ισχυρή χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में जोरदार बर्फबारी","night_text":"अलग-अलग इलाकों में जोरदार बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban heves havazás","night_text":"Foltokban heves havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve forte a tratti","night_text":"Neve forte a tratti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により大雪","night_text":"所により大雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju deres ora rata","night_text":"Udan salju deres ora rata"},{"lang_name":"Korean","lang_iso":"ko","day_text":"곳곳에 폭설","night_text":"곳곳에 폭설"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"零星大雪","night_text":"零星大雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"अनियमित जोरदार बर्फ","night_text":"अनियमित जोरदार बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, ciężkie opady śniegu","night_text":"Miejscowe, ciężkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Queda de neve forte e irregular","night_text":"Queda de neve forte e irregular"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਕਿਤੇ-ਕਿਤੇ ਤੇਜ਼ ਬਰਫ","night_text":"ਕਿਤੇ-ਕਿਤੇ ਤੇਜ਼ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi mari pe alocuri","night_text":"Ninsori în cantităţi mari pe alocuri"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Местами сильный снег","night_text":"Местами сильный снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično jake snežne padavine","night_text":"Mestimično jake snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"තැනින් තැන දැඩි හිම","night_text":"තැනින් තැන දැඩි හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Miestami silné sneženie","night_text":"Miestami silné sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nevadas intensas","night_text":"Nevadas intensas"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med tungt snöfall","night_text":"Områden med tungt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"சீரில்லாத கனமான பனிமழை","night_text":"சீரில்லாத கனமான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా భారీ మంచు","night_text":"చెదురుమదురుగా భారీ మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Düzensiz yoğun kar yağışlı","night_text":"Düzensiz yoğun kar yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями сильний сніг","night_text":"Місцями сильний сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"جہاں تہاں شدید برفباری","night_text":"جہاں تہاں شدید برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết rơi nặng hạt lả tả","night_text":"Tuyết rơi nặng hạt lả tả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"撅部打削","night_text":"撅部打削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"零星大雪","night_text":"零星大雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"片狀大雪","night_text":"片狀大雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika okukhulu lapha nalapha","night_text":"Ukukhithika okukhulu lapha nalapha"}]},{"code":1225,"day":"Heavy snow","night":"Heavy snow","icon":338,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج شديدة","night_text":"ثلوج شديدة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"ভারী তুষারপাত","night_text":"ভারী তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Силни снеговалежи","night_text":"Силни снеговалежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"大雪","night_text":"大雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"大雪","night_text":"大雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Silné sněžení","night_text":"Silné sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Zware sneeuw","night_text":"Zware sneeuw"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Rankka lumisade","night_text":"Rankka lumisade"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige forte","night_text":"Neige forte"},{"lang_name":"German","lang_iso":"de","day_text":"starker Schneefall","night_text":"starker Schneefall"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ισχυρή χιονόπτωση","night_text":"Ισχυρή χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"जोरदार बर्फबारी","night_text":"जोरदार बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Heves havazás","night_text":"Heves havazás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve forte","night_text":"Neve forte"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"大雪","night_text":"大雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju deres","night_text":"Udan salju deres"},{"lang_name":"Korean","lang_iso":"ko","day_text":"폭설","night_text":"폭설"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"大雪","night_text":"大雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"जोरदार बर्फ","night_text":"जोरदार बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Ciężkie opady śniegu","night_text":"Ciężkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Neve intensa","night_text":"Neve intensa"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਤੇਜ਼ ਬਰਫ","night_text":"ਤੇਜ਼ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi însemnate","night_text":"Ninsori în cantităţi însemnate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Сильный снег","night_text":"Сильный снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Jak sneg","night_text":"Jak sneg"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"දැඩි හිම","night_text":"දැඩි හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Silné sneženie","night_text":"Silné sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Fuertes nevadas","night_text":"Fuertes nevadas"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Tungt snöfall","night_text":"Tungt snöfall"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"கனமான பனிமழை","night_text":"கனமான பனிமழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"భారీ మంచు","night_text":"భారీ మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Yoğun kar yağışlı","night_text":"Yoğun kar yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Сильний сніг","night_text":"Сильний сніг"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"شدید برفباری","night_text":"شدید برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết rơi nặng hạt","night_text":"Tuyết rơi nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"打削","night_text":"打削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"大雪","night_text":"大雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"大雪","night_text":"大雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika okunamandla","night_text":"Ukukhithika okunamandla"}]},{"code":1237,"day":"Ice pellets","night":"Ice pellets","icon":350,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"حبيبات جليدية","night_text":"حبيبات جليدية"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"শিলাপাত","night_text":"শিলাপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Градушки","night_text":"Градушки"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"冰丸","night_text":"冰丸"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"冰丸","night_text":"冰丸"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Kroupy","night_text":"Kroupy"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Korrelhagel","night_text":"Korrelhagel"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Rakeet","night_text":"Rakeet"},{"lang_name":"French","lang_iso":"fr","day_text":"Crystaux de glace","night_text":"Crystaux de glace"},{"lang_name":"German","lang_iso":"de","day_text":"Hagel","night_text":"Hagel"},{"lang_name":"Greek","lang_iso":"el","day_text":"Σβόλοι πάγου","night_text":"Σβόλοι πάγου"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बर्फ के गोले","night_text":"बर्फ के गोले"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Apró szemű jégeső","night_text":"Apró szemű jégeső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia gelata","night_text":"Pioggia gelata"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"凍雨","night_text":"凍雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Krikil es","night_text":"Krikil es"},{"lang_name":"Korean","lang_iso":"ko","day_text":"아이스 펠렛","night_text":"아이스 펠렛"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"冰丸","night_text":"冰丸"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"बर्फाचे गोळे","night_text":"बर्फाचे गोळे"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Mokry śnieg","night_text":"Mokry śnieg"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Granizo","night_text":"Granizo"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲੇ","night_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲੇ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Grindină","night_text":"Grindină"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Ледяной дождь","night_text":"Ледяной дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Led pomešan s kišom","night_text":"Led pomešan s kišom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"අයිස් ගුලි","night_text":"අයිස් ගුලි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Krúpy","night_text":"Krúpy"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Granizo","night_text":"Granizo"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Iskorn","night_text":"Iskorn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பனித் துகள்கள்","night_text":"பனித் துகள்கள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"వడగండ్లు","night_text":"వడగండ్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Buz taneleri","night_text":"Buz taneleri"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Крижаний дощ","night_text":"Крижаний дощ"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"برف کے ٹکڑے","night_text":"برف کے ٹکڑے"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa đá","night_text":"Mưa đá"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"削猪","night_text":"削猪"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"冰雹","night_text":"冰雹"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"冰丸","night_text":"冰丸"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Ukukhithika","night_text":"Ukukhithika"}]},{"code":1240,"day":"Light rain shower","night":"Light rain shower","icon":353,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات خفيفة من الأمطار","night_text":"زخَات خفيفة من الأمطار"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"হাল্কা স্বল্পস্থায়ী বৃষ্টিপাত","night_text":"হাল্কা স্বল্পস্থায়ী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни слаби дъждове","night_text":"Краткотрайни слаби дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"小阵雨","night_text":"小阵雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"小陣雨","night_text":"小陣雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé dešťové přeháňky","night_text":"Slabé dešťové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte regenbui","night_text":"Lichte regenbui"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyt sadekuuro","night_text":"Kevyt sadekuuro"},{"lang_name":"French","lang_iso":"fr","day_text":"Averse de pluie légère","night_text":"Averse de pluie légère"},{"lang_name":"German","lang_iso":"de","day_text":"leichte Regenschauer","night_text":"leichte Regenschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής βροχόπτωση","night_text":"Ασθενής βροχόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बारिश की हल्की बौछारें","night_text":"बारिश की हल्की बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe eső, zápor","night_text":"Enyhe eső, zápor"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni piovose deboli","night_text":"Precipitazioni piovose deboli"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"軽いにわか雨","night_text":"軽いにわか雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan ora deres sedhela","night_text":"Udan ora deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 소나기","night_text":"가벼운 소나기"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"小阵雨","night_text":"小阵雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलक्या पावसाच्या सरी","night_text":"हलक्या पावसाच्या सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Lekkie, przelotne opady deszczu","night_text":"Lekkie, przelotne opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros fracos","night_text":"Aguaceiros fracos"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਮੀਂਹ ਦੀ ਹਲਕੀ ਫੁਹਾਰ","night_text":"ਮੀਂਹ ਦੀ ਹਲਕੀ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi uşoare şi de scurtă durată","night_text":"Ploi uşoare şi de scurtă durată"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой ливневый дождь","night_text":"Небольшой ливневый дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slab kratkotrajni pljusak","night_text":"Slab kratkotrajni pljusak"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු වර්ෂාව","night_text":"සැහැල්ලු වර්ෂාව"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé dažďové prehánky","night_text":"Slabé dažďové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeras precipitaciones","night_text":"Ligeras precipitaciones"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt regnskur","night_text":"Lätt regnskur"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான மழைப் பொழிவு","night_text":"இலேசான மழைப் பொழிவு"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి వర్షపు జల్లు","night_text":"తేలికపాటి వర్షపు జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif sağnak yağışlı","night_text":"Hafif sağnak yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невелика злива","night_text":"Невелика злива"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی بارش","night_text":"ہلکی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rào nhẹ","night_text":"Mưa rào nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"肖咯枕雨","night_text":"肖咯枕雨"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小阵雨","night_text":"小阵雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"小陣雨","night_text":"小陣雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engenamandla","night_text":"Imvula engenamandla"}]},{"code":1243,"day":"Moderate or heavy rain shower","night":"Moderate or heavy rain shower","icon":356,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات معتدلة أو شديدة من الأمطار","night_text":"زخَات معتدلة أو شديدة من الأمطار"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মাঝারি ও ভারী স্বল্পস্থায়ী বৃষ্টিপাত","night_text":"মাঝারি ও ভারী স্বল্পস্থায়ী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни умерени или силни дъждове","night_text":"Краткотрайни умерени или силни дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中雨或大阵雨","night_text":"中雨或大阵雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中雨或大陣雨","night_text":"中雨或大陣雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírné nebo silné dešťové přeháňky","night_text":"Mírné nebo silné dešťové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware regenbui","night_text":"Normale of zware regenbui"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas tai rankka sadekuuro","night_text":"Keskivoimakas tai rankka sadekuuro"},{"lang_name":"French","lang_iso":"fr","day_text":"Averse de pluie modérée","night_text":"Averse de pluie modérée"},{"lang_name":"German","lang_iso":"de","day_text":"mäßige bis starke Regenschauer","night_text":"mäßige bis starke Regenschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή βροχόπτωση","night_text":"Μέτρια ή ισχυρή βροχόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य या जोरदार बारिश की बौछारें","night_text":"सामान्य या जोरदार बारिश की बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves felhőszakadás","night_text":"Mérsékelt, vagy heves felhőszakadás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni piovose moderate o forti","night_text":"Precipitazioni piovose moderate o forti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかなまたは強いにわか雨","night_text":"穏やかなまたは強いにわか雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan rada deres utawa deres sedhela","night_text":"Udan rada deres utawa deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 또는 심한 소나기","night_text":"보통 또는 심한 소나기"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中雨或大阵雨","night_text":"中雨或大阵雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम किंवा जोरदार पावसाच्या सरी","night_text":"मध्यम किंवा जोरदार पावसाच्या सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie lub ciężkie, przelotne opady deszczu","night_text":"Średnie lub ciężkie, przelotne opady deszczu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros moderados ou fortes","night_text":"Aguaceiros moderados ou fortes"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਮੀਂਹ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ","night_text":"ਮੀਂਹ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi de scurtă durată moderate sau în cantităţi însemnate","night_text":"Ploi de scurtă durată moderate sau în cantităţi însemnate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный или сильный ливневый дождь","night_text":"Умеренный или сильный ливневый дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umeren ili jak kratkotrajni pljusak","night_text":"Umeren ili jak kratkotrajni pljusak"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හෝ තද වර්ෂාව","night_text":"මධ්යස්ථ හෝ තද වර්ෂාව"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierne alebo silné dažďové prehánky","night_text":"Mierne alebo silné dažďové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvias fuertes o moderadas","night_text":"Lluvias fuertes o moderadas"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttlig eller tung regnskur","night_text":"Måttlig eller tung regnskur"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான அல்லது கனமான மழைப் பொழிவு","night_text":"மிதமான அல்லது கனமான மழைப் பொழிவு"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం నుంచి భారీ వర్షపు జల్లు","night_text":"మధ్యస్థం నుంచి భారీ వర్షపు జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya yoğun sağnak yağışlı","night_text":"Orta kuvvetli veya yoğun sağnak yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірна або сильна злива","night_text":"Помірна або сильна злива"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل یا شدید بارش","night_text":"معتدل یا شدید بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rào vừa hoặc nặng hạt","night_text":"Mưa rào vừa hoặc nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到斗枕雨","night_text":"中到斗枕雨"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大阵雨","night_text":"中到大阵雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中雨或大陣雨","night_text":"中雨或大陣雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engatheni noma enamandla","night_text":"Imvula engatheni noma enamandla"}]},{"code":1246,"day":"Torrential rain shower","night":"Torrential rain shower","icon":359,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات غزيرة من الأمطار","night_text":"زخَات غزيرة من الأمطار"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"মুষলধারায় স্বল্পস্থায়ী বৃষ্টিপাত","night_text":"মুষলধারায় স্বল্পস্থায়ী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Обилни краткотрайни дъждове","night_text":"Обилни краткотрайни дъждове"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"暴雨","night_text":"暴雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"暴雨","night_text":"暴雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Přívalové dešťové přeháňky","night_text":"Přívalové dešťové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Stortregen","night_text":"Stortregen"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Rankka sadekuuro","night_text":"Rankka sadekuuro"},{"lang_name":"French","lang_iso":"fr","day_text":"Averses de pluie torrentielle","night_text":"Averses de pluie torrentielle"},{"lang_name":"German","lang_iso":"de","day_text":"sintflutartige Regenschauer","night_text":"sintflutartige Regenschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Καταρρακτώδης βροχόπτωση","night_text":"Καταρρακτώδης βροχόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"मूसलाधार बारिश की बौछारें","night_text":"मूसलाधार बारिश की बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Viharos felhőszakadás","night_text":"Viharos felhőszakadás"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni piovose torrenziali","night_text":"Precipitazioni piovose torrenziali"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"急な豪雨","night_text":"急な豪雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan deres pathes sedhela","night_text":"Udan deres pathes sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"호우","night_text":"호우"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"暴雨","night_text":"暴雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मुसळधार पावसाच्या सरी","night_text":"मुसळधार पावसाच्या सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przelotne deszcze nawalne","night_text":"Przelotne deszcze nawalne"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva torrencial","night_text":"Chuva torrencial"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਮੀਂਹ ਦੀ ਜ਼ੋਰਦਾਰ ਫੁਹਾਰ","night_text":"ਮੀਂਹ ਦੀ ਜ਼ੋਰਦਾਰ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploaie torențială de scurtă durată","night_text":"Ploaie torențială de scurtă durată"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Сильные ливни","night_text":"Сильные ливни"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Kratkotrajni pljusak koji može izazvati bujice","night_text":"Kratkotrajni pljusak koji može izazvati bujice"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"වේගයෙන් වැටෙන තද වර්ෂාව","night_text":"වේගයෙන් වැටෙන තද වර්ෂාව"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Prívalové dažďové prehánky","night_text":"Prívalové dažďové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvias torrenciales","night_text":"Lluvias torrenciales"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Störtregn","night_text":"Störtregn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பேய் மழை","night_text":"பேய் மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"కుండపోత వర్షం","night_text":"కుండపోత వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Şiddetli sağnak yağmur","night_text":"Şiddetli sağnak yağmur"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Дуже сильна злива","night_text":"Дуже сильна злива"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"طوفانی بارش","night_text":"طوفانی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rào xối xả","night_text":"Mưa rào xối xả"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"较拐急枕雨","night_text":"较拐急枕雨"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"阵暴雨","night_text":"阵暴雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"暴雨","night_text":"暴雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula ewumvimbi","night_text":"Imvula ewumvimbi"}]},{"code":1249,"day":"Light sleet showers","night":"Light sleet showers","icon":362,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات خفيفة من الصقيع","night_text":"زخَات خفيفة من الصقيع"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী হাল্কা বৃষ্টি সহ তুষারপাত","night_text":"স্বল্পস্থায়ী হাল্কা বৃষ্টি সহ তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни слаби суграшици","night_text":"Краткотрайни слаби суграшици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"小冰雹雨","night_text":"小冰雹雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"小冰雹雨","night_text":"小冰雹雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé přeháňky deště se sněhem","night_text":"Slabé přeháňky deště se sněhem"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte natte sneeuwbuien","night_text":"Lichte natte sneeuwbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyitä räntäsadekuuroja","night_text":"Kevyitä räntäsadekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Légères averses de grésil","night_text":"Légères averses de grésil"},{"lang_name":"German","lang_iso":"de","day_text":"leichte Graupelschauer","night_text":"leichte Graupelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενές χιονόνερο","night_text":"Ασθενές χιονόνερο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की ओलावृष्टि बौछारें","night_text":"हल्की ओलावृष्टि बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe ólmos záporeső","night_text":"Enyhe ólmos záporeső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni deboli di nevischio","night_text":"Precipitazioni deboli di nevischio"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"急な軽いみぞれ","night_text":"急な軽いみぞれ"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan es lan salju ora deres sedhela","night_text":"Udan es lan salju ora deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 진눈깨비 소나기","night_text":"가벼운 진눈깨비 소나기"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"小冰雹雨","night_text":"小冰雹雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलक्या गारांच्या सरी","night_text":"हलक्या गारांच्या सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, lekkie opady śniegu z deszczem","night_text":"Przejściowe, lekkie opady śniegu z deszczem"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros fracos com neve","night_text":"Aguaceiros fracos com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲਾ ਮੀਂਹ ਦੀ ਹਲਕੀ ਫੁਹਾਰ","night_text":"ਬਰਫ ਵਾਲਾ ਮੀਂਹ ਦੀ ਹਲਕੀ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Lapoviță de scurtă durată în cantităţi mici","night_text":"Lapoviță de scurtă durată în cantităţi mici"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой ливневый дождь со снегом","night_text":"Небольшой ливневый дождь со снегом"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slab kratkotrajni pljusak pomešan s ledom","night_text":"Slab kratkotrajni pljusak pomešan s ledom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු හිමවර්ෂා වැසි","night_text":"සැහැල්ලු හිමවර්ෂා වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé prehánky dažďa so snehom","night_text":"Slabé prehánky dažďa so snehom"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeros chubascos de aguanieve","night_text":"Ligeros chubascos de aguanieve"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätt snöblandad regnskur","night_text":"Lätt snöblandad regnskur"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான ஆலங்கட்டி பொழிவுகள்","night_text":"இலேசான ஆலங்கட்டி பொழிவுகள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి వడగండ్ల వాన","night_text":"తేలికపాటి వడగండ్ల వాన"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif karla karışık sağnak yağış","night_text":"Hafif karla karışık sağnak yağış"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликі дощі зі снігом","night_text":"Невеликі дощі зі снігом"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی ژالہ باری","night_text":"ہلکی ژالہ باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa tuyết rào nhẹ","night_text":"Mưa tuyết rào nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"轻度鱼假削","night_text":"轻度鱼假削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小阵雨夹雪","night_text":"小阵雨夹雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"小冰雹雨","night_text":"小冰雹雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula enesichotho engatheni","night_text":"Imvula enesichotho engatheni"}]},{"code":1252,"day":"Moderate or heavy sleet showers","night":"Moderate or heavy sleet showers","icon":365,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات معتدلة أو شديدة من الصقيع","night_text":"زخَات معتدلة أو شديدة من الصقيع"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী মাঝারি ও ভারী বৃষ্টি সহ তুষারপাত","night_text":"স্বল্পস্থায়ী মাঝারি ও ভারী বৃষ্টি সহ তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни умерени или силни суграшици","night_text":"Краткотрайни умерени или силни суграшици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中度或大冰雹雨","night_text":"中度或大冰雹雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中度或大冰雹雨","night_text":"中度或大冰雹雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírné nebo silné přeháňky deště se sněhem","night_text":"Mírné nebo silné přeháňky deště se sněhem"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware natte sneeuwbuien","night_text":"Normale of zware natte sneeuwbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakkaita tai rankkoja räntäsadekuuroja","night_text":"Keskivoimakkaita tai rankkoja räntäsadekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Averses de grésil modérées à fortes","night_text":"Averses de grésil modérées à fortes"},{"lang_name":"German","lang_iso":"de","day_text":"mäßige bis starke Graupelschauer","night_text":"mäßige bis starke Graupelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτριο ή ισχυρό χιονόνερο","night_text":"Μέτριο ή ισχυρό χιονόνερο"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य या जोरदार ओलावृष्टि बौछारें","night_text":"सामान्य या जोरदार ओलावृष्टि बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves ólmos záporeső","night_text":"Mérsékelt, vagy heves ólmos záporeső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni di nevischio moderate o forti","night_text":"Precipitazioni di nevischio moderate o forti"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかなまたは強い急なみぞれ","night_text":"穏やかなまたは強い急なみぞれ"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan es lan salju rada deres utawa deres sedhela","night_text":"Udan es lan salju rada deres utawa deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 또는 심한 진눈깨비 소나기","night_text":"보통 또는 심한 진눈깨비 소나기"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中度或大冰雹雨","night_text":"中度或大冰雹雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम किंवा जोरदार गारांच्या सरी","night_text":"मध्यम किंवा जोरदार गारांच्या सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, średnie lub ciężkie opady śniegu z deszczem","night_text":"Przejściowe, średnie lub ciężkie opady śniegu z deszczem"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros moderados ou fortes com neve","night_text":"Aguaceiros moderados ou fortes com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਵਾਲਾ ਮੀਂਹ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ","night_text":"ਬਰਫ ਵਾਲਾ ਮੀਂਹ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Lapoviță de scurtă durată în cantităţi mari şi moderate","night_text":"Lapoviță de scurtă durată în cantităţi mari şi moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренные или сильные ливневые дожди со снегом","night_text":"Умеренные или сильные ливневые дожди со снегом"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umeren ili jak kratkotrajni pljusak pomešan s ledom","night_text":"Umeren ili jak kratkotrajni pljusak pomešan s ledom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හෝ දැඩි හිමවර්ෂා වැසි","night_text":"මධ්යස්ථ හෝ දැඩි හිමවර්ෂා වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierne alebo silné prehánky dažďa so snehom","night_text":"Mierne alebo silné prehánky dažďa so snehom"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Chubascos de aguanieve fuertes o moderados","night_text":"Chubascos de aguanieve fuertes o moderados"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttlig eller tung snöblandad regnskur","night_text":"Måttlig eller tung snöblandad regnskur"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான அல்லது கனமான ஆலங்கட்டி பொழிவுகள்","night_text":"மிதமான அல்லது கனமான ஆலங்கட்டி பொழிவுகள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం నుంచి భారీ వడగండ్ల వాన","night_text":"మధ్యస్థం నుంచి భారీ వడగండ్ల వాన"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya yoğun karla karışık sağnak yağış","night_text":"Orta kuvvetli veya yoğun karla karışık sağnak yağış"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірні або сильні дощі зі снігом","night_text":"Помірні або сильні дощі зі снігом"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل یا شدید ژالہ باری","night_text":"معتدل یا شدید ژالہ باری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa tuyết rào vừa hoặc nặng hạt","night_text":"Mưa tuyết rào vừa hoặc nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到斗鱼假削","night_text":"中到斗鱼假削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大阵雨夹雪","night_text":"中到大阵雨夹雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中度或大冰雹雨","night_text":"中度或大冰雹雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula enesichotho engatheni noma enamandla","night_text":"Imvula enesichotho engatheni noma enamandla"}]},{"code":1255,"day":"Light snow showers","night":"Light snow showers","icon":368,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات خفيفة من الثلوج","night_text":"زخَات خفيفة من الثلوج"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী হাল্কা তুষারপাত","night_text":"স্বল্পস্থায়ী হাল্কা তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни слаби снеговалежи","night_text":"Краткотрайни слаби снеговалежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"小阵雪","night_text":"小阵雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"小陣雪","night_text":"小陣雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé sněhové přeháňky","night_text":"Slabé sněhové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte sneeuwbuien","night_text":"Lichte sneeuwbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyitä lumisadekuuroja","night_text":"Kevyitä lumisadekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Légères averses de neige","night_text":"Légères averses de neige"},{"lang_name":"German","lang_iso":"de","day_text":"leichte Schneegestöber","night_text":"leichte Schneegestöber"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής χιονόπτωση","night_text":"Ασθενής χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"हल्की बर्फबारी बौछारें","night_text":"हल्की बर्फबारी बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe hózápor","night_text":"Enyhe hózápor"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni nevose leggere","night_text":"Precipitazioni nevose leggere"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"急な軽い雪","night_text":"急な軽い雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju ora deres sedhela","night_text":"Udan salju ora deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 폭설","night_text":"가벼운 폭설"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"小阵雪","night_text":"小阵雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"हलक्याशा हिमसरी","night_text":"हलक्याशा हिमसरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, lekkie opady śniegu","night_text":"Przejściowe, lekkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca com neve","night_text":"Chuva fraca com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਦੀ ਹਲਕੀ ਫੁਹਾਰ","night_text":"ਬਰਫ ਦੀ ਹਲਕੀ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori de scurtă durată în cantităţi mici","night_text":"Ninsori de scurtă durată în cantităţi mici"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой снег","night_text":"Небольшой снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slabe kratkotrajne snežne padavine","night_text":"Slabe kratkotrajne snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"සැහැල්ලු හිම වර්ෂා","night_text":"සැහැල්ලු හිම වර්ෂා"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé snehové prehánky","night_text":"Slabé snehové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeras precipitaciones de nieve","night_text":"Ligeras precipitaciones de nieve"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätta snöbyar","night_text":"Lätta snöbyar"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"இலேசான பனிப் பொழிவுகள்","night_text":"இலேசான பனிப் பொழிவுகள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"తేలికపాటి మంచు జల్లులు","night_text":"తేలికపాటి మంచు జల్లులు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif sağnak şeklinde kar","night_text":"Hafif sağnak şeklinde kar"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликий снігопад","night_text":"Невеликий снігопад"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"ہلکی برفباری","night_text":"ہلکی برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rào lẫn tuyết nhẹ","night_text":"Mưa rào lẫn tuyết nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"肖咯阵削","night_text":"肖咯阵削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小阵雪","night_text":"小阵雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"小陣雪","night_text":"小陣雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula enesichotho kodwa engenamandla","night_text":"Imvula enesichotho kodwa engenamandla"}]},{"code":1258,"day":"Moderate or heavy snow showers","night":"Moderate or heavy snow showers","icon":371,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات معتدلة أو شديدة من الثلوج","night_text":"زخَات معتدلة أو شديدة من الثلوج"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী মাঝারি ও ভারী তুষারপাত","night_text":"স্বল্পস্থায়ী মাঝারি ও ভারী তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни умерени или силни снеговалежи","night_text":"Краткотрайни умерени или силни снеговалежи"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中度或大阵雪","night_text":"中度或大阵雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中度或大陣雪","night_text":"中度或大陣雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírné nebo silné sněhové přeháňky","night_text":"Mírné nebo silné sněhové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware sneeuwbuien","night_text":"Normale of zware sneeuwbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakkaita tai rankkoja lumisadekuuroja","night_text":"Keskivoimakkaita tai rankkoja lumisadekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Averses de neige modérées à fortes","night_text":"Averses de neige modérées à fortes"},{"lang_name":"German","lang_iso":"de","day_text":"mäßige bis starke Schneegestöber","night_text":"mäßige bis starke Schneegestöber"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή χιονόπτωση","night_text":"Μέτρια ή ισχυρή χιονόπτωση"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"सामान्य या जोरदार बर्फबारी बौछारें","night_text":"सामान्य या जोरदार बर्फबारी बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves hózápor","night_text":"Mérsékelt, vagy heves hózápor"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni nevose moderate o leggere","night_text":"Precipitazioni nevose moderate o leggere"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかなまたは強い急な雪","night_text":"穏やかなまたは強い急な雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju rada deres utawa deres sedhela","night_text":"Udan salju rada deres utawa deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 또는 심한 폭설","night_text":"보통 또는 심한 폭설"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中度或大阵雪","night_text":"中度或大阵雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"मध्यम किंवा जोरदार हिमसरी","night_text":"मध्यम किंवा जोरदार हिमसरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, średnie lub ciężkie opady śniegu","night_text":"Przejściowe, średnie lub ciężkie opady śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva moderada ou forte com neve","night_text":"Chuva moderada ou forte com neve"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ","night_text":"ਬਰਫ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori de scurtă durată în cantităţi mari şi moderate","night_text":"Ninsori de scurtă durată în cantităţi mari şi moderate"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный или сильный снег","night_text":"Умеренный или сильный снег"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerene ili jake kratkotrajne snežne padavine","night_text":"Umerene ili jake kratkotrajne snežne padavine"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථා හෝ දැඩි හිම වැසි","night_text":"මධ්යස්ථා හෝ දැඩි හිම වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierne alebo silné snehové prehánky","night_text":"Mierne alebo silné snehové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Chubascos de nieve fuertes o moderados","night_text":"Chubascos de nieve fuertes o moderados"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttliga eller kraftiga snöbyar","night_text":"Måttliga eller kraftiga snöbyar"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"மிதமான அல்லது கனமான பனிப் பொழிவுகள்","night_text":"மிதமான அல்லது கனமான பனிப் பொழிவுகள்"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం నుంచి భారీ మంచు జల్లులు","night_text":"మధ్యస్థం నుంచి భారీ మంచు జల్లులు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya yoğun ve sağnak şeklinde kar","night_text":"Orta kuvvetli veya yoğun ve sağnak şeklinde kar"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний або сильний снігопад","night_text":"Помірний або сильний снігопад"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"معتدل یا شدید برفباری","night_text":"معتدل یا شدید برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa rào lẫn tuyết vừa hoặc nặng hạt","night_text":"Mưa rào lẫn tuyết vừa hoặc nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到斗阵削","night_text":"中到斗阵削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大阵雪","night_text":"中到大阵雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中度或大陣雪","night_text":"中度或大陣雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esihambisana nemvula engatheni noma enamandla","night_text":"Isichotho esihambisana nemvula engatheni noma enamandla"}]},{"code":1261,"day":"Light showers of ice pellets","night":"Light showers of ice pellets","icon":374,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات خفيفة من الحبيبات الجليديَة","night_text":"زخَات خفيفة من الحبيبات الجليديَة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী হাল্কা শিলাপাত","night_text":"স্বল্পস্থায়ী হাল্কা শিলাপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни слаби градушки","night_text":"Краткотрайни слаби градушки"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"冰丸小雨","night_text":"冰丸小雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"冰丸小雨","night_text":"冰丸小雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Slabé kroupové přeháňky","night_text":"Slabé kroupové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Lichte korrelhagelbuien","night_text":"Lichte korrelhagelbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Kevyitä raekuuroja","night_text":"Kevyitä raekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Légères averses de crystaux de glace","night_text":"Légères averses de crystaux de glace"},{"lang_name":"German","lang_iso":"de","day_text":"leichte Hagelschauer","night_text":"leichte Hagelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Ασθενής πτώση σβόλων πάγου","night_text":"Ασθενής πτώση σβόλων πάγου"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बर्फ के गोलों की हल्की बौछारें","night_text":"बर्फ के गोलों की हल्की बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Enyhe apró szemű jégeső","night_text":"Enyhe apró szemű jégeső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni deboli di pioggia gelata","night_text":"Precipitazioni deboli di pioggia gelata"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"軽い急な凍雨","night_text":"軽い急な凍雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan krikil es ora deres sedhela","night_text":"Udan krikil es ora deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"가벼운 얼음 알갱이 샤워","night_text":"가벼운 얼음 알갱이 샤워"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"冰丸小雨","night_text":"冰丸小雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"बर्फाच्या गोळ्यांच्या हलक्याशा सरी","night_text":"बर्फाच्या गोळ्यांच्या हलक्याशा सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, lekkie opady mokrego śniegu","night_text":"Przejściowe, lekkie opady mokrego śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros fracos com granizo","night_text":"Aguaceiros fracos com granizo"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲਿਆਂ ਦੀ ਹਲਕੀ ਫੁਹਾਰ","night_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲਿਆਂ ਦੀ ਹਲਕੀ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi în cantităţi mici însoţite de grindină","night_text":"Ploi în cantităţi mici însoţite de grindină"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Небольшой ледяной дождь","night_text":"Небольшой ледяной дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Slabi kratkotrajni pljuskovi pomešani s ledom","night_text":"Slabi kratkotrajni pljuskovi pomešani s ledom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"අයිස් ගුලි සහිත සැහැල්ලු වැසි","night_text":"අයිස් ගුලි සහිත සැහැල්ලු වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Slabé krúpové prehánky","night_text":"Slabé krúpové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Ligeros chubascos acompañados de granizo","night_text":"Ligeros chubascos acompañados de granizo"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Lätta skurar med iskorn","night_text":"Lätta skurar med iskorn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பனித் துகள்களின் இலேசான பொழிவு","night_text":"பனித் துகள்களின் இலேசான பொழிவு"},{"lang_name":"Telugu","lang_iso":"te","day_text":"వడగళ్ళతో తేలికపాటి వర్షం","night_text":"వడగళ్ళతో తేలికపాటి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Hafif buz taneleri şeklinde sağnak yağış","night_text":"Hafif buz taneleri şeklinde sağnak yağış"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Невеликі крижані зливи","night_text":"Невеликі крижані зливи"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"برف کے ٹکڑے کی معتدل بارش","night_text":"برف کے ٹکڑے کی معتدل بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa đá rào nhẹ","night_text":"Mưa đá rào nhẹ"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"有跌削猪","night_text":"有跌削猪"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"小阵冰雹","night_text":"小阵冰雹"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"冰丸小雨","night_text":"冰丸小雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engenamandla ehamba nokukhithika","night_text":"Imvula engenamandla ehamba nokukhithika"}]},{"code":1264,"day":"Moderate or heavy showers of ice pellets","night":"Moderate or heavy showers of ice pellets","icon":377,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"زخَات معتلة أو شديدة من الحبيبات الجليديَة","night_text":"زخَات معتلة أو شديدة من الحبيبات الجليديَة"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"স্বল্পস্থায়ী মাঝারি ও ভারী শিলাপাত","night_text":"স্বল্পস্থায়ী মাঝারি ও ভারী শিলাপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Краткотрайни умерени или силни градушки","night_text":"Краткотрайни умерени или силни градушки"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"中度或大冰丸","night_text":"中度或大冰丸"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"中度或大冰丸","night_text":"中度或大冰丸"},{"lang_name":"Czech","lang_iso":"cs","day_text":"Mírné nebo silné kroupové přeháňky","night_text":"Mírné nebo silné kroupové přeháňky"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware korrelhagelbuien","night_text":"Normale of zware korrelhagelbuien"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakkaita tai rankkoja raekuuroja","night_text":"Keskivoimakkaita tai rankkoja raekuuroja"},{"lang_name":"French","lang_iso":"fr","day_text":"Averses de crystaux de glace modérées à fortes","night_text":"Averses de crystaux de glace modérées à fortes"},{"lang_name":"German","lang_iso":"de","day_text":"mäßige bis starke Hagelschauer","night_text":"mäßige bis starke Hagelschauer"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή πτώση σβόλων πάγου","night_text":"Μέτρια ή ισχυρή πτώση σβόλων πάγου"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"बर्फ के गोलों की सामान्य या भारी बौछारें","night_text":"बर्फ के गोलों की सामान्य या भारी बौछारें"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves apró szemű jégeső","night_text":"Mérsékelt, vagy heves apró szemű jégeső"},{"lang_name":"Italian","lang_iso":"it","day_text":"Precipitazioni moderate o forti di pioggia gelata","night_text":"Precipitazioni moderate o forti di pioggia gelata"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"穏やかなまたは強い急な凍雨","night_text":"穏やかなまたは強い急な凍雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan krikil es rada deres utawa deres sedhela","night_text":"Udan krikil es rada deres utawa deres sedhela"},{"lang_name":"Korean","lang_iso":"ko","day_text":"보통 또는 심한 얼음 알갱이 샤워","night_text":"보통 또는 심한 얼음 알갱이 샤워"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"中度或大冰丸","night_text":"中度或大冰丸"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"बर्फाच्या गोळ्यांच्या मध्यम किंवा जोरदार सरी","night_text":"बर्फाच्या गोळ्यांच्या मध्यम किंवा जोरदार सरी"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Przejściowe, średnie lub ciężkie opady mokrego śniegu","night_text":"Przejściowe, średnie lub ciężkie opady mokrego śniegu"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Aguaceiros moderados ou fortes com granizo","night_text":"Aguaceiros moderados ou fortes com granizo"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲਿਆਂ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ","night_text":"ਬਰਫ ਦੇ ਛੋਟੇ ਗੋਲਿਆਂ ਦੀ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਫੁਹਾਰ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi în cantităţi mari şi moderate însoțite de grindină","night_text":"Ploi în cantităţi mari şi moderate însoțite de grindină"},{"lang_name":"Russian","lang_iso":"ru","day_text":"Умеренный или сильный ледяной дождь","night_text":"Умеренный или сильный ледяной дождь"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umereni ili jaki kratkotrajni pljuskovi pomešani s ledom","night_text":"Umereni ili jaki kratkotrajni pljuskovi pomešani s ledom"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"මධ්යස්ථ හෝ තද අයිස් ගුලි සහිත වැසි","night_text":"මධ්යස්ථ හෝ තද අයිස් ගුලි සහිත වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"Mierne alebo silné krúpové prehánky","night_text":"Mierne alebo silné krúpové prehánky"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Chubascos fuertes o moderados acompañados de granizo","night_text":"Chubascos fuertes o moderados acompañados de granizo"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttliga eller tunga skurar med iskorn","night_text":"Måttliga eller tunga skurar med iskorn"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பனித் துகள்களின் மிதமான அல்லது கனமான பொழிவு","night_text":"பனித் துகள்களின் மிதமான அல்லது கனமான பொழிவு"},{"lang_name":"Telugu","lang_iso":"te","day_text":"మధ్యస్థం నుంచి భారీ వడగళ్ళలో కూడిన భారీ జల్లు","night_text":"మధ్యస్థం నుంచి భారీ వడగళ్ళలో కూడిన భారీ జల్లు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Orta kuvvetli veya yoğun buz taneleri sağnak yağışlı","night_text":"Orta kuvvetli veya yoğun buz taneleri sağnak yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірні або сильні крижані зливи","night_text":"Помірні або сильні крижані зливи"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"برف کے ٹکڑے کی معتدل یا شدید بارش","night_text":"برف کے ٹکڑے کی معتدل یا شدید بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa đá rào vừa hoặc nặng hạt","night_text":"Mưa đá rào vừa hoặc nặng hạt"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"中到斗削猪","night_text":"中到斗削猪"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"中到大阵冰雹","night_text":"中到大阵冰雹"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"中度或大冰丸","night_text":"中度或大冰丸"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engatheni noma enamandla ehamba nesichotho","night_text":"Imvula engatheni noma enamandla ehamba nesichotho"}]},{"code":1273,"day":"Patchy light rain in area with thunder","night":"Patchy light rain in area with thunder","icon":386,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار خفيفة متفاوتة في المنطقة مع رعد","night_text":"أمطار خفيفة متفاوتة في المنطقة مع رعد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত হাল্কা বৃষ্টিপাত","night_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত হাল্কা বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби дъждове на отделни места в области с гръмотевици","night_text":"Слаби дъждове на отделни места в области с гръмотевици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"雷区有零星小雨","night_text":"雷区有零星小雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"雷區有零星小雨","night_text":"雷區有零星小雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"V oblasti bouřky místy slabý déšť","night_text":"V oblasti bouřky místy slabý déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke lichte regen in gebied met onweer","night_text":"Plaatselijke lichte regen in gebied met onweer"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Paikoittainen kevyt sade ukkosalueella","night_text":"Paikoittainen kevyt sade ukkosalueella"},{"lang_name":"French","lang_iso":"fr","day_text":"Légère pluie éparse avec tonnerre par endroit","night_text":"Légère pluie éparse avec tonnerre par endroit"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise leichter Regenfall mit Gewitter","night_text":"stellenweise leichter Regenfall mit Gewitter"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ασθενής βροχή στην περιοχή με βροντές","night_text":"Κατά τόπους ασθενής βροχή στην περιοχή με βροντές"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में गरज के साथ हल्की बारिश","night_text":"अलग-अलग इलाकों में गरज के साथ हल्की बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Foltokban enyhe eső mennydörgéssel, villámlással","night_text":"Foltokban enyhe eső mennydörgéssel, villámlással"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia debole a tratti in zona e tuoni","night_text":"Pioggia debole a tratti in zona e tuoni"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"所により雷を伴う弱い雨","night_text":"所により雷を伴う弱い雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan gludhuk ora deres ora rata ing area","night_text":"Udan gludhuk ora deres ora rata ing area"},{"lang_name":"Korean","lang_iso":"ko","day_text":"천둥을 동반한 지역 곳곳의 가벼운 비","night_text":"천둥을 동반한 지역 곳곳의 가벼운 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"雷区有零星小雨","night_text":"雷区有零星小雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"क्षेत्रात मेघगर्जनेसहित अनियमित हलकासा पाऊस","night_text":"क्षेत्रात मेघगर्जनेसहित अनियमित हलकासा पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, lekkie opady deszczu z grzmieniem w okolicy","night_text":"Miejscowe, lekkie opady deszczu z grzmieniem w okolicy"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva fraca irregular com trovoada","night_text":"Chuva fraca irregular com trovoada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਕਿਤੇ-ਕਿਤੇ ਹਲਕਾ ਮੀਂਹ","night_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਕਿਤੇ-ਕਿਤੇ ਹਲਕਾ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi în cantităţi mici pe porțiuni însoțite de tunete","night_text":"Ploi în cantităţi mici pe porțiuni însoțite de tunete"},{"lang_name":"Russian","lang_iso":"ru","day_text":"В отдельных районах местами небольшой дождь с грозой","night_text":"В отдельных районах местами небольшой дождь с грозой"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Povremena slaba lokalna kiša uz grmljavinu","night_text":"Povremena slaba lokalna kiša uz grmljavinu"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ප්රදේශයේ ගිගුරුම් සහිත තැනින් තැන සැහැල්ලු වර්ෂාව","night_text":"ප්රදේශයේ ගිගුරුම් සහිත තැනින් තැන සැහැල්ලු වර්ෂාව"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"V oblasti búrky miestami slabý dážď","night_text":"V oblasti búrky miestami slabý dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Intervalos de lluvias ligeras con tomenta en la región","night_text":"Intervalos de lluvias ligeras con tomenta en la región"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med lätt regn i område med åska","night_text":"Områden med lätt regn i område med åska"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பகுதியில் இடியுடன் சீரில்லாத இலேசான மழை","night_text":"பகுதியில் இடியுடன் சீரில்லாத இலேசான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"చెదురుమదురుగా ఉరుములతో తేలికపాటి వర్షం","night_text":"చెదురుమదురుగా ఉరుములతో తేలికపాటి వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel gök gürültülü düzensiz hafif yağmur","night_text":"Bölgesel gök gürültülü düzensiz hafif yağmur"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями невеликий дощ інколи з грозою","night_text":"Місцями невеликий дощ інколи з грозою"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"علاقے میں گھن گرج کے ساتھ ہلکی بارش","night_text":"علاقے میں گھن گرج کے ساتھ ہلکی بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa nhẹ lả tả trong khu vực có sấm sét","night_text":"Mưa nhẹ lả tả trong khu vực có sấm sét"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠雷咯地方撅部肖鱼","night_text":"悠雷咯地方撅部肖鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有雷的地方有零星小雨","night_text":"有雷的地方有零星小雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"雷區有零星小雨","night_text":"雷區有零星小雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engatheni lapha nalapha endaweni enokuduma kwezulu","night_text":"Imvula engatheni lapha nalapha endaweni enokuduma kwezulu"}]},{"code":1276,"day":"Moderate or heavy rain in area with thunder","night":"Moderate or heavy rain in area with thunder","icon":389,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"أمطار معتدلة أو شديدة في المنطقة مع رعد","night_text":"أمطار معتدلة أو شديدة في المنطقة مع رعد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত মাঝারি ও ভারী বৃষ্টিপাত","night_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত মাঝারি ও ভারী বৃষ্টিপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени или силни дъждове на отделни места в области с гръмотевици","night_text":"Умерени или силни дъждове на отделни места в области с гръмотевици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"雷区有中或大雨","night_text":"雷区有中或大雨"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"雷區有中或大雨","night_text":"雷區有中或大雨"},{"lang_name":"Czech","lang_iso":"cs","day_text":"V oblasti bouřky mírný nebo silný déšť","night_text":"V oblasti bouřky mírný nebo silný déšť"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware regen in gebied met onweer","night_text":"Normale of zware regen in gebied met onweer"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas tai rankka sade ukkosalueella","night_text":"Keskivoimakas tai rankka sade ukkosalueella"},{"lang_name":"French","lang_iso":"fr","day_text":"Pluie forte à modérée avec tonerre par endroit","night_text":"Pluie forte à modérée avec tonerre par endroit"},{"lang_name":"German","lang_iso":"de","day_text":"mäßiger bis starker Regenfall mit Gewitter","night_text":"mäßiger bis starker Regenfall mit Gewitter"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή βροχή στην περιοχή με βροντές","night_text":"Μέτρια ή ισχυρή βροχή στην περιοχή με βροντές"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में गरज के साथ सामान्य या जोरदार बारिश","night_text":"अलग-अलग इलाकों में गरज के साथ सामान्य या जोरदार बारिश"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A területen foltokban enyhe eső mennydörgéssel, villámlással","night_text":"A területen foltokban enyhe eső mennydörgéssel, villámlással"},{"lang_name":"Italian","lang_iso":"it","day_text":"Pioggia moderata o forte in zona e tuoni","night_text":"Pioggia moderata o forte in zona e tuoni"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"雷を伴う穏やかなまたは強い雨","night_text":"雷を伴う穏やかなまたは強い雨"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan gludhuk rada deres utawa deres ing area","night_text":"Udan gludhuk rada deres utawa deres ing area"},{"lang_name":"Korean","lang_iso":"ko","day_text":"천둥을 동반한 보통 또는 심한 비","night_text":"천둥을 동반한 보통 또는 심한 비"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"雷区有中或大雨","night_text":"雷区有中或大雨"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"क्षेत्रात मेघगर्जनेसहित मध्यम किंवा जोरदार पाऊस","night_text":"क्षेत्रात मेघगर्जनेसहित मध्यम किंवा जोरदार पाऊस"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, średnie lub ciężkie opady deszczu z grzmieniem w okolicy","night_text":"Miejscowe, średnie lub ciężkie opady deszczu z grzmieniem w okolicy"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Chuva moderada ou forte com trovoada","night_text":"Chuva moderada ou forte com trovoada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ","night_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਦਰਮਿਆਨਾ ਜਾਂ ਤੇਜ਼ ਮੀਂਹ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ploi în cantităţi mari şi moderate pe porțiuni însoțite de tunete","night_text":"Ploi în cantităţi mari şi moderate pe porțiuni însoțite de tunete"},{"lang_name":"Russian","lang_iso":"ru","day_text":"В отдельных районах умеренный или сильный дождь с грозой","night_text":"В отдельных районах умеренный или сильный дождь с грозой"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerena ili jaka kiša uz grmljavinu","night_text":"Umerena ili jaka kiša uz grmljavinu"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ප්රදේශයේ ගිගුරුම් සහිත මධ්යස්ථ හෝ තද වැසි","night_text":"ප්රදේශයේ ගිගුරුම් සහිත මධ්යස්ථ හෝ තද වැසි"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"V oblasti búrky mierny alebo silný dážď","night_text":"V oblasti búrky mierny alebo silný dážď"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Lluvias con tormenta fuertes o moderadas en la región","night_text":"Lluvias con tormenta fuertes o moderadas en la región"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt eller tungt regn i område med åska","night_text":"Måttligt eller tungt regn i område med åska"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பகுதியில் இடியுடன் மிதமான அல்லது கனமான மழை","night_text":"பகுதியில் இடியுடன் மிதமான அல்லது கனமான மழை"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఉరుములతో కూడిన మధ్యస్థం నుంచి తీవ్రంగా వర్షం","night_text":"ఉరుములతో కూడిన మధ్యస్థం నుంచి తీవ్రంగా వర్షం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel gök gürültülü orta kuvvetli veya şiddetli yağış","night_text":"Bölgesel gök gürültülü orta kuvvetli veya şiddetli yağış"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний або сильний дощ місцями з грозою","night_text":"Помірний або сильний дощ місцями з грозою"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"علاقے میں گھن گرج کے ساتھ معتدل یا شدید بارش","night_text":"علاقے میں گھن گرج کے ساتھ معتدل یا شدید بارش"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Mưa vừa hoặc nặng hạt trong khu vực có sấm sét","night_text":"Mưa vừa hoặc nặng hạt trong khu vực có sấm sét"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠雷咯地方中到斗落鱼","night_text":"悠雷咯地方中到斗落鱼"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有雷的地方有中到大雨","night_text":"有雷的地方有中到大雨"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"雷區有中或大雨","night_text":"雷區有中或大雨"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Imvula engatheni noma enamandla endaweni enokuduma kwezulu","night_text":"Imvula engatheni noma enamandla endaweni enokuduma kwezulu"}]},{"code":1279,"day":"Patchy light snow in area with thunder","night":"Patchy light snow in area with thunder","icon":392,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج خفيفة متفاوتة في المنطقة مع رعد","night_text":"ثلوج خفيفة متفاوتة في المنطقة مع رعد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত হাল্কা তুষারপাত","night_text":"এলাকায় বজ্রবিদ্যুত সহ অনিয়মিত হাল্কা তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Слаби снеговалежи на отделни места в области с гръмотевици","night_text":"Слаби снеговалежи на отделни места в области с гръмотевици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"雷区有零星小雪","night_text":"雷区有零星小雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"雷區有片狀小雪","night_text":"雷區有片狀小雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"V oblasti bouřky místy slabé sněžení","night_text":"V oblasti bouřky místy slabé sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Plaatselijke lichte sneeuw in gebied met onweer","night_text":"Plaatselijke lichte sneeuw in gebied met onweer"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Paikoittainen kevyt lumisade ukkosalueella","night_text":"Paikoittainen kevyt lumisade ukkosalueella"},{"lang_name":"French","lang_iso":"fr","day_text":"Légère neige éparse avec tonnerre par endroit","night_text":"Légère neige éparse avec tonnerre par endroit"},{"lang_name":"German","lang_iso":"de","day_text":"stellenweise leichter Schneefall mit Gewitter","night_text":"stellenweise leichter Schneefall mit Gewitter"},{"lang_name":"Greek","lang_iso":"el","day_text":"Κατά τόπους ασθενής χιονόπτωση στην περιοχή με βροντές","night_text":"Κατά τόπους ασθενής χιονόπτωση στην περιοχή με βροντές"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में गरज के साथ हल्की बर्फबारी","night_text":"अलग-अलग इलाकों में गरज के साथ हल्की बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"A területen foltokban enyhe havazás mennydörgéssel, villámlással","night_text":"A területen foltokban enyhe havazás mennydörgéssel, villámlással"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve debole a tratti in zona e tuoni","night_text":"Neve debole a tratti in zona e tuoni"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"雷を伴う軽い雪","night_text":"雷を伴う軽い雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju ora deres ora rata nganggo gludhuk ing area","night_text":"Udan salju ora deres ora rata nganggo gludhuk ing area"},{"lang_name":"Korean","lang_iso":"ko","day_text":"천둥을 동반한 지역 곳곳의 가벼운 눈","night_text":"천둥을 동반한 지역 곳곳의 가벼운 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"雷区有零星小雪","night_text":"雷区有零星小雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"क्षेत्रात मेघगर्जनेसहित अनियमित हलकासा बर्फ","night_text":"क्षेत्रात मेघगर्जनेसहित अनियमित हलकासा बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Miejscowe, lekkie opady śniegu z grzmieniem w okolicy","night_text":"Miejscowe, lekkie opady śniegu z grzmieniem w okolicy"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Neve fraca irregular com trovoada","night_text":"Neve fraca irregular com trovoada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਬਰਫ","night_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਕਿਤੇ-ਕਿਤੇ ਹਲਕੀ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi mici pe porțiuni însoțite de tunete","night_text":"Ninsori în cantităţi mici pe porțiuni însoțite de tunete"},{"lang_name":"Russian","lang_iso":"ru","day_text":"В отдельных районах местами небольшой снег с грозой","night_text":"В отдельных районах местами небольшой снег с грозой"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Mestimično slab sneg uz grmljavinu","night_text":"Mestimično slab sneg uz grmljavinu"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ප්රදේශයේ ගිගුරුම් සහිත තැනින් තැන සැහැල්ලු හිම","night_text":"ප්රදේශයේ ගිගුරුම් සහිත තැනින් තැන සැහැල්ලු හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"V oblasti búrky miestami slabé sneženie","night_text":"V oblasti búrky miestami slabé sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nieve moderada con tormenta en la región","night_text":"Nieve moderada con tormenta en la región"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Områden med lätt snöfall i område med åska","night_text":"Områden med lätt snöfall i område med åska"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பகுதியில் இடியுடன் சீரில்லாத இலேசான பனி","night_text":"பகுதியில் இடியுடன் சீரில்லாத இலேசான பனி"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఉరుములతో కూడిన చెదురుమదురుగా తేలికపాటి మంచు","night_text":"ఉరుములతో కూడిన చెదురుమదురుగా తేలికపాటి మంచు"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel gök gürültülü düzensiz hafif kar yağışlı","night_text":"Bölgesel gök gürültülü düzensiz hafif kar yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Місцями невеликий сніг інколи з грозою","night_text":"Місцями невеликий сніг інколи з грозою"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"علاقے میں گھن گرج کے ساتھ ہلکی برفباری","night_text":"علاقے میں گھن گرج کے ساتھ ہلکی برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết nhẹ lả tả trong khu vực có sấm sét","night_text":"Tuyết nhẹ lả tả trong khu vực có sấm sét"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠雷咯地方撅部肖削","night_text":"悠雷咯地方撅部肖削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有雷的地方有零星小雪","night_text":"有雷的地方有零星小雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"雷區有零星小雪","night_text":"雷區有零星小雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esingenamandla lapha nalapha endaweni enokuduma kwezulu","night_text":"Isichotho esingenamandla lapha nalapha endaweni enokuduma kwezulu"}]},{"code":1282,"day":"Moderate or heavy snow in area with thunder","night":"Moderate or heavy snow in area with thunder","icon":395,"languages":[{"lang_name":"Arabic","lang_iso":"ar","day_text":"ثلوج معتدلة أو شديدة في المنطقة مع رعد","night_text":"ثلوج معتدلة أو شديدة في المنطقة مع رعد"},{"lang_name":"Bengali","lang_iso":"bn","day_text":"এলাকায় বজ্রবিদ্যুত সহ মাঝারি ও ভারী তুষারপাত","night_text":"এলাকায় বজ্রবিদ্যুত সহ মাঝারি ও ভারী তুষারপাত"},{"lang_name":"Bulgarian","lang_iso":"bg","day_text":"Умерени или силни снеговалежи в области с гръмотевици","night_text":"Умерени или силни снеговалежи в области с гръмотевици"},{"lang_name":"Chinese Simplified","lang_iso":"zh","day_text":"雷区有中或大雪","night_text":"雷区有中或大雪"},{"lang_name":"Chinese Traditional","lang_iso":"zh_tw","day_text":"雷區有中或大雪","night_text":"雷區有中或大雪"},{"lang_name":"Czech","lang_iso":"cs","day_text":"V oblasti bouřky mírné nebo silné sněžení","night_text":"V oblasti bouřky mírné nebo silné sněžení"},{"lang_name":"Dutch","lang_iso":"nl","day_text":"Normale of zware sneeuw in gebied met onweer","night_text":"Normale of zware sneeuw in gebied met onweer"},{"lang_name":"Finnish","lang_iso":"fi","day_text":"Keskivoimakas tai rankka lumisade ukkosalueella","night_text":"Keskivoimakas tai rankka lumisade ukkosalueella"},{"lang_name":"French","lang_iso":"fr","day_text":"Neige éparse modérée à forte avec tonnerre par endroit","night_text":"Neige éparse modérée à forte avec tonnerre par endroit"},{"lang_name":"German","lang_iso":"de","day_text":"mäßiger bis starker Schneefall mit Gewitter","night_text":"mäßiger bis starker Schneefall mit Gewitter"},{"lang_name":"Greek","lang_iso":"el","day_text":"Μέτρια ή ισχυρή χιονόπτωση στην περιοχή με βροντές","night_text":"Μέτρια ή ισχυρή χιονόπτωση στην περιοχή με βροντές"},{"lang_name":"Hindi","lang_iso":"hi","day_text":"अलग-अलग इलाकों में गरज के साथ सामान्य या जोरदार बर्फबारी","night_text":"अलग-अलग इलाकों में गरज के साथ सामान्य या जोरदार बर्फबारी"},{"lang_name":"Hungarian","lang_iso":"hu","day_text":"Mérsékelt, vagy heves hózápor mennydörgéssel, villámlással","night_text":"Mérsékelt, vagy heves hózápor mennydörgéssel, villámlással"},{"lang_name":"Italian","lang_iso":"it","day_text":"Neve moderata o forte in zona e tuoni","night_text":"Neve moderata o forte in zona e tuoni"},{"lang_name":"Japanese","lang_iso":"ja","day_text":"雷を伴う穏やかなまたは強い雪","night_text":"雷を伴う穏やかなまたは強い雪"},{"lang_name":"Javanese","lang_iso":"jv","day_text":"Udan salju rada deres utawa deres ora rata nganggo gludhuk ing area","night_text":"Udan salju rada deres utawa deres ora rata nganggo gludhuk ing area"},{"lang_name":"Korean","lang_iso":"ko","day_text":"천둥을 동반한 보통 또는 눈","night_text":"천둥을 동반한 보통 또는 눈"},{"lang_name":"Mandarin","lang_iso":"zh_cmn","day_text":"雷区有中或大雪","night_text":"雷区有中或大雪"},{"lang_name":"Marathi","lang_iso":"mr","day_text":"क्षेत्रात मेघगर्जनेसहित मध्यम किंवा जोरदार बर्फ","night_text":"क्षेत्रात मेघगर्जनेसहित मध्यम किंवा जोरदार बर्फ"},{"lang_name":"Polish","lang_iso":"pl","day_text":"Średnie lub ciężkie opady śniegu z grzmieniem w okolicy","night_text":"Średnie lub ciężkie opady śniegu z grzmieniem w okolicy"},{"lang_name":"Portuguese","lang_iso":"pt","day_text":"Neve moderada ou forte com trovoada","night_text":"Neve moderada ou forte com trovoada"},{"lang_name":"Punjabi","lang_iso":"pa","day_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਬਰਫ","night_text":"ਗਰਜ ਵਾਲੇ ਇਲਾਕੇ ਵਿੱਚ ਦਰਮਿਆਨੀ ਜਾਂ ਤੇਜ਼ ਬਰਫ"},{"lang_name":"Romanian","lang_iso":"ro","day_text":"Ninsori în cantităţi mari şi moderate pe porțiuni însoțite de tunete","night_text":"Ninsori în cantităţi mari şi moderate pe porțiuni însoțite de tunete"},{"lang_name":"Russian","lang_iso":"ru","day_text":"В отдельных районах умеренный или сильный снег с грозой","night_text":"В отдельных районах умеренный или сильный снег с грозой"},{"lang_name":"Serbian","lang_iso":"sr","day_text":"Umerene ili jake snežne padavine uz grmljavinu","night_text":"Umerene ili jake snežne padavine uz grmljavinu"},{"lang_name":"Sinhalese","lang_iso":"si","day_text":"ප්රදේශයේ ගිගුරුම් සහිත මධ්යස්ථ හෝ දැඩි හිම","night_text":"ප්රදේශයේ ගිගුරුම් සහිත මධ්යස්ථ හෝ දැඩි හිම"},{"lang_name":"Slovak","lang_iso":"sk","day_text":"V oblasti búrky mierne alebo silné sneženie","night_text":"V oblasti búrky mierne alebo silné sneženie"},{"lang_name":"Spanish","lang_iso":"es","day_text":"Nieve moderada o fuertes nevadas con tormenta en la región","night_text":"Nieve moderada o fuertes nevadas con tormenta en la región"},{"lang_name":"Swedish","lang_iso":"sv","day_text":"Måttligt eller tungt snöfall i område med åska","night_text":"Måttligt eller tungt snöfall i område med åska"},{"lang_name":"Tamil","lang_iso":"ta","day_text":"பகுதியில் இடியுடன் மிதமான அல்லது கனமான பனி","night_text":"பகுதியில் இடியுடன் மிதமான அல்லது கனமான பனி"},{"lang_name":"Telugu","lang_iso":"te","day_text":"ఉరుములతో మధ్యస్థం నుంచి తీవ్రంగా హిమపాతం","night_text":"ఉరుములతో మధ్యస్థం నుంచి తీవ్రంగా హిమపాతం"},{"lang_name":"Turkish","lang_iso":"tr","day_text":"Bölgesel gök gürültülü orta kuvvetli veya yoğun kar yağışlı","night_text":"Bölgesel gök gürültülü orta kuvvetli veya yoğun kar yağışlı"},{"lang_name":"Ukrainian","lang_iso":"uk","day_text":"Помірний або сильний сніг місцями з грозою","night_text":"Помірний або сильний сніг місцями з грозою"},{"lang_name":"Urdu","lang_iso":"ur","day_text":"علاقے میں گھن گرج کے ساتھ معتدل یا شدید برفباری","night_text":"علاقے میں گھن گرج کے ساتھ معتدل یا شدید برفباری"},{"lang_name":"Vietnamese","lang_iso":"vi","day_text":"Tuyết vừa hoặc nặng hạt trong khu vực có sấm sét","night_text":"Tuyết vừa hoặc nặng hạt trong khu vực có sấm sét"},{"lang_name":"Wu (Shanghainese)","lang_iso":"zh_wuu","day_text":"悠雷咯地方中到斗落削","night_text":"悠雷咯地方中到斗落削"},{"lang_name":"Xiang","lang_iso":"zh_hsn","day_text":"有雷的地方有中到大雪","night_text":"有雷的地方有中到大雪"},{"lang_name":"Yue (Cantonese)","lang_iso":"zh_yue","day_text":"雷區有中或大雪","night_text":"雷區有中或大雪"},{"lang_name":"Zulu","lang_iso":"zu","day_text":"Isichotho esingatheni noma esinamandla endaweni enokuduma kwezulu","night_text":"Isichotho esingatheni noma esinamandla endaweni enokuduma kwezulu"}]}]
\ No newline at end of file diff --git a/wolfram.js b/wolfram.js new file mode 100644 index 0000000..35c2398 --- /dev/null +++ b/wolfram.js @@ -0,0 +1,23 @@ +(async () => { + try { + const translatte = require('translatte'); + const axios = require('axios'); + const fs = require('fs'); + + let input = Buffer.from(process.argv[2], 'base64').toString(); + let w_in = (await translatte(input, {from: 'fr', to: 'en'})).text; + let key = fs.readFileSync("./wolframkey").toString(); + let response = (await axios.get(`https://api.wolframalpha.com/v1/result?appid=${key}&i=${encodeURI(w_in)}&units=metric&timeout=10`)).data + let w_out = (await translatte(response, {from: 'en', to: 'fr'})).text; + + console.log(w_out.replace(/([0-9]+)\.([0-9]+)/gm, "$1,$2")); + process.exit(); + } catch (e) { + if (e.message === "Request failed with status code 501") { + process.exit(5); + } else { + console.log("Désolé, je ne parviens pas à accéder à Internet en ce moment. Vérifiez que votre appareil dispose d'une connexion Internet stable et réessayez."); + process.exit(); + } + } +})()
\ No newline at end of file |