├── README.md ├── interview ├── README.md ├── README_QA.md ├── database.md ├── frontend.md ├── git.md ├── images │ └── sklad.jpg ├── interview_questions.md ├── other.md ├── programming_oop.md ├── rails.md ├── ruby.md ├── spec.md ├── tasks.md └── webdev.md └── test_assignments ├── README.md ├── SQL_find_max_score.md ├── SQL_query_for_users.md ├── app_for_managing_people_list.md ├── app_with_page_hierarchy.md ├── app_with_self_destructing_text_messages.md ├── appointments_management_system.md ├── automated_collection_of_active_forum_users.md ├── automated_keyword_search.md ├── automated_unread_messages_checking.md ├── automated_user_data_collection.md ├── billing_system.md ├── calculating_bot_for_telegram.md ├── clinic_management_system.md ├── count_html_tags_by_url.md ├── credit_card_checker.md ├── csv_ascii_converter.md ├── currency_exchange_rails_api.md ├── database_structure_for_shops.md ├── grape_markets_list_app.md ├── import_commits_app.md ├── import_commits_from_github.md ├── import_script_csv_to_psql.md ├── job_advertisement_site.md ├── json_api_for_blog.md ├── json_api_service_without_rails.md ├── lunch_ordering_saas.md ├── meals_delivery_service.md ├── news_site_API.md ├── oblako_group_test_app.md ├── pdf_diploma_generator.md ├── player_statistics.md ├── price_list_export_algorithms_for_marketplace.md ├── prototype_for_car_hiring_system.md ├── rails_api_for_real_estate_site.md ├── rest_api_for_blog.md ├── restaurants_with_tables.md ├── ror_api_reference_counting.md ├── shop_dashboard.md ├── shop_with_checkout.md ├── simple_to_do_list.md ├── solving_mathematical_equations_app.md ├── task_manager_with_authentication.md ├── telegram_bot_sticker_png.md ├── totalizator.md ├── url_shortener_app.md ├── video_view_statistics_service.md ├── weather_statistics_api.md └── web_panel_for_users_control.md /README.md: -------------------------------------------------------------------------------- 1 | # Что это? 2 | 3 | Roadmap или карта знаний современного web-программиста и список рекомендуемой литературы. 4 | 5 | А также список [типичных вопросов](interview/README.md) и [тестовых заданий](test_assignments/README.md) с собеседований Rails разработчика и [тестировщика](interview/README_QA.md). 6 | 7 | Сделано и развивается при поддержке начинающих программистов в телеграм чате [@rubyrush](https://t-do.ru/rubyrush) 👍 8 | 9 | _Оригинал здесь: https://github.com/aristofun/webdevdao_ 10 | 11 | ## Базовые навыки 12 | 13 | - **Математика** 14 | 15 | + Выбирайте из первых курсов ВУЗа любую понятную вам книгу, или понятный вам курс по темам *Алгебра*, *Линейная алгебра*, *Дискретная математика*. 16 | 17 | - **Computer science** 18 | 19 | + МакКонелл "Анализ алгоритмов" отличная обучающая книга для понимания основ 20 | 21 | http://www.technosphera.ru/lib/book/8 22 | 23 | https://books.google.com/books?id=mW4S0AHFKrAC&source=gbs_book_other_versions 24 | 25 | + Математические основы информатики от отцов (в печатном виде на русском не достать, но можно нагуглить в эл. виде скан) 26 | 27 | https://ru.wikipedia.org/wiki/Конкретная_математика 28 | 29 | + Адитья Бхаргава "Грокаем алгоритмы" - возможно, лучшая книжка для старта познания алгоритмов (очень простым и понятным языком; можно нагуглить, но лучше печатный вариант) 30 | 31 | + Курсы по алгоритмам: 32 | 33 | https://www.coursera.org/learn/algorithms-part1 34 | 35 | https://www.coursera.org/learn/analysis-of-algorithms 36 | 37 | + Чарльз Петцольд "Код" (беллетристика про устройство компьютера для всех) 38 | 39 | https://www.litres.ru/charlz-petcold/kod-taynyy-yazyk-informatiki/ 40 | 41 | - **Воображение** 42 | 43 | + Косвенно хорошо развивается математикой, программированием, рисованием, изучением языков. Причем практикой всего этого а не чтением книг. 44 | 45 | + Перельман и все его книги серии "Занимательная..." (прежде всего занимательная физика, занимательная математика, занимательная арифметика) 46 | 47 | https://ru.wikipedia.org/wiki/Перельман,_Яков_Исидорович 48 | 49 | - **Соображалка** 50 | 51 | + Книги Мартина Гарднера полны интересных задач и остроумной математики (Математические головоломки и развлечения, Математические досуги, Математические новеллы и т. д.) 52 | 53 | https://ru.wikipedia.org/wiki/Гарднер,_Мартин 54 | 55 | + Рэймонд Смаллиан менее известен, чем Гарднер, но тоже хорош 56 | 57 | https://ru.wikipedia.org/wiki/Смаллиан,_Рэймонд_Меррилл 58 | 59 | + Книга об остроумных задачах для программистов на собеседованиях 60 | 61 | http://www.litres.ru/uilyam-paundstoun/nayti-umnogo-kak-proverit-logicheskoe-myshlenie-i-tvorcheskie-sposobnosti-kandidata-2/?lfrom=14517722 62 | 63 | https://www.amazon.com/How-Would-Move-Mount-Fuji/dp/0316778494 64 | 65 | + Хорошая книга о математических парадоксах и взгляде на мир 66 | 67 | https://www.livelib.ru/book/1000964673-son-razuma-matematicheskaya-logika-i-ee-paradoksy-haver-fresan 68 | 69 | - **Культура программирования** 70 | 71 | + Для уже работающих программистов 72 | 73 | http://www.litres.ru/stiv-makkonnell/sovershennyy-kod-prakticheskoe-rukovodstvo-po-razrabotke-programmnogo-obespecheniya/?lfrom=14517722 74 | 75 | + Мартин Фаулер "Рефакторинг" — **обязательна к прочтению** после полугода работы программистом (ищите в эл. виде или англ. версию) 76 | 77 | https://www.ozon.ru/context/detail/id/1308678/ 78 | 79 | + Курсы хорошего программиста 80 | 81 | https://goo.gl/jIKpgW 82 | 83 | + Для программистов от 1 года работы: Кент Бек "Test driven development" (есть перевод) 84 | 85 | https://www.amazon.com/Test-Driven-Development-Kent-Beck/dp/0321146530 86 | 87 | + Роберт К. Мартин "Чистый код. Создание, анализ и рефакторинг. Библиотека программиста" 88 | 89 | https://www.ozon.ru/context/detail/id/142429922/ 90 | 91 | - **Проектирование и ООП** 92 | 93 | + Грэди Буч "ОО анализ и дизайн", **обязательна к прочтению**, основополагающая книга 94 | 95 | http://www.helloworld.ru/texts/comp/other/oop/ch01.htm 96 | 97 | Статья по алгоритмам и структурам данных (примеры на JavaScript). 98 | 99 | https://dou.ua/lenta/articles/what-you-should-know-about-algorithms/?utm_source=dlvr.it&utm_medium=linkedin 100 | 101 | - **REST** архитектура 102 | 103 | + https://www.youtube.com/watch?v=IB1IhWbgOws 104 | 105 | - **Git, GitHub** 106 | 107 | + Толковые ссылки для начинающих: 108 | 109 | https://git-scm.com/book/ru/v1/Введение 110 | 111 | http://rgblog.ru/page/git-dlja-chajnika-komandy-kotorye-pomogut-nachat-rabotu 112 | 113 | https://habrahabr.ru/post/123111/ 114 | 115 | + Интерактивная обучалка 116 | 117 | http://learngitbranching.js.org 118 | 119 | ## Frontend 120 | 121 | - **HTML/CSS** 122 | 123 | + Книга 124 | 125 | http://www.litres.ru/erik-frimen/izuchaem-html-xhtml-i-css-8511974/?lfrom=14517722 126 | 127 | + Справочник с примерами 128 | 129 | http://htmlbook.ru/html 130 | 131 | https://devdocs.io/ 132 | 133 | + Learn CSS Layout 134 | 135 | http://learnlayout.com 136 | 137 | - **JS (JavaScript)** 138 | 139 | + Хорошая книга для начинающих 140 | 141 | https://karmazzin.gitbooks.io/eloquentjavascript_ru/content/ 142 | 143 | http://eloquentjavascript.net 144 | 145 | https://learn.javascript.ru/ 146 | 147 | + Хорошая книга для продолжающих 148 | 149 | https://github.com/getify/You-Dont-Know-JS 150 | 151 | ## Backend 152 | 153 | 154 | - **Ruby, Ruby on Rails** 155 | 156 | + Лучший онлайн туториал для самостоятельного изучения 157 | 158 | http://railstutorial.org 159 | 160 | + Коллекция отличных скринкастов (частично устаревшая) 161 | 162 | http://railscasts.com 163 | 164 | + Онлайн-интенсив «Хорошего программиста» 165 | 166 | https://goo.gl/w5BZkM 167 | 168 | + Онлайн-справочник всех языков программирования 169 | 170 | https://devdocs.io/rails~5.2/ 171 | 172 | https://devdocs.io/ruby~2.5/ 173 | 174 | + Онлайн-курс по Ruby (Eng). 175 | 176 | https://leetcode.com/explore/learn/card/become-a-web-developer/ 177 | 178 | + Игорь Симдянов: Самоучитель Ruby - возможно, одна из лучших книжек для начала, поможет построить прочную базу знаний по Ruby 179 | 180 | + Фултон, Арко: Путь Ruby (в печатном виде, но лучше нагуглить) - хорошая книга для начинающих и продолжающих, чтобы заполнить пробелы по Ruby 181 | 182 | - **Python/Django** 183 | 184 | Среди питонистов нет единства в том, какие ресурсы считать лучшими, поэтому ниже ссылки с наиболее авторитетными мнениями: 185 | 186 | + https://www.quora.com/Which-is-the-best-book-for-learning-python-for-absolute-beginners-on-their-own 187 | 188 | + http://www.codepancake.com/5-python-books-for-beginners/ 189 | 190 | + https://stackoverflow.com/questions/4048973/whats-the-best-way-to-start-learning-django 191 | 192 | + https://www.quora.com/What-are-the-resources-to-learn-Django 193 | 194 | + https://devdocs.io/python~3.7/ 195 | 196 | 197 | - **NodeJS** 198 | 199 | Хороших курсов и книг практически нет (при выходе, они сразу устаревают), основа работы с нодой — хорошее знание JavaScript (выше ссылки) + практический опыт работы с ним (знание лучших практик и приемов). 200 | 201 | + https://www.quora.com/What-is-the-best-Node-js-course-online 202 | 203 | + https://www.quora.com/What-are-the-best-resources-for-learning-Node-js 204 | 205 | + https://devdocs.io/node/ 206 | 207 | - **PHP** 208 | 209 | Учить пхп мы не советуем вообще, поэтому приведем только одну ссылку, которую вы должны изучать постоянно, если все-таки отважились на этот отчаянный шаг: 210 | 211 | + http://www.phptherightway.com 212 | 213 | ## Базы данных 214 | 215 | Приведем ссылки на вики и оф. сайты, где есть хорошие руководства по установке и использованию (их нужно читать внимательно). Все, что глубже вам надо искать самому *после* того как обрастете опытом программирования. 216 | 217 | - https://ru.wikipedia.org/wiki/Система_управления_базами_данных 218 | 219 | - https://ru.wikipedia.org/wiki/Реляционная_база_данных 220 | 221 | - https://www.postgresql.org 222 | 223 | - https://ru.wikipedia.org/wiki/NoSQL 224 | 225 | - https://redis.io 226 | 227 | - https://www.w3schools.com/sql/default.asp 228 | 229 | ## DevOps (сисадминство и настройка) 230 | 231 | - Книга [How Linux works](https://books.google.rs/books/about/How_Linux_Works.html?id=wOGUuoHUyAEC&printsec=frontcover&source=kp_read_button&redir_esc=y#v=onepage&q&f=false) 232 | 233 | Скринкасты о простой настройке linux серверов и деплое приложений, не исчерпывающая информация, но хороший старт: 234 | 235 | - https://www.youtube.com/watch?v=aJLRnDJ2CVg 236 | 237 | - https://www.youtube.com/watch?v=vY9QNwX_IsY 238 | 239 | - https://www.youtube.com/watch?v=tQLpAefAKuA 240 | 241 | ## Изучение Английского языка 242 | 243 | - Поиск перевода на английский в контексте для русских слов, выражений и идиом 244 | 245 | http://context.reverso.net 246 | 247 | - Английский язык по плейлистам 248 | 249 | https://www.youtube.com/channel/UC_3oKG5Szq-m6Xz-MjRZgpw 250 | 251 | # PS 252 | 253 | Эти материалы и ссылки взяты из уроков онлайн-интенсива по web разработке на Ruby on Rails «Хорошего программиста» — [goodprogrammer.ru](https://goodprogrammer.ru) 254 | 255 | Список не претендует на универсальность, дополнения и поправки присылайте пулл-реквестами. 256 | -------------------------------------------------------------------------------- /interview/README.md: -------------------------------------------------------------------------------- 1 | # Собеседование Ruby on Rails разработчика 2 | 3 | Ссылка на этот список: https://git.io/fh8Rb 4 | 5 | Вопросы, которые вам могут задать, на которые идеально знать ответ. Уверен, чего-то из этого вы не знаете, поэтому можно почитать материалы на эту тему. С другой стороны, ни в коем случае не ждите дня, когда все это будет отскакивать у вас от зубов. Начинайте искать работу, когда можете ответить на 75% списка. 6 | 7 | 1. [Программирование и ООП](programming_oop.md) 8 | 1. [Ruby](ruby.md) 9 | 1. [Ruby on Rails](rails.md) 10 | 1. [Веб-разработка](webdev.md) 11 | 1. [Тесты, тестирование](spec.md) 12 | 1. [JavaScript, HTML, CSS, фронтенд](frontend.md) 13 | 1. [Git](git.md) 14 | 1. [Базы данных](database.md) 15 | 1. [Другие вопросы](other.md) 16 | 1. [Задачи](tasks.md) 17 | 1. [Список вопросов на собеседованиях по разным темам и языкам (Eng.) ](interview_questions.md) 18 | 19 | ### Дисклеймер 20 | 21 | Как список вопросов, так и ответы на вопросы собираются сообществом студентов и выпускников нашего интенсива по Ruby on Rails. Эти вопросы задавали им на собеседованиях. 22 | 23 | * Хотите добавить вопрос, который задавали вам — присылайте PR 24 | * С вашей точки зрения вопрос сформулирован неудачно — присылайте PR 25 | * Знаете ответ на вопрос, на который в этом списке ещё нет ответа — присылайте PR 26 | * Увидели неточность в ответе — присылайте PR 27 | * Прочитали ответ на вопрос и считаете, что можете ответить лучше и понятнее — присылайте PR 28 | * Нашли опечатку, неправильное форматирование или стилистическую ошибку — присылайте PR 29 | 30 | Практика показала, что те, кто присылали пул-реквесты в этот репозиторий, устроились на работу Ruby on Rails разработчиками. 31 | 32 | ### Как прислать PR 33 | 34 | 1. По-взрослому: форкнуть наш репозиторий, сделать в своем репозитории отдельную ветку, потом прислать pull-request на слияние нашего мастера с вашей веткой. 35 | 2. По-простому: справа сверху в любом из файлов нажать на карандашик (форк будет создан автоматически), отредактировать файл и отправить PR нажав кнопку в форме редактирования снизу. 36 | 37 | ### Форматирование 38 | 39 | Для форматирования используется [Github Flavoured Markdown](https://guides.github.com/features/mastering-markdown/). 40 | 41 | Каждый вопрос начинайте с цифры 1. 42 | 43 | 1. Как загрузить удаленный репозиторий? 44 | 45 | Названия переменных, методов, классов и т.д. оборачивайте в грависы: 46 | 47 | 1. Чем отличается `each` от `map` ? 48 | 49 | Чтобы оформить ответ, используйте `
` с отступом 4 пробела и вложенный в него `` с отступом 4 + 2 = 6 пробелов: 50 | 51 | 52 | ``` 53 | 1. Чем отличается `each` от `map` ? 54 | 55 |
56 | Ответ 57 | `each` занимается просто перебором, `map` занимается перебором и конечным выводом измененного массива, также можно `map` вызвать с помощью bang-меттода для изменения исходного массива. 58 |
59 | ``` 60 | 61 | Если в ответ надо пихнуть список, добавьте пустую строку после `Ответ` 62 | 63 | ``` 64 | 1. Как удалить ветку локально и с удаленного репозитория? 65 | 66 |
67 | Ответ 68 | 69 | * `git branch -d new-branch` 70 | * `git branch -d origin new-branch` 71 | * `git push origin :new-branch` 72 |
73 | ``` 74 | -------------------------------------------------------------------------------- /interview/README_QA.md: -------------------------------------------------------------------------------- 1 | # Путь Тестировщика 2 | 3 | Наверное лучший путь для вкатки в IT, это изучение английского языка. 4 | 5 | Уровни программистов, и что нужно уметь и знать на каждом уровне: 6 | https://docs.google.com/spreadsheets/d/18FIkoJ4OTCj9wIh8GkmeFS0Lb40yKuhFMNbcxYze44s/edit#gid=789031646 7 | 8 | Тестирование, что нужно знать: 9 | Наверное лучший путь для вкатки в IT, это изучение английского языка перед изучением языка программирования. 10 | 11 | Тестирование можно и нужно начинать с теории. Тестирование различают по нескольким форматам так сказать, можно конечно совмещать, но сначала лучше определиться с чем-то одним - веб, мобильное, нагрузочное, перфоманс тестирование и прочие. 12 | Неплохо знать линукс, консоль. Если это Windows, то разработка на Ruby будет проблематичной. В основном на C#, Java или Python. На Ubuntu, можно работать с любым языком программирования (c C# полноценно не получится). Если разбираться с консолью unix подобных систем, то в основном юзают Ubuntu/Mac, они более удобны для разработки/тестирования. Многие сервера настроены так же на Ubuntu. 13 | 14 | Мобильное тестирвоание это свежее и интересное направление, то есть тестирование производится на разных гаджетах. Языки программирования, можно использовать в принципе любые для мобильного тестирования, не обязательно изучать только java для android, либо swift для ios. Языки Python и Ruby, отлично подойдут для мобильного тестирования. Есть инструмент, http://appium.io/, который позволяет писать тесты для мобильных устройств, на таких языках, как Node.js, Python, PHP, Ruby, Java. 15 | 16 | Дальше зависит от того, какой язык программирования Вы знаете, чтобы можно претендовать на автоматизатора тестирования, либо если языки программирования не знаете, то нужно начать с ручного тестирования. Можно работать и набивать руку по составлению документации, тест-кейсов, понимать жизненный цикл бага, получать небольшую ЗП и уже изучать автоматизацию. Есть основные языки автоматизации, это Java, Python, Ruby и работы больше конечно же в больших городах. 17 | 18 | ## Ручное тестирование 19 | 20 | Первая книга, наверное с которой стоит начать это - Книги Романа Савина ( Тестирование ком ) , Святослава Куликова ( Тестирование программного обеспечения ). 21 | Они уже устарели, но они же помогают понять, что такое тестирование. 22 | 23 | Это общий сайт, где много теории, но на английском: 24 | https://www.guru99.com/mobile-testing.html 25 | 26 | В тестировании очень любят спрашивать, как работает интернет 27 | Что такое HTTP: 28 | https://ru.hexlet.io/courses/http_protocol 29 | https://guides.hexlet.io/https-yandex-guide/ 30 | https://www.youtube.com/watch?v=DpWNiMtIsr8 31 | 32 | Как работает интернет: 33 | https://www.youtube.com/watch?v=rfexQ2QyD4I 34 | 35 | Как работает DNS: 36 | https://howdns.works/ep1/ 37 | 38 | Компьютерные сети | Таненбаум Эндрю, Уэзеролл Дэви 39 | https://www.ozon.ru/context/detail/id/135726580/ 40 | 41 | Сразу можно пройти бесплатный курс и получить сертификат по тестированию, начального уровня, очень советую https://stepik.org/course/58743 ( если он доступен, бывает что авторы закрывают ) 42 | Автор, работает в Яндексе. Он очень четко и понятно объясняет что и как, прям с самых-самых азов. 43 | 44 | Так же очень интересный и полезный курс от mail - https://www.youtube.com/watch?v=3MBT9O6i0jk&list=PLrCZzMib1e9pDKLsabJYuODdVJrHYc4Jd 45 | 46 | Полезный курс теории от ITVDN - https://www.youtube.com/watch?v=7EyX8n2Mb1A&list=PLvItDmb0sZw8npbYThWpZs5_cZU9ycos4 47 | 48 | Нужны азы работы с базой данных, к примеру sql либо postgres. В зависимости от работы и написания разных автотестов, рубисты немного халявят, так как у нас есть очень удобный ActiveRecord. Неплохой вводный и бесплатный курс - https://www.youtube.com/watch?v=yOkj-PbCPQ8&list=PLDywto_IU4_4RU0sKfID6OY-np6uGmhlf 49 | 50 | Есть канал тестирования, Михаила Портнова и Энди Кей. 51 | Михаила Портнова ооооочень хорошо дает теорию, но долго - https://www.portnov.com/ru и https://www.youtube.com/watch?v=9ecKqmeb9eA&list=PL_CSTk3_YGZ8i3h8yai0Lp5yrtQ8ga92G 52 | Энди Кей, в своих коротких видео на 5-7, хорошо раскрывает суть тестирования, простыми словами https://www.youtube.com/watch?v=jtEicidgRnM&list=PLN3rAY_-pdQafsbDsX4klNwwzh2IxTyok 53 | 54 | Полезные ( Но платные ) курсы уже от ребят Learnqa: https://www.learnqa.ru/#courses 55 | 56 | Нужен опыт работы с Linux: базовые навыки работы с терминалом. 57 | https://www.youtube.com/watch?v=tQLpAefAKuA 58 | 59 | Управление службами Linux - https://losst.ru/upravlenie-sluzhbami-linux 60 | 61 | Chrome DevTools guide (DOU) - https://dou.ua/lenta/articles/chrome-dev-tools-guide/ 62 | 63 | Обязанности по работе ручного тестировщика: 64 | - Тестирование функционала 65 | - Поиск и контроль проблем 66 | - Анализ полученных данных 67 | - Внесение недочетов в базу 68 | - Создание и поддержка тест-кейсов и тест-планов в актуальном состоянии 69 | - Проверка качества исправления ошибок 70 | 71 | ## Автоматизированно тестирование 72 | 73 | После ручного тестирования, можно осваивать автоматизацию, так как у Вас уже будет база знаний, фундамент. 74 | От того, какой язык программирования выбрать, зависит с какими фреймворками для тестирования можно работать. Зависит на какой системе будете разрабатывать тесты. Но обычно это Ubuntu. Я не говорю что Ruby это единственный язык, на котором можно вести тестирование, много языков подобных есть, к примеру Python, Java, PHP, Javascript. Но Ruby, как минимум, очень приятный язык, который прост, красив, удобен и понятен. Пример кода https://ibb.co/GxGbQd5. Язык программирования, на мой взгляд, важен: 75 | - Так как Вы весь день будете на нем писать и Вам должно это нравится. Руби именно такой язык программирования. 76 | - Он должен хорошо быть оплачиваемый(Ruby, Java, Python, Javascript такие) 77 | - На нем должно быть много вакансий(Python, Java, Javascript такие) 78 | - У языка должно быть хорошее и не токсичное комьюнити (Ruby такой, Javascript не такой, про Java и Python не могу сказать). 79 | Язык можно выучить самому, но самостоятельный путь может быть очень долгим. Скорее всего нужен ментор либо отличные курсы. Я могу порекомендовать ХП, так как сам их закончил, они шаг за шагом, с обратной связью, могут провести через джунгли и помочь найти работу. 80 | Состав преподавателей ХП очень крутой, мы общаемся с выпускниками и преподавателями, уже не первый год. 81 | Курс Хорошего программиста - https://goodprogrammer.ru/ 82 | 83 | В автоматизированном тестировании используется селениум 84 | Что такое селениум и как он работает, для чего нужен (теория) - Selenium WebDriver: полное руководство - https://software-testing.ru/edu/3-online/242-selenium-webdriver и https://habr.com/ru/post/152971/ 85 | 86 | Что такое локаторы - https://software-testing.ru/library/testing/testing-automation/3129-web-element-locators-for-test-automation и https://www.youtube.com/watch?v=9pBp9VDSU6M 87 | Работа с локаторами - https://www.youtube.com/watch?v=_TNh2ydpoOw 88 | 89 | Как на практике применяется xpath/css, и что с помощью них можно сделать: 90 | https://www.youtube.com/watch?v=_LNcuGqbmoY 91 | https://www.youtube.com/watch?v=3BW7zISHri0 92 | https://www.youtube.com/watch?v=zlWiw99bBUk 93 | 94 | Что такое api, как используется, как писать тесты для API. 95 | https://software-testing.ru/edu/1-schedule/271-rest-api 96 | 97 | Инструменты для тестирования API: 98 | https://software-testing.ru/library/testing/functional-testing/2676-open-source-api-testing 99 | 100 | Работа с API: 101 | https://software-testing.ru/library/testing/general-testing/2518-rest-api-testing 102 | 103 | Что такое Postman и как с ним работать. 104 | https://www.postman.com/ 105 | https://www.youtube.com/watch?v=ZpxjS8ZB0MA 106 | 107 | Курс «Тестирование REST API»: 108 | https://software-testing.ru/events/2984-rest-api - платный 109 | https://www.udemy.com/course/api-2020-postman/ -бесплатный 110 | 111 | Сайты с множеством теории на английском + вопросы к собеседованию: 112 | https://devqa.io/software-testing-fundamentals/#api_testing_interview_questions 113 | https://www.techbeamers.com/qa-interview-questions-and-answers-top-20/ 114 | 115 | Что нужно знать для автоматизации, какими ресурсами можно и нужно пользоваться и что нужно чтобы написать первые тесты: 116 | https://docs.google.com/spreadsheets/d/1oj1oJyL1ptDEuWiv8M5F9chDXE_4ij-fx9mRwToAI7s/edit#gid=1402541726 117 | 118 | Обязанности по работе: 119 | - Тестирование функционала 120 | - Поиск и контроль проблем 121 | - Анализ полученных данных 122 | - Внесение недочетов в базу 123 | - Проверка качества исправления ошибок 124 | - Создание и поддержка тест-кейсов и тест-планов в актуальном состоянии 125 | - Разработка и поддержка автоматизированных тестов 126 | - Тестирование REST и SOAP API 127 | - Взаимодействие с командой разработчиков ПО и другими участниками команды 128 | - Проведение полного цикла регрессионного тестирования задач и багрепортов 129 | - Активное участие в настройке тестовых сред и процессов тестирования 130 | -------------------------------------------------------------------------------- /interview/database.md: -------------------------------------------------------------------------------- 1 | # Вопросы по базам данных с собеседований 2 | 3 | ## Общие 4 | 5 | 1. Что такое реляционная база данных? 6 | 7 |
8 | Ответ 9 | Реляционная база данных — это набор данных с предопределенными связями между ними. Эти данные организованны 10 | в виде набора таблиц, состоящих из столбцов и строк. В таблицах хранится информация об объектах, представленных 11 | в базе данных. В каждом столбце таблицы хранится определенный тип данных, в каждой ячейке — значение атрибута. 12 | Каждая строка таблицы представляет собой набор связанных значений, относящихся к одному объекту или сущности. 13 |
14 | 15 | 1. Что такое таблица, кортеж? Что такое primary key? 16 | 17 |
18 | Ответ 19 | Таблица — это набор элементов данных (значений), использующий модель вертикальных столбцов 20 | (имеющих уникальное имя) и горизонтальных строк. Таблица содержит определенное число столбцов, но может иметь 21 | любое количество строк. 22 | Каждая строка однозначно определяется одним или несколькими уникальными значениями, 23 | которые принимают её ячейки из определенного подмножества столбцов. Подмножество столбцов, 24 | которое уникально идентифицирует строку, называется первичным ключом(primary key). 25 | 26 | - Primary key не позволяет создавать одинаковых записей (строк) в таблице; 27 | - PK обеспечивают логическую связь между таблицами одной базы данных. 28 | 29 | По соглашению Rails предполагает, что для первичного ключа используется столбец _id_ в таблице, 30 | который автоматически создается для каждой вашей записи. 31 | 32 | **Кортеж** - это набор именованных значений заданного типа. 33 | 34 | ![Наглядный пример](http://citforum.ru/pictures/it/osbd/img00005.gif) 35 |
36 | 37 | 1. Как реализованы связи между таблицами? Что такое foreign key? 38 | 39 |
40 | Ответ 41 | Между двумя или более таблицами базы данных могут существовать отношения подчиненности. Отношения подчиненности 42 | определяют, что для каждой записи главной таблицы может существовать одна или несколько записей в подчиненной таблице. 43 | 44 | Существует три разновидности связей между таблицами базы данных: 45 | 46 | * «один-ко-многим», 47 | 48 | * «один-к-одному», 49 | 50 | * «многие-ко-многим». 51 | 52 | Внешний ключ **Foreign key**, кратко FK. Обеспечивает однозначную логическую связь, между таблицами одной БД. 53 | Для обеспечения ссылочной целостности в дочерней таблице создается внешний ключ. Во внешний ключ входят 54 | поля связи дочерней таблицы. Для связей типа "один-ко-многим" внешний ключ по составу полей должен совпадать 55 | с первичным ключом родительской таблицы. 56 | 57 | Например, есть две таблицы А и В. В таблице А (обувь), есть первичный ключ: размер, 58 | в таблице В (цвет) должна быть колонка с названием размер. В этой таблице «размер» 59 | это и будет внешний ключ для логической связи таблиц В и А. 60 | 61 | По соглашению Rails предполагает, что столбец, используемый для хранения внешнего ключа в этой модели, имеет имя модели с добавленным суффиксом _id_ 62 |
63 | 64 | 1. Как работает SELECT оператор? 65 | 66 |
67 | Ответ 68 | SELECT - оператор запроса, возвращающий набор данных (выборку) из базы данных. 69 | 70 | Оператор SELECT состоит из нескольких предложений (разделов): 71 | 72 | Сам **SELECT** определяет список возвращаемых столбцов (как существующих, так и вычисляемых), их имена, 73 | ограничения на уникальность строк в возвращаемом наборе, ограничения на количество строк в возвращаемом наборе; 74 | 75 | **FROM** задаёт табличное выражение, которое определяет базовый набор данных для применения операций, определяемых 76 | в других предложениях оператора; 77 | 78 | **WHERE** задает ограничение на строки табличного выражения из предложения FROM; 79 | 80 | **GROUP BY** объединяет ряды, имеющие одинаковое свойство с применением агрегатных функций 81 | 82 | **HAVING** выбирает среди групп, определенных параметром GROUP BY 83 | 84 | **ORDER BY** задает критерии сортировки строк; отсортированные строки передаются в точку вызова. 85 | 86 | Синтаксис оператора SELECT: 87 | 88 | ```sql 89 | SELECT 90 | FROM 91 | [WHERE <условие>] 92 | [GROUP BY <условие>] 93 | [HAVING <условие>] 94 | [ORDER BY <условие>] 95 | ``` 96 |
97 | 98 | 1. Какие бывают виды JOIN? Как каждый работает? 99 | 100 |
101 | Ответ 102 | INNER JOIN - оператор внутреннего соединения, соединяет две таблицы. Выбираются только совпадающие данные из 103 | объединяемых таблиц. 104 | 105 | OUTER JOIN - существует два типа внешнего объединения: LEFT OUTER JOIN и RIGHT OUTER JOIN. 106 | Работают они одинаково, разница заключается в том что LEFT - указывает что "внешней" таблицей будет находящаяся 107 | слева, а RIGHT - справа. Выбираются все данные из внешней таблицы + совпадения из второй таблицы. 108 | 109 | Cross/Full Join - FULL JOIN возвращает объединение объединений LEFT и RIGHT таблиц, комбинируя результат двух запросов. 110 | CROSS JOIN возвращает перекрестное объединение двух таблиц. Результатом будет выборка всех записей первой таблицы 111 | объединенная с каждой строкой второй таблицы. Важным моментом является то, что для кросса не нужно указывать 112 | условие объединения. 113 | 114 | ![Наглядный пример](https://zametkinapolyah.ru/wp-content/uploads/2016/07/type-join.png) 115 |
116 | 117 | 1. Как работают INSERT, UPDATE, DELETE операторы? 118 | 119 |
120 | Ответ 121 | INSERT — оператор, который позволяет добавить строки в таблицу, заполняя их значениями. 122 | Значения можно вставлять перечислением с помощью слова values и перечислив их в круглых скобках через запятую или 123 | оператором SELECT. 124 | 125 | Синтаксис: 126 | 127 | ```sql 128 | INSERT INTO table_name (column1, column2, column3, ...) 129 | VALUES (value1, value2, value3, ...); 130 | ``` 131 | 132 | UPDATE — оператор, позволяющий обновить значения в заданных столбцах таблицы. 133 | 134 | Синтаксис: 135 | 136 | ```sql 137 | UPDATE table_name 138 | SET column1 = value1, column2 = value2, ... 139 | WHERE condition; 140 | ``` 141 | 142 | DELETE — операция удаления записей из таблицы. Критерий отбора записей для удаления определяется выражением WHERE. 143 | В случае, если критерий отбора не определён, выполняется удаление всех записей. 144 | 145 | Синтаксис: 146 | 147 | ```sql 148 | DELETE FROM table_name WHERE condition; 149 | ``` 150 | 151 |
152 | 153 | 1. Что такое индексы? Для чего используются? Плюсы, минусы? 154 | 155 |
156 | Ответ 157 | Индекс — объект базы данных, создаваемый с целью повышения производительности поиска данных. Таблицы в базе 158 | данных могут иметь большое количество строк, которые хранятся в произвольном порядке, и их поиск по заданному 159 | критерию путём последовательного просмотра таблицы строка за строкой может занимать много времени. 160 | Индекс формируется из значений одного или нескольких столбцов таблицы и указателей на соответствующие строки 161 | таблицы и, таким образом, позволяет искать строки, удовлетворяющие критерию поиска. 162 | 163 | Ускорение работы с использованием индексов достигается в первую очередь за счёт того, что индекс имеет структуру, 164 | оптимизированную под поиск. 165 | 166 | Для оптимальной производительности запросов индексы обычно создаются на тех столбцах таблицы, 167 | которые часто используются в запросах. Однако увеличение числа индексов замедляет операции добавления, 168 | обновления, удаления строк таблицы, поскольку при этом приходится обновлять сами индексы. Кроме того, индексы 169 | занимают дополнительный объем памяти. 170 |
171 | 172 | 1. Какие виды индексов бывают? 173 |
174 | Ответ 175 | 176 | "Золотое правило индексирования" — иметь индекс под каждый запрос. 177 | #### По порядку сортировки 178 | **Упорядоченные** — индексы, в которых элементы поля(столбца) упорядочены. 179 | 180 | * Возрастающие 181 | 182 | * убывающие 183 | 184 | **Неупорядоченные** — индексы, в которых элементы неупорядочены. 185 | 186 | #### По источнику данных 187 | * Индексы по представлению (view) 188 | 189 | * Индексы по выражениям (например, в PostgreSQL) 190 | 191 | #### По воздействию на источник данных 192 | * Некластерный индекс 193 | 194 | * Кластерный индекс 195 | 196 | #### По структуре 197 | 198 | * B-деревья 199 | 200 | * B+-деревья 201 | 202 | * B-деревья 203 | 204 | * Хеши 205 | 206 | #### По количественному составу 207 | * Простой индекс (индекс с одним ключом) 208 | 209 | * Главный индекс (индекс по первичному ключу) 210 | 211 | #### По характеристике содержимого 212 | 213 | * Уникальный индекс 214 | 215 | * Разреженный индекс (NoSQL) 216 | 217 | * Пространственный индекс 218 | 219 | * Составной пространственный индекс 220 | 221 | * Полнотекстовый (инвертированный) индекс 222 | 223 | * Хэш-индексы 224 | 225 | * Битовый индекс (bitmap index) 226 | 227 | * Обратный индекс (inverse index) 228 | 229 | * Функциональный (function-based) индекс (индекс по вычисляемому полю) 230 | 231 | * Первичный индекс 232 | 233 | * Вторичный индекс 234 | 235 | * XML-индекс 236 | 237 | #### По механизму обновления 238 | 239 | * Полностью перестраиваемый 240 | * Пополняемый (балансируемый) 241 | 242 | #### По покрытию индексируемого содержимого 243 | 244 | * Полностью покрывающий (полный) индекс 245 | 246 | * Частичный (partial) индекс 247 | 248 | * Инкрементный (Delta) индекс 249 | 250 | * Real-time индекс 251 | 252 | #### Индексы в кластерных системах 253 | 254 | * Глобальный индекс 255 | 256 | * Сегментный индекс 257 | 258 | * Локальный индекс 259 | 260 | http://tokarchuk.ru/2012/08/indexes-classification/ 261 |
262 | 1. Что такое полнотекстовый поиск? 263 | 1. Что такое транзакции? 264 |
265 | Ответ 266 | 267 | Транза́кция — группа последовательных операций с базой данных, 268 | которая представляет собой логическую единицу работы с данными. 269 | Транзакция может быть выполнена либо целиком и успешно (**Commit**), 270 | соблюдая целостность данных и независимо от параллельно идущих других транзакций, 271 | либо не выполнена вообще (**Rollback**), и тогда она не должна произвести никакого эффекта. 272 | 273 | https://ru.wikipedia.org/wiki/Транзакция_(информатика) 274 | 275 |
276 | 1. Расскажите об уровнях изолированности транзакции 277 |
278 | Ответ 279 | 280 | **Уровень изолированности транзакций** — условное значение, 281 | определяющее, в какой мере в результате выполнения логически параллельных транзакций в СУБД 282 | допускается получение несогласованных данных. Шкала уровней изолированности транзакций 283 | содержит ряд значений, проранжированных от наинизшего до наивысшего; 284 | более высокий уровень изолированности соответствует лучшей согласованности данных, 285 | но его использование может снижать количество физически параллельно выполняемых транзакций. 286 | 287 | #### Проблемы параллельного доступа с использованием транзакций 288 | 289 | При параллельном выполнении транзакций возможны следующие проблемы: 290 | 291 | * потерянное обновление (англ. lost update) 292 | 293 | * «грязное» чтение (англ. dirty read) 294 | 295 | * неповторяющееся чтение (англ. non-repeatable read) 296 | 297 | * фантомное чтение (англ. phantom reads) 298 | 299 | #### Уровни изоляции 300 | 301 | Под «уровнем изоляции транзакций» понимается степень обеспечиваемой внутренними механизмами СУБД 302 | (то есть не требующей специального программирования) защиты от всех или некоторых видов 303 | вышеперечисленных несогласованности данных, возникающих при параллельном выполнении транзакций. 304 | 305 | Первый из них является самым слабым, последний — самым сильным, 306 | каждый последующий включает в себя все предыдущие. 307 | 308 | * Read uncommitted (чтение незафиксированных данных) 309 | * Read committed (чтение фиксированных данных) 310 | * Repeatable read (повторяемость чтения) 311 | * Serializable (упорядочиваемость) 312 | 313 | https://ru.wikipedia.org/wiki/Уровень_изолированности_транзакций 314 | 315 |
316 | 1. Что такое блокировочные и версионные СУБД? 317 | 1. Что такое репликация, для чего нужна? 318 |
319 | Ответ 320 | 321 | Репликация — одна из техник масштабирования баз данных. 322 | Состоит эта техника в том, что данные с одного сервера базы данных постоянно копируются (реплицируются) 323 | на один или несколько других (называемые репликами). 324 | Для приложения появляется возможность использовать не один сервер для обработки всех запросов, а несколько. 325 | Таким образом появляется возможность распределить нагрузку с одного сервера на несколько. 326 | 327 | Существует два основных подхода при работе с репликацией данных: 328 | 329 | * Репликация Master-Slave; 330 | * Репликация Master-Master. 331 | 332 | https://highload.today/replikatsiya-dannykh/ 333 | 334 |
335 | 336 | 1. Что такое шардинг (партиционирование)? 337 |
338 | Ответ 339 | 340 | Шардинг (иногда шардирование) — это другая техника масштабирования работы с данными. 341 | Суть его в разделении (партиционирование) базы данных на отдельные части так, 342 | чтобы каждую из них можно было вынести на отдельный сервер. 343 | Этот процесс зависит от структуры Вашей базы данных и выполняется прямо в приложении в отличие от репликации: 344 | 345 | **Вертикальный шардинг** 346 | 347 | Вертикальный шардинг — это выделение таблицы или группы таблиц на отдельный сервер. 348 | 349 | **Горизонтальный шардинг** 350 | 351 | Горизонтальный шардинг — это разделение одной таблицы на разные сервера. 352 | Это необходимо использовать для огромных таблиц, которые не умещаются на одном сервере. 353 | 354 | https://highload.today/sharding-i-replikatsiya/ 355 | 356 |
357 | 358 | 1. Типичные bottle necks? 359 | 1. Объяснить разницу между SQL Injection and CSS Injection? 360 | 1. Что такое BETWEEN? 361 | 1. Чем Like отличается от Ilike? 362 | 1. Чем Having отличается от Where? 363 | 364 |
365 | Ответ 366 | `Where` фильтрует строки. 367 | 368 | `Having` фильтрует группы (например, сначала группировка с применением `Group by`, а затем уже выборка по условию с применением `Having`). 369 | Пример можно посмотреть здесь: http://sql-tutorial.ru/ru/book_having_clause.html 370 |
371 | 372 | 1. Что такое нормализация и денормализация базы данных? 373 | 374 |
375 | Ответ 376 | Нормализация — процесс преобразования отношений базы данных к виду, отвечающему нормальным формам. 377 | 378 | Нормальные формы — это рекомендации по проектированию баз данных. 379 | 380 | Для нормализации необходимо упорядочить данные в группы и найти логические связи между этими группами данных. 381 | 382 | Денормализация — намеренное приведение структуры базы данных в состояние, не соответствующее критериям нормализации, обычно проводимое с целью ускорения операций чтения из базы за счет добавления избыточных данных. 383 | 384 | https://office-menu.ru/uroki-sql/51-normalizatsiya-bazy-dannykh 385 | https://oracle-patches.com/db/3632-нормализация-и-денормализация-базы-данных-нормальные-формы 386 |
387 | 388 | 1. Основная причина, по которой Redis работает быстрее PostgreSQL? 389 | 390 |
391 | Ответ 392 | Причина в месте хранения данных. В Redis данные хранятся в оперативной памяти, в PostgreSQL на жёстком диске. 393 | 394 | https://ru.wikipedia.org/wiki/Redis 395 | 396 |
397 | 398 | 1. Приложение, базу, сервер не трогали - но спустя какое-то время запрос стал работать медленнее. Почему? 399 | 400 |
401 | Ответ 402 | 403 | При выполнении запроса пишется статистика, которая содержит статистические характеристики по запросу. Если она забьется, или превысит какой-то порог - то запрос будет выполняться медленнее из-за большого разброса статистичеких значений. Индексы не помогут, и будут отбрасываться. 404 |
405 | 406 | 1. Что такое журнал транзакций SQL? 407 |
408 | Журнал транзакций SQL - это файл, содержащий журналы, которые были созданы в процессе регистрации транзакций, произошедших в базе данных. 409 | 410 | Журналы транзакций SQL являются последовательными по своей природе и могут быть разделены на куски, называемые виртуальными файлами журналов. 411 | 412 | Журнал транзакций SQL поддерживает следующее: 413 | 414 | * Восстановление незавершенных транзакций. 415 | * Rollback SQL транзакции. 416 | * Высокая доступность. 417 | * Восстановление БД 418 | 419 | Резервное копирование журнала транзакций - это не что иное, как резервное копирование всех транзакций базы данных, произошедших со времени последнего резервного копирования журнала транзакций. Эти резервные копии могут быть выполнены в полном и инкрементальном режимах. 420 | 421 |
422 | 423 | Где искать ответы: 424 | 425 | * https://www.pgexercises.com — тренажер для написания запросов 426 | * https://sqlzoo.net/ 427 | * https://sqlbolt.com/ 428 | * http://sql-tutorial.ru/sqlbook/ru 429 | 430 | ## PostgreSQL 431 | 432 | Вопросы: 433 | 434 | 1. pgBouncer — что это и зачем нужно? 435 |
436 | 437 | Ответ 438 | 439 | **pgbouncer** — это пул соединения для PostgreSQL. 440 | Любое приложение может подключаться к pgbouncer так, 441 | как будто это сервер PostgreSQL ,и pgbouncer будет создавать соединения к действующему серверу PostgreSQL или 442 | переиспользовать существующие соединения. 443 | 444 | Главная цель pgbouncer это снизить потери производительности при создании новых соединений (новых процессов) к PostgreSQL. 445 | 446 | pgbouncer поддерживает несколько типов создания новых соединений и переиспользования существующих соединений: 447 | 448 | **Пул сессий (Session pooling)** 449 | 450 | **Пул транзакций. (Transaction pooling)** 451 | 452 | **Пул операторов (Statement pooling)** 453 | 454 | http://evtuhovich.ru/blog/2012/02/12/pgbouncer/ 455 | 456 | http://pgbouncer.ru/usage/ 457 | 458 | https://postgrespro.ru/docs/postgrespro/10/pgbouncer 459 | 460 |
461 | 1. Системы репликации, что это и зачем нужно? 462 | 1. PgQ (другие очереди)? 463 |
464 | Ответ 465 | 466 | PgQ — это еще одна система очередей, написаная skytools на базе PostgreSql. 467 | Если написать руками очередь на БД, то она будет работать медленно и создавать большую нагрузку. 468 | В PgQ удалось избежать этого за счет использования «особой PostgreSql магии». 469 | PgQ — транзакционная очередь, что гарантирует, что вы увидите каждой событией хотя бы один раз. 470 | 471 | Особенностью PgQ является то, что события из нее достаются пачками (batch). 472 | Поэтому надо быть внимательным, чтобы не отреагировать на одно и то же событие несколько раз 473 | (например, если обработчик собыий аварийно завершился, перед выходом стоит все необработанные события 474 | отправить на повтор и закрыть пакет). 475 | 476 |
477 | 1. Что такое синхронные и асинхронные операции? 478 | 1. Как устроены и функционируют индексы PostgreSQL? 479 |
480 | Ответ 481 | 482 | https://habr.com/ru/company/mailru/blog/261871/ 483 |
484 | 485 | 1. Как воплощён и работает механизм транзакций в PG? 486 |
487 | Ответ 488 | 489 | Транзакция откатывается по явному `ROLLBACK TRANSACTION` или закрывается по явному `COMMIT TRANSACTION`. Если ни то ни другое не было вызвано транзакция будет продолжать висеть открытой. Посмотреть висячие транзакции можно командой `DBCC OPENTRAN`. 490 | 491 | https://postgrespro.ru/docs/postgresql/9.6/sql-rollback-prepared 492 |
493 | 494 | 495 | Где искать ответы: 496 | 497 | * https://www.codecademy.com/learn/learn-sql 498 | * http://2sql.ru/ 499 | -------------------------------------------------------------------------------- /interview/frontend.md: -------------------------------------------------------------------------------- 1 | # Вопросы по фронтенду с собеседований 2 | 3 | 1. Что такое DOM? Какая у него структура, идентификаторы элементов? 4 | 5 | 1. JavaScript, опыт работы с ним, используемые библиотеки? 6 | 7 | 1. Какие существуют типы данных в JavaScript? 8 | 9 | 1. Что такое функция в JavaScript? 10 | 11 | 1. Что такое стрелочная функция (arrow function) в JavaScript? 12 | 13 | 1. Области видимости переменных и функций? 14 | 15 | 1. Как реализовано ООП в JavaScript? 16 | 17 | 1. Что означает ключевое слово `this` для функции и объекта? 18 | 19 | 1. Какие отличия между методами `call` и `apply`? 20 | 21 | 1. Что такое события? Методы `bind` / `unbind`. 22 | 23 | 1. Как происходит всплытие события в DOM? Как предотвратить всплытие события? 24 | 25 | 1. Что такое колбеки? 26 | 27 | 1. В чем отличие операторов `==` и `===` в JavaScript? 28 | 29 | 1. Что такое AJAX-запросы? 30 | 31 |
32 | Ответ 33 | 34 | **AJAX** — Asynchronous Javascript and XML, асинхронный JavaScript и XML. 35 | 36 | **AJAX-запрос** — фоновое обращение с клиентской стороны к серверу без перезагрузки страницы. 37 |
38 | 39 | 1. Рассказать, что происходит во время AJAX-запросов и для чего они нужны 40 | 41 |
42 | Ответ 43 | XHR-запрос (XMLHttpRequest) на сервер отправляется при помощи JavaScript. 44 | 45 | Сервер с учётом данных запроса формирует ответ с JSON/XML-содержимым. В браузере часть содержимого страницы заменяется при помощи скрипта. При этом пользователь остаётся на той же странице. 46 | 47 | Это позволяет ускорить загрузку страницы и сделать сёрфинг более комфортным для пользователя. 48 | 49 | ![AJAX-запрос](https://b.radikal.ru/b43/1905/9c/b0c1fe1da18f.png) 50 | 51 | http://rusrails.ru/working-with-javascript-in-rails 52 |
53 | 54 | Где искать ответы: 55 | 56 | * https://learn.JavaScript.ru/ 57 | -------------------------------------------------------------------------------- /interview/git.md: -------------------------------------------------------------------------------- 1 | # Вопросы по git с собеседований 2 | 3 | 1. Что такое VCS? Что такое Git? Почему его используют? 4 | 5 |
6 | Ответ 7 | Version Control System (система контроля версий) — программное обеспечение для облегчения работы с изменяющейся информацией. 8 | 9 | https://ru.wikipedia.org/wiki/Система_управления_версиями 10 | 11 | Git — распределённая система контроля версий, которая даёт возможность разработчикам отслеживать изменения в файлах и работать совместно с другими разработчиками. 12 | 13 | Подход Git к хранению данных больше похож на набор снимков миниатюрной файловой системы. При каждом сохранении состояния своего проекта в Git, система запоминает, как выглядит каждый файл в этот момент, и сохраняет ссылку на этот снимок. 14 |
15 | 16 | 1. Как создать репозиторий, подключить внешний репозиторий? 17 | 18 |
19 | Ответ 20 | На примере пользователя `username`, создавшего репозиторий `project` на Гитхабе. 21 | 22 | ``` 23 | git init 24 | git add 25 | git commit -m "first commit" 26 | git remote add origin git@github.com:username/project.git 27 | git push -u origin master 28 | ``` 29 |
30 | 31 | 1. Как загрузить удаленный репозиторий? 32 | 33 |
34 | Ответ 35 | 36 | ``` 37 | git clone git@github.com:username/project.git 38 | ``` 39 |
40 | 41 | 1. Что такое коммит? Как посмотреть историю коммитов? 42 | 43 |
44 | Ответ 45 | Коммит — подтверждение изменений. 46 | 47 | История коммитов 48 | 49 | ``` 50 | git log 51 | ``` 52 | 53 | https://git-scm.com/book/ru/v2/Основы-Git-Просмотр-истории-коммитов 54 |
55 | 56 | 1. Какие состояния файлов существуют в системе Git 57 | 58 |
59 | Ответ 60 | В Git'е файлы могут находиться в одном из трёх состояний: зафиксированном, изменённом и подготовленном. "Зафиксированный" значит, что файл уже сохранён в вашей локальной базе. К изменённым относятся файлы, которые поменялись, но ещё не были зафиксированы. Подготовленные файлы — это изменённые файлы, отмеченные для включения в следующий коммит. 61 | 62 | Таким образом, в проектах, использующих Git, есть три части: каталог Git'а (Git directory), рабочий каталог (working directory) и область подготовленных файлов (staging area). 63 |
64 | 65 | 1. Что такое ветка в Git? 66 | 67 |
68 | Ответ 69 | Организованная система ссылок на коммиты. 70 | 71 | Ветка по умолчанию в Git'е называется `master`. Когда вы создаёте коммиты на начальном этапе, вам дана ветка `master`, указывающая на последний сделанный коммит. При каждом новом коммите она сдвигается вперёд автоматически. 72 | 73 | Ответвление от основной ветки осуществляется для работы с определенной фичей. 74 |
75 | 76 | 1. Отличия между командами `merge` и `rebase`? 77 | 78 |
79 | Ответ 80 | В Git'е есть два способа включить изменения из одной ветки в другую: `merge` (слияние) и `rebase` (перемещение). 81 | 82 | * `merge` 83 | 84 | Это более простая команда. 85 | 86 | Git создаёт новый снимок состояния, который является результатом трёхходового слияния, и автоматически создаёт новый коммит, который указывает на этот новый снимок состояния. Такой коммит называют коммит-слияние, так как он является особенным из-за того, что имеет больше одного предка. 87 | 88 | * `rebase` 89 | 90 | В этом случае находится общий предок для двух веток (на которой вы находитесь сейчас и на которую вы выполняете перемещение); для каждого из коммитов в текущей ветке берётся его дельта и сохраняется во временный файл; текущая ветка устанавливается на тот же коммит, что и ветка, на которую выполняется перемещение; и, наконец, одно за другим применяются все изменения. Таким образом, все коммиты переписываются с новыми значениями хешей. 91 | 92 | При этом история коммитов становится более аккуратной и красивой. Она выглядит как линейная последовательность коммитов, когда в действительности она выполнялась параллельно. 93 | 94 | https://git-scm.com/book/ru/v1/Ветвление-в-Git-Перемещение 95 |
96 | 97 | 1. Золотое правило `rebase`? 98 | 99 |
100 | Ответ 101 | Не перемещайте коммиты, которые вы уже отправили в публичный репозиторий. 102 | 103 | Если вы будете следовать этому указанию, всё будет хорошо. Если нет — люди возненавидят вас, вас будут презирать ваши друзья и семья. 104 | 105 | Правило вытекает из свойства `rebase` переписывать историю коммитов. 106 |
107 | 108 | 1. Как загрузить последние изменения с определенной ветки? 109 | 110 |
111 | Ответ 112 | 113 | ``` 114 | git pull --rebase 115 | ``` 116 |
117 | 118 | 1. Как отправить свои изменения на удаленный репозиторий? 119 | 120 |
121 | Ответ 122 | 123 | ``` 124 | git add 125 | git commit -m "Commit message" 126 | git push 127 | ``` 128 |
129 | 130 | 1. Как добавить изменения в уже созданный коммит? изменить название такого коммита? 131 | 132 |
133 | Ответ 134 | 135 | ``` 136 | git add 137 | git commit --amend` 138 | ``` 139 |
140 | 141 | 1. Как удалить ветку локально и с удаленного репозитория? 142 | 143 |
144 | Ответ 145 | 146 | ``` 147 | git branch -d new-branch 148 | git branch -d origin new-branch 149 | git push origin :new-branch 150 | ``` 151 |
152 | 153 | 1. Что такое запросы на слияние (pull requests)? Как их создавать? 154 | 155 |
156 | Ответ 157 | Удобная система взаимодействия между автором внесения изменений и хозяином репозитория, позволяющая обсуждать изменения и вносить правки по их ходу. 158 | 159 | https://www.youtube.com/watch?v=M7ZYkjOWr6g 160 | 161 | https://www.youtube.com/watch?v=Wz7RDh6CylI 162 |
163 | 164 | 1. Как перенести изменения из одной ветку в другую (2 способа)? 165 | 166 |
167 | Ответ 168 | Использовать cherry-pick 169 | 170 | https://www.youtube.com/watch?v=BP53rBf1PUE 171 | 172 | https://www.youtube.com/watch?v=-fDa6ntlBXg 173 | 174 | Второй способ немного сложнее, нужно сделать ответвление и затем смержить в обе ветки код. 175 |
176 | 177 | 1. Разница между git и svn (если есть)? 178 | 179 |
180 | Ответ 181 | Главное отличие Git от Subversion заключается в том, что Git — распределенная система контроля версий. 182 | 183 | * Сервер вообще не нужен. Можно работать локально. 184 | * В отличие от Subversion, если сервер с «главным» репозиторием, куда пушат свои изменения все разработчики 185 | (хотя формально в Git нет никакого «главного» репозитория), вдруг прилег — ничего страшного. Делаем коммиты в 186 | локальный репозиторий и ждем, когда сервер вернется. 187 | * Git дает нам нормальное шифрование «из коробки», безо всяких танцев с бубнами, как в случае с Subversion. 188 | * Git не раскидывает по каталогам служебную информацию (файл «.svn»?), вместо этого она хранится только в корне 189 | репозитория. 190 |
191 | 1. Для чего нужен SSH-ключ? 192 | 193 |
194 | Ответ 195 | SSH-ключи используются для облегчённой авторизации на различных сервисах. 196 | 197 | SSH-ключ состоит из двух частей 198 | 199 | * id_rsa — закрытая часть, которая должна быть доступна только вам, ни кому и ни когда нельзя давать к ней доступ, этот файл можно переносить с компа на ком. так чтобы был у вас был только 1 ключ, но тут свои риски, например у вас в одном месте кто-то получил доступ к $HOME, следовательно все ваши аккаунты потенциально взломали 200 | * id_rsa.pub — открытая часть, бесполезна без закрытой, её можно показывать всем, можно даже повесить на своём сайте, чтобы желающие дать вам доступ на свой сервер могли быстро добавить ваш открытый ключ в файл `~/.ssh/authorized_keys`. 201 |
202 | 203 | 1. `git commit` — в каких случаях писать `-am`, `-a` и `-m`? 204 | 205 |
206 | Ответ 207 | Создание коммита с сообщением (**m**essage) для файлов, находящихся в staging area, которые предварительно туда добавлены: 208 | 209 | ``` 210 | git add some.file 211 | git commit -m "Your message here" 212 | ``` 213 | 214 | Создание коммита для индексированных (отслеживаемых) файлов **а**втоматически (без предварительной команды `add`). Новые файлы в коммит не попадут: 215 | 216 | ``` 217 | git commit -a -m "Your message here" 218 | ``` 219 | 220 | Можно просто 221 | 222 | ``` 223 | git commit -am "Your message here" 224 | ``` 225 |
226 | 227 | 1. Что такое `gitflow`? 228 | 229 |
230 | Ответ 231 | Ветвление — это основное понятие в git. Весь GitHub Flow основан именно на нём и согласно ему есть только одно правило: всё, что находится в master-ветке — гарантированно стабильно и готово к деплою в любой момент. Поэтому чрезвычайно важно, чтобы любая ваша новая ветвь создавалась именно от mastera. 232 |
233 | 234 | Где искать ответы: 235 | 236 | * https://git-scm.com/docs 237 | * https://githowto.com/ru 238 | * https://learn.javascript.ru/screencast/git 239 | -------------------------------------------------------------------------------- /interview/images/sklad.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aristofun/webdevdao/6a6aa63bfceae17c67ae8725e96f15c75e6cf6d8/interview/images/sklad.jpg -------------------------------------------------------------------------------- /interview/interview_questions.md: -------------------------------------------------------------------------------- 1 | # Подборка вопросов на собеседованиях 2 | 3 | https://github.com/MaximAbramchuck/awesome-interview-questions 4 | -------------------------------------------------------------------------------- /interview/other.md: -------------------------------------------------------------------------------- 1 | # Разные вопросы по программированию с собеседований 2 | 3 | 1. Интерпретируемые vs комилируемые языки, в чём разница? 4 | 5 | 1. Что такое рефакторинг? 6 | 7 |
8 | Ответ 9 | Рефакторинг представляет собой процесс такого изменения программной системы, при котором не меняется внешнее поведение кода, но улучшается его внутренняя структура. Это способ систематического приведения кода в порядок, при котором шансы появления новых ошибок минимальны. 10 | 11 | В сущности, при проведении рефакторинга кода вы улучшаете его дизайн уже после того, как он написан. 12 |
13 | 14 | 1. Что такое code smell? 15 | 16 |
17 | Ответ 18 | Термин, обозначающий код с признаками (запахами) проблем в системе. Это могут быть: дублирование кода, длинный метод, большой класс, длинный список параметров, расходящиеся модификации, операторы типа switch, ленивый класс, временное поле, отказ от наследства 19 | 20 | https://ru.wikipedia.org/wiki/%D0%9A%D0%BE%D0%B4_%D1%81_%D0%B7%D0%B0%D0%BF%D0%B0%D1%88%D0%BA%D0%BE%D0%BC#%D0%92%D1%80%D0%B5%D0%BC%D0%B5%D0%BD%D0%BD%D0%BE%D0%B5_%D0%BF%D0%BE%D0%BB%D0%B5 21 |
22 | 23 | 1. Какие методы, библиотеки применяете для дебагинга? 24 | 25 |
26 | Ответ 27 | 28 | * web-console 29 | * debugger 30 | * byebug 31 | * pry 32 |
33 | 34 | 1. Каким приложением для написания кода пользуетесь, почему? 35 | 36 |
37 | Ответ 38 | 39 | * Rubymine 40 | * Vscode 41 | * Sublime 42 | * Atom 43 |
44 | 45 | 1. Какие знаете системы тикетов и организации задач? Какими пользовались? Плюсы, минусы? 46 | 47 |
48 | Ответ 49 | 50 | * Jira 51 | * YouTrack 52 | * Pivotaltrecker 53 | * Redmine 54 | * Mantis 55 | * Asana 56 |
57 | 58 | 1. Какие источники используете для информации? Какие сайты, книги? 59 | 1. Какие задачи интересуют больше? 60 | 1. Какие хобби, увлечения, спорт? 61 | 1. Есть ли свой блог, о чем? 62 | 1. Три последние книги? Что понравилось, не понравилось? 63 | 1. Какими трудами, поступками в своей жизни можешь гордиться? 64 | 1. Какой уровень владения английским языком? 65 | 1. Ваш самый удачный проект? 66 | 1. На каких инструментах играете, изучаете что-то связанное с музыкой, можете что-то сыграть? 67 | 1. Что такое хешфункции (md5, sha1/2), какими свойствами обладают? 68 | 1. Чем отличаются массив и связный список? 69 | 1. Какие операции быстрее в массиве, какие в связном списке? 70 | 71 | 1. Как найти причину «зависания» сложного скрипта на руби? Как решать эту проблему? (в Linux) 72 | 73 |
74 | Ответ 75 | 76 | * изучить условия воспроизведения проблемы (в каком окружении и как запускается скрипт). 77 | * изучить код скрипта, добавить где нужно побольше логов. 78 | * локализовать место (места) зависания. 79 | * сформировать список гипотез "почему именно тут зависает" и отработать их по порядку. 80 | * проанализировать дисковую и сетевую активость скрипта спец. утилитами, попробовать разные версии руби, другую ОС, внутри докера, профайлер — добавить по вкусу на любом шаге 81 |
82 | 83 | 1. С какими алгоритмами сортировки сталкивался? 84 | -------------------------------------------------------------------------------- /interview/rails.md: -------------------------------------------------------------------------------- 1 | # Вопросы по Ruby on Rails с собеседований 2 | 3 | 1. Что такое ActiveRecord, и какие средства предоставляет для работы с объектами? 4 | 5 |
6 | Ответ 7 | ActiveRecord это паттерн программирования. AR является популярным способом доступа к данным реляционных баз данных в объектно-ориентированном программировании. ActiveRecord еще называют буквой M в MVC — которая является слоем в системе, ответственным за представление бизнес-логики и данных. 8 | 9 | Active Record упрощает создание и использование бизнес-объектов, данные которых требуют персистентного хранения в базе данных. Сама по себе эта реализация паттерна Active Record является описанием системы ORM (Object Relational Mapping). Active Record это фреймворк ORM. 10 | 11 | Active Record предоставляет нам несколько механизмов, наиболее важными из которых являются способности для: 12 | 13 | * Представления моделей и их данных. 14 | * Представления связей между этими моделями. 15 | * Представления иерархий наследования с помощью связанных моделей. 16 | * Валидации моделей до того, как они станут персистентными в базе данных. 17 | * Выполнения операций с базой данных в объектно-ориентированном стиле. 18 | 19 | Подробнее: 20 | 21 | * http://rusrails.ru/active-record-basics 22 | * https://dic.academic.ru/dic.nsf/ruwiki/1264999 23 |
24 | 25 | 1. За что отвечают Model, View, Controller уровни в Rails? 26 | 27 |
28 | Ответ 29 | MVC — это паттерн программирования, который подразумевает схему разделения данных приложения, пользовательского интерфейса и управляющей логики на три отдельных компонента. 30 |
31 | 32 | 1. Как работает роутинг? Что такое ресурсные роуты? Как они формируются? 33 | 34 |
35 | Ответ 36 | Браузеры запрашивают страницы от Rails, выполняя запрос по URL, используя определенный метод HTTP, такой как GET, POST, PATCH, PUT и DELETE. 37 | 38 | Роутинг распознает запрос по методу и по URL и направляет его в экшн контроллера или в приложение Rack. 39 | 40 | Он также может генерировать пути и URL, избегая необходимость жестко прописывать строки в ваших вьюхах. 41 | 42 | Ресурсный роутинг позволяет быстро объявлять все общие маршруты для заданного ресурсного контроллера. Вместо объявления отдельных маршрутов для экшнов `index`, `show`, `new`, `edit`, `create`, `update` и `destroy`, ресурсный маршрут объявляет их одной строчкой кода. 43 | 44 | http://rusrails.ru/rails-routing 45 |
46 | 47 | 1. Как использовать `content_for` и `yield`? 48 | 1. Что такое скоупы (scopes)? Как использовать? 49 | 50 |
51 | Ответ 52 | 53 | Скоупы позволяют задавать часто используемые запросы, к которым можно обращаться как к вызовам метода в связанных 54 | объектах или моделях. С помощью этих скоупов можно использовать такие методы как where, joins и includes. 55 | Все методы скоупов возвращают объект `ActiveRecord::Relation`, который позволяет вызывать на нем 56 | дополнительные методы (такие как другие скоупы). 57 | 58 | Для определения простого скоупа мы используем метод scope внутри класса, передав запрос, который хотим запустить при вызове этого скоупа: 59 | 60 | ```rb 61 | class Article < ApplicationRecord 62 | scope :published, -> { where(published: true) } 63 | end 64 | 65 | ``` 66 | Подробнее [тут](http://rusrails.ru/active-record-query-interface#scopes) 67 |
68 | 69 | 1. Что такое ActiveJob? Когда его использовать? 70 |
71 | Ответ 72 | Active Job - это фреймворк для объявления заданий и их запуска на разных бэкендах очередей. Эти задания могут быть чем угодно: от регулярно запланированных чисток до списаний с карт или рассылок. 73 | В общем, всем, что может быть выделено в небольшие работающие части и запускаться параллельно. 74 | 75 | Имеет встроенные адаптеры для планировщиков фоновых задач: 76 | 77 | * Sidekiq 78 | * Resque 79 | * Delayed Job 80 | * и т.д. 81 | 82 | [Rails docs en](https://edgeguides.rubyonrails.org/active_job_basics.html) 83 | 84 | [Rails docs ru](http://rusrails.ru/active_job_basics) 85 |
86 | 87 | 1. Что такое Asset Pipeline? 88 |
89 | Ответ 90 | Asset Pipeline (файлопровод) - фреймворк для соединения и минимизации, или сжатия ассетов JavaScript и CSS. 91 | Он также добавляет возможность писать эти ассеты на других языках и препроцессорах, таких как CoffeeScript, Sass и ERB. 92 | Это позволяет автоматически комбинировать ассеты приложения с ассетами других гемов. 93 | 94 | Первой особенностью файлопровода является соединение ассетов, что может уменьшить количество запросов, необходимых браузеру для отображения страницы. 95 | Браузеры ограничены в количестве запросов, которые они могут выполнить параллельно, поэтому меньшее количество запросов может означать более быструю загрузку вашего приложения. 96 | 97 | Второй особенностью файлопровода является минимизация или сжатие ассетов. Для файлов CSS это выполняется путем удаления пробелов и комментариев. Для JavaScript могут быть применены более сложные процессы. Можно выбирать из набора встроенных опций или определить свои. 98 | 99 | Третьей особенностью файлопровода является то, что он позволяет писать эти ассеты на языке более высокого уровня с дальнейшей прекомпиляцией до фактического ассета. Поддерживаемые языки по умолчанию включают Sass для CSS, CoffeeScript для JavaScript и ERB для обоих. 100 | 101 | [Rails docs en](https://guides.rubyonrails.org/asset_pipeline.html) 102 | 103 | [Rails docs ru](http://rusrails.ru/asset-pipeline) 104 |
105 | 1. Что такое serializer и для чего он нужен? Где применяется? В чем его основная задача? 106 |
107 | Ответ 108 | Сериализация (serialization) - процесс перевода каких-либо структур данных в последовательность битов. 109 | Обратный процесс называется "десериализация" (deserialization). 110 | 111 | Сериализация используется для передачи объектов по сети и сохранения их в файлы. Например: сериализация заполненного объекта в XML-документ с последующей передачей документа 112 | по HTTP или протоколам электронной почты. 113 | 114 | Также часто используется для преобразования информации в формат JSON. 115 | 116 | В Rails интерфейс базовой сериализации представлен модулем `ActiveModel::Serialization` 117 | Вам необходимо объявить хэш, содержащий атрибуты, которые вы хотите сериализовать. Атрибуты должны быть строками, не символами. 118 | 119 | Что касается JSON, то Active Model также предоставляет модуль `ActiveModel::Serializers::JSON` для сериализации/десериализации JSON. 120 | 121 | [Статья в wiki о сериализации](https://ru.wikipedia.org/wiki/Сериализация) 122 | 123 | [Rails docs ru](http://rusrails.ru/active-model-basics) 124 | 125 | [Rails docs en](https://api.rubyonrails.org/classes/ActiveModel/Serialization.html) 126 |
127 | 128 | 1. Что такое presenter и для чего он нужен? Где применяется? В чем его основная задача? 129 |
130 | Ответ 131 | Presenter - паттерн проектирования, простой класс (в Rails), использующийся для вынесения какой-либо логики по обработке моделей из слоя контроллеров и слоя представлений. 132 | 133 | Например: 134 | 135 | ```rb 136 | module Posts 137 | class IndexPresenter 138 | # здесь как раз и разбивается логика шаблона и контроллера, 139 | # перенесите сюда логику из контроллеров 140 | def posts 141 | Posts.all 142 | end 143 | 144 | def authors 145 | Authors.all 146 | end 147 | 148 | def post_published_count 149 | Post.published_count 150 | end 151 | end 152 | end 153 | ``` 154 | Так будет выглядеть экшн `index` в контроллере 155 | 156 | ```rb 157 | def index 158 | @presenter = Posts::IndexPresenter.new 159 | end 160 | ``` 161 | 162 | Так это будет представлено во `view` 163 | 164 | ```rb 165 |

166 | Всего опубликовано: <%= @presenter.published_count %> 167 |

168 | <%= @presenter.authors # проход по массиву и отображение%> 169 | ``` 170 | 171 | Подробнее [тут](https://kpumuk.info/ruby-on-rails/simplifying-your-ruby-on-rails-code/) 172 | 173 | Еще можно [здесь](http://blog.rukomoynikov.ru/dekorator-prezenter-helper-v-ruby/) 174 | 175 |
176 | 177 | 1. Что такое валидации? Как написать свои валидации? Для чего нужны валидации? Где применяются валидации? Примеры Валидаций. 178 |
179 | Ответ 180 | Валидации используются, чтобы быть уверенными, что только проверенные данные сохраняются в вашу базу данных. 181 | Например, для вашего приложения может быть важно, что каждый пользователь предоставил валидный электронный и почтовый адреса. 182 | 183 | Валидации на уровне модели - наилучший способ убедиться, что в базу данных будут сохранены только валидные данные. Они не зависят от базы данных, не могут быть обойдены конечными пользователями и удобны в тестировании и обслуживании. 184 | Rails представляет простоту в обслуживании, представляет встроенные хелперы для общих нужд, а также позволяет создавать свои собственные методы валидации. 185 | 186 | Пример простейшей валидации передачу в модель `Person` данных из поля `name`: 187 | 188 | ```rb 189 | class Person < ApplicationRecord 190 | validates :name, presence: true 191 | end 192 | 193 | Person.create(name: "John Doe").valid? # => true 194 | Person.create(name: nil).valid? # => false 195 | ``` 196 | 197 | Разработчик так же в праве написать свои собственные правила валидации, которые будут располагаться в каталоге `app/validators`. 198 | 199 | Пример кастомной валидации `email` по определенному пользователем шаблону: 200 | 201 | ```rb 202 | class EmailValidator < ActiveModel::EachValidator 203 | def validate_each(record, attribute, value) 204 | unless value =~ /\A([^@\s]+)@((?:[-a-z0-9]+\.)+[a-z]{2,})\z/i 205 | record.errors[attribute] << (options[:message] || "is not an email") 206 | end 207 | end 208 | end 209 | 210 | class Person < ApplicationRecord 211 | validates :email, presence: true, email: true 212 | end 213 | ``` 214 | [Rails docs ru](http://rusrails.ru/active-record-validations) 215 | 216 | [Rails docs en](https://guides.rubyonrails.org/active_record_validations.html) 217 |
218 | 1. Есть ли у Rails механизм, который отслеживает изменения в базе данных? 219 | 220 | 1. Что такое `Rack`? 221 | 222 |
223 | Ответ 224 | https://www.8host.com/blog/kratkij-obzor-veb-serverov-dlya-prilozhenij-ruby/ 225 | 226 | Rack это промежуточное программное обеспечение, оно делит входящие HTTP-запросы на различные этапы, затем обрабатывает их по частям, после чего посылает ответ веб-приложения (контроллера). 227 | 228 | Программа Rack состоит из двух отдельных компонентов: обработчика и адаптера, с помощью которых происходит обмен данными между веб-серверами и приложениями (фреймворками). 229 | 230 | Какие серверы есть: 231 | 232 | * WEBrick 233 | * Thin 234 | * Puma 235 | * Unicorn 236 | * Phusion Passenger 237 | * Iodine 238 |
239 | 240 | [Как устроен Rack](https://gist.github.com/Integralist/8341704) 241 | 242 | * https://www.youtube.com/watch?v=NJ-ilQMsqMs 243 | * https://www.youtube.com/watch?v=MHYMObuEahc 244 | * https://www.youtube.com/watch?v=DzrVB1-KyTU 245 | * https://www.8host.com/blog/kratkij-obzor-veb-serverov-dlya-prilozhenij-ruby/ 246 |
247 | 248 | 1. Что такое `partial` и для чего используются? 249 | 250 |
251 | Ответ 252 | partial — это кусочек кода, который можно вынести в отдельный темплейт, для удобства использования и для использования в других представлениях. 253 |
254 | 255 | 1. Что такое Haml, Slim? Какие плюсы на ваш взгляд, их использования? 256 | 257 |
258 | Ответ 259 | Haml и Slim — это шаблонизаторы, используются для удобства использования и минимизации написания кода в представлениях. Сокращает в несколько раз написание кода, нет проблем в закрывании тегов, не получится что тег не закрыт и код не работает. Меньше вероятность что можно ошибиться + лучше читаемость в коде. 260 | 261 | http://slim-lang.com 262 | 263 | https://haml.ru 264 |
265 | 266 | 1. Что означает несколько расширений файла example.html.erb? 267 | 268 |
269 | Ответ 270 | 271 | **example** — название файла 272 | 273 | **html** — расширение, которое позволяет использовать стандартный язык разметки HyperText Markup Language 274 | 275 | **erb** — позволяет включить использование кода написанного на языке Ruby вместе с языком разметки 276 |
277 | 278 | 1. Что такое ERB? Можете расшифровать аббревиатуру? 279 | 280 |
281 | Ответ 282 | ERB — Embedded Ruby (встроенный Ruby) 283 |
284 | 285 | 1. Знать и рассказать структуру папок Rails приложения. 286 | 287 |
288 | Ответ 289 | 290 | 📂 app — основные файлы приложения 291 | └📁 assets — картинки, стили, js 292 | └📁 controllers — контроллеры 293 | └📁 helpers — хелперы 294 | └📁 jobs — задания 295 | └📁 mailers — рассыльщики 296 | └📁 models — модели 297 | └📁 views — представления 298 | └📁 layouts — макеты 299 | 📂 config — конфигурация маршрутов, базы данных и т.д 300 | └📁 environments — настройки сред приложения 301 | └📁 locales — интернационализация 302 | 📂 db — текущая схема базы данных, сиды 303 | └📁 migrates — файлы миграции 304 | 📂 lib — внешние модули 305 | 📂 log — журналы логов 306 | 📂 public — доступна извне как есть, статичные файлы и скомпилированные ассеты 307 | 📂 test — структурирована по тестам моделей / контроллеров / интеграционным 308 | └📂 fixtures — вспомогательные данные (фикстуры) 309 | 📂 tmp — временные файлы (такие как файлы кэша и pid) 310 | 📂 vendor — код сторонних разработчиков, например, внешние гемы. 311 | └📂 plugins — внешние плагины 312 | 313 | http://rusrails.ru/getting-started-with-rails#sozdanie-prilozheniya-blog 314 |
315 | 316 | 1. Какие связи для связывания моделей в приложении Rails вы знаете? 317 | 318 |
319 | Ответ 320 | Rails поддерживает шесть типов связей: 321 | 322 | * `belongs_to` 323 | * `has_one` 324 | * `has_many` 325 | * `has_many :through` 326 | * `has_one :through` 327 | * `has_and_belongs_to_many` 328 | 329 | http://rusrails.ru/active-record-associations#tipy-svyazey 330 |
331 | 332 | 1. Привести примеры использования `has_many`, `belongs_to`, `has_and_belongs_to_many`, `has_one`, `has_many :through`? 333 | 334 |
335 | Ответ 336 | Фильм имеет имеет множество сезонов, сезон принадлежит фильму и имеет множество серий. У каждого фильма может быть только один официальный сайт. В каждом фильме снимается множество актёров, при этом каждый актёр снимается в разных фильмах: 337 | 338 | ```rb 339 | class Film < ApplicationRecord 340 | has_many :seasons 341 | has_many :episodes, through: :seasons 342 | 343 | has_one :official_site 344 | has_and_belongs_to_many :actors 345 | end 346 | 347 | class Season < ApplicationRecord 348 | belongs_to :film 349 | has_many :episodes 350 | end 351 | 352 | class Episode < ApplicationRecord 353 | belongs_to :season 354 | end 355 | 356 | class OfficialSite < ApplicationRecord 357 | belongs_to :film 358 | end 359 | 360 | class Actor < ApplicationRecord 361 | has_and_belongs_to_many :films 362 | end 363 | ``` 364 | 365 | http://rusrails.ru/active-record-associations#tipy-svyazey 366 |
367 | 368 | 1. Что лучше выбрать `has_many :through` или `has_and_belongs_to_many`? 369 | 370 |
371 | Ответ 372 | 373 | Это зависит от контекста связи `many-to-many`. 374 | 375 | Если планируется использование дополнительной логики в этой связи, создание дополнительных полей в соединительной таблице, то лучше отдать предпочтение `has_many :through`. В этом случае применяются промежуточные модели-связки. 376 | 377 | В том случае, если достаточно простой соединительной таблицы, то можно обойтись `has_and_belongs_to_many` (т.н. HBTM). 378 | 379 | http://rusrails.ru/active-record-associations#dopolnitelnye-metody-stolbtsov 380 |
381 | 382 | 1. Что такое полиморфные связи? 383 | 384 |
385 | Ответ 386 | Особый вид связи, при которой модель может принадлежать сразу нескольким моделям. 387 | 388 | Например, картинку можно добавлять к статье, комментарию, пользователю. 389 | 390 | ```rb 391 | class Picture < ApplicationRecord 392 | belongs_to :imageable, polymorphic: true 393 | end 394 | 395 | class Article < ApplicationRecord 396 | has_many :pictures, as: :imageable 397 | end 398 | 399 | class Comment < ApplicationRecord 400 | has_many :pictures, as: :imageable 401 | end 402 | 403 | class User < ApplicationRecord 404 | has_many :pictures, as: :imageable 405 | end 406 | ``` 407 | 408 | При этом картинка сохраняет в себе имя класса и `id` объекта, которому она принадлежит. В приведённом примере у картинки имеются атрибуты `imageable_id` и `imageable_type`, это возможно благодаря миграции: 409 | 410 | ```rb 411 | class CreatePictures < ActiveRecord::Migration[5.2] 412 | def change 413 | create_table :pictures do |t| 414 | t.references :imageable, polymorphic: true, index: true 415 | end 416 | end 417 | end 418 | ``` 419 | 420 | http://rusrails.ru/active-record-associations#polymorphic-associations 421 | 422 |
423 | 424 | 1. Что такое `pluralize` и как он может быть полезен на проекте? 425 | 1. Что такое `i18n` (интернационализация)? 426 | 427 |
428 | Ответ 429 | Адаптация приложения к особенностям региона, в котором он будет использоваться. 430 | 431 | Название `i18n` происходит от английского слова _internationalization_, между первой и последней буквами _i_ и _n_ 18 букв. 432 | 433 | Гем `i18n`, поставляемый с Ruby on Rails (начиная с Rails 2.2), представляет простой и расширяемый фреймворк для перевода приложения на язык, отличный от английского, а также изменения формата даты, времени, валюты и т.д. 434 | 435 | Rails автоматически добавляет все файлы `.rb` и `.yml` из директории `config/locales` к пути загрузки переводов. 436 | 437 | http://rusrails.ru/rails-internationalization-i18n-api 438 |
439 | 440 | 1. Что такое `dependent` связь? 441 | 442 |
443 | Ответ 444 | 445 | Опция `:dependent` указывает, что необходимо сделать с зависимой моделью (моделями) при удалении текущей модели. В зависимости от типа связи может принимать значения: 446 | 447 | * `:delete` — связанные объекты будут удалены прямо из базы данных без вызова метода `destroy`, т.е. без соответствующих коллбэков 448 | * `:delete_all` — см. `:delete` 449 | * `:destroy` — будет вызван `destroy` на связанных объектах 450 | * `:nullify` — внешний ключ будет установлен `NULL` 451 | * `:restrict_with_error` — при наличии связанного объекта вызовет ошибку 452 | * `:restrict_with_exception` — при наличии связанного объекта вызовется исключение 453 | 454 | http://rusrails.ru/active-record-associations 455 |
456 | 457 | 1. Что такое `t.references`? 458 | 459 |
460 | Ответ 461 | Столбец таблицы в миграции, указывающий на принадлежность к другой таблице. Например, книга принадлежит автору: 462 | 463 | ```rb 464 | class CreateBooks < ActiveRecord::Migration[5.2] 465 | def change 466 | create_table :books do |t| 467 | t.references :author 468 | end 469 | end 470 | end 471 | ``` 472 | 473 | http://rusrails.ru/active-record-associations 474 |
475 | 476 | 1. Что такое exception и от чего наследуется? 477 | 1. Как сгенерировать модель, контрoллер, представление (вьюху) 478 | 479 |
480 | Ответ 481 | 482 | В Rails для создания моделей, контроллеров и представлений используется консольная команда `rails generate` (или `rails g`) с необходимыми ключами. 483 | Находиться при этом нужно в папке проекта. 484 | Генераторы в Rails сильно упрощают создание проекта, т.к. нет необходимости создавать каждый файл вручную. 485 | 486 | Например создание контроллера для модели "Greetings" в котором будет экшн `hello`: 487 | 488 | ```rb 489 | $ bin/rails generate controller Greetings hello 490 | create app/controllers/greetings_controller.rb 491 | route get "greetings/hello" 492 | invoke erb 493 | create app/views/greetings 494 | create app/views/greetings/hello.html.erb 495 | invoke test_unit 496 | create test/controllers/greetings_controller_test.rb 497 | invoke helper 498 | create app/helpers/greetings_helper.rb 499 | invoke assets 500 | invoke coffee 501 | create app/assets/javascripts/greetings.coffee 502 | invoke scss 503 | create app/assets/stylesheets/greetings.scss 504 | ``` 505 | [Rails docs en](https://guides.rubyonrails.org/command_line.html#rails-generate) 506 |
507 | 508 | 1. Что такое scaffolding? Зачем он используется и где применяется? 509 | 510 |
511 | Ответ 512 | Rails Scaffold - встроенный генератор, который запускает другие генераторы Rails, чтобы одной командой сгенерировать набор из модели, контроллера, вьюх, тестов, миграций и т.д. 513 | Предоставляется возможность создавать собственные предустановки генерации. 514 | 515 | [Rails docs en](https://guides.rubyonrails.org/v3.2/getting_started.html#getting-up-and-running-quickly-with-scaffolding) 516 |
517 | 518 | 1. Как реализовано кеширование в рельсах? 519 | 520 |
521 | Ответ 522 | 523 | Кэширование означает хранение контента, генерируемого в цикле запрос-отклик, и повторное использование его при ответе на подобные запросы. 524 | Кэширование значительно загрузку страниц, снижает количество запросов к серверу. 525 | 526 | Виды кэширования: 527 | 528 | * Кэширование страницы — начиная с Rails 4 добавляется гемом `actionpack-page_caching` 529 | * Кэширование экшна — начиная с Rails 4 добавляется гемом `actionpack-action_caching` 530 | * Кэширование фрагмента — позволяет фрагменту логики вьюхи быть обернутым в блок кэша и обслуженным из хранилища кэша для последующего запроса 531 | * Кэширование матрешкой (Russian doll caching) — Можно вкладывать кэшированные фрагменты в другие кэшированные фрагменты. Eсли обновляется отдельный продукт, другие внутренние фрагменты могут быть повторно использованы при регенерации внешнего фрагмента. 532 | 533 | Rails также предоставляет другие виды кэширования 534 | 535 | Подробнее: 536 | 537 | [Rails docs ru](http://rusrails.ru/caching-with-rails-an-overview) 538 | 539 | [Rails docs en](https://guides.rubyonrails.org/caching_with_rails.html) 540 |
541 | 542 | 1. ActiveRecord Query Interface - интерфейс запросов активрекорд. Для чего используется? Перечислите методы. 543 | 1. Чем отличаются методы `find` и `find_by`? 544 | 1. Представьте, что есть огромная табл. `users`. Как можно перебрать ее элементы максимально быстро? 545 | 546 |
547 | Ответ 548 | Быстро можно перебрать с помощью find_each, стандартно по 1000 записей. 549 | 550 | * `batch_size` — сколько обрабатывать записей за раз 551 | * `start` — с какого id к примеру продолжить работу 552 | * `finish` — может использоваться совместно с `start`, к примеру чтобы выслать письма только пользователям с первичным ключом от 2000 до 10000: 553 | 554 | https://apidock.com/rails/ActiveRecord/Batches/ClassMethods/find_each 555 | 556 | http://rusrails.ru/active-record-query-interface 557 |
558 | 559 | 1. Что такое проблема N+1 запроса? 560 | 1. Как можно решить проблему N+1 в Rails? 561 | 562 |
563 | Ответ 564 | Указанный код выполнит 10 + 1 запрос в БД (первый запрос загрузит 10 клиентов, а затем для каждого клиента будет сделано по запросу). 565 | 566 | ```rb 567 | clients = Client.limit(10) 568 | 569 | clients.each do |client| 570 | puts client.address.postcode 571 | end 572 | ``` 573 | 574 | Проблему N+1 можно решить при помощи метода `includes`, при этом Active Record обеспечивает то, что все указанные связи загружаются с использованием минимально возможного количества запросов: 575 | 576 | ```rb 577 | clients = Client.includes(:address).limit(10) 578 | 579 | clients.each do |client| 580 | puts client.address.postcode 581 | end 582 | ``` 583 | 584 | В данном случае будет сделано всего два запроса: 585 | 586 | ```sql 587 | SELECT * FROM clients LIMIT 10 588 | SELECT addresses.* FROM addresses WHERE (addresses.client_id IN (1,2,3,4,5,6,7,8,9,10)) 589 | ``` 590 | 591 | http://rusrails.ru/active-record-query-interface#neterpelivaya-zagruzka-svyazey 592 |
593 | 594 | 1. Как без рендеринга шаблона сказать мобильному приложению, что у него нет прав на просмотр определённого контента одной строкой в контроллере? 595 | 596 |
597 | Ответ 598 | 599 | ```rb 600 | head :forbidden 601 | ``` 602 | 603 | или 604 | 605 | ```rb 606 | render status: 403 607 | ``` 608 | 609 | https://guides.rubyonrails.org/layouts_and_rendering.html 610 |
611 | 612 | 1. Что такое Service Objects, Form Objects, View Objects, Query Objects, для чего они нужны? 613 | 614 |
615 | Ответ 616 | Это обычные классы Ruby, которые применяются для рефакторинга Rails-приложения, инкапсулируя часть логики моделей / представлений / контроллеров. 617 | 618 | Service Objects, например, используются, когда одновременно задействованы несколько моделей, когда производятся сложные действия с моделями. 619 | 620 | Form Objects используются, когда отправка одной формы изменяет несколько моделей. 621 | 622 | View Objects используются, например, когда большой метод внутри модели используется только отображения данных. 623 | 624 | Query Objects используются для сложных SQL запросов, утяжеляющих модели/контроллеры. 625 | 626 | https://habr.com/ru/post/158011/ 627 |
628 | 629 | 1. Назовите отличия Hash и HashWithIndifferentAccess 630 | 631 |
632 | Ответ 633 | Отличие состоит в том, что из хэша нельзя достать значение по строковому ключу. Только по символу. 634 | 635 | В HashWithIndifferentAccess можно получить ключ двумя способами. 636 | 637 | https://stackoverflow.com/questions/31890778/difference-between-ruby-s-hash-and-activesupport-s-hashwithindifferentaccess 638 |
639 | 640 | 1. Чем отличается after_save от after_commit? Почему это плохие паттерны? 641 | 1. Есть 2 версии приложения и в новой версии мы хотим поменять у уже существующей колонки значения на дефолтные, но чтоб в старом приложении все работало со старыми значениями (бд одна само собой). Как ты это будешь делать? Какую миграцию напишешь? 642 | 1. Пустое приложение, как ты сделаешь регистрацию пользователя и отправку ему имейла сразу после регистрации? Доп вопрос - как гарантировать, что мы юзеру отошлем только 1 имейл? 643 | 644 | Где искать ответы: 645 | 646 | * http://guides.rubyonrails.org/ 647 | * http://rusrails.ru/ 648 | * http://ruby-doc.org 649 | -------------------------------------------------------------------------------- /interview/ruby.md: -------------------------------------------------------------------------------- 1 | # Вопросы по Ruby с собеседований 2 | 3 | 1. Какие типы данных используются в Ruby? Что такое массив? хэш? строка? число? время? символ? 4 |
5 | Ответ 6 | 7 | #### Числа 8 | 9 | Числа (`Numeric`) в Ruby выглядят так: 10 | 11 | ``` rb 12 | 5 # целое число Integer 13 | -12 # отрицательное целое число 14 | 076 # восьмеричное число 15 | 0b010 # двоичное число 16 | 0x89 # шестнадцатиричное число 17 | 4.5 # число с плавающей точкой Float 18 | 2+3i # комплексное число Complex 19 | Rational(2, 3) # рациональная дробь ⅔ Rational 20 | ``` 21 | 22 | #### Логический тип 23 | 24 | Логический (булевый) тип — это вариация на тему «да» или «нет». В Ruby он представлен двумя 25 | предопределёнными переменными `true` («истина» или «да») и `false` («ложь» или «нет»). 26 | Появляется логический тип в результате логических операций или вызова логических методов (обычно заканчиваются на знак вопроса `?`). 27 | 28 | Чаще всего логический тип возникает как результат сравнения. 29 | 30 | `true` возвращает любой объект, в т.ч. `0`, за исключением `false` и `nil` (`nil` — это символ пустоты). 31 | 32 | #### Массивы 33 | 34 | Разработчики Ruby решили не реализовывать особых классов для динамических массивов, списков, стеков и тому подобного. 35 | Они все это реализовали в массивах — структурах данных типа (или класса — в Ruby всё равно) `Array`. 36 | Сделано это путём добавления специальных методов; например, методы `.push` и `.pop` для стека. 37 | 38 | Особенности массивов в Ruby: 39 | 40 | * Нет ограничений (это общий принцип языка). Массивы могут быть сколь угодно длинными. 41 | * Динамичность: размер массива легко меняется. 42 | * Гетерогенность: один массив может хранить данные разных типов. 43 | * Библиотека итераторов на каждый случай жизни. Эта возможность позволяет не использовать циклы для обработки 44 | данных в массивах, а, следовательно, избегать множества ошибок, связанных с неосторожным обращением с циклами. 45 | Итераторы реализуются на высочайшем уровне. 46 | * Много других методов. Все элементарные задачи для массивов решаются вызовом нужного метода. 47 | 48 | ``` rb 49 | [1, 0, 740, 14, 25] # целочисленный массив 50 | 51 | ["a", "й", "6", 'Br', "Это массив строк"] 52 | 53 | [[1, 2], [3, 4]] # двумерный целочисленный массив; Матрица — это объект класса Matrix 54 | 55 | # Двумерный массив — это не матрица целых чисел 56 | ["1-й элемент смешанного массива", "7.343", [4, "вепрь"], [3, 67, 4326, 12, 3781357, 84221, "строка делает этот подмассив смешанным, но это не беда"]] 57 | 58 | array = ["Этот массив пойдёт в переменную array", "Як-цуп-цоп, парви каридулла"] 59 | ``` 60 | 61 | #### Строки 62 | 63 | Стро́ки (`String`) — это ряды букв и других символов. В Ruby стро́ки используют наработки языка Perl. 64 | 65 | Стро́ки начинаются и заканчиваются `"` (программистскими кавычками) или `'` (машинописным апострофом). 66 | 67 | Чаще [принято](https://github.com/rubocop-hq/ruby-style-guide#consistent-string-literals) использовать одинарные кавычки. Однако в случае интерполяции и применении спецсимволов таких, как `\t`, `\n`, `'`используются двойные. 68 | 69 | Вот небольшой список их возможностей: 70 | * Нет ограничений. Длина строки́ может достигать поистине фантастических размеров. 71 | * Динамичность. Стро́ки можно расширять или уменьшать (для этого есть методы `+` и `[]`). 72 | * Любой объект преобразуется в строку (методы `.inspect` и `.to_s` есть у любого объекта). 73 | * Строка обладает обширной библиотекой методов, которые работают с правилами (это методы `.gsub`, `.match`, 74 | `.scan`, `.split`). 75 | * Конкатенация и интерполяция 76 | 77 | ``` rb 78 | '2' + '2' #=> "22" # конкатенация 79 | 80 | name = 'Вася' 81 | "Привет, #{name}!" #=> "Привет, Вася" # интерполяция 82 | ``` 83 | 84 | #### Ассоциативные массивы 85 | 86 | Ассоциативные массивы (класс `Hash`) подобны массивам упорядоченных пар. 87 | 88 | Работают они подобно словарям: фигурная скобка символизирует боковой вид на открытую книгу, а стрелка `=>` покажет читателю связь каждой сущности с какой-то другой. Вторая фигурная скобка говорит, что пора закрывать книгу. 89 | 90 | Структурными элементами хеша являются ключи и соответствующие им значения. 91 | 92 | ``` rb 93 | hash = { "мама" => "мыла раму", 807 => "Это число улыбается!" } 94 | 95 | hash["мама"] #=> "мыла раму" 96 | hash["807"] #=> nil 97 | hash[807] #=> "Это число улыбается!" 98 | ``` 99 | 100 | При использовании хешей в качестве аргументов метода возможна запись без фигурных скобок, а если в качестве ключа используются символы, то и без стрелок. 101 | 102 | ``` rb 103 | Wife.new(age: 18, bust: 90, waist: 60, hips: 90) 104 | ``` 105 | 106 | Ассоциативные массивы оставляют возможность хранения данных разного типа только в ассоциативном виде. 107 | 108 | #### Диапазоны значений 109 | 110 | Чтобы было удобней получать подмассив или подстроку, был введён тип данных — диапазон (класс `Range`). 111 | 112 | Диапазон формируется тремя элементами: начало, конец и тип протяжённости (символ `..` или `...`). 113 | 114 | Начало и конец должны быть одного типа данных (одного класса) и быть перечислимыми, что значит, иметь метод `.succ` (succedent — «последующему»). 115 | 116 | Применение `..` подразумевает включение конечного элемента. Применение `...` исключает конечный элемент. 117 | 118 | Пример диапазонов: 119 | 120 | ``` rb 121 | "a".."z" 122 | "a"..."z" # то же, что и "a".."y" 123 | 1..100 124 | 1...100 # то же, что и 1..99 125 | ``` 126 | 127 | Начиная с версии 2.6.0 вводится понятие бесконечного диапазона. 128 | 129 | Пример применения: 130 | 131 | ``` rb 132 | array[3..] # возвратит массив с элементами array, соответствующие индексом от 3-го до последнего 133 | ``` 134 | 135 | #### Символы 136 | 137 | В Ruby есть особый класс `Symbol`. Синтаксически объекты этого класса обозначаются двоеточием. 138 | 139 | Например, `:a`, `:b`, `:symbol`. 140 | 141 | Символ похож на строку (`String`). Одно из главных отличий заключается в том, что у каждого символа есть только один экземпляр. 142 | 143 | Что это означает на практике? И в чём отличие от строки? 144 | 145 | Например, у нас есть такие объекты: 146 | 147 | ```rb 148 | a = "slovo" 149 | b = "slovo" 150 | c = "slovo" 151 | 152 | d = :slovo 153 | e = :slovo 154 | f = :slovo 155 | ``` 156 | 157 | Дело в том, что в этом примере объекты `a`, `b` и `c` — это три разных объекта, они ссылаются на разные ячейки в памяти компьютера. 158 | 159 | А вот объекты `d`, `e` и `f` — это всё один объект. В этом легко убедиться: 160 | 161 | ```rb 162 | a.object_id #=> 47103948599080 163 | b.object_id #=> 47103948574540 164 | c.object_id #=> 47103948569400 165 | 166 | d.object_id #=> 1294428 167 | e.object_id #=> 1294428 168 | f.object_id #=> 1294428 169 | ``` 170 | 171 | Символы часто используются в хэшах в качестве ключей. Одна из причин этого вытекает из свойств символов иметь лишь один экземпляр. Это позволяет экономить потребление памяти компьютера. 172 | 173 | Ещё одно свойство символов — статичность. Т.е. к ним нельзя применить методы, подобные `downcase` или `+`. 174 | 175 | И ещё одно важное применение символов, когда к ним применяется метод `to_proc`. 176 | 177 | ```rb 178 | downator = :downcase.to_proc 179 | downator.call('STROKA') #=> "stroka" 180 | ``` 181 | 182 | Как это работает? Дело в том, что в переменной `downator` хранится блок `proc { |arg| arg.downcase }` 183 | 184 | На практике такое свойство часто применяют при операциях с массивами, например: 185 | 186 | ```rb 187 | ['STROKA', 'SLOVO'].map(&:downcase) #=> ["stroka", "slovo"] 188 | ``` 189 |
190 | 191 | 1. Как хранится массив в памяти? 192 | 193 | 1. Какую структуру данных применить для проверки "парности скобок" вида `([])` и `([[))`? 194 | 195 | 1. Почему в Ruby `1660 / 100 ≠ 16.6`? 196 | 197 |
198 | Ответ 199 | Если все аргументы арифметического выражения целые числа, то результат будет целым, если хотя бы одно число с плавающей запятой, то результат будет числом с плавающей запятой. 200 | 201 | Таким образом, чтобы получить `16.6` нужно чтобы одно из чисел имело тип `Float`. 202 | 203 | https://stackoverflow.com/questions/5502761/why-is-division-in-ruby-returning-an-integer-instead-of-decimal-value 204 |
205 | 206 | 1. Почему в Ruby `24.0 * 0.1 ≠ 2.4`? 207 |
208 | Ответ 209 | Поскольку внутренне компьютеры используют формат (binary floating point), который не может точно представить число как 0.1, 0.2 или 0.3. 210 | 211 | Когда код компилируется или интерпретируется, ваш «0.1» уже округляется до ближайшего числа в этом формате, что приводит к небольшой ошибке округления даже до того, как произойдет вычисление. 212 | 213 | https://floating-point-gui.de/basic/ 214 | 215 | https://github.com/rdp/ruby_tutorials_core/wiki/Ruby-Talk-FAQ#floats_imprecise 216 | 217 | https://en.wikipedia.org/wiki/Floating-point_arithmetic#Accuracy_problems 218 |
219 | 220 | 1. Какие структуры есть в ruby? 221 | 222 |
223 | Ответ 224 | Что такое struct, abstract, open struct 225 | Структуры в Руби следующие: 226 | 227 | * `struct` 228 | * `abstract` 229 | * `openstruct` 230 | 231 | Структуры позволяют так же работать с методами по примеру полного аналога класса. Полностью заменяют классы и возможно даже немного удобнее их. Но все пишут что не надо заменять структуры на классы полностью, они могут быть хороши только в не больших размерах и объемах коллекций. 232 | 233 | struct и open struct это упрощенная форма создания классов, в котором мы указываем что должно быть передано в struct для вывода программы. 234 | 235 | * struct — принимает четкое кол-во параметров для вывода программы. 236 | 237 | ``` rb 238 | person = :name, :age 239 | 240 | p.name = "Karthik" 241 | p.age = 30 242 | 243 | puts "Hello, I am #{p.name}, age #{p.age}" 244 | ``` 245 | 246 | либо 247 | 248 | ``` rb 249 | person = :name, :age 250 | 251 | p = "Karthik", 30 252 | 253 | puts "Hello, I am #{p.name}, age #{p.age}" 254 | ``` 255 | 256 | OpenStruct — не ругается, если параметров передано больше чем есть. 257 | 258 | ``` rb 259 | require 'ostruct' 260 | 261 | p.name= "Karthik" 262 | p.age = 30 263 | 264 | puts "Hello, I am #{p.name}, age #{p.age}" 265 | ``` 266 |
267 | 268 | 1. Что такое `loop`, `while`, `map`, `each`? 269 | 270 |
271 | Ответ 272 | 273 | `loop`, `while` — это управляющие конструкции, создающие циклы, повторение кода по условию/без условий. 274 | 275 | `each`, `map` — итераторы, перебирают все элементы у объекта (унаследованы от `Numerable`). 276 | 277 | Итераторы — это методы, которые принимают блоки и выполняют код в блоках для элементов коллекций (массивов, интервалов или хэшей). 278 | 279 | https://www.rubyguides.com/ruby-tutorial/loops/ 280 | 281 | https://www.rubyguides.com/2018/10/ruby-map-method/ 282 | 283 | http://rubycode.ru/ruby/osnovy/57-chislovye-iteratory.html 284 | 285 | http://queirozf.com/entries/ruby-map-each-collect-inject-reject-select-quick-reference 286 |
287 | 288 | 1. Чем отличается `each` от `map` ? 289 | 290 |
291 | Ответ 292 | 293 | `each` занимается просто перебором, `map` занимается перебором и конечным выводом измененного массива, также можно `map` вызвать с помощью bang-метода для изменения исходного массива. 294 |
295 | 296 | 1. Какие ещё циклы и итераторы есть в Ruby? 297 | 298 |
299 | Ответ 300 | 301 | Циклы `until`, `for` 302 | 303 | Итераторы `times`, `upto`, `downto`, `step` 304 | 305 | https://i-love-ruby.gitlab.io/#_loops 306 |
307 | 308 | 1. Назовите отличия `inject` и `reduce`. 309 | 310 |
311 | Ответ 312 | 313 | Это алиасы. 314 |
315 | 316 | 1. Какие переменные бывают, где они используются, где они доступны (поля видимости)? 317 | 318 |
319 | Ответ 320 | 321 | Локальные переменные `variable` — локальная переменная, она доступна только в той области видимости, где была определена. 322 | 323 | Переменные экземпляра класса `@variable` — доступны только в методах экземпляра класса, где они определены. При первом вызове возвращают `nil`. 324 | 325 | Глобальные переменные `$variable` — область видимости — вся программа (опасно использовать, т.к. потом сложно изменить, где и кто её поменял). 326 | 327 | Переменные класса `@@variable` — область видимости — класс в котором они определены и все экземпляры данного класса. 328 | 329 | http://rubycode.ru/ruby/osnovy/54-oblast-vidimosti-i-tipy-obektov.html 330 |
331 | 332 | 1. Что такое переменная с одной `@` и переменная с двумя `@@`? 333 | 334 |
335 | Ответ 336 | 337 | Переменные экземпляра класса `@variable` — начинаются с `@`. Переменные экземпляра класса доступны в методах экземпляра класса, где они определены. 338 | 339 | Переменные класса `@@variable` — начинаются с двух символов `@`. Их область видимости — класс в котором они определены и все экземпляры данного класса. 340 |
341 | 342 | 1. Чем `require` отличается от `require_relative`? 343 | 344 |
345 | Ответ 346 | 347 | С возможностью указания абсолютного пути и относительного `require` подключает файлы/гемы по относительному пути в строгом соответствии `./1/ruby.rb`, начиная с корня приложения `require_relative` подключает файлы без относительного пути и без указания разрешения файла, запускает прогу из той же директории, где лежит файл запуска `require_relative '1/ruby.rb'`. 348 | 349 | http://ruby.qkspace.com/ruby-require-require_relative 350 |
351 | 352 | 1. Что такое гемы? Как с ними работать? 353 | 354 | 1. Как создать геттер и сеттер методы в ruby? 355 | 356 |
357 | Ответ 358 | C помощью методов 359 | 360 | - `attr_reader` 361 | - `attr_writer` 362 | - `attr_accessor` — объединяет attr_reader и attr_writer 363 | 364 | ``` rb 365 | class Tovar 366 | # Метод для установки цены 367 | def price=(price) 368 | @price = price 369 | end 370 | 371 | def price 372 | @price 373 | end 374 | end 375 | ``` 376 | 377 | http://rubyclub.blogspot.com/2012/10/ruby_15.html 378 | 379 | http://findnerd.com/list/view/How-to-create-getter-and-setter-methods-in-Ruby/13615/ 380 |
381 | 382 | 1. Что такое `attr_reader`, `attr_writer`, `attr_accessor`? 383 | 384 |
385 | Ответ 386 | 387 | Все классы наследуют методы `Module`. 388 | 389 | `attr_reader`, `attr_writer`, `attr_accessor` являются его методами. 390 | 391 | Что делают эти методы внутри класса? 392 | 393 | `attr_reader` создаёт переменную экземпляра и метод-геттер, который возвращает её значение 394 | 395 | Эти записи эквивалентны: 396 | 397 | ```rb 398 | attr_reader :name 399 | 400 | def name 401 | @name 402 | end 403 | ``` 404 | 405 | `attr_writer` создаёт метод-сеттер, позволяющий изменять переменную экземпляра. 406 | 407 | Эти записи эквивалентны: 408 | 409 | ```rb 410 | attr_writer :name 411 | 412 | def name=(name) 413 | @name = name 414 | end 415 | ``` 416 | 417 | `attr_accessor` объединяет функционал `attr_reader` и `attr_writer`. 418 | 419 | http://ruby-doc.org/core-2.5.1/Module.html#method-i-attr_reader 420 | 421 | http://ruby-doc.org/core-2.5.1/Module.html#method-i-attr_writer 422 | 423 | http://ruby-doc.org/core-2.5.1/Module.html#method-i-attr_accessor 424 |
425 | 426 | 1. Что означает ключевое слово `self`? 427 | 428 |
429 | Ответ 430 | 431 | `self` относится к самому объекту, вызывает сам себя, без создания класса. Обычно применяется к методам внутри класса, чтобы можно вызвать без создания нового экземпляра класса. 432 | 433 | Так же можно сообщить что все методы будут `self`, делается с помощью `class << self`. 434 |
435 | 436 | 1. Что такое синглтон-методы и синглтон-классы? 437 | 438 |
439 | Ответ 440 | Синглтон-метод — метод, который может принадлежать только одному объекту. Это даёт возможность добавлять уникальное поведение отдельным объектам. 441 | 442 | ```rb 443 | cat = Animal.new 444 | dog = Animal.new 445 | 446 | def dog.barking 447 | 'WOOF! WOOF!' 448 | end 449 | 450 | dog.barking 451 | # => "WOOF! WOOF!" 452 | dog.singleton_methods 453 | # => [:barking] 454 | 455 | cat.barking 456 | # => NoMethodError (undefined method `barking' for #) 457 | cat.singleton_methods 458 | # => [] 459 | ``` 460 | 461 | Методы класса (`self`-методы) на самом деле тоже являются синглтон-методами класса `Class`. 462 | 463 | Таким образом, в Руби все методы принадлежат какому-то классу. 464 | 465 | Синглтон-класс — это анонимный класс, в котором размещаются синглтон-методы объекта. 466 | 467 | ```rb 468 | dog.singleton_class 469 | # => #> 470 | 471 | dog.singleton_class.method_defined?(:barking) 472 | # => true 473 | 474 | cat.singleton_class.method_defined?(:barking) 475 | # => false 476 | ``` 477 | 478 | Синглтон-класс встраивается в путь наследования и поиска метода интерпретатором Ruby. 479 | 480 | ```rb 481 | dog.singleton_class.superclass 482 | # => Animal 483 | ``` 484 | 485 | Подробнее [тут](https://habr.com/ru/post/143990/) 486 |
487 | 488 | 1. Что такое `super`-методы и как они работают/где применяются? 489 | 490 |
491 | Ответ 492 | `super` - ключевое слово, вызывает из родительского класса метод с аналогичным названием, что и метод вызывающий `super`. Применяется при переопределинии методов в дочерних классах. 493 | 494 | ``` 495 | class Text 496 | def initialize(body:) 497 | @body = body 498 | end 499 | end 500 | 501 | class Note < Text 502 | def initialize(body:) 503 | super 504 | @date = Time.now 505 | end 506 | end 507 | 508 | # Если количество параметров в методе родительского и дочернего классов не совпадает 509 | # можно явно задать аргументы ключевому слову super 510 | class Article < Text 511 | def initialize(body:, title:) 512 | super(body: body) # Явное задание количества аргументов для super 513 | @title = title 514 | end 515 | end 516 | 517 | text = Text.new(body: 'Просто текст') 518 | note = Note.new(body: 'Заметка') 519 | article = Article.new(title: 'Статья', body: 'Текст статьи') 520 | 521 | p text # 522 | p note # 523 | p article # 524 | 525 | ``` 526 |
527 | 528 | 529 | 1. Что такое модуль в ruby? Какая разница между классом и модулем? 530 | 531 |
532 | Ответ 533 | Модули в Руби похожи на классы в том, что они содержат набор методов, константы, другие модули и определения классов. 534 | 535 | Модули задаются как классы, только слово `module` используется вместо `class`. 536 | 537 | В отличие от классов создать объекты на основе модуля нельзя, модуль не может иметь подклассы. Вместо этого вы добавляете недостающую функциональность класса или отдельного объекта с помощью модуля. 538 | 539 | Модули — одиночки, нет иерархии и наследования. 540 | 541 | https://habr.com/post/49353/ 542 |
543 | 544 | 1. Как организовано наследование в Ruby? 545 | 546 |
547 | Ответ 548 | 549 | Наследование в Ruby — прямое. У каждого класса может быть только один родительский класс. 550 | 551 | Синтаксический сахар: 552 | 553 | ``` rb 554 | class Animal 555 | end 556 | 557 | class Dog < Animal 558 | end 559 | ``` 560 | 561 | В Ruby всё в конечном счёте принадлежит классу `BasicObject`. 562 | 563 | ``` rb 564 | str = "Я - строка" 565 | str.class #=> String 566 | str.class.superclass #=> Object 567 | str.class.superclass.superclass #=> BasicObject 568 | ``` 569 | 570 | Однако в Ruby можно сымитировать множественное наследование с помощью модулей, подключая их при помощи include/extend. 571 |
572 | 573 | 1. Чем отличается `include` от `extend`? Что такое `prepend`? 574 | 575 |
576 | Ответ 577 | 578 | * `include` — необходимо создать экземпляр класса, чтобы задействовать логику модуля; 579 | * `extend` — позволяет включить дополнительное расширение или функциональность без создания экземпляра класса, непосредственно в используемом классе. 580 | 581 | https://habr.com/post/143483/ 582 | 583 | https://inet777.ru/comments/8436/metod-module-prepend-v-ruby-2 584 | 585 | C помощью `prepend` методы модуля устанавливаются первоочередными при поиске метода в классе, в который включен модуль. 586 |
587 | 588 | 1. Реализация множественного наследования в ruby? 589 | 590 |
591 | Ответ 592 | 593 | Реализация возможна через модули с помощью подключения `include`/`extend`. 594 |
595 | 596 | 1. Если в модуле сделать `extend self`, что произойдёт? 597 | 598 |
599 | Ответ 600 | 601 | Как указано выше, `extend` позволяет подключить методы модуля к классу без создания экземпляра. 602 | 603 | Для модуля `self` — это сам модуль. 604 | 605 | Поэтому добавление `extend self` позволит использовать инстанс-методы модуля в качестве его `self`-методов. 606 | 607 | Без `extend self`: 608 | 609 | ```rb 610 | module MyModule 611 | def my_method 612 | puts 'Hello!' 613 | end 614 | end 615 | 616 | MyModule.my_method 617 | 618 | # undefined method `my_method' for MyModule:Module (NoMethodError) 619 | ``` 620 | 621 | После добавления: 622 | 623 | ```rb 624 | module MyModule 625 | extend self 626 | 627 | def my_method 628 | puts 'Hello!' 629 | end 630 | end 631 | 632 | MyModule.my_method 633 | 634 | # Hello! 635 | ``` 636 | 637 | https://blog.bigbinary.com/2012/06/28/extend-self-in-ruby.html#so-how-does-extend-self-work 638 |
639 | 640 | 1. Какие есть способы вызова методов в ruby? 641 | 642 |
643 | Ответ 644 | 645 | * `.call` — не может вызвать методы без нового класса 646 | 647 | * `.send` — может вызвать методы без нового класса 648 | 649 | * `.eval` — не используется, так как очень медленный 650 | http://quabr.com/35400337/ruby-send-vs-call-method 651 |
652 | 653 | 1. Что такое `proc`, `lambda`, `block`? И какие отличия есть между ними? 654 | 655 |
656 | Ответ 657 | Это анонимные функции, которые представляют из себя блоки. 658 | 659 | `lambda` требует чтобы кол-во аргументов в блоке, соответствовало преданным в блок, так же `lambda` возвращает значение без блока, можно вызвать на переменной метод `call` и передать к примеру `return 'any'`, `lambda` выведет. 660 | 661 | `proc` не требует и может работать без передачи аргументов, но не может вызваться методом `call` и вернуть переданное значение методом `return`. 662 | 663 | `block` это кусочек ruby кода, который заключен в фигурные скобки и блок выполняется для каждого массива значений. 664 |
665 | 666 | 1. Многопоточность в ruby? 667 | 668 | 1. Какие сервера бывают под Ruby? 669 | 670 |
671 | Ответ 672 | 673 | https://www.8host.com/blog/kratkij-obzor-veb-serverov-dlya-prilozhenij-ruby/ 674 | 675 | * WeBrick 676 | * Phusion Passenger 677 | * Puma 678 | * Thin 679 | * Unicorn 680 | * Iodine 681 |
682 | 683 | 1. Что такое safe navigation? 684 | 685 |
686 | Ответ 687 | 688 | В новом синтаксисе выражение из примеров можно записать так: 689 | 690 | `image = user&.profile&.thumbnails&.large` 691 | 692 | Оператор применяется для сокращения выражений, где выполняется проверка существования объекта и 693 | затем обращение к методу объекта только в случае положительной проверки: 694 | 695 | `obj.nil? && obj.some_method` 696 | 697 | Вместе с лаконичным видом такая реализация дает быструю проверку на `nil`, 698 | так как изменения реализованы на уровне парсера и ruby-код в проверках не участвует. 699 | После того, как встретился `nil`, дальнейшее выполнение цепочки прерывается. 700 | Проверка выполняется именно на `nil`, а не на логическое условие, 701 | поэтому если результатом окажется `false`, то выполнение будет успешно продолжено по цепочке дальше. 702 | 703 | Если в метод передаются аргументы, то, в отличие от `try`, 704 | они вычисляются только в том случае, если объект существует и метод реально вызывается. 705 | Например, для ActiveSupport в выражении `obj.try(:foo, bar())` всегда будет выполняться `bar()`, 706 | даже если `obj` не существует. Но в выражении `obj&.foo(bar())`, 707 | аргумент `bar()` будет вычислен только тогда, когда `obj` не равен `nil`. 708 | 709 | http://mitrev.net/ruby/2015/11/13/the-operator-in-ruby/ 710 | 711 | https://www.competa.com/blog/ruby-safe-navigation-operator-methods/ 712 | 713 | https://habr.com/ru/company/truevds/blog/271301/ 714 | 715 | https://medium.com/@CohenCarlisle/why-you-shouldnt-be-using-rails-try-for-nil-safe-navigation-in-ruby-d3123a3965ac 716 |
717 | 718 | 1. Как и чем проверить скорость работы методов? К примеру, что работает быстрее `each`, `proc` или `lambda`? 719 |
720 | Ответ 721 | 722 | Существуют гемы для сравнения скорости работы методов, например, `benchmark-ips`. 723 | 724 | С учётом особенностей синтаксиса гема пишется код, в котором тестируются выбранные методы. При запуске программа тестируют производительность методов с указанием разницы в процентах. 725 | https://github.com/evanphx/benchmark-ips 726 |
727 | 728 | 1. Какие существуют Ruby интерпретаторы? 729 |
730 | Ответ 731 | 732 | * CRuby 733 | * MRI 734 | * JRuby (MRi на базе JVM) 735 | * Rubinius (реализация многопоточности на самом Ruby, достаточно успешная, но не без сайдэффектов) 736 | * TruffleRuby 737 | 738 | https://habr.com/ru/post/337100/ 739 |
740 | 741 | 1. Что такое JIT? 742 |
743 | Ответ 744 | Just-In-Time (JIT) компиллятор оптимизирует, часто вызываемые методы. Таким образом, они будут запускаться быстрее в последующих вызовых. Главная цель JIT - это пропуск нескольких или всех шагов интерпретации. 745 | 746 | https://blog.heroku.com/ruby-just-in-time-compilation 747 | https://ru.wikipedia.org/wiki/JIT-%D0%BA%D0%BE%D0%BC%D0%BF%D0%B8%D0%BB%D1%8F%D1%86%D0%B8%D1%8F 748 | https://www.youtube.com/watch?v=AJIAMT7ilHw 749 |
750 | 751 | 1. Какую сортировку использует метод `sort` в ruby? 752 | -------------------------------------------------------------------------------- /interview/spec.md: -------------------------------------------------------------------------------- 1 | # Вопросы по тестированию приложений с собеседований 2 | 3 | 1. Для чего нужны тесты? 4 | 5 |
6 | Ответ 7 | Тесты позволяют сократить время на проверку написанного кода. 8 |
9 | 10 | 2. Что такое TDD и BDD? 11 | 12 |
13 | Ответ 14 | 15 | * TDD — Разработка через тестирование, Test Driven Development. Сначала пишем тест, затем реализуем его в коде. 16 | 17 | * BDD — Разработка через поведение, Behavior-driven development. Расширение подхода TDD к разработке и тестированию, при котором особое внимание уделяется поведению системы/модуля в терминах бизнеса(заказчика). Как правило, такие тесты иллюстрируют и тестируют различные сценарии, которые интересны непосредственно клиенту системы. В связи с этим при составлении таких тестов часто используется фреймворки, обладающие синтаксисом, обеспечивающим читаемость тестов не только программистом, но и представителями заказчика. 18 | 19 | * DDD - Предметно-ориентированное проектирование, Domain-driven design. Набор принципов и схем, направленных на создание оптимальных систем объектов. Процесс разработки сводится к созданию программных абстракций, которые называются моделями предметных областей. 20 | 21 | https://medium.com/daily-coding/p-fb4441d5179c 22 |
23 | 24 | 3. Что такое спеки, фабрики, моки, стабы, musta_matchers? 25 | 26 |
27 | Ответ 28 | 29 | * Спеки — спецификация, утвержденный документ, являющийся основой для разработки компьютерной программы и для ее тестирования. Либо это исполняемый файл для проверки теста. 30 | * Фабрики — Это набор данных, которые определены нами заранее и которые будут вызываться в тестах. К примеру мы можем создать фабрику `people` с набором имен, возраста, цвета кожи и все это рандомно, с проверкой и тестированием модели `people`. 31 | * Моки это поддельные методы с заранее запрограммированным поведением и соглашениями. 32 | * Стабы похожи на шпионов, но они заменяют целевую функцию (заглушки). Вы можете использовать стабы для управления поведением метода, чтобы форсировать какие-то события в коде (например, выброс ошибки). 33 | * Musta_matchers — Маста матчер позволяет проводить проверку до прогона теста. То есть `before_action` и `before_filter`. Матчеры позволяют запускать к примеру создание нового юзера с помощью колбека `before`. 34 | 35 | http://matchers.shoulda.io/ 36 |
37 | 38 | 4. Что такое юнит тесты, интеграционные тесты, функциональные тесты? 39 | 40 |
41 | Ответ 42 | 43 | **Модульное тестирование** (юнит-тесты) — предназначены для тестирования отдельных модулей/классов. Суть их в том, что мы тестируем поведение только одного класса за раз. Если класс ссылается на инстансы других классов — мы их мокаем. То есть подсовываем им фэйковый класс, который имеет тот же интерфейс, но внутри не реализация методов, а проверка, вызывали ли метод, с каким аргументами, сколько раз вызывали и т.д. 44 | 45 | **Функциональное тестирование** — это тестирования всего приложения в сборе. Если это REST API, то у нас через curl дергаются реальные методы, отправляются более менее реальные запросы и валидируются ответы. Если web-страничка, то это UI тесты с силениумом/phantom.js/zombi.js или, если нам не нужно еще и js тестить, просто curl + какой виртуальный браузер на том же php. Вообще по хорошему функциональные тесты не допускают никаких моков и т.д. но опять же если очень хочется то можно (опять же обращение к сторонним сервисам, контроля за которыми у нас нету). 46 | 47 | **Интеграционное тестирование** — тестирование нескольких модулей в связке. То есть мы тестируем наш компонент или его самодостаточный кусок в реальных условиях. Если этот компонент для работы с файлами — разрешаем ему доступ к файлам. Если база данных — то даем реальное соединение с базой. А можем что-то и замокать. 48 | 49 | Это как говорится, зависит от задачи. Скажем обращение к сторонним апишкам стоит мокать и стабить. Главная цель этих тестов, удостовериться что модули вместе работают хорошо. Особенно важно это когда модули пишут разные люди. 50 |
51 | 52 | 5. Какие гемы для тестирования вы знаете? 53 | 54 |
55 | Ответ 56 | 57 | * Rspec (https://relishapp.com/rspec/rspec-rails/docs) 58 | * Cucumber (https://cucumber.io/, https://habr.com/post/332754/) 59 | * FactoryBot (бывший FactoryGirl) 60 | * DatabaseCleaner 61 | * Capybara 62 | * CapybaraWebkit 63 | * Watir 64 |
65 | 66 | 6. Какие книги по тестированию читали? 67 | 68 |
69 | Ответ 70 | Книги по тестированию: 71 | 72 | https://www.amazon.com/s/ref=nb_sb_noss?url=search—alias%3Dstripbooks&field—keywords=rspec+rails 73 |
74 | 75 | -------------------------------------------------------------------------------- /interview/tasks.md: -------------------------------------------------------------------------------- 1 | # Задачи на собеседованиях 2 | 3 | 1. **Тыры-пыры, она же foo-bar**. Напишите программу, которая выводит на экран числа от 1 до 100. При этом вместо чисел, кратных 3, программа должна выводить слово «Hi», а вместо чисел, кратных 5 — слово «By». Если число кратно и 3, и 5, то программа должна выводить слово «HiBy». 4 | 1. Имеется строка набранная в разном регистре, например: «ВотТакаяСтрока» требуется получить в результате строку где буквы меняют регистр, то есть: «вОТтАКАЯсТРОКА». Напишите, пожалуйста, код. 5 | 1. Дана строка `s` и словарь `dict` , содержащий некие слова. Определите, можно ли строку `s` сегментировать в последовательность разделенных пробелом слов, содержащихся в словаре `dict`. 6 | 7 | Пример: дано, `s` = «двадесятка», `dict` = [«два», «десятка», «девятка»]. Программа должна вернуть `true`, потому что «двадесятка» могут быть сементированы как «два десятка». 8 | 9 | 1. Найдите непрерывный подмассив в массиве (содержащем как минимум 1 элемент), который имеет максимальную сумму элементов. 10 | 11 | Пример: [-1, -13, -2, 1, -3, 4, -1, 2, 1, -5, 4] должно вернуть [4, -1, 2, 1]. 12 | 13 | 1. Дан треугольник. Найдите минимальный путь от вершины до основания. На каждом шаге вы можете двигаться только на соседние цифры, находящиеся в ряду ниже. 14 | 15 | Пример: 16 | 17 | ``` 18 | [ 19 | [2], 20 | [3,4], 21 | [6,5,7], 22 | [4,1,8,3] 23 | ] 24 | ``` 25 | 26 | Здесь длина минимального пути от вершины до основания равна 11 (т.к 2+3+5+1 = 11). 27 | 28 | 1. У компании имеется следующий склад (см. рис), три ряда стеллажей, стоящие в ряд по 700 ед. Каждый стеллаж содержит 5 полок. Каждая полка содержит 6 ячеек. Между рядами стеллажей есть проходы. Между стеллажами в одном ряду проходов нет. Ширина полок одинакова и равна ширине прохода. Зеленым цветом обозначены проходы. 29 | 30 | Кладовщику выдается случайный перечень ячеек, из которых требуется взять товар. Помогите составить маршрут передвижения кладовщика по складу, начиная движение от стола, таким образом, чтобы он затратил минимально возможный путь. 31 | 32 | 1. Достаточно описать шаги алгоритма решения задачи. 33 | 1. Объясните почему решение оптимальное. 34 | 35 | ![Оптимальное решение](images/sklad.jpg) 36 | 37 | 1. Найдите минимальную разницу в минутах между двумя моментами времени из списка. 38 | 39 | Например, если массив такой `["2:10pm", "1:30pm", "10:30am", "4:42pm"]`, программа должна вернуть 40, потому что минимальная разница — между 1:30pm и 2:10pm и она равна 40 минутам. 40 | 41 | На вход всегда передается массив из как минимум двух элементов, все элементы массива заданы в корректном формате и уникальны. 42 | 43 | 1. Написать функцию `get_change(money, price)`, которая рассчитывает сдачу для суммы и возвращает массив монет, набор монет 1c, 5с, 10с, 25с, 50с, 1$. Возвращаемый массив это массив из шести элементов, где каждый элемент это количество монет каждого типа. 44 | 45 | ``` 46 | getChange(3.14, 1.99) => [0, 1, 1, 0, 0, 1] 47 | getChange(3, 0.01) => [4, 0, 2, 1, 1, 2] 48 | getChange(4, 3.14) => [1, 0, 1, 1, 1, 0] 49 | getChange(0.45, 0.34) => [1, 0, 1, 0, 0, 0] 50 | ``` 51 | 52 | 1. **Palindrome Swapper**: Have the function `PalindromeSwapper(str)` take the `str` parameter being passed and determine if a palindrome can be created by swapping two adjacent characters in the string. If it is possible to create a palindrome, then your program should return the palindrome, if not then return the string `-1`. The input string will only contain alphabetic characters. 53 | 54 | For example: if `str` is `"rcaecar"` then you can create a palindrome by swapping the second and third characters, so your program should return the string `racecar` which is the final palindromic string. 55 | 56 | Examples: 57 | 58 | * Input: `"anna"`, Output: `anna` 59 | * Input: `"kyaak"`, Output: `kayak` 60 | 61 | 1. Реализовать возможность скрытия логина скайпа (логин может быть разделен точкой). Символ скрытия по умолчанию `"ххх"`. 62 | 63 | Логин может встретиться в двух местах: 64 | 65 | 1. В строчке. skype:some.login 66 | 1. В html тэге . Пример `skype` 67 | 68 | 1. Реализовать возможность скрытия произвольного количества цифр телефонного номера. По умолчанию скрывается 3 последние цифры. По умолчанию символ замены цифр `"х"`. 69 | 70 | Формат номера `+1 111 111 11 11`. Результат выполнения: `+1 111 111 1х хх`. 71 | 72 | Пробелов между цифрами может быть сколько угодно, но результат выполнения должен приводиться к формату `+1 111 111 11 11`. 73 | 74 | 1. Пользователь вводит строки, содержащие цифры, разделенные запятыми. Например "1,2,3,4". Пустая строка означает окончание ввода. После окончания ввода одной строки, запрашивается следующая и т.д. Две пустых строки подряд означает, что пользователь закончил ввод данных. Необходимо проверить что введенная матрица является квадратной (количество строк равно количеству столбцов). Если матрица является квадратной, то посчитать ее определитель. 75 | 76 | 1. **HTML Elements**: Have the function `HTMLElements(str)` read the `str` parameter being passed which will be a string of HTML DOM elements and plain text. The elements that will be used are: `b, i, em, div, p`. 77 | 78 | For example: if `str` is `"

hello world

"` then this string of DOM elements is nested correctly so your program should return the string `true`. 79 | 80 | If a string is not nested correctly, return the first element encountered where, if changed into a different element, would result in a properly formatted string. If the string is not formatted properly, then it will only be one element that needs to be changed. 81 | 82 | For example: if `str` is `"
helloworld"` then your program should return the string `div` because if the first `
` element were changed into a ``, the string would be properly formatted. 83 | 84 | Examples: 85 | 86 | * Input: `"

"`, Output: `div` 87 | * Input: `"
abc

test test test

"`, Output: `i` 88 | 89 | 1. **K Unique Characters**: Have the function `KUniqueCharacters(str)` take the `str` parameter being passed and find the longest substring that contains `k` unique characters, where `k` will be the first character from the string. The substring will start from the second position in the string because the first character will be the integer `k`. 90 | 91 | For example: if `str` is `"2aabbacbaa"` there are several substrings that all contain 2 unique characters, namely: `["aabba", "ac", "cb", "ba"]`, but your program should return `"aabba"` because it is the longest substring. If there are multiple longest substrings, then return the first substring encountered with the longest length. `k` will range from 1 to 6. 92 | 93 | Examples: 94 | 95 | * Input: `"3aabacbebebe"`, Output: `"cbebebe"` 96 | * Input: `"2aabbcbbbadef"`, Output: `"bbcbbb"` 97 | 98 | 1. **Сумма квадратов**: Программа должна вернуть строку `'true'`, если заданное число является суммой квадратов и `'false'`, если не является. 99 | 100 | Например: 101 | 102 | * 25 должно вернуть `'true'`, потому что `25 = 3² + 4²` 103 | * 1601 должно вернуть `'true'`, потому что `1601 = 40² + 1²` 104 | 105 | 1. **Сравнение массивов**: Даны два массива массивов. Сравнить массивы и вернуть `true`, если массивы массивов одинаковы. Элементы в массиве могут быть переставлены местами, и значения внутри этих массивов могут тоже быть переставлены. 106 | 107 | Например: 108 | * ```# func([[5, 0], [5, 0], [5, 0]], [[5, 0], [5, 0], [0, 5]]) #=> true``` 109 | * ```# func([[2, 3], [5, 0]], [[5, 0], [3,2]]) #=> true``` 110 | 111 | 1. **Покупка/продажа зерна**: Дан массив с ценами на зерно по дням. Цена покупки и продажи одинакова в этот день. Найти **индексы дня** покупки и последующей продажи для получения максимальной выгоды. 112 | 113 | Вернуть массив из 2х элементов: индекс дня покупки и индекс дня продажи или пустой массив. 114 | 115 | Например: 116 | * ``` profit([13, 6, 3, 4, 10, 2, 3]) #=> [2, 4] ``` 117 | * ``` profit([13, 6, 3, 1]) #=> [] ``` 118 | 119 | 1. **Сумма цифр**: Написать функцию, которая принимает на вход число, суммирует цифры в нём, потом, если получилось число из 2 и более цифр, суммирует цифры в нём и так далее, пока не получится однозначное число, которе функция возвращает. Такое число называется «цифровым корнем» исходного числа. 120 | -------------------------------------------------------------------------------- /interview/webdev.md: -------------------------------------------------------------------------------- 1 | # Вопросы по веб-разработке с собеседований 2 | 3 | 1. Что происходит после того, как вы вводите название сайта в браузер и нажимаете Enter? Подробно объяснить. 4 |
5 | Ответ 6 | 7 | #### *1. Парсинг URL - можно отнести к условно первому этапу (не считая самого процесса ввода символов в поисковом поле браузера), во время которого*: 8 | - Браузер проверяет список предзагруженных HSTS (HTTP Strict Transport Security). Это список сайтов, которые требуют, чтобы к ним обращались только по HTTPS. Если нужный сайт есть в этом списке, то браузер отправляет ему запрос через HTTPS вместо HTTP. В противном случае, начальный запрос посылается по HTTP. 9 | - Конвертируются не-ASCII Unicode символы в название хоста. 10 | 11 | #### *2. Следующий этап - Определение DNS* 12 | - Браузер проверяет наличие домена в своём кэше. Если домена там нет, то браузер вызывает библиотечную функцию *gethostbyname* (отличается в разных ОС) для поиска нужного адреса в файле *hosts*. 13 | - Если домен нигде не закэширован и отсутствует в файле hosts, gethostbyname отправляет запрос к сетевому DNS-серверу. 14 | - Запрос к сетевому DNS-серверу называется ARP-запросом. 15 | - Для того, чтобы отправить ARP-запрос браузеру необходимо отыскать целевой IP-адрес, а также знать MAC-адрес интерфейса, который будет использоваться для отправки ARP-запроса. 16 | 17 | #### *3. Открытие сокета и сборка TCP-сегмента/пакета* 18 | - Когда браузер получает IP-адрес конечного сервера, то он берёт эту информацию и данные об используемом порте из URL (80 порт для HTTP, 443 для HTTPS), осуществляет вызов функции socket системной библиотеки и запрашивает поток TCP сокета. 19 | - Этот запрос сначала проходит через транспортный уровень, где собирается TCP-сегмент. Получившийся сегмент отправляется на сетевой уровень, на котором добавляется дополнительный IP-заголовок, IP-адрес сервера назначения и адрес текущей машины — теперь сегмент сформирован. 20 | 21 | #### *4. TLS handshake — для передачи пакетов данных между клиентом (компьютером) и сервером важно установить TCP-соединение. Это соединение устанавливается с помощью процесса, называемого трехсторонним рукопожатием TCP / IP, реализованного следующим образом*: 22 | 23 | - Клиентская машина отправляет SYN-пакет на сервер, спрашивая, открыт ли он для новых подключений. 24 | - Если на сервере есть открытые порты, которые могут принимать и инициировать новые соединения, он ответит, используя пакет SYN / ACK. 25 | - Клиент получит пакет SYN / ACK от сервера и подтвердит его, отправив пакет ACK. 26 | 27 | #### *5. Обработка HTTP-запросов на сервере* 28 | - Одним из инструментов обработки запросов/ответов на стороне сервера является HTTPD. Наиболее популярные HTTPD-серверы это Apache или Nginx для Linux и IIS для Windows. 29 | - Сервер разбирает запрос по следующим параметрам: метод HTTP-запроса (наиболее распространенные — GET/POST), домен, запрашиваемые пути. 30 | - Сервер находит контент, который соответствует запросу и парсит файл с помощью обработчика. 31 | 32 | #### *6. Парсинг HTML и интерпретация CSS* 33 | - Главной задачей HTML-парсера является разбор разметки в специальное дерево — «parse tree» — это дерево DOM-элементов. 34 | - Во время разбора браузер парсит CSS-файлы, каждый из которых разбирается в объект StyleSheet. 35 | 36 | #### *7. Рендеринг страниц и пост-рендеринговое исполнение* 37 | - Путём перебора DOM-узлов и вычисления для каждого узла значений CSS-стилей создаётся «Дерево рендера» (Render Tree или Frame Tree). 38 | - Вычисляются координаты каждого узла. Вычисляются финальные позиции слоёв и через Direct3D/OpenGL отдаются композитные команды. 39 | - После завершения рендеринга, браузер исполняет JavaScript-код в результате срабатывания часового механизма или в результате действий пользователя. 40 | 41 | #### *Для более детального ознакомления:* 42 | - https://habr.com/ru/company/htmlacademy/blog/254825/ 43 | - https://github.com/alex/what-happens-when 44 | - https://medium.com/@maneesha.wijesinghe1/what-happens-when-you-type-an-url-in-the-browser-and-press-enter-bb0aa2449c1a 45 |
46 | 47 | 1. Что такое сессия? Для чего используется? 48 | 1. Что такое процессы? Как с ними работать? 49 | 1. Что такое DNS? 50 | 1. Настройка http-серверов. 51 | 1. Сравните сервер аппликейшены и сервис апликейшены (Nginx, Apache, Puma, Webrick). 52 | 1. Nginx, его отличие от apache? 53 | 54 |
55 | Ответ 56 | Два самых широко распространенных веб-сервера. Если рассматривать жизненные примеры, то основные различия между Apache и Nginx в том как они обрабатывают запросы к статическому и динамическому контенту. 57 |
58 | 59 | 1. Почему используют не Puma, а Nginx? 60 | 1. Балансировка нагрузки на сервера приложений (haproxy). 61 | 1. Чем отличается HTTP от HTTPS? 62 | 63 |
64 | Ответ 65 | 66 | * HyperText Transfer Protocol 67 | 68 | * HyperText Transfer Protocol Secure — расширение протокола HTTP для поддержки шифрования в целях повышения безопасности. 69 |
70 | 71 | 1. Из чего состоит HTTP запрос? 72 | 1. Что такое HTTP OPTIONS? 73 | 74 |
75 | Ответ 76 | 77 | Используется для определения возможностей веб-сервера или параметров соединения для конкретного ресурса. 78 | В ответ серверу следует включить заголовок Allow со списком поддерживаемых методов. 79 | Также в заголовке ответа может включаться информация о поддерживаемых расширениях. 80 |
81 | 82 | https://developer.mozilla.org/ru/docs/Web/HTTP/Methods/OPTIONS 83 | https://ru.wikipedia.org/wiki/HTTP#OPTIONS 84 | https://habr.com/ru/post/342432/ 85 | 1. Какое шифрование имеет HTTPS? 86 | 87 |
88 | Ответ 89 | 90 | Защиту данных в HTTPS обеспечивает криптографический протокол SSL/TLS, 91 | который шифрует передаваемую информацию. По сути этот протокол является обёрткой для HTTP. 92 | Он обеспечивает шифрование данных и делает их недоступными для просмотра посторонними. 93 | Протокол SSL/TLS хорош тем, что позволяет двум незнакомым 94 | между собой участникам сети установить защищённое соединение через незащищённый канал. 95 | 96 | https://yandex.ru/blog/company/77455 97 | https://habr.com/ru/post/188042/ 98 | https://firstssl.ru/faq/general-questions/chto-takoe-https 99 |
100 | 101 | 1. Что такое сессии? Для чего нужны? 102 | 1. Какое максимальное количествол кб, может весить 1 кука в сессии RoR? 103 | 104 |
105 | Ответ 106 | 4 kb 107 |
108 | 109 | 1. Что такое crontab и для чего используются? 110 | 1. Как устроен HTTP, какие есть заголовки, как работают cookies, как работает HTTPS? 111 | 112 | 1. Реализация протокола AMQP 113 | 114 |
115 | Ответ 116 | AMQP протокол используется для передачи данных между компонентами системы. Основная идея состоит в том, что отдельные подсистемы (или независимые приложения) могут обмениваться произвольным образом сообщениями через AMQP-брокер, который осуществляет маршрутизацию, возможно гарантирует доставку, распределение потоков данных, подписку на нужные типы сообщений. 117 | 118 | Брокеры: RabbitMQ (гем `bunny`), ActiveMQ, Apache Kafka. 119 | 120 | https://ru.wikipedia.org/wiki/AMQP 121 | https://kt.team/hr/blog/rabbitmq 122 | https://www.bigdataschool.ru/blog/kafka-vs-rabbitmq-big-data.html#:~:text=%D0%A7%D0%B5%D0%BC%20%D0%9A%D0%B0%D1%84%D0%BA%D0%B0%20%D0%BE%D1%82%D0%BB%D0%B8%D1%87%D0%B0%D0%B5%D1%82%D1%81%D1%8F%20%D0%BE%D1%82%20%D0%9A%D1%80%D0%BE%D0%BB%D0%B8%D0%BA%D0%B0,(topic)%20%D0%BD%D1%83%D0%B6%D0%BD%D1%8B%D0%B5%20%D0%B8%D0%BC%20%D1%81%D0%BE%D0%BE%D0%B1%D1%89%D0%B5%D0%BD%D0%B8%D1%8F. 123 | https://habr.com/ru/company/itsumma/blog/416629/ 124 |
125 | 126 | 1. Что такое OSI-модель? Сколько уровней она имеет, опишите их. 127 | 128 |
129 | Ответ 130 | Модель Open Systems Interconnection (OSI) – это скелет, фундамент и база всех сетевых сущностей. Модель определяет сетевые протоколы, распределяя их на 7 логических уровней. Важно отметить, что в любом процессе, управление сетевой передачей переходит от уровня к уровню, последовательно подключая протоколы на каждом из уровней. 131 | 132 | https://ru.wikipedia.org/wiki/%D0%A1%D0%B5%D1%82%D0%B5%D0%B2%D0%B0%D1%8F_%D0%BC%D0%BE%D0%B4%D0%B5%D0%BB%D1%8C_OSI 133 | https://wiki.merionet.ru/seti/18/model-osi-eto-prosto/ 134 |
135 | 136 | 1. Назовите отличия протокола TCP и UDP. 137 | 138 |
139 | Ответ 140 | Протокол TCP (Transmission Control Protocol) – это сетевой протокол, который «заточен» под соединение. Иными словами, прежде, чем начать обмен данными, данному протоколу требуется установить соединение между двумя хостами. Данный протокол имеет высокую надежность, поскольку позволяет не терять данные при передаче, запрашивает подтверждения о получении от принимающей стороны и в случае необходимости отправляет данные повторно. При этом отправляемые пакеты данных сохраняют порядок отправки, то есть можно сказать, что передача данных упорядочена. Минусом данного протокола является относительно низкая скорость передачи данных, за счет того что выполнение надежной и упорядоченной передачи занимает больше времени, чем в альтернативном протоколе UDP. 141 | 142 | Протокол UDP (User Datagram Protocol), в свою очередь, более прост. Для передачи данных ему не обязательно устанавливать соединение между отправителем и получателем. Информация передается без предварительной проверки готовности принимающей стороны. Это делает протокол менее надежным – при передаче некоторые фрагменты данных могут теряться. Кроме того, упорядоченность данных не соблюдается – возможен непоследовательный прием данных получателем. Зато скорость передачи данных по данному транспортному протоколу будет более высокой. 143 | 144 | https://wiki.merionet.ru/seti/23/tcp-i-udp-v-chem-raznica/ 145 | http://pyatilistnik.org/chem-otlichaetsya-protokol-tcp-ot-udp/ 146 | https://yandex.ru/q/question/computers/chem_otlichaetsia_tcp_ot_udp_66a93f75/ 147 | https://habr.com/ru/company/oleg-bunin/blog/461829/ 148 |
149 | 150 | 1. Что такое RPC? 151 | 152 |
153 | Ответ 154 | RPC (от англ. Remote Procedure Call, RPC) Удалённый вызов процедур, реже Вызов удалённых процедур — класс технологий, позволяющих компьютерным программам вызывать функции или процедуры в другом адресном пространстве (на удалённых компьютерах, либо в независимой сторонней системе на том же устройстве). Обычно реализация RPC-технологии включает в себя два компонента: сетевой протокол для обмена в режиме клиент-сервер и язык сериализации объектов (или структур, для необъектных RPC). 155 | 156 | https://ru.wikipedia.org/wiki/%D0%A3%D0%B4%D0%B0%D0%BB%D1%91%D0%BD%D0%BD%D1%8B%D0%B9_%D0%B2%D1%8B%D0%B7%D0%BE%D0%B2_%D0%BF%D1%80%D0%BE%D1%86%D0%B5%D0%B4%D1%83%D1%80 157 |
158 | -------------------------------------------------------------------------------- /test_assignments/README.md: -------------------------------------------------------------------------------- 1 | # Список тестовых заданий на позицию Ruby on Rails разработчика 2 | 3 | Ссылка на этот список: https://git.io/JvQHV 4 | 5 | [SQL: запрос к БД](SQL_find_max_score.md) 6 | 7 | [SQL: написать запросы к базе данных](SQL_query_for_users.md) 8 | 9 | [Non-rails framework: text web-app with self-destructing messages](app_with_self_destructing_text_messages.md) 10 | 11 | [RoR + Selenium: автоматизированный сбор списка активных юзеров](automated_collection_of_active_forum_users.md) 12 | 13 | [RoR + Selenium: автоматизированный поиск тем по ключевым словам на форуме](automated_keyword_search.md) 14 | 15 | [RoR + Selenium: автоматизированная проверка новых личных сообщений на форуме](automated_unread_messages_checking.md) 16 | 17 | [RoR + Selenium: автоматизированный сбор данных юзеров](automated_user_data_collection.md) 18 | 19 | [RoR: бот-калькулятор для Telegram](calculating_bot_for_telegram.md) 20 | 21 | [Ruby + JSON RESTful API: приложение с объявлениями о работе](job_advertisement_site.md) 22 | 23 | [Ruby + JSON API: сервис без использования Ruby on Rails](json_api_service_without_rails.md) 24 | 25 | [RoR: JSON API с экшенами для блога](json_api_for_blog.md) 26 | 27 | [RoR: API для обменника валют](currency_exchange_rails_api.md) 28 | 29 | [JSON API: прототип для системы бронирования авто](prototype_for_car_hiring_system.md) 30 | 31 | [JSON API: учет посещенных ссылок](ror_api_reference_counting.md) 32 | 33 | [RoR: meals delivery service](meals_delivery_service.md) 34 | 35 | [RoR: выгрузка тестового прайс-листа и создание карточек для онлайн-магазина](price_list_export_algorithms_for_marketplace.md) 36 | 37 | [RoR + Ember: API для сайта продажи/аренды недвижимости](rails_api_for_real_estate_site.md) 38 | 39 | [RoR + Ember: простой трекер задач](simple_to_do_list.md) 40 | 41 | [RoR: таск-менеджер с функцией аутентификации](task_manager_with_authentication.md) 42 | 43 | [RoR: панель администратора магазина](shop_dashboard.md) 44 | 45 | [Ruby: функция Checkout для магазина](shop_with_checkout.md) 46 | 47 | [Ruby: тотализатор](totalizator.md) 48 | 49 | [Ruby: конвертер из CSV в ASCII таблицу](csv_ascii_converter.md) 50 | 51 | [Ruby: сервис статистики видеопросмотров](video_view_statistics_service.md) 52 | 53 | [Ruby: сервис проверки кредитных карт](credit_card_checker.md) 54 | 55 | [TelegramBot: конвертация стикеров в PNG-файлы](telegram_bot_sticker_png.md) 56 | 57 | [RoR + Front end: RESTful JSON API для управления пользователями сайта](web_panel_for_users_control.md) 58 | 59 | [RoR + PostgreSQL: приложение, которое импортирует коммиты GitHub в БД](import_commits_from_github.md) 60 | 61 | [RoR: консольное приложение для проверки статистики футбольных матчей](player_statistics.md) 62 | 63 | [RoR: JSON API для новостного сайта](news_site_API.md) 64 | 65 | [RoR: simple appointments management system](appointments_management_system.md) 66 | 67 | [RoR: приложение для ведения списка персон](app_for_managing_people_list.md) 68 | 69 | [RoR: импорт коммитов из репозитория GitHub](import_commits_app.md) 70 | 71 | [RoR: billing system](billing_system.md) 72 | 73 | [RoR: структура БД для хранения данных о товарах и магазинах](database_structure_for_shops.md) 74 | 75 | [RoR: система решения математических уравнений](solving_mathematical_equations_app.md) 76 | 77 | [RoR: подсчет различных видов html-тегов по вводимым url](count_html_tags_by_url.md) 78 | 79 | [RoR: генерация pdf-файлов (дипломов) по гитхабу](pdf_diploma_generator.md) 80 | 81 | [RoR: REST API для блога](rest_api_for_blog.md) 82 | 83 | [RoR: система бронирования столов в ресторанах (только модели)](restaurants_with_tables.md) 84 | 85 | [RoR: API для управления списками задач](oblako_group_test_app.md) 86 | 87 | [RoR: Приложение для заказа обеда](lunch_ordering_saas.md) 88 | 89 | [RoR: Приложение для управления поликлиникой](clinic_management_system.md) 90 | 91 | [RoR: Приложение для построения небольшого сайта с иерархией страниц](app_with_page_hierarchy.md) 92 | 93 | [RoR: Приложение для сокращения ссылок](url_shortener_app.md) 94 | 95 | [Grape + Ruby\/RoR: Приложения для импорта маркетов валют](grape_markets_list_app.md) 96 | 97 | [ROR6 + Grape: API для статистики по погоде](weather_statistics_api.md) 98 | -------------------------------------------------------------------------------- /test_assignments/SQL_find_max_score.md: -------------------------------------------------------------------------------- 1 | ## SQL: запрос к БД 2 | 3 | Есть таблица `users` [ id (int), email (str), score (int), company_id(int) ] 
со связью «один ко многим» с таблицей `companies` [ id(int), name(str) ] 
 4 | 5 | **Задание** 6 | 7 | Получить выборку [ id, email, score, company_id ] с максимальным `score` по каждой компании. 8 | 9 | `Users` 10 | 11 | |ID|email|score|company_id| 12 | |---|---|---|---| 13 | |1|user1@test.home|8|1| 14 | |2|user2@test.home|8|2| 15 | |3|user3@test.home|4|1| 16 | |4|user4@test.home|1|2| 17 | |5|user5@test.home|2|1| 18 | |6|user6@test.home|3|2| 19 | |7|user7@test.home|0|1| 20 | |8|user8@test.home|6|2| 21 | |9|user9@test.home|9|1| 22 | 23 | Result 24 | 25 | |ID|email|score|company_id| 26 | |---|---|---|---| 27 | |9|user9@test.home|9|1| 28 | |2|user2@test.home|8|2| -------------------------------------------------------------------------------- /test_assignments/SQL_query_for_users.md: -------------------------------------------------------------------------------- 1 | ## SQL: написать запросы к базе данных 2 | 3 | **Условия** 4 | 5 | Дана таблица `users` с полями `id`, `group_id`. 6 | 7 | ```sql 8 | CREATE TEMP TABLE users(id bigserial, group_id bigint); 9 | INSERT INTO users(group_id) VALUES (1), (1), (1), (2), (1), (3); 10 | ``` 11 | 12 | В этой таблице, упорядоченной по `id` необходимо: 13 | 14 | - выделить непрерывные группы по `group_id` с учётом указанного порядка записей (их 4); 15 | 16 | - подсчитать количество записей в каждой группе; 17 | 18 | - вычислить минимальный `id` записи в группе. 19 | 20 | Для таблицы: 21 | 22 | | id | group_id | 23 | | ------- | -------- | 24 | | 1 | 1 | 25 | | 2 | 1 | 26 | | 3 | 1 | 27 | | 4 | 2 | 28 | | 5 | 1 | 29 | | 6 | 3 | 30 | 31 | Непрерывными группами можно считать: 32 | 33 | | group_id | 34 | | -------- | 35 | | 1 | 36 | | 2 | 37 | | 1 | 38 | | 3 | 39 | 40 | Запрос должен выводить: 41 | 42 | | min_id | group_id | count | 43 | | ------ | -------- | ------ | 44 | | 1 | 1 | 3 | 45 | | 4 | 2 | 1 | 46 | | 5 | 1 | 1 | 47 | | 6 | 3 | 1 | -------------------------------------------------------------------------------- /test_assignments/app_for_managing_people_list.md: -------------------------------------------------------------------------------- 1 | ## RoR: приложение для ведения списка персон 2 | 3 | **Задание** 4 | 5 | Создать приложение для ведения списка персон и склонений их ФИО. 6 | 7 | **Требования** 8 | 9 | _В системе есть персоны (People):_ 10 | 11 | * first_name — обязательное поле; 12 | * last_name — необязательное поле; 13 | * middle_name — необязательное поле; 14 | * sex (пол) — необязательное поле; 15 | * full_name — обязательное поле. 16 | 17 | `full_name` пишется в БД автоматически исходя из предоставленных `first_name`, `last_name`, `middle_name`. 18 | 19 | `sex` может быть только 2-х типов — «Мужской» и «Женский». 20 | 21 | Необходимо реализовать автоматическую запись в БД склонений `first_name`, `last_name`, `middle_name`, `full_name` для каждой персоны при их создании и изменении. Склонения ФИО должны быть записаны НЕ в таблицу `peoples`. 22 | 23 | _Падежи:_ 24 | 25 | * родительный 26 | * дательный 27 | * творительный 28 | * винительный 29 | * предложный 30 | 31 | _Страницы_ 32 | 33 | 1. Страница «Список Персон» 34 | 35 | Отображается таблица всех персон. 36 | Колонки таблицы: Имя, Фамилия, Отчество, ФИО в родительном падеже, Пол, Действия. 37 | 38 | В колонке «Действия» 3 кнопки: 39 | 40 | * переход на страницу редактирования персоны; 41 | * удаление персоны. 42 | 43 | На странице кнопка есть «создать персону». 44 | 45 | 2. Страница «Персона» 46 | 47 | * таблица со всеми данными персоны (включая все склонения имени, фамилии, отчества, ФИО); 48 | * кнопка «Назад в список персон»; 49 | * кнопка «Редактирование персоны». 50 | 51 | 3. Форма персоны 52 | 53 | * поля — имя, фамилия, отчество, пол; 54 | * кнопка «Назад на страницу персоны». 55 | 56 | **Особенности, требования к реализации** 57 | 58 | * Rails; 59 | * имена русские / жителей СНГ; 60 | * нужно покрыть тестами; 61 | * в системе нет ролей, аутентификации или авторизации; 62 | * требований к оформлению нет; 63 | * можно использовать любые гемы. 64 | 65 | Ответ к заданию — проект на GitHub/GitLab/Bitbucket. -------------------------------------------------------------------------------- /test_assignments/app_with_page_hierarchy.md: -------------------------------------------------------------------------------- 1 | ## RoR: приложение для построения небольшого сайта с иерархией страниц 2 | 3 | **Задание** 4 | 5 | Необходимо продемонстрировать умение программировать на Ruby с помощью Rails. Будет круто если вы выложите задачу на `github`, и покроете ее тестами на `rspec`. 6 | 7 | Создать небольшой сайт, который состоит из текстовых страниц, организованных в иерархию. То есть, одна страница может быть под-страницей другой страницы. 8 | 9 | **Функционал** 10 | 11 | На главной странице расположено дерево страниц сайта. 12 | 13 | ``` 14 | страница 15 | подстраница 16 | подстраница 17 | подподстраница 18 | страница 19 | ``` 20 | 21 | Каждая страница описывается следующими полями: 22 | - `имя страницы` - строка, удовлетворяет условию `[a-zA-Z0-9_]`, ДОПУСТИМЫ РУССКИЕ 23 | СИМВОЛЫ 24 | - `заголовок страницы` - произвольная строка 25 | - `текст страницы` - произвольный текст, в котором может присутствовать html-разметка. 26 | 27 | Адресная схема мини-сайта: 28 | 29 | `[site]name1/name2/name3` - открывается страница с именем `name3`, которая является под-страницей страницы `name2`, которая является под-страницей страницы `name1`. 30 | На странице виден её текст и заголовок, а также поддерево всех её подстраниц. 31 | 32 | `[site]name1/name2/name3/edit` - страница открывается в режиме редактирования - можно редактировать заголовок и текст. 33 | После сохранения нужно делать редирект на адрес `[site]name1/name2/name3`. 34 | 35 | `[site]name1/name2/name3/add` - форма добавления подстраницы к текущей странице, можно задать имя, заголовок и текст. 36 | После добавления нужно делать редирект на адрес `[site]name1/name2/name3/[новое имя]`. 37 | 38 | `[site]add` - форма добавления корневой страницы. 39 | 40 | При сохранении или добавлении текст страниц должен подвергаться следующим преобразованиям: 41 | 42 | - `**[строка]**` => `[строка]` (выделение жирным) 43 | - `\\[строка]\\` => `[строка]` (выделение курсивом) 44 | - `((name1/name2/name3 [строка]))` преобразовывать в ссылку на страницу `[site]name1/name2/name3` 45 | Однако, при редактировании страницы пользователь должен править неформатированный текст. 46 | 47 | **Требования** 48 | 49 | Реализовать это всё нужно на `Rails >= 4.0`, `Ruby >= 2.2`. 50 | Время отдачи любой из страниц вида `[site]name1/name2/` не должно превышать 100 ms для теста утилитой `ab` c параметрами `-с 100 -n 10000`. 51 | 52 | Обращать внимание на: 53 | - архитектуру приложения 54 | - читаемость кода 55 | - комментирование кода 56 | - безопасность кода 57 | - дизайн не важен 58 | -------------------------------------------------------------------------------- /test_assignments/app_with_self_destructing_text_messages.md: -------------------------------------------------------------------------------- 1 | ## Non-rails framework: text web-app with self-destructing messages 2 | 3 | Build a web application, which creates text self-destructing 4 | messages. 5 | 6 | **Requirements** 7 | 8 | A user opens the website and creates a message. The application generates a safe link to this saved message (such as: http://yourapp.com/message/ftr45e32fgv56d2 ). 9 | 10 | The user should be able to choose a destruction option: 11 | 12 | - destroy message after the first link visit 13 | 14 | - destroy after 1 hour 15 | 16 | All the messages stored on the server side should be encrypted using the AES algorithm (you can use any library for text encryption). 17 | 18 | Cover your application with the unit and integration tests using 19 | rspec. 20 | 21 | **Technologies** 22 | 23 | Use any non-rails framework (sinatra, hanami or any other) for ruby backend. Also please deploy your application to Heroku. 24 | 25 | **Bonus points for implementing** 26 | 27 | - message should be encrypted on the frontend side, using a password and should be sent to backend in an encrypted format (to view the message, the user should enter a correct password) 28 | 29 | - self-destruction of messages after a given number of link visits or after a given number of hours -------------------------------------------------------------------------------- /test_assignments/appointments_management_system.md: -------------------------------------------------------------------------------- 1 | ## RoR: simple appointments management system 2 | 3 | **Requirements** 4 | 5 | This is a simple appointments management system. It should have a web interface for customers and ability to integrate it through the REST JSON API with the 3rd party applications. 6 | 7 | Here is a short list of specs we would like to be implemented. Everything what isn’t outlined here is up to you. Feel free to add anything necessary by your opinion. 8 | 9 | * As a user I can register in the system (please put a few lines why you have chosen this implementation approach). 10 | 11 | * As a user I can see a list of my upcoming and past appointments. 12 | 13 | * As a user I can create new appointment and with as many reminders as I need. 14 | 15 | * As a user in the web interface I can see a list of submitted appointments through the API and confirm or cancel them. 16 | 17 | _​Key specs for objects(​remember, everything else is up to you)_ 18 | 19 | * Appointment has several statuses (pending/confirmed/canceled). 20 | 21 | * Let’s assume that appointment has a one hour length and can’t be overlapped by another one. 22 | 23 | * Reminder has status (reminded or not), time to raise remind before appointment. 24 | 25 | * Please add any other restrictions you think are fitable to system objects and don’t forget to describe a reason. 26 | 27 | _​API_ 28 | 29 | * As a guest, if I know user API key, I can post request to create appointment on a specific date with defined reminder. 30 | 31 | * As a quest, if I know user API key, I can receive the list of user appointments and filter it by date (let’s keep it simple, can specify only one day in params and receive appointments exactly during this day). 32 | 33 | * As a system I should be able to monitor API usage and store general statistics per each user. Please store type of request and its time. 34 | 35 | * As a system I should be able to send reminders for appointments in the specified time. 36 | 37 | **Technical notes** 38 | 39 | * For each chosen technology like DB, Scheduling, Stats Collector, API responses builder try to describe what options are in general and why the option you have chosen is the best one here. 40 | 41 | * The code quality should we perfect as well as timing of delivering this task. 42 | 43 | * The code should be covered with unit, functional and integration tests (please use RSpec+Capybara). 44 | 45 | * Front-end can be pretty very simple. The source code of application should be uploaded on GitHub in the end. -------------------------------------------------------------------------------- /test_assignments/automated_collection_of_active_forum_users.md: -------------------------------------------------------------------------------- 1 | ## RoR + Selenium: автоматизированный сбор списка активных юзеров 2 | 3 | Необходимо продемонстрировать умение не только решать поставленную задачу, но и качественно оформлять код: 4 | 5 | - выбирать содержательные названия для классов, методов и переменных; 6 | 7 | - писать разумные комментарии к каждому классу и методу, указывать тип и описание для каждого параметра; 8 | 9 | - создавать методы и классы разумного размера (по количеству строк); 10 | 11 | - использовать константы с понятными названиями вместо «магических чисел». 12 | 13 | Необходимо обдумать не только «позитивный» случай, но и возможные ошибки в процессе обработки (на практике они более чем возможны). В том числе случай, когда меняется структура страниц и алгоритм перестаёт функционировать корректно. Все такие ошибки должны правильно и, по возможности, унифицированно обрабатываться. 14 | 15 | **Задание** 16 | 17 | Реализуйте автоматизированный сбор списка самых активных участников вашего любимого форума (или любого форума, где есть список пользователей, отсортированный по числу сообщений). 18 | 19 | **Предполагаемый алгоритм решения задачи** 20 | 21 | - залогиниться на форуме, используя предоставленные логин и пароль аккаунта, если это требуется для получения списка пользователей; 22 | 23 | - получить список пользователей, отсортированный по числу сообщений; 24 | 25 | - собрать все `username` аккаунтов (и число их сообщений), у которых больше N сообщений, пролистывая страницы списка; 26 | 27 | - занести информацию в таблицу `forum_users` базы данных с полями `{ VARCHAR username, INT messages_count, DATE scraped_date }`, где `username` + `scraped_date` (дата сбора данных) имеют ограничение на уникальность (unique constraint). В случае наличия записи — не обновлять данные. 28 | 29 | **Технологии** 30 | 31 | Задание нужно реализовать на Ruby On Rails в виде периодической задачи Resque + Resque Scheduler, где логин и пароль аккаунта, а также расписание выполнения хранятся в конфигурационном файле. 32 | 33 | Рекомендуем продумать архитектуру решения: желательно выделить «низкий уровень» элементарных запросов и «высокий уровень» управления навигацией и обработки ошибок навигации. Обязательно использовать принцип «тонких контроллеров» для resque jobs. -------------------------------------------------------------------------------- /test_assignments/automated_keyword_search.md: -------------------------------------------------------------------------------- 1 | ## RoR + Selenium: автоматизированный поиск тем по ключевым словам на форуме 2 | 3 | Необходимо продемонстрировать умение не только решать поставленную задачу, но и качественно оформлять код: 4 | 5 | - выбирать содержательные названия для классов, методов и переменных; 6 | 7 | - писать разумные комментарии к каждому классу и методу, указывать тип и описание для каждого параметра; 8 | 9 | - создавать методы и классы разумного размера (по количеству строк); 10 | 11 | - использовать константы с понятными названиями вместо «магических чисел». 12 | 13 | Необходимо обдумать не только «позитивный» случай, но и возможные ошибки в процессе обработки (на практике они более чем возможны). В том числе случай, когда меняется структура страниц и алгоритм перестаёт функционировать корректно. Все такие ошибки должны правильно и, по возможности, унифицированно обрабатываться. 14 | 15 | **Задание** 16 | 17 | Реализуйте автоматизированный поиск тем по ключевым словам на вашем любимом форуме. 18 | 19 | **Предполагаемый алгоритм решения задачи** 20 | 21 | - залогиниться на форуме, используя предоставленные логин и пароль аккаунта, если это требуется для получения списка пользователей; 22 | 23 | - получить список тем с ключевыми словами, используя поиск по форуму; 24 | 25 | - собрать все названия и URL тем из списка результатов, а также количество сообщений в каждой из них; 26 | 27 | - желательно также получить стартовое сообщение темы. 28 | 29 | **Технологии** 30 | 31 | Задание нужно реализовать на Ruby On Rails в виде API-вызова, где логин и пароль аккаунта, а также поисковая фраза (`query`) являются GET-параметрами, а ответ — JSON-объектом с полем `success: true`, `data` - списком объектов с полями `title`, `body`, `replies_count`, `url`, описывающих найденные темы. 32 | 33 | Рекомендуем продумать архитектуру решения: желательно выделить «низкий уровень» элементарных запросов и «высокий уровень» управления навигацией и обработки ошибок навигации. Обязательно использовать принцип «тонких контроллеров» для resque jobs. -------------------------------------------------------------------------------- /test_assignments/automated_unread_messages_checking.md: -------------------------------------------------------------------------------- 1 | ## RoR + Selenium: автоматизированная проверка новых личных сообщений на форуме 2 | 3 | Необходимо продемонстрировать умение не только решать поставленную задачу, но и качественно оформлять код: 4 | 5 | - выбирать содержательные названия для классов, методов и переменных; 6 | 7 | - писать разумные комментарии к каждому классу и методу, указывать тип и описание для каждого параметра; 8 | 9 | - создавать методы и классы разумного размера (по количеству строк); 10 | 11 | - использовать константы с понятными названиями вместо «магических чисел». 12 | 13 | Необходимо обдумать не только «позитивный» случай, но и возможные ошибки в процессе обработки (на практике они более чем возможны). В том числе случай, когда меняется структура страниц и алгоритм перестаёт функционировать корректно. Все такие ошибки должны правильно и, по возможности, унифицированно обрабатываться. 14 | 15 | **Задание** 16 | 17 | Реализуйте автоматизированную проверку наличия новых личных сообщений на вашем любимом форуме. 18 | 19 | **Предполагаемый алгоритм решения задачи** 20 | 21 | - залогиниться на форуме, используя предоставленные логин и пароль аккаунта; 22 | 23 | - перейти в раздел личных сообщений; 24 | 25 | - попытаться найти элемент,содержащий число новых сообщений; 26 | 27 | - в случае его наличия — прочитать `inner Text/value`. 28 | 29 | Задание нужно реализовать на Ruby On Rails в виде API-вызова, где логин и пароль аккаунта являются GET-параметрами, а ответ - JSON-объектом с единственным полем `unread_messages_count`. 30 | 31 | Рекомендуем продумать архитектуру решения: желательно выделить «низкий уровень» элементарных запросов и «высокий уровень» управления навигацией и обработки ошибок навигации. Обязательно использовать принцип «тонких контроллеров». -------------------------------------------------------------------------------- /test_assignments/automated_user_data_collection.md: -------------------------------------------------------------------------------- 1 | ## RoR + Selenium: автоматизированный сбор данных юзеров 2 | 3 | Необходимо продемонстрировать умение не только решать поставленную задачу, но и качественно оформлять код: 4 | 5 | - выбирать содержательные названия для классов, методов и переменных; 6 | 7 | - писать разумные комментарии к каждому классу и методу, указывать тип и описание для каждого параметра; 8 | 9 | - создавать методы и классы разумного размера (по количеству строк); 10 | 11 | - использовать константы с понятными названиями вместо «магических чисел». 12 | 13 | Необходимо обдумать не только «позитивный» случай, но и возможные ошибки в процессе обработки (на практике они более чем возможны). В том числе случай, когда меняется структура страниц и алгоритм перестаёт функционировать корректно. Все такие ошибки должны правильно и, по возможности, унифицированно обрабатываться. 14 | 15 | **Задание** 16 | 17 | Реализуйте автоматизированный сбор данных о пользователях вашего любимого форума. 18 | 19 | **Предполагаемый алгоритм решения задачи** 20 | 21 | - залогиниться на форуме, используя предоставленные логин и пароль аккаунта, если это требуется для получения списка пользователей; 22 | 23 | - получить список пользователей, отсортированный по алфавиту; 24 | 25 | - Собрать все `username` аккаунтов и для каждого получить аватар (именно картинку, а не просто URL) со страницы профиля; 26 | 27 | - занести информацию в таблицу `forum_users` базы данных с полями `{ VARCHAR username, VARCHAR profile_url, VARCHAR avatar_image, DATE last_scraped_date }`, если запись уже существует - обновить данные. 28 | 29 | **Технологии** 30 | 31 | Задание нужно реализовать на Ruby On Rails в виде периодической задачи Resque + Resque Scheduler, где логин и пароль аккаунта, а также расписание выполнения хранятся в конфигурационном файле. 32 | 33 | Работу с аватарами реализовать с использованием гема carrierwave. 34 | 35 | Рекомендуем продумать архитектуру решения: желательно выделить «низкий уровень» элементарных запросов и «высокий уровень» управления навигацией и обработки ошибок навигации. Обязательно использовать принцип «тонких контроллеров» для resque jobs. -------------------------------------------------------------------------------- /test_assignments/billing_system.md: -------------------------------------------------------------------------------- 1 | ## RoR: billing system 2 | 3 | **Requirements** 4 | 5 | Please build us a new billing system. We sell a widget in 3 different ways: 6 | 7 | 1. Direct sale for $100 per item. 8 | 9 | 2. Affiliates who resell our widget based on a tiered billing system. They pay us based on how many widgets they sell total. 10 | 11 | * They sell 0-500 widgets in a month, $60 per widget. 12 | * They sell 501-1000 widgets in a month, $50 per widget. 13 | * They sell 1001+ widgets in a month, $40 per widget. 14 | 15 | We have the following Affiliates: 16 | * A Company: Sells the widget for $75/ea. 17 | * Another Company: Sells the widget for $65/ea. 18 | * Even More Company: Sells the widget for $80/ea. 19 | 20 | 3. Resellers who resell our widget based on a flat billing system. They pay us $50 per widget. 21 | 22 | We have the following Resellers: 23 | * Resell This: Sells the widget for $75 24 | * Sell More Things: Sells the widget for $85 25 | 26 | All three groups can receive orders for this service. An order includes a quantity of widgets ordered, a method used, and an amount paid. 27 | 28 | Build a class that generates 100 randomized orders for one month. These orders should be randomly assigned to each of the 6 possible types of sale and should be for a random number of widgets between 1 and 100. Build a service object that we can use to generate billing reports. 29 | 30 | This library needs to generate the following reports: 31 | * Total amount we should bill each Affiliate and Reseller. 32 | * Profit earned by each Affiliate and Reseller. 33 | * Total revenue for the company from all sales: Affiliate, Reseller and Direct. 34 | 35 | **Additional information** 36 | 37 | This object needs to have a simple and documented interface that we can easily integrate with our existing systems. For the purposes of the test, a persistence layer is not required. Also, testing is very important to our team so please provide some basic unit tests (Rspec or Minitest preferred). -------------------------------------------------------------------------------- /test_assignments/calculating_bot_for_telegram.md: -------------------------------------------------------------------------------- 1 | ## RoR: бот-калькулятор для Telegram 2 | 3 | **Условия выполнения задания** 4 | 5 | - Выполнить задание нужно на Rails (на языке Ruby). 6 | 7 | - Использовать библиотеки для создания Телеграм-ботов нельзя. 8 | 9 | - Чтобы сдать задание, нужно: 10 | 11 | - ссылку на исходный код под лицензией Apache 2.0 в каком-либо открытом git-репозитории (GitHub, GitLab, Bitbucket); 12 | 13 | - ссылку на работающего бота (в качестве бесплатного хостинга можно использовать, например, Heroku); 14 | 15 | - решения нескольких задач (условия приведены в форме). 16 | 17 | - Срок выполнения задания — чем скорее, тем лучше :) Откладывать в долгий ящик не надо, но и торопиться сделать все за один день не обязательно. Мы рассчитываем, что за неделю вы справитесь, но если справитесь за две — ничего страшного. 18 | 19 | **Задание** 20 | 21 | Напишите ​Телеграм-бота,​ который отображает в окне Телеграма примитивный кнопочный калькулятор: 22 | 23 | - кнопки цифр 0-9; 24 | 25 | - кнопки арифметических действий (+, -); 26 | 27 | - кнопка сброса (AC). 28 | 29 | Реализация основывается на двух возможностях Телеграма: 30 | 31 | - редактировать ранее отправленные сообщения; 32 | 33 | - показывать многоуровневые «клавиатуры» из кнопок. 34 | 35 | При нажатии стандартной кнопки «Start» бот отправляет пользователю сообщение с текстом «0» и клавиатурой. Пользователь никаких сообщений боту не отправляет, только нажимает кнопки, что приводит к редактированию исходного сообщения: если нажать кнопки 1 и 3, например, текст сообщения поменяется на «13». Аналогично с арифметическими действиями. 36 | 37 | Обратите внимание: вам не нужно писать разбор арифметического выражения, простые калькуляторы этого не делают. 38 | 39 | **Внимание**: разные пользователи могут пользоваться калькулятором независимо, для каждого из них должна храниться своя версия состояния. -------------------------------------------------------------------------------- /test_assignments/clinic_management_system.md: -------------------------------------------------------------------------------- 1 | # Реализовать проект по управлению поликлиникой 2 | 3 | Виды пользователей: 4 | 5 | - пациент (User) 6 | - врач (Doctor) 7 | - Admin 8 | 9 | Для каждого вида пользователей необходимо реализовать следующий функционал: 10 | 11 | 1. Пациент может зарегистрироваться, войти в свой личный кабинет (Profile), просматривать список врачей по категориям, записаться на прием, получить рекомендации от врача после приема. 12 | 1. Врач может войти в личный кабинет (Profile), просмотреть список записавшихся пациентов, дать рекомендации пациенту. Врач может относится к определенной категории (терапевт, кардиолог и тд). 13 | 1. Админ имеет доступ к списку пациентов и врачей. Может создавать категории, врачей, асайнить определенного врача к категории. (можно реализовать через ActiveAdmin/Administrate) 14 | 15 | Требования по аутентификации и авторизации: 16 | 17 | - использовать devise; 18 | - реализовать login через phone-password; 19 | - использовать gem cancancan для разграничения прав пользователей; 20 | 21 | Требования по таблице категорий: 22 | 23 | - валидация на уникальность по имени; 24 | - возможность добавления нескольких врачей; 25 | 26 | Требования по таблицам Врач-Пациент: 27 | 28 | - реализовать связь many-to-many; 29 | - у врача может быть только 10 открытых записей (одновременно); 30 | - запись автоматически закрывается (не удаляется) после того, как врач напишет пользователю рекомендацию; 31 | 32 | Общие требования: 33 | 34 | - Сделать публичную часть для пациентов и врачей; 35 | - Для реализации админки можно использовать ActiveAdmin; 36 | - Картинки хранить на S3 или Cloudinary; 37 | - Выложить проект на Heroku, а код на GitHub. Прислать ссылки + доступы в админ часть и публичную часть. 38 | 39 | -------------------------------------------------------------------------------- /test_assignments/count_html_tags_by_url.md: -------------------------------------------------------------------------------- 1 | ## RoR: подсчет различных видов html-тегов по вводимым url 2 | 3 | **Задание** 4 | 5 | Реализовать подсчет различных видов html-тегов по вводимым url (Rails-приложение). 6 | 7 | **Функционал** 8 | 9 | 1. Главная страница должна содержать поле для указания URL и кнопку. По отправке формы делать запрос на указанный URL (использовать `Nokogiri`), в ответе выводить количество каждого из html-тегов в ответе по указанному адресу (сколько раз встречается в документе), например, `div` - 5 раз, `p` - 1 раз и т. п. Оформить в виде таблицы. 10 | 2. Также реализовать сохранение этих данных в базе (`Postgre`). В одной модели (`Document`) храним `url`, в связанной (`Tag`) - теги и их количество. 11 | 3. Добавить в проект регистрацию и авторизацию (`Devise`). Шаблоны `Devise` можно не переделывать. 12 | 4. Для авторизованных пользователей выводить данные по вводимым ранее url (сохраненным в БД). Сделать ресурс documents (экшены: `index` - список url, `show` - список тегов с кол-вом для url, `destroy` - понятно) и вложенный ресурс `documents/:id/tags` (экшены: `show` - тег и кол-во, `edit/update` (только количества), `destroy`). На индексной странице сделать пейджинг с помощью `Kaminari` (показывать по 5 записей на странице). Добавить всевозможные ссылки (на `edit`, `destroy` и т. п. - можно использовать бутстраповские иконки вместо текста в ссылках). 13 | 14 | Использовать `HAML` и `SASS`, аккуратно оформить все страницы с помощью `Bootstrap` (кроме страниц от `Devise`). 15 | -------------------------------------------------------------------------------- /test_assignments/credit_card_checker.md: -------------------------------------------------------------------------------- 1 | ## Ruby: credit card checker 2 | 3 | **Task** 4 | 5 | Write a program that accepts a credit card number as a command-line argument. The program should print the card's type (or Unknown) as well a Valid/Invalid indication of whether or not the card passes the Luhn algorithm. 6 | 7 | Hint: use git, cover with specs, make some user friendly interface (can be a command line), make it modular. 8 | 9 | Before a credit card is submitted to a financial institution, it generally makes sense to run some simple reality checks on the number. The numbers are a good length and it's common to make minor transcription errors when the card is not scanned directly. The first check people often do is to validate that the card matches a known pattern from one of the accepted card providers. Some of these patterns are: 10 | 11 | | Card Type | Begins With | Number Length | 12 | | ---------- |------------ | ------------- | 13 | | AMEX | 34 or 37 | 15 | 14 | | Discover | 6011 | 16 | 15 | | MasterCard | 51-55 | 16 | 16 | | Visa | 4 | 13 or 16 | 17 | 18 | All of these card types also generate numbers such that they can be validated by the Luhn algorithm, so that's the second check systems usually try. 19 | 20 | 1. The steps are: 21 | 22 | 1.1. Starting with the next to last digit and continuing with every other digit going back to the beginning of the card, double the digit 23 | 24 | 1.2. Sum all doubled and untouched digits in the number 25 | 26 | 1.3. If that total is a multiple of 10, the number is valid 27 | 28 | 2. For example, given the card number `4408 0412 3456 7893`: 29 | 30 | 2.1. `8 4 0 8 0 4 2 2 6 4 10 6 14 8 18 3` 31 | 32 | 2.2. `8+4+0+8+0+4+2+2+6+4+1+0+6+1+4+8+1+8+3 = 70` 33 | 34 | 2.3. `70 % 10 == 0 #=> Thus that card is valid.` 35 | 36 | 3. Let's try one more, `4417 1234 5678 9112`: 37 | 38 | 3.1. `8 4 2 7 2 2 6 4 10 6 14 8 18 1 2 2` 39 | 40 | 3.2. `8+4+2+7+2+2+6+4+1+0+6+1+4+8+1+8+1+2+2 = 69` 41 | 42 | 3.3. `69 % 10 != 0 #=> That card is not valid.` 43 | -------------------------------------------------------------------------------- /test_assignments/csv_ascii_converter.md: -------------------------------------------------------------------------------- 1 | Разработать конвертор из CSV файла в таблицу из ASCII символов. Первая строка файла задает типы столбцов. Следующие строки — сами данные (разделитель — точка с запятой). 2 | 3 | Типы: 4 | 5 | * int — целое число (выравнивание вправо) 6 | * string — строка, строковые данные бьются на слова и выводятся в столбик 7 | * money — денежная единица, форматирование 2 занака после запятой, разделитель разрядов — пробел 8 | 9 | Исходные данные (как пример): 10 | 11 | ``` 12 | int;string;money 13 | 1;aaa bbb ccc;1000.33 14 | 5;aaaa bbb;0.001 15 | 13;aa bbbb;10000.00 16 | ``` 17 | 18 | На выходе скрипта Должно быть: 19 | 20 | ``` 21 | +-----------------+ 22 | | 1|aaa | 1 000,33| 23 | | |bbb | | 24 | | |ccc | | 25 | +--+----+---------+ 26 | | 5|aaaa| 0,01| 27 | | |bbb | | 28 | +--+----+---------+ 29 | |13|aa |10 000,00| 30 | | |bbbb| | 31 | +--+----+---------+ 32 | ``` 33 | -------------------------------------------------------------------------------- /test_assignments/currency_exchange_rails_api.md: -------------------------------------------------------------------------------- 1 | # Rails API для обменника 2 | 3 | Необходимо реализовать сервис со следующим функционалом на Ruby on Rails. 4 | 5 | В базе данных (желательно применить Postgresql) должна быть таблица `Currency` 6 | и соответствующая модель. 7 | 8 | ### Колонки для таблицы: 9 | 10 | 1. `id` — первичный ключ 11 | 2. `name` — название валюты 12 | 3. `rate` — курс валюты к рублю 13 | 14 | Должна быть `Rake task` для обновления данных в таблице currency. Данные по курсам валют можно взять [отсюда](http://www.cbr.ru/scripts/XML_daily.asp). 15 | 16 | ### Реализовать 2 REST API метода: 17 | 18 | 1. `GET /currencies` — должен возвращать список курсов валют с возможностью пагинации 19 | 2. `GET /currency/` — должен возвращать курс валюты для переданного id 20 | 21 | Ответ должен быть в формате JSON. 22 | 23 | Наличие тестов обязательно. 24 | 25 | API должно быть закрыто bearer авторизацией. 26 | -------------------------------------------------------------------------------- /test_assignments/database_structure_for_shops.md: -------------------------------------------------------------------------------- 1 | ## RoR: структура БД для хранения данных о товарах и магазинах 2 | 3 | **Задание** 4 | 5 | Необходимо реализовать структуру БД для хранения данных о товарах, магазинах и городах, в которых они находятся, а также остатках конкретных товаров в конкретных магазинах. 6 | 7 | **Требуемые данные** 8 | 9 | 1. Магазин — название, адрес, станция метро(если есть), город. 10 | 2. Товар — артикул, название, вес, размер, цвет, цена, остаток в магазинах. 11 | 12 | _На основе данной структуры данных реализовать следующий функционал:_ 13 | 14 | - Возможность сгенерировать xls/xlsx файл с перечислением артикулов и остатков по конкретным магазинам формата (артикул / название магазина / остаток). 15 | 16 | - Должна быть также возможность выбирать любые другие поля из перечисленных выше для добавления в файл. 17 | 18 | - Немаловажно сделать удобным выбор магазинов, остатки из которых должны присутствовать в отчёте. 19 | 20 | **Используемые технологии** 21 | 22 | - Ruby >= 2.2.x 23 | 24 | - Ruby on Rails >= 4.x 25 | 26 | - Postgresql 10 27 | 28 | - Гемсет на свое усмотрение 29 | 30 | Результаты нужно разместить в публичном репозитории GitHub и дать на него ссылку. -------------------------------------------------------------------------------- /test_assignments/grape_markets_list_app.md: -------------------------------------------------------------------------------- 1 | ## GRAPE: импорт маркетов по заданной ссылке 2 | 3 | Необходимо реализовать сервис со следующим функционалом с использованием гема `Grape`. 4 | Данные по маркетам нужно взять отсюда: https://absrest.realexchange.pro/public/tickers24h 5 | 6 | 7 | Реализовать **2 REST API** метода: 8 | 9 | - `GET` /currencies — должен возвращать список маркетов 10 | 11 | Пример ответа: 12 | 13 | ```ruby 14 | [ 15 | { 16 | market: 'BCH/BTC', 17 | base_unit: 'bch', 18 | quote_unit: 'btc', 19 | last_price: 0.01209 20 | }, 21 | { 22 | market: 'BCH/USDT', 23 | base_unit: 'bch', 24 | quote_unit: 'usdt', 25 | last_price: 291.14 26 | }, 27 | # ........ 28 | ] 29 | ``` 30 | 31 | - `GET` /currency/ — должен возвращать информацию про маркет по имени маркета. 32 | 33 | Пример ответа: 34 | 35 | ```ruby 36 | { 37 | market: 'BCH/BTC', 38 | base_unit: 'bch', 39 | quote_unit: 'btc', 40 | last_price: 0.01209 41 | } 42 | ``` 43 | 44 | Данные по `base_unit` и `quote_unit` нужно вытянуть c поля `market`. 45 | 46 | При REST запросе на Ваш сервис, Ваше приложение должно взять данные со стороннего сервиса и выдать отформатированный ответ. 47 | -------------------------------------------------------------------------------- /test_assignments/import_commits_app.md: -------------------------------------------------------------------------------- 1 | ## RoR: импорт коммитов из репозитория GitHub 2 | 3 | **Задание** 4 | 5 | Создайте простое приложение на Ruby on Rails 5, которое бы соответствовало следующим требованиям: 6 | 7 | * Приложение должно быть доступно в публичном репозитории на GitHub и содержать историю вашей работы над ним. 8 | 9 | * Если для запуска приложения будут необходимы другие приложения (СУБД и т.п.), то они должны устанавливаться и запускаться через Docker (docker-compose). 10 | 11 | * В файле `README.md` должна быть инструкция по инсталляции и запуску вашего приложения. 12 | 13 | * Для реализации приложения могут быть использованы любые сторонние библиотеки. 14 | 15 | * Необходимо написать тесты (Rspec) для контроллера и остального кода импортирующего данные коммитов. 16 | 17 | **Функционал** 18 | 19 | * Импорт всех коммитов определенного автора из репозитория с github.com в базу данных (см. http://developer.github.com/v3/repos/commits/ List commits on repository). 20 | Как пример: https://api.github.com/repos/thoughtbot/guides/commits. 21 | 22 | * Пользователь самостоятельно вводит `:owner`, `:repo`, `:author_email` и инициирует импорт. 23 | 24 | * Старые данные в базе заменяются новыми. 25 | 26 | * Отобразить коммиты в табличном виде по 10 записей на страницу. 27 | 28 | * Реализовать групповое удаление записей, которое производилось бы асинхронно без перезагрузки страницы. -------------------------------------------------------------------------------- /test_assignments/import_commits_from_github.md: -------------------------------------------------------------------------------- 1 | ## RoR + PostgreSQL: приложение, которое импортирует коммиты GitHub в БД 2 | 3 | Создать простое приложение, которое импортирует все коммиты из репозитория на GitHub в базу данных (использовать PostgreSQL). 4 | 5 | **Функционал** 6 | 7 | - На главной странице приложения вы вводите имя пользователя GitHub и его репозиторий и инициируете импорт (перед новым импортом очищать таблицы). 8 | 9 | - Пример данных для импорта для пользователя `thoughtbot` и репозитория `guides`: https://api.github.com/repos/thoughtbot/guides/commits 10 | 11 | - В БД создать 2 таблицы: 12 | 13 | - `commits` (поля: дата коммита, user_id, хеш коммита, описание коммита); 14 | 15 | - `users` (поля: имя, email). 16 | 17 | - Результат импорта вывести в виде таблицы с постраничной разбивкой. 18 | 19 | - Добавить форму поиска коммитов по email пользователя. 20 | 21 | - Реализовать редактирование имени пользователя у какого-либо коммита, которое производилось бы асинхронно без перезагрузки страницы (обновление модели `User` и у всех коммитов на видимой странице). 22 | 23 | - Реализация импорта должна учитывать, что есть репозитории с десятками тысяч коммитов. 24 | 25 | **Требования** 26 | 27 | - Написать тесты на RSpec по импорту и моделям. 28 | 29 | - Результатом должно стать развернутое приложение (например, на Heroku) и ссылка на GitHub. -------------------------------------------------------------------------------- /test_assignments/import_script_csv_to_psql.md: -------------------------------------------------------------------------------- 1 | В рамках тестового задания нужно разработать скрипт импорта товаров из csv файлов в базу данных PostgreSQL. 2 | 3 | В базе данных имеем таблицу товаров: 4 | 5 | ```ruby 6 | create_table "products", force: :cascade do |t| 7 | t.string "price_list" 8 | t.string "brand", null: false 9 | t.string "code", null: false 10 | t.integer "stock", default: 0, null: false 11 | t.decimal "cost", precision: 12, scale: 2, null: false 12 | t.string "name" 13 | end 14 | ``` 15 | 16 | Есть 3 тестовых файла для импорта (прайса). (ссылки на прайсы в гугл.док утеряны.) 17 | 18 | Прайсы имеют различные типы разделителей `;` и `,`, также отстутствует единая последовательность в заголовках и их наименованиях. В одном из прайсов содержимое находилось в `""`. 19 | 20 | Соответствие колонок в тестовых файлах импорта: 21 | 22 | price_1.csv: 23 | * Производитель: brand 24 | * Артикул: code 25 | * Количество: stock 26 | * Цена: cost 27 | * Наименование: name 28 | 29 | price_2.csv: 30 | * Производитель: brand 31 | * Артикул: code 32 | * Количество: stock 33 | * Цена: cost 34 | * НаименованиеТовара: name 35 | 36 | price_3.csv: 37 | * Производитель: brand 38 | * Номер: code 39 | * Кол-во: stock 40 | * Цена: cost 41 | * Наименование: name 42 | 43 | Нужно учесть: 44 | 45 | * Уникальность code + brand в рамках одного price_list. В случае конфликта должен сохраниться последний 46 | * brand и code регистронезависимые. Т.е. TOYOTA и Toyota считаются одинаковыми 47 | * Повторный импорт прайса с измененными данными. Позиции, которых не стало в прайсе, не должны остаться в базе после импорта. 48 | * Если кол-во указано как > n, записывать n 49 | * Отбрасывать невалидные строки. При этом поле name не обязательное и может быть сохранено как пустое 50 | * Файлы могут содержать большое кол-во строк (до 1 млн). Можно добавлять колонки \ индексы в базу для оптимизации импорта 51 | * Могут быть другие прайсы с другим наименованием\последовательностью колонок 52 | 53 | * Не обязательно, но большим плюсом будут тесты RSpec 54 | -------------------------------------------------------------------------------- /test_assignments/job_advertisement_site.md: -------------------------------------------------------------------------------- 1 | ## Ruby + JSON RESTful API: приложение с объявлениями о работе 2 | 3 | Сделать приложение на Ruby с JSON RESTful API. 4 | 5 | **Требования:** 6 | 7 | - Пользователь оставляет объявление (announcement) о работе, а другие пользователи могут на это объявление откликаться (response) с ценой («я могу за столько-то»). 8 | 9 | - Автор объявления может отменить (cancel) его. В этом случае все отклики должны быть автоматически отклонены (declined). 10 | 11 | - Автор может принять (accept) один из откликов, тогда другие отклики должны быть отклонены (declined), а объявление стать закрытым (closed). 12 | 13 | - На закрытое или отмененное объявление нельзя оставлять отклики. 14 | 15 | - Пользователь оставивший отклик может сам свой отклик отменить (cancel). 16 | В этом случае статус отклика должен быть cancelled, а не declined. 17 | 18 | - Также в API должны быть методы для получения своего объявления со всеми откликами и получения списка всех активных объявлений (без откликов). 19 | 20 | **Сущности** 21 | 22 | - `Announcement` (`id`, `user_id`, `description`, `status`), 23 | `description` — текст, не более 1000 символов; 24 | 25 | - `Response` (`id`, `announcement_id`, `user_id`, `price`, `status`), 26 | `price` - int, цена в рублях, от 100 до 10000; 27 | 28 | - `User` (`id`). 29 | 30 | **Статусы объявления** 31 | 32 | - `active` - активно, можно откликаться; 33 | - `cancelled` - отменено автором; 34 | - `closed` - закрыто (есть принятый отклик). 35 | 36 | **Статусы отклика на объявление** 37 | 38 | - `pending` - новый отклик; 39 | - `cancelled` - отменен автором отклика; 40 | - `declined` - отменен автором объявления (или автоматически, если объявление закрыто или отменено); 41 | - `accepted` - принято автором объявления. 42 | 43 | **Ограничения** 44 | 45 | - откликаться можно только на активное объявление; 46 | - если автор объявления отклонил чей-то отклик, то повторно откликаться нельзя; 47 | - если автор отклика отменил свой отклик, то он может повторно откликнуться на это же объявление. 48 | 49 | **Аутентификация** 50 | 51 | В API вместо полноценной аутентификации, можно передавать `user_id` в заголовках запроса. 52 | 53 | Также можно сделать эндпоинт для создания пользователя для тестов: POST/users, который будет создавать нового пользователя и возвращать его `id`. 54 | 55 | **Тесты** 56 | 57 | Обязательны. 58 | 59 | **Время на выполнение задания** 60 | 61 | Перед тем, как выполнять задание, оцените время на выполнение (без учета времени на настройку проекта). Напишите в README проекта оценку и фактическое время выполнения. 62 | Только честно :) -------------------------------------------------------------------------------- /test_assignments/json_api_for_blog.md: -------------------------------------------------------------------------------- 1 | ## RoR: JSON API с экшенами для блога 2 | 3 | Задание на знания Ruby on Rails. 4 | 5 | **Требования** 6 | 7 | У нас имеется некий блог со следующими сущностями: 8 | 9 | 1. Юзер. Имеет только логин. 10 | 11 | 2. Пост, принадлежит юзеру. Имеет заголовок, содержание, айпи автора (сохраняется отдельно для каждого поста). 12 | 13 | 3. Оценка, принадлежит посту. Принимает значение от 1 до 5. 14 | 15 | **Задача** 16 | 17 | Создать JSON API на RoR со следующими экшенами: 18 | 19 | 1. Создать пост. Принимает заголовок и содержание поста (не могут быть пустыми), а также логин и айпи автора. Если автора с таким логином еще нет, необходимо его создать. Возвращает либо атрибуты поста со статусом 200, либо ошибки валидации со статусом 422. 20 | 21 | 2. Поставить оценку посту. Принимает айди поста и значение, возвращает новый средний рейтинг поста. 22 | 23 | Важно: экшен должен корректно отрабатывать при любом количестве конкурентных запросов на оценку одного и того же поста. 24 | 25 | 3. Получить топ N постов по среднему рейтингу. Просто массив объектов с заголовками и содержанием. 26 | 27 | 4. Получить список айпи, с которых постили несколько разных авторов. Массив объектов с полями: айпи и массив логинов авторов. 28 | 29 | **Технологии** 30 | 31 | Ruby 2.5+, RoR 5+, PostgreSQL 10+. Результат лучше всего опубликовать на GitHub. 32 | 33 | Базу данных используем PostgreSQL. Для девелопмента написать скрипт в `db/seeds.rb`, который генерирует тестовые данные. Часть постов должна получить оценки. Скрипт должен использовать тот же код, что и контроллеры, можно вообще дергать непосредственно сервер курлом или ещё чем-нибудь. 34 | 35 | Постов в базе должно быть хотя бы 200K, авторов лучше сделать в районе 100 штук, айпишников использовать штук 50 разных. Экшены должны на стандартном железе работать достаточно быстро как для указанного объёма данных (быстрее 100ms), так и для намного большего, то есть нужен хороший запас в плане оптимизации запросов. Для этого можно использовать денормализацию данных и любые другие средства БД. 36 | 37 | Можно использовать любые нужные гемы, обязательно наличие спеков, хорошо покрывающих разные кейсы. В коде желательно не использовать рельсовых антипаттернов (типа коллбэков и валидаций в моделях), сервис-классы наше всё. Также желательно не использовать генераторов и вообще обойтись без лишних мусорных файлов в репозитории. -------------------------------------------------------------------------------- /test_assignments/json_api_service_without_rails.md: -------------------------------------------------------------------------------- 1 | ## Требуется создать JSON API сервис на Ruby без использования Ruby on Rails. 2 | 3 | В качестве веб-фреймворка, необходимо использовать *sinatra, hanami, roda* или что-нибудь другое, но **не** *Ruby on Rails*. Доступ к БД можете осуществлять с помощью *ORM (active_record, sequel, rom)*, можете и без *ORM*, как посчитаете нужным. 4 | 5 | 6 | **Сущности:** 7 | 8 | 1. User. 9 | - Имеет только логин. 10 | 2. Post. 11 | - Принадлежит юзеру. 12 | - Имеет заголовок, содержание, айпи автора (сохраняется отдельно для каждого поста). 13 | 3. Rating. 14 | - Принадлежит посту. 15 | - Принимает значение от 1 до 5. 16 | 17 | **Экшены:** 18 | 19 | 1. Создать пост. 20 | - Принимает заголовок и содержание поста (не могут быть пустыми), а также логин и айпи автора. Если автора с таким логином еще нет, необходимо его создать. 21 | - Возвращает либо атрибуты поста со статусом 200, либо ошибки валидации со статусом 422. 22 | 2. Поставить оценку посту. 23 | - Принимает айди поста и значение. 24 | - Возвращает новый средний рейтинг поста. 25 | - **Важно:** *экшен должен корректно отрабатывать при любом количестве конкурентных запросов на оценку одного и того же поста.* 26 | 3. Получить топ N постов по среднему рейтингу. 27 | - Просто массив объектов с заголовками и содержанием. 28 | 29 | 30 | 4. Получить список айпи, с которых постило несколько разных авторов. 31 | - Массив объектов с полями: айпи и массив логинов авторов. 32 | 33 | **Дополнительно:** 34 | 35 | - Базу данных используем *PostgreSQL*. Для девелопмента написать скрипт в *db/seeds.rb*, который генерирует тестовые данные. Часть постов должна получить оценки. Скрипт должен использовать созданный *JSON API* сервер (можно посылать запросы курлом или еще чем-нибудь). 36 | - Постов в базе должно быть хотя бы 200к, авторов лучше сделать в районе 100 штук, айпишников использовать штук 50 разных. 37 | - Экшены должны на стандартном железе работать достаточно быстро как для указанного объема данных (быстрее 100 мс, если будет работать медленнее, то ничего страшного, все равно присылайте решение), так и для намного большего, то есть нужен хороший запас в плане оптимизации запросов. Для этого можно использовать денормализацию данных и любые другие средства БД. Можно использовать любые нужные гемы, обязательно наличие спеков, хорошо покрывающих разные кейсы. Архитектуру сервиса организуйте на "свой вкус". Желательно не использовать генераторов и вообще обойтись без лишних мусорных файлов в репозитории. 38 | -------------------------------------------------------------------------------- /test_assignments/lunch_ordering_saas.md: -------------------------------------------------------------------------------- 1 | # Lunch Ordering SaaS 2 | 3 | Each company that uses the services of delivery meals, sooner or later, comes to the great and original idea to develop their own service to order a lunch. Many start, but only few of them bring it to the end. The objective of this task is to develop very small MVP, which could be taken and used already in production. 4 | 5 | We will try to simplify the problem as much as possible. Please find User Stories below. Let’s assume that there is only one organization in the application, all users belong to it. 6 | 7 | * As a guest I should be able to sign up with name, email and password. 8 | * As a guest I should be able to sign in with email and password. 9 | * As a first registered user in the system, I became a Lunches Admin. 10 | * As a user I can edit my profile 11 | * As a user I can see a weekdays on the dashboard page 12 | * As a user, when I click on the weekday(today or days in the past), I can see menu ­ list of items with prices. 13 | * As a user, when I choose items from menu, I can only choose one item from the first course, one item from the main course and one drink. Total 3 items. 14 | * As a user I can press Submit button to process my order. 15 | * As a Lunches Admin, I can browse registered users. 16 | * As a Lunches Admin, I can browse days and see users’ orders there. 17 | * As a Lunches Admin, I can add items in menu only for today by adding a name and price. 18 | * As a Lunches Admin, I can upload photo for each menu item 19 | * As a Lunches Admin, on the date page I can see the list of orders and total lunch cost for today. 20 | 21 | Let’s assume that instead of calling to the Lunches Delivery Company, they have a smart ERP which can request the order for today through our API at a specific time. 22 | 23 | * As a system, I should be able to provide list of the orders for today with details for each person through RESTful JSON API endpoint. 24 | * As a system, I should have a secure API. 25 | 26 | General Notes 27 | 28 | * Keep your code clean. 29 | * Thin controllers, fat models. Don’t forget about validations 30 | * Prefer quality to the speed of delivering this task 31 | * The code should be covered with unit, functional and integration tests. (Please use RSpec+Capybara) 32 | * Front­end can be pretty very simple. 33 | * The source code of application should be uploaded on github.com and deployed to heroku in the end. 34 | * Connect Travis­CI to your public repository 35 | 36 | Recommended technologies If you know your way, skip this step. Otherwise we are expecting from you to use these gems in project ­ Rails 4+, devise, twitter bootstrap, haml, simple_form, carrierwave, rspec, capybara 37 | 38 | Next complexity level: 39 | 40 | * Add organizations 41 | * Add registration through Google Apps 42 | * Auto Suggest for menu items 43 | * Weekly Menus 44 | -------------------------------------------------------------------------------- /test_assignments/meals_delivery_service.md: -------------------------------------------------------------------------------- 1 | ## RoR: meals delivery service 2 | 3 | **Requirements** 4 | 5 | Each company that uses the services of delivery meals, sooner or later, comes to the great and original idea to develop their own service to order a lunch. Many start, but only few of them bring it to the end. The objective of this task is to develop very small MVP, which could be taken and used already in production. 6 | 7 | We will try to simplify the problem as much as possible. Please find User Stories below. Let's assume that there is only one organization in the application, all users belong to it. 8 | 9 | - As a guest I should be able to sign up with name, email and password 10 | 11 | - As a guest I should be able to sign in with email and password 12 | 13 | - As a first registered user in the system, I become a Lunches Admin 14 | 15 | - As a user I can edit my profile 16 | 17 | - As a user I can see a weekdays on the dashboard page 18 | 19 | - As a user, when I click on the weekday(today or days in the past), I can see menu ­ list of items with prices 20 | 21 | - As a user, when I choose items from menu, I can only choose one item from the first 22 | course, one item from the main course and one drink. Total 3 items 23 | 24 | - As a user I can press Submit button to process my order 25 | 26 | - As a Lunches Admin, I can browse registered users 27 | 28 | - As a Lunches Admin, I can browse days and see users’ orders there 29 | 30 | - As a Lunches Admin, I can add items in menu only for today by adding a name and 31 | price 32 | 33 | - As a Lunches Admin, I can upload photo for each menu item 34 | 35 | - As a Lunches Admin, on the date page I can see the list of orders and total lunch cost for today 36 | 37 | Let’s assume that instead of calling to the Lunches Delivery Company, they have a smart ERP which can request the order for today through our API at a specific time. 38 | 39 | - As a system, I should be able to provide list of the orders for today with details for each person through RESTful JSON API endpoint 40 | 41 | - As a system, I should have a secure API 42 | 43 | **General Notes** 44 | 45 | - Keep your code clean 46 | 47 | - Thin controllers, fat models. Don’t forget about validations 48 | 49 | - Prefer quality to the speed of delivering this task 50 | 51 | - The code should be covered with unit, functional and integration tests. (Please use RSpec+Capybara) 52 | 53 | - Front­end can be pretty very simple 54 | 55 | - The source code of application should be uploaded on GitHub and deployed to 56 | Heroku in the end 57 | 58 | - Connect Travis­CI to your public repository 59 | 60 | **Recommended technologies** 61 | 62 | If you know your way, skip this step. ​Otherwise we are expecting from you to use these gems in project: Rails 4+, Devise, Twitter Bootstrap, HAML, simple_form, Carrierwave, RSpec, Capybara. 63 | 64 | **Next complexity level** 65 | 66 | - Add organizations 67 | 68 | - Add registration through Google Apps 69 | 70 | - Auto Suggest for menu items 71 | 72 | - Weekly Menus -------------------------------------------------------------------------------- /test_assignments/news_site_API.md: -------------------------------------------------------------------------------- 1 | ## RoR: JSON API для новостного сайта 2 | 3 | **Задание** 4 | 5 | 1. Спроектировать БД. 6 | 2. Реализовать API согласно ТЗ. 7 | 3. Реализовать аутентификацию в АПИ (регистрацию можно не делать). 8 | 4. Подготовить тестовые данные (дамп базы, скрипт для генерации тестового набора данных). 9 | 5. Покрыть код тестами. 10 | 6. Выложить код в репозиторий на GitHub. 11 | 12 | Формат маршрутов для доступа к методам, а также формат ответа и запросов можете выбрать и реализовать сами. 13 | 14 | **Условия** 15 | 16 | _Новость_ 17 | Представляет собой объект новости и должен содержать следующую информацию: 18 | * заголовок; 19 | * анонс; 20 | * текст; 21 | * статус (опубликована, не опубликована). 22 | 23 | _Пользователь_ 24 | Содержит в себе как минимум информацию о конкретном пользователе, а именно: 25 | * логин; 26 | * пароль; 27 | * ФИО; 28 | * подпись. 29 | 30 | Функции: 31 | * может создавать новость; 32 | * может обновлять/удалять свою новость; 33 | * может добавлять новость в избранное. 34 | 35 | _Функции каталога_ 36 | Взаимодействие с пользователем происходит посредством HTTP-запросов к API серверу. Все ответы представляют собой JSON объекты. 37 | 38 | _Сервер реализует следующие методы_ 39 | * только аутентифицированный пользователь может создавать/обновлять новости; 40 | * выдача всех новостей конкретного автора; 41 | * выдача списка авторов; 42 | * выдача списка новостей; 43 | * показывать запрошенную новость; 44 | * выдача всех непрочитанных пользователем новостей. 45 | 46 | **Используемые технологии** 47 | 48 | При выполнении задания используйте следующие технологии: 49 | * Ruby не ниже 2.5; 50 | * Rails 5; 51 | * RSpec; 52 | * БД Postgres; -------------------------------------------------------------------------------- /test_assignments/oblako_group_test_app.md: -------------------------------------------------------------------------------- 1 | ## Oblako Group Test-app 2 | 3 | Необходимо сделать API, позволяющее рендерить содержимое страницы, за это отвечает экшн GET /projects, который возвращает всю структуру, необходимую для рендеринга страницы: 4 | image 5 | 6 | Далее на странице имеется функционал, позволяющий перечеркивать задачи, для этого нужно реализовать отдельный экшн для обновления задачи PATCH /project/:id/todos/:id, который в свою очередь будет обновлять значение checked. 7 | 8 | Далее рассмотрим окно создания задачи. Тут нужно предусмотреть следующее: задача может быть добавлена в существующий список, либо в новый. Таким образом, если в списке выбора категории выбрать пункт «Новая категория», должно появиться поле для ввода названия нового списка, и, после сабмита формы, список должен отобразиться на главной странице с новой задачей. Для этих целей на стороне апи лучше всего сделать экшн POST /todos. 9 | 10 | Стоит за ранее позаботиться о сидах, с которыми будет удобно разрабатывать и проверять приложение. В качестве примера можно использовать этот файл. 11 | 12 | Таким образов в результате API должен предоставлять следующие методы: 13 | 14 | GET /projects - вернуть все проекты с задачами 15 | POST /todos - создать новую задачу 16 | PATCH /projects/id/todo/id - обновить задачу 17 | 18 | ### API принимает следующие параметры: 19 | 20 | - todo[todoname] - имя задачи (string) 21 | - project[projectname] - имя проекта (string) 22 | - project[id] - id проекта (integer) 23 | -------------------------------------------------------------------------------- /test_assignments/pdf_diploma_generator.md: -------------------------------------------------------------------------------- 1 | ## RoR: генерация pdf-файлов (дипломов) по гитхабу 2 | 3 | Мы в UCHi.RU пишем на руби и нам часто приходится иметь дело с обработкой JSON. 4 | Ещё мы проводим онлайн-олимпиады и генерируем pdf-дипломы на лету. 5 | Поэтому наше задание про это. 6 | 7 | **Задание** 8 | 9 | Нужно по адресу публичного репозитория на гитхабе найти трёх его самых активных контрибьюторов и сгенерировать для них простые pdf-дипломы и архив с ними. 10 | 11 | Спроектируйте приложение, напишите тесты проверяющие его работоспособность, 12 | и разверните его на любой публичной платформе (например, на бесплатном аккаунте в Хероку). 13 | Код, конечно же, должен быть на Гитхабе. 14 | 15 | **Полезные ссылки, которые могут пригодится:** 16 | 17 | Git: 18 | https://git-scm.com/book/en/v2 19 | https://proglib.io/p/git-for-half-an-hour 20 | http://gitimmersion.com/index.html 21 | https://learngitbranching.js.org 22 | https://try.github.io/levels/1/challenges/3 23 | 24 | Docker: 25 | https://www.docker.com 26 | https://habrahabr.ru/post/253877 27 | http://rus-linux.net/MyLDP/vm/docker/docker-tutorial.html 28 | https://proglib.io/p/docker 29 | https://habrahabr.ru/post/310460 30 | 31 | Хероку: 32 | https://blog.heroku.com/container-registry-and-runtime 33 | https://devcenter.heroku.com/articles/container-registry-and-runtime 34 | -------------------------------------------------------------------------------- /test_assignments/player_statistics.md: -------------------------------------------------------------------------------- 1 | ## RoR: консольное приложение для проверки статистики футбольных матчей 2 | 3 | **Предметная область** 4 | 5 | * Есть игроки, которые играют за команду, принимая участие в матчах. 6 | * Есть показатели (например, «пробежал 10+ км», «сделал 70% точных передач»). 7 | * Игроки в каждом матче какие-то показатели выполняют, а какие-то нет. 8 | 9 | **Задание** 10 | 11 | Создать модели к данной предметной области. 12 | 13 | Написать методы, которые позволяют: 14 | 15 | * отметить, что игрок выполнил такой-то показатель в матче; 16 | * проверить выполнил ли игрок конкретный показатель хотя бы один раз за предыдущие 5 матчей команды; 17 | * выбрать топ-5 игроков по конкретному показателю в конкретной команде и по всем командам в целом. 18 | 19 | P.S. Полный набор атрибутов в моделях не принципиален, так что можно обойтись минимальным. -------------------------------------------------------------------------------- /test_assignments/price_list_export_algorithms_for_marketplace.md: -------------------------------------------------------------------------------- 1 | ## RoR: выгрузка тестового прайс-листа и создание карточек для онлайн-магазина 2 | 3 | **Задание** 4 | 5 | Для создания нового маркетплейса необходимо произвести выгрузку из тестового прайс-листа, [ссылка на прайс-лист](h​ttps://drive.google.com/open?id=1422EskkhBB2Yj7SaVN7Qn4o2ZkFOosY0). 6 | 7 | За основу берем стандарты Яндекс.Маркет по обработке и вводу информации в 8 | прайс-листы, формируемые поставщиками. 9 | 10 | **Способы ввода информации:** 11 | 12 | - Автоматический. ​Обработка csv/xls из указанных источников. Источник указываем в административном модуле, при заполнении карточки поставщика. 13 | 14 | - Ручной.​ Ввод товарной позиции (разделов и подразделов) производится в ручном режиме в административном модуле с назначением поставщика. 15 | 16 | Важно: при автоматическом и ручном вводе информации необходимо избегать конфликта версий для согласованности разделов и подразделов. 17 | 18 | В первой итерации создаем административный модуль только для внутреннего использования (роль Супер-администратор). Данный модуль должен включать в себя информацию о загруженных прайс-листах и поставщиках в виде простой таблички. 19 | 20 | Ручной метод ввода товарной карточки, разделов и подразделов пока реализовывать не нужно. Административный модуль может использовать любой предложенный вами дашборд (GUI, с которым вам проще работать). 21 | 22 | **Фильтры** 23 | 24 | Реализовать на основе главных передаваемых параметров в данной товарной категории (бренд, размеры, вес и так далее). Для MVP допустимо автоматическое отображение фильтров. 25 | 26 | В следующей итерации необходимо реализовать настройку отображения фильтров в ручном режиме. 27 | 28 | **Сортировка** 29 | 30 | В данной первой итерации рассматриваем следующие алгоритмы сортировки: сначала дешевле, сначала дороже, по алфавиту. 31 | 32 | **GUI** 33 | 34 | Для тестирования MVP требуется использовать один из популярных CSS-фреймворков. Мы работаем со следующими сборками: ​http://getbootstrap.com/​, https://getmdl.io/​,h​ttps://materializecss.com/ 35 | 36 | [Примерный визуальный образ каталога](https://www.figma.com/proto/LT7nmllCTYQmZ4EwmrrDkGp5/%D0%A4%D1%80%D0%B5%D0%B9%D0%BC-%D0%B4%D0%BB%D1%8F-%D0%BC%D0%B0%D0%B3%D0%B0%D0%B7%D0%B8%D0%BD%D0%BE%D0%B2?node-id=122%3A185&scaling=min-zoom). 37 | 38 | К работе над товарными карточками переходим после реализации загрузки данного прайс-листа (и двух-трех дополнительных листов от других поставщиков). Дополнительные прайс-листы для тестирования будут созданы позже. -------------------------------------------------------------------------------- /test_assignments/prototype_for_car_hiring_system.md: -------------------------------------------------------------------------------- 1 | ## JSON API: прототип для системы бронирования авто 2 | 3 | **Задание** 4 | 5 | В рамках тестового задания нужно разработать прототип системы бронирования автомобилей. 6 | 7 | **Условия** 8 | 9 | В базе содержится определенное количество автомобилей различных марок и года выпуска, а также стоимость брони за один день. Считаем, что авто в базу заносятся через другое приложение, писать для этого API не нужно. 10 | 11 | Клиент может забронировать единовременно только один автомобиль. Минимальный срок аренды автомобиля — 1 день, максимальный — 30 дней. Клиент может делать поиск доступных авто на определённые даты. Клиент может забронировать доступный авто. В момент бронирования клиенту начисляются бонусы равные стоимости брони. 12 | 13 | Итак, в рамках ТЗ должно получится бэкенд-приложение с: 14 | 15 | 1. Endpoint для регистрации клиента (Sign up); 16 | 17 | 2. Endpoint для входа (Sign in); 18 | 19 | 3. Endpoint для поиска авто на заданные даты; 20 | 21 | 4. Endpoint для бронирования авто; 22 | 23 | 5. Endpoint для истории броней клиента; 24 | 25 | Формат для всех endpoint - JSON. 26 | 27 | Не обязательно, но большим плюсом будет документация к API, доступная по какому-либо URL. 28 | 29 | Исходный код можете разместить на GitHub или Bitbucket. -------------------------------------------------------------------------------- /test_assignments/rails_api_for_real_estate_site.md: -------------------------------------------------------------------------------- 1 | ## RoR + Ember: API для сайта продажи/аренды недвижимости 2 | 3 | **Условия** 4 | 5 | *Ember* 6 | 7 | Модели: 8 | 9 | - `Building` (здание). Поля: `class:string`, `street:string`, `house_number:string`, `floors:number`; 10 | 11 | - `Block` (офисные блоки). Поля: `area:number`, `floor:number`; 12 | 13 | - `Price` (цена). Поля: `value:number`, `currency:number`, `1` — рубли, `2` — доллары, `3` — евро). 14 | 15 | Связи: 16 | 17 | - `Building hasMany Blocks`; 18 | 19 | - `Block belongsTo Building`; 20 | 21 | - `Block hasMany Offers`; 22 | 23 | - `Offer belongsTo Price`. 24 | 25 | Создать раут `buildings`. 26 | 27 | Создать `template buildings`, в котором будут 4 `input` поля (класс, улица, номер дома и этаж) и кнопка «Добавить». 28 | 29 | При нажатии на кнопку «Добавить» отправлять save-запрос к API, в промисе мы добавляем созданный `building` в массив `buildings`. После этого зачищаем форму. Ниже формы отображаем массив созданных `buildings`. 30 | 31 | **Дополнительно:** 32 | 33 | В `template buildings` добавить возможность добавлять `block` => `offer` => `price`. То есть помимо обычных инпутов в форму создания здания добавить ещё кнопку «Добавить блок». При нажатии на неё появляется форма с инпутами для создания модели `block`, которая привязывается к модели `building`. В форме блока, соответственно, есть кнопка «Добавить предложение», при нажатии на которую появляется форма с полями `offer` и кнопкой «Добавить цену». Цена по аналогии. 34 | 35 | *Rails* 36 | 37 | Создать небольшое API. 38 | 39 | Модели: 40 | 41 | - `Building` (здание). Поля: `class:string`, `street:string`, `house_number:string`, `floors:integer`; 42 | 43 | - `Block` (офисные блоки). Поля: `area:integer`, `floor:integer`; 44 | 45 | - `Offer` (предложение). Поля: `offer_type:string`, `rent` — аренда, `sale` — продажа; 46 | 47 | - `Price` (цена). Поля: `value:integer` (limit — 8), `currency:integer`, `1` — рубли, `2` — доллары, `3` — евро). 48 | 49 | Связи: 50 | 51 | - `Building has_many :blocks`; 52 | 53 | - `Block belongs_to :building`; 54 | 55 | - `Block has_many :offers`; 56 | 57 | - `Offer has_one :price`. 58 | 59 | Контроллеры: 60 | 61 | Создать контроллер для `building` с методами `create`, `update`, `delete`, `index`, `show`. 62 | 63 | В `create` должна создаваться модель `Building` (без параметров в запросе, просто вызывать метод создания модели). Возвращать `render json` созданной модели. 64 | 65 | В `update` должна сохраняться модель `Building` с соответствующим `id` (без параметров в запросе, просто вызывать метод сохранения модели). Возвращать `render json` созданной модели. 66 | 67 | В `delete` удалять модель с соответствующим `id`. 68 | 69 | В `show` возвращать `render json` модели `Building` с определённым `id`. 70 | 71 | В `index` возвращать `Building`. В `params` могут быть переданы все поля модели `building` и по ним желательно вести поиск и возвращать отфильтрованные значения. 72 | 73 | Выбор БД на ваше усмотрение. 74 | 75 | *SQL* 76 | 77 | Написать одинаковые запросы на SQL и на Rails ORM. 78 | 79 | Найти все офисные блоки от 150 до 300 кв.м включительно, которые находятся на 1, 8 или 10 этажах, сдаются в аренду по цене не более $5000 в зданиях класса «А» на Пресненской набережной. 80 | 81 | *Объединение frontend + backend + БД* 82 | 83 | С фронта отправлять запрос на созданное Rails API. В `create` методе `buildings_controller` берём поля из тела POST-запроса. -------------------------------------------------------------------------------- /test_assignments/rest_api_for_blog.md: -------------------------------------------------------------------------------- 1 | ## RoR: REST API для блога 2 | 3 | ### Часть 1. REST API для блога 4 | 5 | **1.1 Модели** 6 | 7 | `Post` — записи в блоге, 8 | 9 | - `title` — строковое, обязательное 10 | - `body` — строковое, обязательное 11 | - `author` — ссылка на автора 12 | - `published_at` — дата-время размещения записи 13 | 14 | `Comment` — комментарии к записям 15 | 16 | - `body` — строковое, обязательное 17 | - `author` — ссылка на автора 18 | - `published_at` — дата-время размещения комментария 19 | 20 | `User` — пользователи. Поскольку у нас есть авторы, нужна модель в которой мы будем их хранить. 21 | 22 | - `nickname` — строковое, обязательное 23 | - `email` — строковое, обязательное 24 | - `password` — строковое, обязательное 25 | 26 | **1.2 Эндпоинты** 27 | 28 | - Реализовать эндпойнт для аутентификации. Как его сделать, up to you. 29 | - POST /api/v1/posts.json 30 | 31 | Отправляем: 32 | 33 | - `title` 34 | - `body` 35 | - `published_at` 36 | 37 | В ответ получаем json с полями: 38 | 39 | - `id` 40 | - `title` 41 | - `body` 42 | - `published_at` 43 | - `author_nickname` 44 | 45 | Если в запросе не передали `published_at`, то нужно подставлять текущий момент времени. Если передали не все поля, то ответ должен содержать одно поле `errors` — массив ошибок. 46 | 47 | - GET /api/v1/posts/:post_id.json 48 | 49 | Получить post по его id, поля в ответе как в эндпойнте POST /api/v1/posts.json 50 | 51 | - GET /api/v1/posts.json 52 | Отправляем: 53 | 54 | - `page` 55 | - `per_page` 56 | 57 | Получаем в ответ список записей отсортированных полю published_at по убыванию поля каждой записи как в эндпойнте POST /api/v1/posts.json. В заголовках ответа нужно передать общее количество страниц и записей. 58 | 59 | - Эндпойнты для комментариев можно не делать 60 | 61 | **1.3 Прочие требования** 62 | 63 | - Rails 5.x 64 | - Postgres 9.x 65 | - Rspec 3.x 66 | - Json — ActiveModelSerializer или jsonapi-resources 67 | - В таблицах нужно указывать все необходимые индексы 68 | - Код моделей и контроллеров нужно покрыть тестами 69 | - Работающее приложение нужно разместить на heroku 70 | 71 | ### Часть 2. Интерфейс, загрузка файлов и фоновые задачи 72 | 73 | **2.1 Загрузка аватара** 74 | 75 | На базе первой части сделать страницу, где пользователь может загрузить свой 76 | аватар. Интерфейс может быть простейшим, сделанным на дефолтном бутстрапе. 77 | Пользователю нужно выбирать файл `jpg/png` размером до 3мб, загружать его и видеть 78 | его превью после загрузки, урезанный до 300x300px. Файлы нужно загружать на S3 79 | 80 | **2.2 Аналитический отчет** 81 | 82 | На базе первой части , сделать аналитический отчёт. 83 | 84 | Эндпоинт: POST /api/v1/reports/by_author.json 85 | 86 | Параметры запроса: 87 | 88 | - `start_date` — начало интервала 89 | - `end_date` — конец интервала 90 | - `email` — куда отправить отчёт 91 | 92 | Поля в ответе: 93 | 94 | - `message: “Report generation started”` 95 | 96 | Эндпоинт добавляет задачу на генерацию отчёта в очередь, очередь обрабатывается отдельным процесом. Готовый отчёт отправляется на email указанный в задаче. 97 | 98 | Отчёт должен представлять собой таблицу со столбцами: 99 | 100 | - `nickname` 101 | - `email` 102 | - количество записей за период 103 | - количество комментариев за период 104 | 105 | Строки в отчёте должны быть отсортированы по значению вычисляемому как (количество постов + количество комментариев/10). Таблицу можно оформить как в виде html таблицы так и при помощи ASCII символов. Для этого задания нужно заполнить базу тестовыми данными, для чего удобно использовать gem `faker`. 106 | 107 | **2.3 Общие требования ко второй части** 108 | 109 | Результат выполнения второй части тестового задания так же нужно опубликовать на 110 | heroku в виде работающего приложения. 111 | -------------------------------------------------------------------------------- /test_assignments/restaurants_with_tables.md: -------------------------------------------------------------------------------- 1 | Необходимо сделать систему для резервации столов в ресторанах. 2 | 3 | В каждом ресторане есть столы. Эти столы можно резервировать. При этом шаг резервации - 30 минут, а пользователь может резервировать стол на 30, 60, 90 и т.д. минут. В каждой резервации должен быть пользователь. У каждого ресторана есть график работы, который может переваливать за полночь. Резервации на один стол не должны пересекаться. При этом, если одна резервация закончилась в 5 вечера, вторая может начинаться в 5 вечера. 4 | 5 | Интересует только реализация моделей и структура базы данных. 6 | 7 | Обязательные условия выполнения: 8 | 9 | * 2 коммита с разрывом в 2 часа. 1 коммит - стартовая инициализация проекта. 2 коммит - готовая работа. 10 | * Исключить из Gitignore папку Log. 11 | * Продумать шаги по улучшению кода, если бы было больше времени и описать их в сопроводительном письме к решению тестового. 12 | -------------------------------------------------------------------------------- /test_assignments/ror_api_reference_counting.md: -------------------------------------------------------------------------------- 1 | ## Реализуйте web-приложение для простого учета посещенных (неважно, как, кем и когда) ссылок. 2 | 3 | 4 | **Требования к приложению:** 5 | - Приложение предоставляет *JSON API* по *HTTP*. 6 | - Приложение предоставляет два *HTTP* ресурса. 7 | 8 | **Ресурсы:** 9 | 1. Ресурс загрузки посещений. 10 | - Принимает *POST*-запрос, по адресу `/visited_links`, в формате: `{"links": ["https://ya.ru", "https://ya.ru?q=123"]}` 11 | - Ресурс служит для передачи в сервис массива ссылок в *POST*-запросе. Вре- 12 | менем их посещения считается время получения запроса сервисом. 13 | 14 | 15 | 2. Ресурс получения статистики: 16 | - Принимает *GET*-запрос, по адресу `/visited_domains`, формата: `/visited_domains?from=1545221231&to=1545217638` 17 | - Отдает ответ формата: `{ "domains": ["ya.ru"], "status": "ok" }` 18 | - Ресурс служит для получения *GET*-запросом списка уникальных доменов, посещенных за переданный интервал времени. 19 | -------------------------------------------------------------------------------- /test_assignments/shop_dashboard.md: -------------------------------------------------------------------------------- 1 | ## RoR: панель администратора магазина 2 | 3 | **Задание** 4 | 5 | Тестовое задание заключается в написании несложного управляющего интерфейса для магазина загогулин. 6 | 7 | **Условия** 8 | 9 | На сайте магазина загогулин отображаются товары (загогулины), разбитые по категориям. 10 | 11 | Категории имеют древовидную структуру. У категории есть название, родитель (другая категория или `NULL`) и слаг (генерируется автоматически из названия товара, если не задан). 12 | 13 | Товар принадлежит к одной категории, имеет название, слаг, изображение и описание. 14 | 15 | **Требования** 16 | 17 | Необходимо: 18 | 19 | 1. Сделать раздел редактирования категорий товаров. Администратор может: создать категорию, изменить категорию, удалить категорию (товары не 20 | должны в ней удаляться), изменить порядок категорий внутри ветки (перетаскиванием, на странице списка), переподчинить категорию другому родителю (перетаскиванием). 21 | 22 | 2. Сделать раздел редактирования товаров. Администратор может: cоздать товар (выбрав соответствующую категорию, и загрузив при этом изображение), удалить товар, изменить товар. 23 | 24 | 3. Запрограммировать навигацию по двум разделам («Товары» и «Категории») в соответствии со стандартными правилами, чтобы всегда было понятно «Где я нахожусь?» и «Куда я могу отсюда пойти?» 25 | -------------------------------------------------------------------------------- /test_assignments/shop_with_checkout.md: -------------------------------------------------------------------------------- 1 | ## Ruby: функция Checkout для магазина 2 | 3 | **Условия** 4 | 5 | Дан список товаров: 6 | 7 | | Код | Название | Цена | 8 | | ------ | ---------- | ------ | 9 | | CC | Кока Кола | $1.50 | 10 | | PC | Пепси Кола | $2.00 | 11 | | WA | Вода | $0.85 | 12 | 13 | Для некоторых продуктов есть определенные правила дисконтирования: 14 | 15 | - если покупаете 3 и более бутылки Пепси Колы, то стоимость каждой бутылки Пепси Колы снижается на 20%; 16 | 17 | - если покупаете одну бутылку Кока Колы, то вторая даётся бесплатно. 18 | 19 | **Задача** 20 | 21 | Реализуйте класс `Checkout` и необходимые дополнительные классы, которые считают общую стоимость покупки. 22 | 23 | **Пример использования:** 24 | 25 | ``` 26 | co = Checkout.new(pricing_rules)
 27 | co.add(item)
p 28 | co.total 29 | ``` 30 | 31 | Примеры: 32 | 33 | - Input: CC PC WA
 34 | 35 | Output: $4.35
; 36 | 37 | - Input: CC PC CC CC
 38 | 39 | Output: $5.00
; 40 | 41 | - Input: PC CC PC WA PC CC
 42 | 43 | Output: $7.15
; 44 | 45 | Оценивается работоспособность, структура, архитектура, используемые шаблоны проектирования и тесты (используйте RSpec). -------------------------------------------------------------------------------- /test_assignments/simple_to_do_list.md: -------------------------------------------------------------------------------- 1 | ## RoR + Ember: простой трекер задач 2 | 3 | **Функционал:** 4 | 5 | - создание задач; 6 | 7 | - закрытие (закрытые должны быть перечеркнутыми) и переоткрытие задач; 8 | 9 | - удаление задач. 10 | 11 | **Внешний вид:** 12 | 13 | У задачи должно быть название, расширенное описание и приоритет (minor, major, critical). [Примерный вид начальной страницы (`url/tasks`)](http://joxi.ru/5mdoZxeS96war1). 14 | 15 | Строки списка должны быть раскрашены в зависимости от приоритета (критичный — красный, мажорный — жёлтый, минорный — зелёный). [Примерный вид добавления задачи (`url/task/new`)](http://joxi.ru/v29DKEVcBLB5mG) (слева все тот же список задач, а справа форма добавления новой задачи). 16 | 17 | Для верстки использовать foundation. [Аддон для эмбера](https://www.npmjs.com/package/ember-cli-foundation-6-sass). 18 | 19 | **Технологии:** 20 | 21 | - backend: RoR 5.2+ (API mode); 22 | 23 | - frontend: Ember.js 3.2+; 24 | 25 | - DB: MongoDB. -------------------------------------------------------------------------------- /test_assignments/solving_mathematical_equations_app.md: -------------------------------------------------------------------------------- 1 | ## RoR: система решения математических уравнений 2 | 3 | **Задание** 4 | 5 | Система должна состоять из двух основных компонентов: фронтенд и бэкенд сервер. 6 | 7 | _**Фронтенд** сервер — основной функционал_ 8 | 9 | RoR приложение должно предоставлять: 10 | 11 | 1. Выбор типа уравнения (по умолчанию линейное и квадратное). 12 | 13 | 2. Форму ввода параметров для решения уравнения. 14 | 15 | 3. Передачу параметров уравнения на бэкенд сервер в формате JSON. 16 | 17 | 4. Получение и отображение результата в «дружественном» виде. 18 | 19 | _Дополнительные пожелания_ 20 | 21 | 1. Использование CSS на формах / страницах «Выбор», «Вввод», «Результат». 22 | 23 | 2. Использование JS / Ajax / JS-framework на формах / страницах «Выбор», «Ввод», «Результат». 24 | 25 | 3. Использование тестовых фреймворков TestUnit / RSpec / Cucumber (один или несколько). 26 | 27 | 4. Обеспечить валидацию параметров и обработку исключительных ситуаций (500 от бэкенда, ввод буквенных параметров, 28 | ввод дробных параметров и т.д.). 29 | 30 | _**Бэкенд** сервер — основной функционал_ 31 | 32 | Допустимо использование приложения на Sinatra или подобном фреймворке. Приложение должно: 33 | 34 | 1. Предоставить точку входа для получения параметров уравнения. 35 | 36 | 2. Обеспечить решение уравнения. 37 | 38 | 3. Предоставить ответ в формате JSON. 39 | 40 | _Дополнительные пожелания_ 41 | 42 | 1. Использование наследования при решении различных типов уравнения (единый интерфейс для решения любого типа уравнения). 43 | 44 | 2. Обеспечение валидации параметров и обработки исключительных ситуаций (недостаточное количество параметров, неверный тип уравнения, неверный тип аргументов и тд). 45 | 46 | 3. Использование TestUnit / RSpec / Cucumber. 47 | 48 | 4. Использование аутентификации при приеме запроса. -------------------------------------------------------------------------------- /test_assignments/task_manager_with_authentication.md: -------------------------------------------------------------------------------- 1 | ## RoR: таск-менеджер с функцией аутентификации 2 | 3 | **Функции приложения** 4 | 5 | Полный процесс авторизации пользователя: 6 | 7 | - Регистрация нового пользователя, Sign in, Sign out, Forgot Password, Unlock, Update Account. 8 | 9 | - После регистрации пользователь попадает на список задач, которые либо он создал сам, либо ему назначили. 10 | 11 | - Создать полный CRUD процесс задач: создание, удаление, просмотр, изменение. 12 | 13 | **Требования к реализации** 14 | 15 | У пользователя есть следующие атрибуты: 16 | 17 | - имя, фамилия — обязательные поля; 18 | 19 | - email — обязательное поле, уникальное; 20 | 21 | - пароль; 22 | 23 | У задачи следующие атрибуты: 24 | 25 | - название задачи — обязательно; 26 | 27 | - описание задачи — текст, не обязательно; 28 | 29 | - кто создал — пользователь, обязательно; 30 | 31 | - на кого назначена — пользователь, обязательно; 32 | 33 | - статус задачи — new, started, finished. 34 | 35 | Требования к вьюшкам: 36 | 37 | - HAML или Slim; 38 | 39 | - Twitter Bootstrap; 40 | 41 | - JQuery. 42 | 43 | Требование к коду: 44 | 45 | - Rspec - тестовое покрытие кода 100 %, проверка через гем Simplecov (вьюшки тестировать не надо); 46 | 47 | - зелёный Rubocop. 48 | 49 | **Оценка задания** 50 | 51 | При оценке тестового задания будут учитываться следующие пункты: 52 | 53 | - следование Style Guides; 54 | 55 | - соответствие требованиям к тестированию, полнота тестов; 56 | 57 | - DRY; 58 | 59 | - наличие «интересной функции», которая не описана в требованиях, но может быть полезной в проекте. 60 | 61 | Код выложить на GitHub или Bitbucket и прислать ссылку. -------------------------------------------------------------------------------- /test_assignments/telegram_bot_sticker_png.md: -------------------------------------------------------------------------------- 1 | ## TelegramBot: конвертация стикеров в PNG-файлы 2 | 3 | Create Telegram chat bot. 4 | 5 | Use Ruby and related technology stack to create simple Telegram bot to convert Telegram stickers to PNG files. 6 | 7 | **Requirements:** 8 | 9 | - Create Telegram bot with configurable ID. 10 | 11 | - Implement long polling method to get updates from the API. 12 | 13 | - Implement bot command /start. Bot should answer the description. 14 | 15 | - When user send some text message, bot should response the warning message with small description. 16 | 17 | - When user send some built-in Telegram sticker, bot should response same sticker as a PNG file. 18 | 19 | - User should be able to save PNG to the device (phone, computer, etc). 20 | 21 | - Use static code analyzer. 22 | 23 | - Create Github repository with all code work and valid README file. 24 | 25 | **Additional score requirements:** 26 | 27 | - Cover all necessary code with unit tests. 28 | 29 | **Implementation details:** 30 | 31 | - Use last stable Ruby version. 32 | 33 | - You can use any other gems you want, but make the choice reasonably. 34 | 35 | - Write code as clean and as readable as possible. 36 | 37 | - Consider using RSpec for testing. 38 | 39 | - Consider using RuboCop as a static analyzer. 40 | 41 | - Consider using GitFlow workflow. 42 | -------------------------------------------------------------------------------- /test_assignments/totalizator.md: -------------------------------------------------------------------------------- 1 | ## Ruby: тотализатор 2 | 3 | **Условия** 4 | 5 | На вход подаются 2 счёта на игру (реальный и предполагаемый игроком), на выходе получаем количество заработанных или потерянных очков.
 6 | 7 | Функция на вход принимает 4 целочисленных значения от 0 до 9, на выходе возвращает целочисленное значение от -1 до 1

. Первые 2 значения — реальный счёт игры
, следующие 2 значения — предполагаемый счёт игры
. 8 | 9 | Если реальный счет игры 2:1, а предполагаемый — 0:1, то параметры функции — 2, 1, 0, 1.
 Если реальный счёт игры 0:3, а предполагаемый счёт 2:1, то параметры функции — 0, 3, 2, 1.

 10 | 11 | Функция должна возвращать: 
 12 | 13 | - 1, если счёт угадан полностью; 14 | 15 | - 0, если угадано, какая команда выиграла; 16 | 17 | - -1, если не угадан ни реальный счет, ни кто выиграл. 18 | 19 | Пример использования:
 20 | 21 | - score(0, 1, 0, 1) вернет 1 (счет угадан полностью)
; 22 | 23 | - score(2, 1, 1, 0) вернет 0 (угадано какая команда выиграла)
; 24 | 25 | - score(0, 4, 2, 0) вернет -1 (ничего не угадано). -------------------------------------------------------------------------------- /test_assignments/url_shortener_app.md: -------------------------------------------------------------------------------- 1 | ## RoR: Приложение для сокращения ссылок - url shortener 2 | 3 | - Необходимо реализовать сервис сокращения ссылок. Данный сервис должен реализовывать 3 запроса: 4 | - `POST` **/urls** который возвращает короткий url 5 | - `GET` **/urls/:short_url** который возвращает длинный URL и увеличивает счетчик запросов на 1 6 | - `GET` **/urls/:short_url/stats** который возвращает количество переходов по URL 7 | 8 | - Проект необходимо реализовать на Ruby On Rails. 9 | 10 | - База Данных - на выбор. 11 | 12 | - Необходимо вести статистику уникальных IP запросов. 13 | -------------------------------------------------------------------------------- /test_assignments/video_view_statistics_service.md: -------------------------------------------------------------------------------- 1 | ## Ruby: сервис статистики видеопросмотров 2 | 3 | Напишите на Ruby сервис, реализующий REST API со следующими функциями: 4 | 5 | - Принимает от клиентов уведомления о том, что клиент смотрит видео. 6 | 7 | Параметры: `customer_id` — идентификатор пользователя, `video_id` — идентификатор видео, которое смотрит пользователь. 8 | 9 | - Отвечает на запрос, сколько видео потоков смотрит пользователь в данный момент. 10 | 11 | Параметры: `customer_id` - идентификатор пользователя. 12 | 13 | - Отвечает на вопрос, сколько пользователей смотрят данное видео. 14 | 15 | Параметры: `video_id` — идентификатор видео. 16 | 17 | **Дополнительные сведения:** 18 | 19 | - Клиенты посылают уведомления о просмотре видео каждые 5 секунд, пока работает плеер. Если в течение 6 и более секунд уведомление от пользователя не пришло, то считается, что просмотр этого видео завершен. 20 | 21 | - Клиентов много и их не интересует ответ на уведомление о просмотре. 22 | 23 | - Запросы 2 и 3 приходят существенно реже, нежели запрос 1. 24 | 25 | - Ответ на запрос 2 должен быть максимально актуальным. 26 | 27 | - Ответ на запрос 3 может отставать и отражать ситуацию не на текущий момент, а, например, на минуту назад. 28 | 29 | Использовать можно любой фреймворк, можно не использовать. Для хранилища можно использовать: память внутри самого ruby-приложения, postgresql, redis. 30 | 31 | По желанию: реализовать адаптеры для разных хранилищ. -------------------------------------------------------------------------------- /test_assignments/weather_statistics_api.md: -------------------------------------------------------------------------------- 1 | ## ROR6 + Grape: API для статистики по погоде 2 | 3 | **Требования** 4 | 5 | Как источник данных можно использовать https://developer.accuweather.com/apis. 6 | 7 | Город можно использовать любой (можно захардкодить). 8 | 9 | Законченный код передать в виде приватного репозитория на GitHub 10 | 11 | API открыт для всех, авторизация не нужна. 12 | 13 | Должны быть интеграционные тесты на эндпоинты и юнит тесты на общие классы/модули. 14 | 15 | Ожидаемая нагрузка на любой эндпоинт: 5 RPS 16 | 17 | 18 | **Необходимые эндпоинты** 19 | 20 | /weather/current - Текущая температура 21 | 22 | /weather/historical - Почасовая температура за последние 24 часа (https://developer.accuweather.com/accuweather-current-conditions-api/apis/get/currentconditions/v1/{locationKey}/historical/24) 23 | 24 | /weather/historical/max - Максимальная темперетура за 24 часа 25 | 26 | /weather/historical/min - Минимальная темперетура за 24 часа 27 | 28 | /weather/historical/avg - Средняя темперетура за 24 часа 29 | 30 | /weather/by_time - Найти температуру ближайшую к переданному timestamp (например 1621823790 должен отдать температуру за 2021-05-24 08:00. Из имеющихся данных, если такого времени нет вернуть 404) 31 | 32 | /health - Статус бекенда (Можно всегда отвечать OK) 33 | 34 | 35 | **Дополнительно** 36 | 37 | Рекомендуется хранить данные о температуре локально для снижения нагрузки на сторонний API. 38 | 39 | Рекомендуется использовать библиотеки: Rails 6, Grape, Delayed::Job, Rufus, RSpec, VCR. 40 | 41 | Приветствуется использование кеширования и Trailblazer, swagger документации, Docker -------------------------------------------------------------------------------- /test_assignments/web_panel_for_users_control.md: -------------------------------------------------------------------------------- 1 | ## RoR + Front end: RESTful JSON API для управления пользователями сайта 2 | 3 | **Задание** 4 | 5 | Разработайте веб-интерфейс для управления пользователями сайта. Используйте _Ruby 2.6_ и _Ruby on Rails 5_. 6 | 7 | **Требования** 8 | 9 | *Пользователи* 10 | 11 | Создайте сущность для пользователей с атрибутами (все обязательные): 12 | 13 | - имя; 14 | - уникальный email; 15 | - пароль; 16 | - аватар. 17 | 18 | *Интерфейс* 19 | 20 | В панели управления можно просматривать, создавать, изменять, удалять пользователей. Уделите большое внимание внешнему виду и дизайну. Для создания интерфейса используйте Bootstrap или любой другой CSS-фреймворк. Сайт должен отображаться на мобильных и десктопных устройствах. 21 | 22 | *API* 23 | 24 | Разработайте RESTful JSON API для мобильных приложений, где можно будет: 25 | 26 | - регистрироваться по почте и паролю; 27 | - получать и изменять свои данные; 28 | - просматривать информацию о других пользователях. 29 | 30 | **Дополнительные детали** 31 | 32 | Результат загрузите на GitHub, приложение разверните на сервере. Ссылку на репозиторий отправьте на почту. По вопросам обращайтесь в Telegram. 33 | 34 | Оцениваем качество кода, читаемость, соответствие гайдлайнам синтаксиса и дизайна, внимание к деталям. Использование библиотек приветствуется, ограничений нет. --------------------------------------------------------------------------------