123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247 |
- // Светофор
- // Используя асинхронную функцию и бесконечный цикл, просимулируйте светофор:
- // Для отображения включения того или иного света используйте один или три DOM-элемента.
- // Stage 2
- // Сделайте trafficLight более универсальной - добавьте в параметры DOM-элемент для отображения, а так же время
- // работы каждого цвета
- traffic_light: {
- const delay = ms => new Promise(ok => setTimeout(() => ok(ms), ms));
- let trafficLightEl = document.createElement('div');
- document.body.append(trafficLightEl);
- trafficLightEl.classList.add('traffic-light');
- let red = document.createElement('div');
- trafficLightEl.append(red);
- red.classList.add('cell');
- let yellow = document.createElement('div');
- trafficLightEl.append(yellow);
- yellow.classList.add('cell');
- let green = document.createElement('div');
- trafficLightEl.append(green);
- green.classList.add('cell');
- async function trafficLight(greenEl, yellowEl, redEl, greenTime, yellowTime, redTime) {
- while (true) {
- greenEl.classList.add('green');
- await delay(greenTime);
- greenEl.classList.remove('green');
- yellowEl.classList.add('yellow');
- await delay(yellowTime);
- yellowEl.classList.remove('yellow');
- redEl.classList.add('red');
- await delay(redTime);
- redEl.classList.remove('red');
- }
- }
- trafficLight(green, yellow, red, 6000, 1000, 6000);
- }
- // PedestrianTrafficLight
- // Напишите упрощенный светофор для пешеходов
- // Stage 2
- // Используя Promise.race, domEventPromise и кнопку в DOM сделайте пешеходный светофор с кнопкой, который так
- // же переключается по времени периодически.
- // Stage 3
- // Не давайте возможности пешеходам сильно наглеть - предусмотрите задержку, после которой будет работать
- // кнопка.
- pedestrian_traffic_light: {
- const delay = ms => new Promise(ok => setTimeout(() => ok(ms), ms));
- let pedestrianTrafficLightEl = document.createElement('div');
- document.body.append(pedestrianTrafficLightEl);
- pedestrianTrafficLightEl.classList.add('traffic-light');
- let red = document.createElement('div');
- pedestrianTrafficLightEl.append(red);
- red.classList.add('cell');
- let green = document.createElement('div');
- pedestrianTrafficLightEl.append(green);
- green.classList.add('cell');
- let button = document.createElement('button');
- button.innerText = 'switch';
- document.body.append(button);
- function domEventPromise(element, eventName) {
- function executor(resolve) {
- function myEvent(event) {
- element.disabled = true;
- element.removeEventListener(eventName, myEvent);
- setTimeout(() => resolve(event), 2000);
- }
- element.disabled = false;
- element.addEventListener(eventName, myEvent)
- }
- return new Promise(executor);
- }
- async function pedestrianTrafficLight(ms) {
- while (true) {
- red.classList.add('red');
- await Promise.race([
- delay(ms),
- domEventPromise(button, 'click')
- ]);
- red.classList.remove('red');
- green.classList.add('green');
- await delay(ms);
- green.classList.remove('green');
- }
- }
- pedestrianTrafficLight(6000);
- }
- // speedtest
- // Написать асинхронную функцию, где:
- // count - количество повторов
- // parallel - количество одновременных запросов/промисов в одном повторе
- // getPromise - функция, которая умеет вернуть нужный Вам промис для тестирования скорости его работы
- // которая будет в цикле count раз создавать parallel промисов с помощью переданной функции getPromise,
- // дожидаться выполнения всех parallel промисов, после чего цикл повторяется.
- // Замерить время общее время выполнения, и вычислить:
- // duration, общую длительность работы цикла
- // parallelDuration, среднее время обработки запроса параллельно (за какое время исполнилось parallel*count
- // промисов),
- // paralledSpeed, скорость в запросах в миллисекунду
- // queryDuration, реальное среднее время запроса (отталкиваясь от count и времени работы цикла).
- // querySpeed, реальное средняя скорость запроса
- // Эти переменные вернуть в одном объекте-результате (см. заготовку выше)
- // Для отладки попробуйте на delay (пример выше есть, реальное время будет отличаться на единицы-десятки
- // миллисекунд). Потом можете попробовать на swapi.dev. Не создавайте чрезмерно много параллельных запросов.
- speedtest: {
- const delay = ms => new Promise(ok => setTimeout(() => ok(ms), ms));
- function makeProfileTimer() {
- let t0 = performance.now();
- return function () {
- let t1 = performance.now();
- return t1 - t0;
- }
- }
- async function speedtest(getPromise, count, parallel = 1) {
- let timer = makeProfileTimer();
- for (let i = 0; i < count; i++) {
- let promises = [];
- for (let j = 0; j < parallel; j++) {
- promises.push(getPromise());
- }
- console.log(await Promise.all(promises));
- }
- let duration = timer();
- let parallelDuration = duration / (count * parallel);
- let parallelSpeed = 1 / parallelDuration;
- let queryDuration = duration / count;
- let querySpeed = 1 / queryDuration;
- return {
- duration,
- querySpeed, //средняя скорость одного запроса
- queryDuration, //
- parallelSpeed,
- parallelDuration
- }
- }
- speedtest(() => delay(1000), 10, 10).then(result => console.log(result));
- // {duration: 10000,
- // querySpeed: 0.001, //1 тысячная запроса за миллисекунду
- // queryDuration: 1000, //1000 миллисекунд на один реальный запрос в среднем
- // parallelSpeed: 0.01 // 100 запросов за 10000 миллисекунд
- // parallelDuration: 100 // 100 запросов за 10000 миллисекунд
- speedtest(() => fetch('http://swapi.dev/api/people/1').then(res => res.json()), 10, 5).then(result => console.log(result));
- }
- // gql
- // Напишите функцию gql, которая осуществляет GraphQL запрос. Функция принимает три параметра:
- // Эндпоинт - адрес сервера. Например "http://shop-roles.node.ed.asmer.org.ua/graphql"
- // Текст запроса (query).
- // Параметры(переменные) (variables) запроса объектом
- // Функция должна возвращать промис, созданный fetch со следующими настройками:
- // Метод POST
- // Заголовки:
- // Content-Type - application/json
- // Accept- application/json
- // Тело - JSON, объект с двумя ключами - query (текст запроса) и variables
- gql: {
- function gql(endpoint, query, variables) {
- return fetch(endpoint, {
- method: 'POST',
- headers: {
- 'Content-Type': 'application/json',
- 'Accept': 'application/json'
- },
- body: JSON.stringify({
- query,
- variables
- }),
- }).then(response => response.json());
- }
- (async () => {
- const catQuery = `query cats($q: String){
- CategoryFind(query: $q){
- _id name
- }
- }`
- const cats = await gql("http://shop-roles.node.ed.asmer.org.ua/graphql", catQuery, { q: "[{}]" })
- console.log(cats) //список категорий с _id name и всем таким прочим
- const loginQuery = `query login($login:String, $password:String){
- login(login:$login, password:$password)
- }`
- const token = await gql("http://shop-roles.node.ed.asmer.org.ua/graphql", loginQuery, { login: "test457", password: "123123" })
- console.log(token)
- })()
- }
- // jwtDecode
- // Напишете функцию jwtDecode, которая принимает единственный параметр token и возвращает информацию из
- // переданного JWT токена.
- // Алгоритм раскодирования:
- // Разбить токен на три части. Разделитель - . (точка)
- // Выделить среднюю часть.
- // Используя функцию atob раскодировать среднюю часть из кодировки Base64, получив JSON
- // Раскодировать JSON
- // Вернуть раскодированные данные из JSON
- // Учтите, что в качестве токена может быть передана какая-то дичь. В таком случае раскодировка не получится,
- // и функция:
- // Не должна сыпать красными матюками (ошибками) в консоль
- // Должна просто вернуть undefined
- jwtDecode: {
- const token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOnsiaWQiOiI2MzIyMDVhZWI3NGUxZjVmMmVjMWEzMjAiLCJsb2dpbiI6InRlc3Q0NTciLCJhY2wiOlsiNjMyMjA1YWViNzRlMWY1ZjJlYzFhMzIwIiwidXNlciJdfSwiaWF0IjoxNjY4MjcyMTYzfQ.rxV1ki9G6LjT2IPWcqkMeTi_1K9sb3Si8vLB6UDAGdw";
- function jwtDecode(token) {
- let result;
- try {
- let mediumStr = token.split('.')[1];
- result = JSON.parse(atob(mediumStr));
- } catch (e) {
- }
- return result;
- }
- console.log(jwtDecode(token));
- //{
- // "sub": {
- // "id": "632205aeb74e1f5f2ec1a320",
- // "login": "test457",
- // "acl": [
- // "632205aeb74e1f5f2ec1a320",
- // "user"
- // ]
- // },
- // "iat": 1668272163
- //}
- try {
- console.log(jwtDecode()); //undefined
- console.log(jwtDecode("дичь")); //undefined
- console.log(jwtDecode("ey.ey.ey")); //undefined
- console.log('до сюда доработало, а значит jwtDecode не матерился в консоль красным цветом');
- }
- finally {
- console.log('ДЗ, видимо, окончено');
- }
- }
|