<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/">
  <channel>
    <language>ru</language>
    <title>Pet-проекты</title>
    <description>Интересные пет-проекты, которые можно легко реализовать, если следовать нашим инструкциям. Создавайте pet-проекты, чтобы практиковаться и наполнять портфолио.</description>
    <link>https://tproger.ru/tag/interesting-projects</link>
    <atom:link href="https://tproger.ru/tag/interesting-projects/feed" rel="self" type="application/rss+xml"/>
    <lastBuildDate>Fri, 23 Oct 2026 20:21:17 GMT</lastBuildDate>
    <sy:updatePeriod>hourly</sy:updatePeriod>
    <sy:updateFrequency>12</sy:updateFrequency>
    <image>
      <title>Pet-проекты</title>
      <link>https://tproger.ru</link>
      <url>https://tproger.ru/apple-touch-icon.png</url>
    </image>
    <item>
      <title>Как джуниору доказать, что в него нужно вкладываться: прочитай, если скоро собеседование</title>
      <link>https://tproger.ru/articles/kak-dzhunioru-dokazat--chto-v-nego-nuzhno-vkladyvatsya--prochitaj--</link>
      <comments>https://tproger.ru/articles/kak-dzhunioru-dokazat--chto-v-nego-nuzhno-vkladyvatsya--prochitaj--?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Дима Дмитриев]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-dzhunioru-dokazat--chto-v-nego-nuzhno-vkladyvatsya--prochitaj--</guid>
      <description><![CDATA[<p>Как джуниору получить оффер в IT в 2026: чего боятся работодатели, как доказать свою ценность и пройти собеседование в условиях высокой конкуренции.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-dzhunioru-dokazat--chto-v-nego-nuzhno-vkladyvatsya--prochitaj--">Как джуниору доказать, что в него нужно вкладываться: прочитай, если скоро собеседование</a>»</p>]]></description>
      <category><![CDATA[Карьера]]></category>
      <category><![CDATA[Собеседование]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 27 Mar 2026 09:00:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Вы закончили курсы, сделали пару pet-проектов, заполнили резюме и откликнулись на 300 вакансий. В ответ получаете пугающую тишину и ноль приглашений на джоб-сайтах. В комьюнити с начала 2025 года говорят, что попасть в IT без опыта невозможно, но компании продолжают брать джунов. Более того, они готовы платить зарплату и тратить время на обучение — только не всем подряд.</p><h2>Что происходит на рынке прямо сейчас</h2><p>За первую половину 2025 года количество IT-вакансий на Хабр Карьере упало на 32%, на HeadHunter — на 20%. Индекс конкуренции на Хабр Карьере в феврале 2026 года достиг 21,3 — это в два раза выше, чем год назад. На каждую вакансию джуниора сейчас приходится в среднем 11,1 резюме. Для сравнения: на вакансию сеньора — всего 2,3 резюме.</p><p>Почему так? Причин несколько. Компании оптимизируют бюджеты, замедлился рост отрасли, AI взял на себя часть рутинных задач. Параллельно на рынок вышло много выпускников курсов и вузов — спрос на IT-образование высокий, и новых кандидатов стало больше.</p><p>Но вот парадокс: джуниоров избыток, а мидлов и сеньоров по-прежнему не хватает. <b>Компании не могут найти опытных специалистов, значит, бизнесу приходится растить своих — и вот тут появляется шанс для джуниоров. Их берут вместо дорогих мидлов на поддержку кода, фикс багов, рутинные задачи.</b></p><blockquote>“Классически самыми быстрыми точками входа в профессию были, есть и остаются QA, бизнес-анализ и системный анализ. Особенно если ваш предыдущий опыт так или иначе был связан с аналитической работой — это серьезное преимущество для перехода в бизнес- или системные аналитики.<br /><br />Кстати, факт: многие рекрутеры успешно переходят и продолжают переходить именно на позиции бизнес- и системных аналитиков. Более того, несколько лет назад как минимум двое моих коллег сменили профессию и ушли в это направление — сейчас это уже крепкие специалисты уровня middle-plus.<br /><br />QA — еще одно направление, в котором можно действительно много развиваться, начав с ручного тестирования. Дальше есть несколько траекторий роста:<br />- углубляться в ручное тестирование;<br />- освоить автоматизацию;<br />- уйти в нагрузочное тестирование.<br /><br />И на каждой из этих веток можно отлично себя чувствовать профессионально и финансово<br /><br /></blockquote><p>Работодатели не готовы вкладываться в обучение каждого джуниора — только в тех, кто покажет, что инвестиции окупятся. Чтобы понять, как получить оффер, нужно посмотреть на ситуацию глазами компаний.</p><h2>Почему компании боятся брать джуниоров</h2><p>С точки зрения работодателя наём джуниора — это риск. Вот что пугает бизнес:</p><h3>Накрученный опыт в резюме</h3><p>Многие джуниоры завышают свой уровень, чтобы попасть на более высокие позиции. Обман вскрывается либо на собеседовании, либо на испытательном сроке, но компания уже потратила время и деньги. Процессинг одного кандидата занимает около двух недель, не считая времени на поиск. Часто приходится привлекать рекрутинговые агентства — это дополнительные расходы.</p><h3>Долгая окупаемость</h3><p>Джуниору нужно минимум 6 месяцев, чтобы начать приносить ощутимую пользу. В течение этого времени ему платят зарплату, его обучают, на него тратят время тимлида и коллег, но не каждая компания готова ждать так долго.​</p><h3>Риск увольнения</h3><p>Что если вложить в джуниора ресурсы, обучить его, а он уйдёт к конкурентам через год? По статистике, джуниоры работают на первом месте в среднем 5-8 месяцев, а для компании это выглядит как слив инвестиций.​</p><p>Именно эти страхи нужно развеять, если вы хотите получить оффер. И для этого нужно понимать, как работает модель найма джунов.</p><h2>Как компании растят джуниоров</h2><p>Когда компания решает нанять джуниора, она работает по конкретной схеме. Вас берут не как универсального разработчика, которого можно бросить на любую задачу, вас берут под конкретную роль в конкретной команде с узким набором функций.</p><p><b>Схема выглядит так:</b> вас нанимают с базовыми техническими знаниями и в течение 1-3 месяцев обучают делать что-то одно. Например, работать с определённым участком кода, поддерживать легаси, писать тесты, фиксить баги по чётким инструкциям.</p><p>Когда вы выходите в команду, вы уже знаете свою зону ответственности, коллегам не нужно постоянно объяснять, что делать — вы справляетесь с простыми задачами самостоятельно. Это не превратит вас в мидла за три месяца, рост в грейде происходит только через работу с реальными проектами и задачами, но вы станете джуниором, который приносит пользу с первых недель, а не сидит в сторонке и учится полгода за счёт компании.</p><h2>Как доказать, что вы стоите инвестиций</h2><h3>Не накручивайте грейд</h3><p>Первое и главное правило: не врите про свой уровень. Компании тратят две недели на обработку одного кандидата, и если обман вскроется на собеседовании или испытательном сроке, вы просто сожжёте свою репутацию, а IT-комьюнити узкое, информация расходится быстро.</p><blockquote>Указывайте курсы, которые вы прошли. Лучше всего, если это будут программы от непосредственных работодателей (например, от Яндекса или банков) — они наиболее приближены к тому, чем люди занимаются в реальной жизни.<br /><br />Вообще сертификаты сами по себе для неопытного специалиста значат мало. Сейчас на курсы смотрят с некоторой долей скепсиса, и профильное образование все еще в приоритете. Но если у вас нет возможности получить даже заочное профильное образование, курсы указывать надо. Для джуна это подтверждение того, что вы прошли базовый путь и соответствуете техническому уровню специалиста.<br /><br /><b>Главный тезис:</b> Ваше резюме должно показывать, что вы — нормальный, надежный человек, с которым можно работать.<br /></blockquote><p>Если у вас только pet-проекты и учебные задачи, не называйте это коммерческим опытом. Работодатель не ждёт от вас опыта мидла, он ищет человека с базовыми знаниями, которого можно быстро обучить под свои задачи.</p><blockquote>Если у вас был опыт работы до IT — неважно какой — его нужно указать. Особенно ценно, если это крупные компании и долгосрочное сотрудничество (например, три года финансистом в «Северстали» или банке). Это отличный знак для работодателя, потому что:<br /><br />- вы понимаете, как работает корпоративная среда, и уже адаптированы в ней;<br />- вы знаете, что такое трудовая дисциплина;<br />- вас не нужно учить базовым вещам: как вести себя на встречах, что можно и нельзя, как работает бизнес и почему нельзя хамить руководителю.<br /><br />В таком случае обучение будет одновекторным: оно коснется сугубо изучения новой IT-специальности и погружения в компанию, а не воспитания базовой ответственности.<br /></blockquote><h3>Покажите готовность учиться конкретным вещам</h3><p>Компания заточит вас под свой проект, поэтому лучше уберите фразу в резюме: “Хочу изучать современные технологии и развиваться во всех направлениях”. Лучше покажите, что готовы глубоко погрузиться в конкретный стек или задачу. Если компания ищет человека на поддержку старого кода, покажите, что вам интересно разбираться в чужой кодовой базе и рефакторить её.</p><blockquote>Важный плюс этих направлений: начальные требования к кандидатам здесь ниже, чем, например, в разработке. Это значит, что на старте можно сильно выехать на хороших софт-скиллах или на навыках, которые вы уже наработали в прошлой карьере — особенно если вы идете в IT не сразу после учебы, а с бэкграундом из другой сферы.</blockquote><h3>Покажите понимание бизнес-задач</h3><p>Работодателя волнует, сможете ли вы закрывать задачи, которые приносят компании деньги. Поэтому на собеседовании объясните, какие проблемы вы решали в своих учебных проектах и как это применимо к задачам компании. Если вы делали pet-проект, опишите его не через технологии, а через результат. Например, что вы автоматизировали процесс сбора данных, который раньше занимал три часа ручной работы.</p><blockquote>Если вы идете сразу после обучения, резюме нужно разнообразить. Обязательно добавьте ссылки на пет-проекты, если они были.<br /><br />Для свитчеров: Если вы меняете сферу (например, были маркетологом, а хотите в UI/UX), вам нужны ссылки на работы, которые вы сделали сами, и краткое описание пройденных курсов.<br /><br />Для студентов: Укажите подработки, которые вы вели во время учебы. Офисные задачи будут в приоритете, но даже условно длительная работа курьером с положительной характеристикой покажет вашу надежность.</blockquote><h3>Дайте сигналы стабильности</h3><p>Работодатель боится, что вы уйдёте через полгода, поэтому если вы планируете задержаться надолго, дайте понять это на собеседовании: спросите про карьерный трек,  уточните, как устроен рост внутри компании, поинтересуйтесь, какие проекты планируются на ближайшие год-два.</p><blockquote>Джунам действительно приходится оценивать себя самостоятельно. И я бы здесь прямо не цеплялся за деньги, потому что предложения бывают разные, и действительно, ещё одна проблема джуна: когда ты не знаешь рынок, тебе тяжело вообще оценить, насколько предложение «вкусное».<br /><br />Если вас позовут на трёхмесячную стажировку в какой-нибудь банк и скажут, что будут платить 15 тысяч рублей, — соглашайтесь. Потому что:<br /><br />- Либо после стажировки вы проявите себя, и вам предложат работу на хорошую ставку;<br />- Либо не предложат, но вы добавите в резюме строчку о трёхмесячной практике в банке — и на вас будут смотреть совершенно по-другому.<br /><br />На первую джуновую работу, если вы только пришли в IT или это ваша первая работа вообще, не нужно смотреть на деньги и рубиться за них. Вы должны понимать: первые как минимум три месяца вы получаете сугубо опыт. Нормально этот опыт будет котироваться, и вы сможете продавать себя по рыночной ставке, только когда отработаете год. И это должен быть год на одном месте. Если начнёте «прыгать» по компаниям — выстрелите себе в колено, и резюме станет только слабее.</blockquote><h2>Первые полгода — как оправдать инвестиции</h2><h3>Почему полгода — ваш самый сложный период</h3><p>Компания окупает вложения в джуниора <b>примерно за полгода</b>. В это время вы выполняете простую линейную работу, постепенно набираете скорость, учитесь работать в команде. <b>За эти шесть месяцев</b> вероятность вашего увольнения минимальна — уйти к другому работодателю с такими маленьким опытом сложно.</p><h3>Берите простые задачи и закрывайте их качественно</h3><p><b>В первые месяцы</b> от вас никто не ждёт архитектурных решений или оптимизации узких мест. Вас будут загружать линейными задачами: мелкие фичи, баг-фиксы, рефакторинг, ваша задача — делать их быстро и без косяков.</p><h3>Не требуйте постоянного гайдинга</h3><p>Учитесь искать ответы самостоятельно, изучайте документацию, смотрите, как похожие задачи решали до вас в кодовой базе, гуглите ошибки. Задавайте вопросы только тогда, когда действительно застряли, и формулируйте их так, чтобы коллега мог ответить быстро.</p><h3>Фиксируйте свой прогресс</h3><p>Ведите список задач, которые закрыли. Отмечайте, что нового узнали, какие проблемы решили. Это нужно, чтобы на встрече с тимлидом или на ревью испытательного срока вы могли чётко показать, что сделали за это время.</p><h3>Принимайте ответственность за свои ошибки</h3><p>Вы будете ломать прод, заливать баги или забывать тестить. Это нормально для джуниора, ненормально — прятаться, молчать или сваливать вину на других. Если вы накосячили, сразу говорите об этом, объясните, что пошло не так, и предложите, как это исправить.</p><h2>От джуниора до мидла — реальные сроки</h2><p>Рост до уверенного мидла занимает в среднем три года, грейды в разных компаниях определяются по-разному, но временная дистанция примерно одинаковая. Ускорить этот процесс можно, но критично — попытки форсировать рост убивают ключевые компетенции.</p><p>Через год работы вы станете интересны другим работодателям. К этому моменту у вас уже есть реальный опыт в команде, закрытые задачи, понимание процессов, а ваша стоимость на рынке вырастет.</p><blockquote>Поэтому наиболее выигрышная стратегия сейчас — говорить на первых встречах честно про зарплату: «Первый год меня зарплата не так волнует, меня волнует возможность получать высокую зарплату в будущем, когда я получу опыт и буду его стоить».<br /><br />Особенно актуально это сейчас, на падающем рынке: компаниям больно брать новых людей, все пытаются пересмотреть зарплаты, занижать синьоров и мидлов, сокращать численность. Поэтому любая джуновая ставка для человека с минимальным опытом или без него вообще — на вес золота.<br /><br />Гораздо важнее потратить это время не на то, чтобы рубиться за лишние 10-15-20 тысяч рублей к зарплате, а на то, чтобы получить опыт, который позволит вам через год зарабатывать в 10 раз больше.</blockquote><p>Компания, которая в вас вложилась, это понимает и будет предлагать вам понятный карьерный трек, пересматривать зарплату и условия. Если проект закроется или стек изменится, вас переведут в другую команду.</p><h2>Чек-лист для джуниора</h2><h3>На этапе поиска работы:</h3><ul><li>Не завышайте грейд в резюме</li><li>Покажите готовность учиться конкретным технологиям под проект</li><li>Объясняйте свои pet-проекты через решённые проблемы, а не через стек</li><li>Задавайте вопросы про карьерный трек и долгосрочные планы компании</li><li>Не занижайте свою стоимость</li></ul><blockquote>Оценивать себя «по медиане» вообще не надо. Нужно исходить из тех предложений, которые идут.<br /><br />Если у вас спрашивают: «Какая у вас минимальная цифра?» — называйте сумму, которая нужна вам именно для сведения концов с концами. Не называйте цифру, потому что «посмотрел среднее на HeadHunter, решил, что я молодец, добавил чуть-чуть и хочу зарабатывать прямо сейчас». Это плохая стратегия даже в суперкраткосрочной перспективе.<br /><br />Карьера — это всегда долгий путь. Помните: первый год работы — это работа не за деньги, это работа за опыт, который через год позволит сделать резкий скачок. Более того, если вы устраиваетесь в нормальный банк, в нормальную IT- или добывающую компанию и показываете себя как ценный сотрудник на позиции джуна, то через короткое время вам в любом случае предложат переход на нормальную ставку с адекватной зарплатой — и вам всё понравится.<br /><br />Для работодателя джун — это как «кот в мешке». Не добавляйте ему сомнений и желания сделать выбор не в вашу пользу, давая волю жадности. Это всегда работа в будущее.</blockquote><h3>В первые полгода работы:</h3><ul><li>Закрывайте простые задачи качественно, не гонитесь за сложными</li><li>Ищите ответы самостоятельно, задавайте вопросы точечно</li><li>Ведите список закрытых задач и навыков</li><li>Признавайте ошибки сразу и предлагайте решения</li></ul><h3>Через год работы:</h3><ul><li>Оцените свой прогресс и обсудите его с тимлидом</li><li>Уточните условия роста и пересмотра зарплаты</li><li>Решите, хотите ли остаться в компании или искать новые возможности</li></ul><p>Рынок изменился, конкуренция выросла, но спрос на джуниоров остался, просто они теперь нужны бизнесу для поддержки, обучения и роста внутри компании. Теперь вы знаете, как это работает.</p>]]></content:encoded>
    </item>
    <item>
      <title>Создаём микросервис обработки изображений на Go с gRPC</title>
      <link>https://tproger.ru/articles/sozdayom-mikroservis-obrabotki-izobrazhenij-na-go-s-grpc-2</link>
      <comments>https://tproger.ru/articles/sozdayom-mikroservis-obrabotki-izobrazhenij-na-go-s-grpc-2?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Go разработчик]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/sozdayom-mikroservis-obrabotki-izobrazhenij-na-go-s-grpc-2</guid>
      <description><![CDATA[<p>В этой статье мы рассмотрим создание микросервиса обработки изображений на golang с использованием технологии gRPC. Цель статьи - показать как может выглядеть такой сервис и что он может в себя включать.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/sozdayom-mikroservis-obrabotki-izobrazhenij-na-go-s-grpc-2">Создаём микросервис обработки изображений на Go с gRPC</a>»</p>]]></description>
      <category><![CDATA[Веб-разработка]]></category>
      <category><![CDATA[Микросервисы]]></category>
      <category><![CDATA[Golang]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[gRPC]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 17 Mar 2026 05:00:02 GMT</pubDate>
      <content:encoded><![CDATA[<p><b>Вступление</b></p><p>В этой статье мы рассмотрим создание микросервиса обработки изображений на golang с использованием технологии **gRPC**. Цель статьи - показать как может выглядеть такой сервис и что он может в себя включать. В результате мы получим полностью рабочий сервис по обработке изображений, который принимает данные, сохраняет исходную картинку,сжимает её, накладывает на неё ватермарку, изменяет размер изображения, и конвертирует его в нужный формат.</p><p>Разберём возможные варианты взаимодействия клиента с сервером для обработки больших объектов, в нашем случае это картинки:</p><p><b>1. HTTP/1.1 (REST)</b></p><p>Передача изображений в виде текстовых чанков (например, base64) приводит к значительным накладным расходам: бинарные данные увеличиваются на ~33% при кодировании в Base64, а текстовый формат неэффективен для больших объёмов.</p><p><b>2. WebSocket</b></p><p>Подходит для долгоживущих сессий и двустороннего обмена, но избыточен, если нам нужно просто «принять изображение → обработать → вернуть результат». Удержание тысяч соединений ради однократных операций — неоптимально.</p><p><b>3. gRPC</b> использует:</p><p><b>Protocol Buffers</b> — строго типизированный, компактный бинарный формат,</p><p><b>HTTP/2</b> — мультиплексирование, потоки, сжатие заголовков,</p><p><b>Client-Streaming</b> — идеально подходит для передачи одного большого файла (например, изображения) в одном вызове.</p><p><b>I. Постановка задачи</b></p><p><b>Сервис должен:</b></p><p>Принимать изображение и параметры (format, compress, watermark, width[], height[]),</p><p>Сохранять оригинал с уникальным путём (./download/YYYY/MM/DD/UUID/img/...),</p><p>Накладывать водяной знак,</p><p>Генерировать версии заданных размеров,</p><p>Сохранять полученные изображения,</p><p>Возвращать список путей.</p><p>Пример:</p><p>Запрос с width = [1920, 1280], height = [1080, 720], format = "webp", watermark = "logo.png"</p><p>→ Сервис вернёт два пути:</p><p>./download/2026/02/08/abc123/img/abc123_1920x1080.webp</p><p>./download/2026/02/08/abc124/img/abc124_1280x720.webp</p><p><b>II. Архитектура приложения</b></p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/af4f6a18-dac9-4728-bbb3-decfe99bc1c5.webp" alt="" /></figure><p><b>Обработка происходит в строгом порядке:</b></p><p>1.Приём → 2. Сохранение исходного файла→ 3. Сжатие → 4. Watermark → 5. Resize → 6. Конвертация → 7. Ответ.</p><p><b>Структура хранения:</b></p><p>./download/2026/02/08/a1b2c3d4-.../img/</p><p>├── a1b2c3d4-....jpg          ← оригинал</p><p>├── a1b2c3d4-..._800x600.png</p><p>└── a1b2c3d4-..._1024x768.png</p><p><b>Необходимые инструменты:</b></p><p>Для работы с WebP мы используем библиотеку <a href="https://pkg.go.dev/golang.org/x/image/webp" rel="nofollow">golang.org/x/image/webp</a> , а исходные утилиты можно скачать на <a href="https://developers.google.com/speed/webp/download?hl=ru" rel="nofollow">официальной странице Google</a>.</p><p>Для генерации protobuff нам нужен  <b>protoc-gen-go</b></p><p><b>protoc-gen-go-grpc</b></p><p>Позволяет генерировать определения сервисов Go для буфера протокола, заданного нашим .proto файлом <a href="https://github.com/grpc/grpc-go/releases" rel="nofollow">protoc-gen-go-grpc</a></p><p>Также для работы webp нам потребуется работа с CGO, которую мы рассмотрим отдельно.</p><p><b> III. Реализация proto файла</b></p><p>Для начала работы опишем наш proto файл. Это будет сервис с единственным rpc который будет обрабатывать картинки пользователей.</p><p>./proto/image.proto</p><p>Мы используем Client-Streaming RPC — клиент может отправить несколько сообщений, сервер — один ответ. Этот способ поможет нам в случае необходимости гибкого расширения и избежания ограничений на размер одного сообщения.</p><p><b>V. Реализация основных функций</b></p><p><b>1. Создание сервера</b></p><p><b>1.1 Генерация  go файлов из .proto:</b>  Сгенерируем файлы для реализации сервера с помощью protoc:</p><p>У нас должно получиться 2 файла image.pb.go и image_grpc.pb.go в директории proto</p><p><b>1.2 Реализуем конструктор сервера и interceptor</b> (аналог middleware в grpc) восстановления после паники:</p><p>./internal/app/server.go</p><p>Теперь реализуем функцию запуска нашего grpc сервера:</p><p>Мы создали наш grpc сервер, но пока нет никакой реализации ImageServiceServer который сгенерировал нам protoc, это просто интерфейс который нам и нужно реализовать.</p><p><b>2. Реализация ImageServiceServer</b></p><p>Нам необходимо создать структуру ImageServer которая реализует интерфейс ImageServiceServer с его методом DownloadImage, также создадим конструктор для него :</p><p>./internal/app/image.go</p><p>Нам осталось реализовать ключевые функции для нашего сервиса, а именно: saveSourceFiles: отвечает за сохранение исходных файлов и их сжатие, watermark: наложение ватермарки , resizeAndSave: изменения размера картинки и его конвертация в нужный формат изображения.</p><p><b>3. Сохранение оригинала</b></p><p>Мы создаем путь для сохранения картинки, сохраняем её с необходимым для клиента уровнем сжатия и потом для удобства всю метаинформацию об картинке помещаем уже в нашу структуру и работаем в дальнейшем только с ней:</p><p>./internal/app/save.go</p><p>Для ускорения нашего процесса обработки все этапы мы будем выполнять конкурентно с помощью горутин.</p><p><b>4. Водяной знак </b></p><p>Следующим этапом идёт наложение водяного знака на нашу картинку. Процесс наложения: мы передаем каждой горутине по изображению, они его обрабатывают, а для того чтобы убедиться что они все обработались мы применяем sync.WaitGroup. Сам процесс наложения водяного знака это задание параметров для установки его на исходную картинку, в нашем случае мы делаем её полупрозрачную с небольшим углом поворота и в случайном месте и сохраняем её:</p><p>./internal/app/watermark.go</p><p>Остаётся только изменить размер и сохранить в нужном формате наши обработанные изображения.</p><p><b>5. Resize и конвертация.</b></p><p>Теперь создадим файл resize.go и реализуем функцию изменения размера изображении и сохранения в нужном нам формате:</p><p>./internal/app/resize.go</p><p>Теперь реализуем main.go в котором создадим и вызовем наш сервис обработки изображений.</p><p>./internal/cmd/main.go</p><p><b>VI. CGO</b></p><p>Наше приложение полностью готово, но теперь нужно удостовериться, что у нас работает поддержка CGO. Для начала нужно убедиться что мы скачали и установили webp по ссылке [официальная страница Google](https://developers.google.com/speed/webp/download?hl=ru). Далее нам необходимо установить GCC, без него go не может распознать импортированные C файлы, скачиваем и устанавливаем [официальные зеркала GNU](https://gcc.gnu.org/mirrors.html). Теперь нужно проверить, что переменная CGO_ENABLED=1, для этого используем команду go env и проверяем, если она равна 0, то используем go set  CGO_ENABLED=1 и проверяем ,что она применилась, если нет то перезагружаем нашу систему и проверяем. Теперь мы готовы собрать наше приложение и приступить к тестированию.</p><p><b>VII. Тестирование и оптимизация</b></p><p><b>Тестирование с Bruno</b></p><p>Здесь вы можете тестировать удобными для вас средствами такими как Postman, Bruno, Yaak, grpccurl и т.д., главное чтобы они поддерживали тестирование grpc методов. Рассмотрим пример с Bruno:</p><p>1.Конвертируйте изображение в Base64: Image to Base64 Converter</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/3b10f151-2654-42b1-b6a2-1e6805d79ba2.webp" alt="" /></figure><p>2.Откройте Bruno создайте новый grpc запрос</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/94dba9c1-7930-43f5-accf-1753036005db.webp" alt="" /></figure><p>3. Выбираем метод grpc:</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/b614edcd-171f-49e5-8ba2-cd4b73283551.webp" alt="" /></figure><p>4.Уберите ползунок с reflection и укажите .proto файл</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/8a88b632-4d1a-41a0-9818-0822a6613551.webp" alt="" /></figure><p>5.Выберите метод DownloadImage</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/2a0f8f65-cb62-4442-a867-10d3c69f145d.webp" alt="" /></figure><p>6.В поле message заполните поле в соответствии с параметрами, например:</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/8f454490-7182-4641-8a31-f56fe6236546.webp" alt="" /><figcaption>если появляются проблемы при подключении к сервису, то не выносите текстовое представление картинки в переменную</figcaption></figure><p>В поле image нужно скопировать текстовую строку ,что идёт после запятой, сгенерированную на шаге 1</p><p>7.Далее нужно запустить наше приложение и подключиться к нему с помощью кнопки →</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/4a166e9e-22d3-4369-be1e-b68534623765.webp" alt="" /></figure><p>В случае успеха должен появиться статус streaming</p><p>8.Отправляем наше сообщение/сообщения нажав на кнопку "Send message" один или несколько раз и завершаем нашу передачу сообщений с помощью кнопки → (если не нажать то приложение будет ожидать приёма сообщений). Результатом будет возврат путей наших обработанных сообщений</p><figure><img src="https://media.tproger.ru/user-uploads/136053/2026-02-23/7e269ec1-2cec-4926-8ccc-a9de76d3e9ff.webp" alt="" /></figure><p><b>VIII. Заключение</b></p><p>Подведем итоги, мы создали сервис который:</p><p>Использует gRPC для эффективной передачи данных,</p><p>Поддерживает WebP, JPEG, PNG,</p><p>Безопасен в конкурентной среде,</p><p>Можно легко масштабировать.</p><p>В результате получился сервис обработки изображений. Этот подход применим не только к изображениям, но и к любым бинарным данным.</p><p>Исходный код доступен по <a href="https://github.com/art9276/image-converter" rel="nofollow">ссылке</a></p><p><b>Спасибо за внимание!</b></p>]]></content:encoded>
    </item>
    <item>
      <title>От татуировок к чат-ботам — как хобби вдохновляют IT-проекты</title>
      <link>https://tproger.ru/articles/ot-tatuirovok-k-chat-botam---kak-hobbi-vdohnovlyayut-it-proekty</link>
      <comments>https://tproger.ru/articles/ot-tatuirovok-k-chat-botam---kak-hobbi-vdohnovlyayut-it-proekty?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Татьяна Жукова]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/ot-tatuirovok-k-chat-botam---kak-hobbi-vdohnovlyayut-it-proekty</guid>
      <description><![CDATA[<p>В новом выпуске подкаста Tproger Иван, тату-мастер и создатель Telegram-бота для генерации эскизов татуировок, рассказывает, как нейросети (Grok, ChatGPT, DALL·E) помогли ему упростить работу и попробовать себя в no-code разработке. Узнайте, как хобби и технологии открывают новые горизонты в IT.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/ot-tatuirovok-k-chat-botam---kak-hobbi-vdohnovlyayut-it-proekty">От татуировок к чат-ботам — как хобби вдохновляют IT-проекты</a>»</p>]]></description>
      <category><![CDATA[API]]></category>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Боты]]></category>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Маркетинг]]></category>
      <category><![CDATA[Хобби]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Бизнес]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 20 Oct 2025 10:00:03 GMT</pubDate>
      <content:encoded><![CDATA[<p><i>В новом выпуске подкаста «Чем живут айтишники» Маша Даровская, шеф-редактор Tproger и автор телеграм-канала «Деврелишна», беседует с Иваном, тату-мастером и создателем </i><a href="https://t.me/GenaSketchBot">Telegram-бота</a><i> для генерации эскизов татуировок. Узнайте, как нейросети вроде Grok и ChatGPT помогают создавать минималистичные эскизы, почему татуировки — это проще, чем кажется, и как ИИ может пригодиться даже в судебных разбирательствах.  </i></p><p><b>Маша Даровская (Tproger)</b>: Сегодня мы обсуждаем разные хобби и интересные проекты в IT. У нас в гостях Иван, который создал телеграм-бота для генерации эскизов татуировок. Иван, расскажи немного о себе.</p><p><b>Иван</b>: Всем привет! Меня зовут Иван, мне 32 года. Я создал генератор тату-эскизов с помощью вайб-кодинга, нейросети Grok и ChatGPT. Я тату-мастер, работаю в этой сфере уже 13 лет — это мой основной заработок и основная деятельность. Но уже давно хочется чего-то нового: выйти из зоны комфорта, попробовать себя в чём-то другом. Вот сейчас и пробую.</p><h2>Идея создания чат-бота для тату-эскизов</h2><p><b>Маша Даровская</b>: Расскажи, как тебе вообще пришла идея создать чат-бота, который генерирует эскизы?</p><p><b>Иван</b>: Дело в том, что я отношусь к той категории тату-мастеров, которые не любят рисовать. Думаю, таких немного, но я действительно не люблю и не умею рисовать. Прошлым летом я пробовал генерировать эскизы с помощью нейросетей, тестировал разные варианты, но ничего не могло создать идеальный минимализм. Под минимализмом я имею в виду, например, контурный эскиз кота из фотографии. Это специфика моей работы — я в основном занимаюсь минимализмом, графикой. А нейросети выдают сложные, детализированные арты, которые мне не подходят. Поэтому я забросил это дело.</p><p>Весной я подключил премиум-версию ChatGPT по другому поводу — хотел писать других ботов. Но потом решил попробовать попросить его сгенерировать эскизы. И он сделал это идеально. В процессе общения я спросил: можем ли мы интегрировать твой API в Telegram-бота, чтобы генерировать эскизы? Так и появилась эта идея.</p><p><b>Маша Даровская:</b> Когда ты говоришь, что не умеешь рисовать, слушателям может быть непонятно: всё равно ведь нужно уметь хотя бы срисовывать эскиз?</p><p><b>Иван</b>: Здесь всё упирается в опыт. Сама отрисовка не требует особых навыков. Я начал заниматься татуировками 13 лет назад, когда друзья позвали меня сделать тату. Я посмотрел, как это происходит: человек переводит контурный эскиз, обводит, закрашивает — как раскраска. Мне это показалось простым, поэтому я и начал. Если речь о реализме или портретах, это сложнее, но даже там с опытом можно научиться срисовывать. Но я не делаю реализм — мне это неинтересно.</p><p><b>Маша Даровская: </b>Тебе казалось, что это просто, а оказалось, что не так?</p><p><b>Иван:</b> Делать татуировки действительно просто. Я до сих пор так считаю. Первые пять лет я удивлялся: почему все не делают татуировки? Это легко, приятно, и деньги неплохие. Я никогда не понимал, зачем люди ходят на нелюбимую работу, если можно заниматься татуировками. У меня нет особой любви к рисованию или татуировкам — это просто работа.</p><p><b>Маша Даровская:</b> Были какие-то необычные татуировки, которые у тебя заказывали?</p><p><b>Иван</b>: Особой любви к этому делу у меня не было, поэтому я мало что запоминал. Но был один случай: делал татуировку под губой у девушки с никнеймом «Сосиписос». Она набила надпись «Соси Песос». Эта татуировка набрала в Instagram около полутора тысяч сохранений. Это было давно, ещё до рилсов. Такие штуки делал.</p><h2>Создание чат-бота и его влияние на работу</h2><p><b>Маша Даровская: </b>Когда ты решил создать бота, насколько он упростил тебе работу?</p><p><b>Иван</b>: Сам бот мне работу особо не упростил, но ChatGPT сильно помог. Я перестал использовать iPad для рисования эскизов — теперь он только для мультиков сына. Я просто пишу в ChatGPT: «Сделай мне это», и почти всегда получаю нужный результат. Иногда с детализированными эскизами он может «тупить» — например, неправильно нарисовать хвост змеи. Но если дать референс с фото татуировки и попросить доработать на белом фоне, он справляется отлично. Мне почти ничего не нужно делать.</p><p><b>Маша Даровская: </b>Клиентам нормально показывать такие эскизы?</p><p><b>Иван: </b>Они даже не знают, чем это отличается от ручной работы. Я в 95% случаев сразу предупреждаю, что не рисую, работаю по готовым эскизам. Теперь я генерирую их через ChatGPT, выкладываю в канал и говорю, что это мои работы. Не вижу в этом ничего плохого.</p><p><b>Маша Даровская: </b>Расскажи подробнее, как ты делал бота и сколько времени ушло?</p><p><b>Иван:</b> Сам бот я написал за неделю на Python, без сервера и деплоя. Сложности начались с деплоем. Было две версии: первая — простая, без оплаты и геймификации, я разместил её на Railway с автодеплоем. Вторая — на российском Timeweb, с монетизацией. Самые сложные моменты — деплой, подключение монетизации и работа с версиями библиотек. Иногда я тратил 10 часов на одну внутреннюю ошибку при запуске.</p><p><b>Маша Даровская:</b> Скрипт на Python, и ты подключал его к API?</p><p><b>Иван: </b>Да, генерация идёт через DALL·E. Сначала пробовал Stable Diffusion, но результаты были ужасными — не хватало оптимизации промтов, как в ChatGPT. DALL·E автоматически улучшает запросы, например, для «змеи с кинжалом». Но через API DALL·E не поддерживает image-to-image, что для меня важно. Для этого нужен Stable Diffusion, но там свои сложности.</p><p><b>Маша Даровская:</b> Думал как-то дорабатывать бота?</p><p>Иван: Да, следующий шаг — интегрировать Stable Diffusion для работы с референсами. Для этого нужна отдельная модель под каждый стиль татуировки, обученная на 100–150 эскизах. Это требует сервера с GPU, что стоит около 1500 рублей в месяц. Пока это кажется сложным, но когда я начинал, тоже думал, что всё сложно, а оказалось проще.</p><p><b>Маша Даровская:</b> Думал о браузерной версии или приложении?</p><p>Иван: Да, но сейчас приоритет — маркетинг. Сделать бота — одно, а привлечь аудиторию — другое. У меня около 130 пользователей без особого продвижения, но это не целевая аудитория. Оплаты пока скромные — несколько транзакций по 15 рублей за генерацию. Есть пакеты: чем больше покупаешь, тем дешевле. Себестоимость одной генерации — около 4 рублей, но с комиссиями выходит больше.</p><p><b>Маша Даровская: </b>Что было самым сложным при создании бота?</p><p>Иван: Не код, а ошибки, которые я не понимал. Для опытного программиста это, может, и просто, но я иногда сидел до четырёх утра, решая одну проблему. Несколько раз хотел бросить, но в итоге всё решалось.</p><h2>Другие проекты и планы</h2><p><b>Маша Даровская: </b>Ты говорил, что начинал с других ботов. Каких именно?</p><p><b>Иван:</b> Сделал бота-врача, который отвечает на вопросы о здоровье. Но он неактуален — люди могут получить то же самое бесплатно, например, в DeepSeek. Монетизация возможна через рекламу, но это не то. Пока дохода нет.</p><p><b>Маша Даровская:</b> Видишь ли ты себя вайб-кодером в будущем?</p><p><b>Иван</b>: Программирование мне интересно. Вайб-кодинг хорош тем, что можно самому реализовать идею, создать MVP, проверить спрос. Если проект пойдёт, можно нанять программистов. Это круто для проверки идей без больших затрат.</p><p><b>Маша Даровская:</b> Ты хотел сменить сферу деятельности. Почему?</p><p><b>Иван: </b>На самом деле, мне не нравится делать татуировки. Раньше казалось крутым, но я всегда смотрел в сторону бизнеса. У меня была студия пять лет, но я её закрыл. Сейчас меня интересуют pet-проекты — создавать небольшие продукты, раскручивать их. Это может стать кейсом для портфолио, например, в продакт-менеджменте. Я не разбираюсь в IT, но знаю, что там ценят реальные достижения.</p><p><b>Маша Даровская: </b>Пробовал учиться чему-то в IT?</p><p><b>Иван: </b>Изучаю DevOps — знакомый работает в этой сфере, предлагал попробовать. Я быстро составил резюме, упомянул бота, но выбрали другого кандидата. DevOps кажется сложным, требует много времени. Учиться тяжело, особенно когда ты один, без команды, и отвечаешь за всё — код, маркетинг. Ещё есть семья, ипотека — это добавляет сложности.</p><h2>Работа с нейросетями и их применение</h2><p><b>Маша Даровская:</b> Какая нейросеть тебе больше нравится?</p><p><b>Иван:</b> Grok — для кода, он чётче, меньше ошибок. ChatGPT — для общения, структуры бота, геймификации. Grok я использовал в бесплатной версии, ChatGPT — в премиум. Grok помог выбрать идею для бота: я поделился заметками, и он посоветовал сосредоточиться на этом проекте.</p><p><b>Маша Даровская: </b>Есть ли нетривиальные способы применения нейросетей?</p><p><b>Иван:</b> Сейчас я использую ChatGPT для судебного разбирательства. Арендодатель не возвращает залог за квартиру, придирается к мелочам. ChatGPT помог составить досудебную претензию и юридические сообщения. Я общаюсь в правовом поле, корректирую его тексты минимально. Он подсказал, что шансы выиграть — 90%, упомянул законы о естественном износе. Это интересный опыт, и если получится, будет крутой кейс.</p><p><b>Маша Даровская: </b>Совет для тех, кто хочет попробовать, но боится?</p><p><b>Иван:</b> Не бойтесь. Это интересно. Ты один дома, пишешь идею в ChatGPT, он подсказывает, что делать: разложить по полочкам, собрать MVP. С маркетингом сложнее, но в остальном — бери и делай.</p>]]></content:encoded>
    </item>
    <item>
      <title>Как защитить pet-проект почти бесплатно, но эффективно</title>
      <link>https://tproger.ru/articles/kak-zashhitit-pet-proekt-pochti-besplatno--no-effektivno</link>
      <comments>https://tproger.ru/articles/kak-zashhitit-pet-proekt-pochti-besplatno--no-effektivno?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Светлана Гринь]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-zashhitit-pet-proekt-pochti-besplatno--no-effektivno</guid>
      <description><![CDATA[<p>Как эффективно защитить pet-проект: управление секретами, логирование, бэкапы, локальные туннели и другие базовые правила безопасности
</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-zashhitit-pet-proekt-pochti-besplatno--no-effektivno">Как защитить pet-проект почти бесплатно, но эффективно</a>»</p>]]></description>
      <category><![CDATA[API]]></category>
      <category><![CDATA[Инструменты]]></category>
      <category><![CDATA[Git]]></category>
      <category><![CDATA[Безопасность]]></category>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[SQL]]></category>
      <category><![CDATA[Slack]]></category>
      <category><![CDATA[Боты]]></category>
      <category><![CDATA[Базы данных]]></category>
      <category><![CDATA[Навыки]]></category>
      <category><![CDATA[Сервисы]]></category>
      <category><![CDATA[ICO]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Мессенджер]]></category>
      <category><![CDATA[Приложение]]></category>
      <category><![CDATA[Взлом]]></category>
      <category><![CDATA[Сервер]]></category>
      <category><![CDATA[Библиотеки]]></category>
      <category><![CDATA[1C]]></category>
      <category><![CDATA[Разработка]]></category>
      <category><![CDATA[Grafana]]></category>
      <category><![CDATA[CI/CD]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 17 Jun 2025 10:00:03 GMT</pubDate>
      <content:encoded><![CDATA[<p>Pet-проекты помогают развивать профессиональные навыки и воплощать собственные идеи, но не стоит забывать об их информационной безопасности. Делать сервис и не думать об инфобезе — всё равно что строить дом без фундамента: выглядит добротно, но всё может рухнуть в самый неожиданный момент. Разберём, как недорого и эффективно защитить проект.</p><h2>Что такое pet-проект и зачем его защищать</h2><p><b>Pet-проект</b> (от английского pet — «домашний питомец») — тренировочный проект, который разработчик создаёт в свободное время по собственному желанию. Обычно их делают, чтобы освоить новую технологию, пополнить портфолио или поучаствовать в хакатонах.</p><p>Такие проекты часто воспринимают как что-то «несерьёзное», но пренебрежение информационной безопасностью может привести к неприятным последствиям. Злоумышленники используют уязвимости pet-проектов для получения доступа к ресурсам разработчика, кражи данных и будущих атак на более крупные цели.</p><p>Кроме того, защита pet-проекта — важный навык, который высоко ценится работодателями.</p><p>Рассмотрим основные правила кибербезопасности, которые нужно учитывать при работе над pet-проектом.</p><h2>Безопасное управление секретами</h2><p><b>Секреты</b> — это чувствительные данные, такие как пароли, токены доступа, ключи API, SSH-ключи, сертификаты и другие данные, которые обеспечивают аутентификацию и шифрование. Если добавить секреты в код, злоумышленники могут получить полный контроль над вашей инфраструктурой.</p><h3>Какие правила нужно соблюдать</h3><ul><li>Не храните секреты в коде. Храните секреты в отдельных файлах env. и добавьте эти файлы в .gitignore, чтобы они не попадали в репозиторий.</li><li>Придерживайтесь принципа минимальных привилегий. Каждый сервис должен иметь только те права, которые необходимы для выполнения своих задач.</li><li>Регулярно обновляйте секреты. Меняйте токены и пароли периодически, особенно после обнаружения утечек или изменений в проекте.</li><li>Используйте менеджеры секретов. Популярные сервисы: Doppler, HashiCorp Vault, AWS Secrets Manager, 1Password Developer Tools.</li><li>Мониторьте утечки. Можно использовать такие инструменты, как GitGuardian, TruffleHog, Gitleaks.</li><li>Шифруйте секреты. Используйте библиотеки типа cryptography в Python и подключайте шифрование на уровне операционной системы.</li></ul><h2>Безопасность CI/CD</h2><p><b>Пайплайн CI/CD</b> (Continuous Integration / Continuous Delivery) — автоматизированный процесс сборки, тестирования и развёртывания приложений. Он помогает автоматически интегрировать код и деплоить его на различные среды.</p><p>Если злоумышленник получит доступ к пайплайну, он может внедрить вредоносный код в ваше приложение, остановить весь процесс разработки или развёртывания, украсть данные пользователей и т.д.</p><h3>Способы защиты пайплайна</h3><ul><li>Моделируйте угрозы. Оцените, какие угрозы наиболее вероятны на каждом этапе пайплайна: от коммита кода до деплоя на сервер.</li><li>Проверяйте зафиксированный код. Используйте статический анализ кода для автоматического поиска уязвимостей.</li><li>Защитите Git-репозитории. Настройте двухфакторную аутентификацию (2FA), ограничьте доступ к репозиториям, используйте обязательную проверку пул-реквестов двумя разработчиками.</li><li>Изолируйте пайплайн. Не запускайте его на том же сервере, где крутится ваше продакшн-приложение.</li></ul><p>Дополнительно стоит шифровать секреты в пайплайне и минимизировать их передачу между этапами сборки.</p><h2>Сервисы мониторинга и логирования</h2><p><b>Логирование</b> — запись событий, ошибок и других данных о работе приложения в специальные файлы или базы данных. По сути, это дневник.</p><p><b>Мониторинг</b> — наблюдение за состоянием приложения, инфраструктуры или сервисов в реальном времени для своевременного выявления падения сервера, роста ошибок и других проблем.</p><p>Анализ логов помогает выявлять баги, попытки несанкционированного доступа, долгие запросы, ошибки базы данных. Мониторинг позволяет мгновенно реагировать на сбои, а также с его помощью вы узнаете, хватает ли приложению серверных мощностей.</p><h3>Примеры популярных сервисов</h3><p><a href="https://logtail.ru/">Logtail </a>— простой инструмент для сбора и анализа логов, есть бесплатный тариф.</p><p><a href="https://github.com/paper-trail-gem/paper_trail">Papertrail</a> — удобный сервис для быстрого поиска по логам, бесплатный план для небольших проектов (10 Мб в день).</p><p><a href="https://docs.sentry.io/">Sentry</a> —  хорош для отслеживания ошибок в приложениях на клиентской стороне и сервере.</p><p><a href="https://betterstack.com/">BetterStack</a> — мониторинг доступности сайтов и серверов с бесплатными уведомлениями об инцидентах по почте, через SMS и Slack.</p><p><a href="https://grafana.com/pricing/">Grafana Cloud Free</a> — мониторинг с красивыми дашбордами, бесплатный лимит ресурсов до 10 тыс. серий данных, 50 ГБ трафика.</p><p><a href="https://prometheus.io/">Prometheus</a> и <a href="https://grafana.com/">Grafana</a> — Prometheus собирает метрики, Grafana их визуализирует.</p><p><a href="https://uptimerobot.com/">UptimeRobot</a> — проверка доступности вашего проекта каждые 5 минут, бесплатный тариф на 50 мониторингов.</p><h2>Бэкап и восстановление данных</h2><p><b>Бэкап</b> — это создание резервной копии данных, которую можно использовать для восстановления в случае утраты или повреждения оригиналов. Может показаться, что для pet-проекта это излишне, однако от случайных удалений данных, взломов серверов, утечек данных никто не застрахован. А ещё можно откатиться к рабочей версии, если будут ошибки в коде и деплойменте.</p><h3>Как сделать бэкап пошагово</h3><ol><li>Определите данные, которые необходимо бэкапить: какие данные критически важны, какие можно восстановить вручную.</li><li>Выберите место хранения: облачные сервисы, собственные серверы, внешние носители, Git-репозиторий.</li><li>Выберите тип бэкапа: при полном копируются все данные целиком, при инкрементном — изменения с момента последнего копирования, при дифференциальном — изменения с момента последнего полного бэкапа.</li><li>Настройте автоматизацию, чтобы не забывать делать бэкапы вручную. Можно использовать скрипты, планировщики задач или бэкап-сервисы.</li><li>Проверьте бэкап. Проведите тестовое восстановление.</li><li>Определите частоту бэкапа. Например, можно проводить полный бэкап раз в неделю и инкрементные бэкапы каждый день.</li><li>Защитите чувствительные данные.</li></ol><h2>Локальные туннели</h2><p>При разработке pet-проекта может возникнуть необходимость показать результат внешнему миру. Кроме того, многие внешние сервисы, такие как платёжные системы и мессенджеры, тоже требуют «боевые» URL для отправки запросов. Однако открывать порты на своём устройстве напрямую небезопасно. Локальные туннели создают временный внешний URL-адрес без развертывания на реальном сервере.</p><p>Когда вы запускаете туннель через специальный инструмент, он:</p><ul><li>устанавливает зашифрованное соединение между вашим компьютером и своим публичным сервером;</li><li>создаёт внешний адрес;</li><li>пересылает все запросы, которые приходят на этот адрес, вашему локальному приложению.</li></ul><p>Трафик при этом шифруется и проходит через защищённый канал.</p><h3>Примеры инструментов</h3><p><a href="https://ngrok.com/?ref=gobigger">Ngrok </a>— самый известный инструмент для быстрого создания туннелей. Есть бесплатный тариф.</p><p>Порты от<b> VSCode</b> — отличное решение для пользователей Visual Studio Code, удобно для быстрой демонстрации.</p><p><a href="https://dev.vk.com/ru/libraries/tunnel">VK Tunnel</a> — российская альтернатива, подходит для работы через VK Cloud.</p><p><b>Tuna</b> и <a href="https://xtunnel.ru/">xTunnel </a>— простые в использовании решения, есть бесплатные тарифы.</p><h2>Чек-лист по инфобезу для тех, кто делает pet-проект</h2><ol><li>Регулярно обновляйте зависимости. Используйте автоматические инструменты, например, Dependabot или npm audit.</li><li>Настройте базовые HTTP-заголовки безопасности. Добавьте заголовки Content-Security-Policy, X-Frame-Options, Strict-Transport-Security, чтобы минимизировать риск XSS, Clickjacking и других атак.</li><li>Используйте бесплатные SSL-сертификаты. Подключите HTTPS через бесплатные сервисы, например, Let's Encrypt.</li><li>Очищайте и валидируйте ввод данных. Фильтрация и валидация данных защитит от SQL-инъекций и XSS.</li><li>Создайте отдельные учётные записи для разных сервисов. Не используйте одну и ту же учётную запись везде.</li><li>Минимизируйте доступы к базе данных. Если сервису нужно только читать, не давайте права на запись или удаление.</li><li>Используйте бесплатные инструменты для сканирования уязвимостей. Проверьте код через такие сканеры, как SonarQube Community Edition, Snyk, OWASP ZAP.</li><li>Делайте резервные копии. Настройте автоматические бэкапы базы данных и важных файлов.</li><li>Не храните секреты в коде. Используйте .env файлы и убедитесь, что они добавлены в .gitignore.</li><li>Включите двухфакторную аутентификацию (2FA). На всех сервисах, где это возможно, включите 2FA для дополнительной защиты.<br /></li></ol><p>А больше про разработку и все, что с ней связано, в нашем<a href="https://t.me/tproger_web"> тг-канале</a>!</p>]]></content:encoded>
    </item>
    <item>
      <title>От университета к дата-сайенс в МТС за год: как я проходил обучение в Школе аналитиков</title>
      <link>https://tproger.ru/articles/ot-universiteta-k-data-sajens-v-mts-za-god--kak-ya-prohodil-obuchenie-v-wkole-analitikov</link>
      <comments>https://tproger.ru/articles/ot-universiteta-k-data-sajens-v-mts-za-god--kak-ya-prohodil-obuchenie-v-wkole-analitikov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[МТС]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/ot-universiteta-k-data-sajens-v-mts-za-god--kak-ya-prohodil-obuchenie-v-wkole-analitikov</guid>
      <description><![CDATA[<p>Максим Коновалов расскажет, как стал Data Scientist в МТС, пройдя школу аналитиков данных МТС и стажировку. </p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/ot-universiteta-k-data-sajens-v-mts-za-god--kak-ya-prohodil-obuchenie-v-wkole-analitikov">От университета к дата-сайенс в МТС за год: как я проходил обучение в Школе аналитиков</a>»</p>]]></description>
      <category><![CDATA[Обучение программированию]]></category>
      <category><![CDATA[Big Data]]></category>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Искусственный интеллект]]></category>
      <category><![CDATA[Машинное обучение]]></category>
      <category><![CDATA[Навыки]]></category>
      <category><![CDATA[Стажировка]]></category>
      <category><![CDATA[HR]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Data Science]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 20 Feb 2025 14:52:20 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет! Я Максим, дата-сайентист из МТС. Работаю в команде банковского скоринга: наш продукт определяет кредитные риски и вероятность мошенничества. В компанию я попал через школу аналитиков данных МТС и стажировку. Сегодня расскажу, как попасть на работу в крутую компанию без 10 лет опыта работы.</p><h2>С чем я пришел в Школу</h2><p>До поступления в школу я занимался программированием, сейчас учусь в университете на специальности «Робототехника и искусственный интеллект». У нас в программе, разумеется, есть курсы по машинному обучению и Python с практикой. В дополнение я проходил бесплатные курсы на Stepik и похожих платформах, был на митапах по Data Science, пробовал проходить стажировки. Плюсом делал небольшие pet-проекты, но коммерческих работ не было.</p><p>Год назад я наткнулся на лендинг Школы. Мне понравилось, как расписана программа, кем являются преподаватели — это и подкупило. Последним аргументом стала возможность попасть на стажировку в МТС.</p><p>В итоге я подал заявку, прошел вступительный экзамен (в форме теста), написал мотивационное письмо — и, наконец, попал на обучение. Из огромного числа заявок прошли отбор лишь 120 человек.</p><h2>Много математики, много домашки и баллы за кофе с одногруппниками: как строилось обучение</h2><p>Обучение началось через несколько дней после зачисления в Школу. Иногда я думал о том, что программа может оказаться такой же, как на курсах, которые проходил раньше: структура не очень, все в записи, часть материала потеряла актуальность и так далее. Но оказалось все наоборот.</p><p>Занятия были очень интенсивными: два раза в неделю мы слушали лекции, по три часа каждая (всего мы отучились 360 часов!). Весь материал читали преподаватели во время трансляции. Там же отвечали на вопросы студентов по теме лекции или о себе и работе. Живое общение очень мотивировало посещать трансляции, а не ждать записи и откладывать «на потом».</p><p>Программа состояла из нескольких блоков: SQL, Python, математическая статистика, оптимизация, классический ML, визуализация, временные ряды и A/B-тесты, Big Data, RecSys, NLP, кейсы в ML и System Design. Около половины программы заняла теория: математика, статистика, теория вероятности и прочее. Другая половина — это работа с данными, Python, машинное обучение.</p><blockquote>За пятнадцать лет работы в DS я пришел к выводу, что с коллегами, которые ловко освоили хайповые либы и не обладают фундаментальными знаниями, работается как на минном поле — никогда не знаешь где рванет. Часто эти ошибки касаются базовой статистики, интервальных оценок, а еще чаще — работы алгоритмов. Строгие теоретические выкладки подменяются мифами, а давно преодоленные ограничения старых реализаций алгоритмов становятся догматами. Отсюда и идет целеполагание нашей программы. При этом учить одну лишь теорию скучно, и у студентов возникнут справедливые вопросы о применимости знаний. При создании программы я старался дать за весьма ограниченный срок (всего год) и базу, и практические навыки. Это нужно, чтобы специалист на выходе стал самостоятельным: мог построить end2end-приложение с ML — от скраппинга данных до деплоя и оценки эффективности решения в деньгах. Это действительно сложно: начать с занятий Python и SQL и за год дойти до Spark и PyTorch, параллельно двигаясь от алгебры, оптимизации и статистики до устройства трансформерных архитектур и проблем смещений (bias) в рекомендательных системах. При этом базовые блоки выступают фундаментом для дальнейших занятий, и курс с середины не пройти.</blockquote><p>Многие преподаватели делили их на теорию и практику: изучили материал на лекции и сразу попробовали применить его при выполнении какой-то задачи.</p><p>Почти после каждого занятия мы получали домашнее задание на неделю — или более объемную итоговую работу, если закончили какой-то блок. Разумеется, все по теме лекции: от посчитать какую-то вероятность до написать бэкенд сайта для бронирования книг.</p><p>Что-то было довольно простым, например, все тот же <a href="https://github.com/BigMak1/Book-Store">сайт</a>. Но иногда приходилось довольно долго думать.</p><p>Хороший пример — итоговая работа по Big Data. Нам дали файлы датасетов, по которым надо было выполнить четыре задачи:</p><ol><li>Проанализировать данные, описать проблемы, которые в них содержатся (проблемы хранения тоже считаются), и предложить решения.</li><li>Реализовать поток данных из топика, который бы удовлетворял конкретные условия.</li><li>Реализовать batch-поток для обработки исторических данных и построить на его основе четыре отчета.</li><li>Спроектировать модель данных и таблицы для хранения информации из предыдущих задач. И протестировать эту модель на нескольких запросах.</li></ol><p>Многие домашки были построены так, что их можно сразу класть в портфолио и подавать как пет-проекты. Например, домашкой по ML было близкое к реальному техническое задание от продакт-оунера: внедрить ML-модель в прод.</p><p>До начала курса я был знаком с основами математической статистики, SQL, Python и ML, и Школа аналитиков данных смогла дать мне главное — практический опыт, которого не хватало. С каждым месяцем обучение становилось интереснее: я начал узнавать вещи, о которых никогда не слышал.</p><figure><img src="https://media.tproger.ru/user-uploads/101078/2025-02-18/3a846a1c-7b83-45cb-b837-7924adf6036e.png" alt="" /></figure><p>А еще меня впечатлила сама организация. Спасибо Алине Веденской и Марии Теплинской за то, что регулярно постили анонсы и новости курса и всегда быстро давали обратную связь.</p><h2>Еще нас мотивировали с помощью челленджей</h2><p>Мы получали баллы за посещение лекций, домашки и внешнюю активность — те самые челленджи. Это могли быть пост про Школу в своих соцсетях или фотка, на которой ты пьешь кофе с другими студентами. За очки можно было купить мерч, плюс на их основе строился рейтинг студентов.</p><figure><img src="https://media.tproger.ru/user-uploads/101078/2025-02-18/21532edb-6c33-402b-9ba9-a93f537c33fa.jpeg" alt="" /><figcaption>Вот такими были задания, за которые давали баллы.</figcaption></figure><p>Хотя должен признать, что мне не хватило нетворкинга и живого общения: лекций, конференций, мероприятий в офлайне. Но большинство студентов живут в разных городах и учатся/работают параллельно со Школой аналитиков данных, так что вряд ли это вообще возможно реализовать.</p><h2>Высокий рейтинг — возможность попасть на стажировку</h2><p>У топ-5 студентов по учебному рейтингу была возможность пройти все этапы отбора на стажировку в упрощенном порядке: мы сразу выбирали отдел, в котором хотели бы работать, и попадали на интервью с руководителем команды.</p><p>У остальных студентов и других кандидатов все было сложнее: нужно пройти первичное интервью с рекрутером, дождаться его решения, и только потом, если оно окажется положительным, тебя пригласят на интервью с руководителем команды, в которую хочешь попасть.</p><figure><img src="https://media.tproger.ru/user-uploads/101078/2025-02-18/1e273997-ffff-4988-a44b-f5c9d3695aa4.jpeg" alt="" /><figcaption>Мой сертификат выглядел так.</figcaption></figure><h2>А потом пошли стажировки и адаптация</h2><p>Благодаря учебе у меня появилась хорошая теоретическая база, небольшие проекты в портфолио, навыки работы с конкретными инструментами и контакты с коллегами, которые раньше были нашими преподавателями. Но было все равно сложновато.</p><p>Все потому, что появился огромный объем информации: по процессам, по продуктам, по ролям — все, что скопилось у отдела за много лет работы. И этот объем надо было как-то усвоить в максимально сжатые сроки: изучать документацию, читать чужой код, разбираться, что этот код сделал и почему именно так.</p><p>Но я всегда мог написать вопрос в общий чат, и коллеги помогали разобраться с конкретной задачей.</p><p>Конечно, параллельно с первого дня стажировки я начал работать. Например, первой задачей было построить скоринговую ML-модель — по типу тех, которые делают коллеги. Делать нужно было все:</p><ul><li>сборку и расчет данных;</li><li>препроцессинг;</li><li>фильтрацию стабильных признаков во времени по PSI;</li><li>построение и сохранение ансамбля моделей;</li><li>расчет метрик качества;</li><li>создание отчета по построенной модели.</li></ul><p>И здесь помогло обучение в Школе аналитиков данных (особенно блок Big Data). Мы учились на тех инструментах, которыми я пользовался на стажировке и пользуюсь до сих пор. Например, когда я только попал на стажировку, уже очень хорошо разбирался в модуле Spark, успел позапускать на нем код — так что тратить время на изучение инструмента не пришлось.</p><h2>Так, очень быстро и незаметно пробежали три месяца</h2><p>Как такового перехода из стажировки в штат у меня не было — я закрывал спринты, постепенно брал на себя более сложные задачи (например, строил внешнюю модель для внешнего заказчика). Мне даже сложно прочертить четкую границу между работой стажера и на нынешней должности, потому что проекты остались теми же:</p><ul><li>реализовывать новые фичи для ML-моделей на основе данных телекома;</li><li>сделать аналитику по продуктам финтеха;</li><li>построить ML-модель для потока внешних клиентов и так далее.</li></ul><p>Тем не менее появилось планирование и долгосрочные цели. Если раньше я был «на подхвате», и тимлид давал по задаче за раз, то теперь потихоньку начал формироваться бэклог на следующий квартал: мне начали ставить конкретные задачи с дедлайнами.</p><p>Как я узнал от HR, после завершения стажировки около 60% сотрудников переходят в штат компании. Это меня удивило и замотивировало — не хотелось попасть в оставшиеся 40%.</p><h2>Что осталось рассказать</h2><p>Я остался доволен учебой в Школе и дальнейшим треком по нескольким причинам:</p><ul><li>качественные и хорошо структурированные знания, которые вы либо не сможете найти в открытом доступе, либо потратите на это кучу времени;</li><li>преподаватели — действующие сотрудники МТС, опытные специалисты с огромной экспертизой;</li><li>классное, открытое общение: и менеджеры, и преподаватели всегда готовы помочь;</li><li>домашки не были абстрактными и больше походили на пет-проекты — с такими точно можно собрать портфолио и стучаться в крупные IT-компании.</li></ul><p>В целом, этот курс стал для меня отличным стартом в мире Data Science. Моей целью было получить навыки и знания, которые могут помочь мне попасть на стажировку в МТС — и я их получил. Заранее изучил теорию, с которой буду сталкиваться на работе, и отточил ее на домашних заданиях, выяснил, как все устроено в командах, и познакомился с будущими коллегами.</p><p>А тем, кто только поступает в Школу, я советую быть активными: ходить на лекции, выполнять домашки и получать баллы. Звучит просто и обыденно, но от этого действительно зависит, сможете ли вы попасть на стажировку и получить работу.</p>]]></content:encoded>
    </item>
    <item>
      <title>Автор диплома, написанного Chat GPT, научил нейросеть общаться с девушками вместо себя</title>
      <link>https://tproger.ru/articles/avtor-diploma--napisannogo-chat-gpt--nauchil-nejroset-obshhatsya-vmesto-sebya-s-devuwkami</link>
      <comments>https://tproger.ru/articles/avtor-diploma--napisannogo-chat-gpt--nauchil-nejroset-obshhatsya-vmesto-sebya-s-devuwkami?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Андрей Коротков]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/avtor-diploma--napisannogo-chat-gpt--nauchil-nejroset-obshhatsya-vmesto-sebya-s-devuwkami</guid>
      <description><![CDATA[<p>В итоге нашел «ту самую» и сделал ей предложение — тоже по совету ChatGPT.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/avtor-diploma--napisannogo-chat-gpt--nauchil-nejroset-obshhatsya-vmesto-sebya-s-devuwkami">Автор диплома, написанного Chat GPT, научил нейросеть общаться с девушками вместо себя</a>»</p>]]></description>
      <category><![CDATA[Нейронные сети]]></category>
      <category><![CDATA[Искусственный интеллект]]></category>
      <category><![CDATA[OpenAI]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Twitter]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 01 Feb 2024 11:13:21 GMT</pubDate>
      <content:encoded><![CDATA[<p>Александр Жадан, ставший известным после <a href="https://tproger.ru/articles/novosti-chatgpt-student-rggu-napisal-diplom-nejrosetju-a-microsoft-voskreshaet-yahoo">диплома, написанного ChatGPT</a>, рассказал в социальной сети X (бывший Twitter), как использовал нейросеть для знакомства с девушками в Tinder.</p><p>Идея пришла после того нескольких провальных переписок и свиданий. Девушки, по его словам, были с «характерными минусами». Кроме того, Жадан не был готов тратить слишком много времени и денег на поиск подходящей девушки (потому что, кроме походов на свидания, нужно «успевать работать, заниматься хобби, учиться и общаться с людьми»).</p><h2>В итоге он научил нейросеть искать пары и общаться в Tinder вместо себя</h2><p>Эксперимент начался в 2022 году. За основу был взять API GPT-3, к которому у Жадана был ранний доступ (никакого ChatGPT в паблике еще не было). Парень научил его отбирать вероятно подходящих девушек (у которых есть хотя бы две фотографии в профиле) и завязывать общение после мэтча:</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/8981ddc7-b91f-4a1c-95f3-c863972ffefa.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><blockquote>GPT общался без моего вмешательства по запросу «ты парень, общаешься с девушкой впервые. Твоя задача: не сразу, но пригласить на свидание». Костыльно и не очень человечно, зато работало.</blockquote><p>Диалоги по скрипту быстро заканчивали, потому что GPT звал на свидания в лес, упорно предлагал курицу с овощами и выдавал «душную» теорию не к месту. Кроме того, бот поначалу не учитывал предыдущие сообщения (пришлось отдельно учить его запоминать контекст):</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/89a4a9fe-81d1-49de-8237-13fa6a0b33e1.png" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><h2>С выходом ChatGPT общение стало лучше</h2><p>Жадан дообучил нейросеть по собственным диалогам, настроил фильтр, чтобы девушка не прилетали «кринж-истории» — по крайней мере, вначале. И прикрутил систему распознавания лиц (обучал ее на свайпах с другого аккаунта). Также через API ChatGPT и FlutterFlow научил отсеивать кандидаток по разным критериям, например, без анкет, публикующих фото с цветами, указывающих знак зодиака.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/d3d49061-0282-4c9d-ac74-4b81881f1972.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><p>В итоге модель начала лучше отбирать профили и общаться. С некоторыми парень уже начинал общаться лично в Telegram, а нейросеть выдавала саммари: краткую историю общения и информацию о девушке.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/de6b4946-4347-48bf-83c9-9901ccd862f2.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><p>Тем не менее нейросеть все еще косячила: могла назначала свидания на одно время, обещала принести на встречу пять литров компота.</p><h2>Вторая версия на ChatGPT-4 стала сложнее, но лучше</h2><p>Жадан интегрировал календарь и Telegram, прикрутил новую систему распознавания по фото, параллельно попросил обычный ChatGPT помочь — тот предложил в начале общения рассказывать про детство, цели и ценности и определил признаки идеальной партнерши. В итоге получилось улучшить качество переписок и возобновить общение с некоторыми девушками. А еще появился дополнительный фильтр — если ценности и какие-то черты не совпадали, бот заканчивал общение.</p><p>Допом появились бот в Telegram, который присылал статусы переписок и обращался к Жадану, когда не был уверен в ответе, и валидация ответа.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/89832394-dc1a-4acd-aba3-941dd2abafcf.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><p>За месяц ChatGPT V2 получила почти 5 тысяч мэтчей в Tinder Gold. А на количество встреч можете посмотреть здесь:</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/c7596d1f-33a3-433b-a40b-a5dfcf81a8eb.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><p>В итоге остались 4 девушки: с тремя сохранились дружеские отношения, а четвертая оказалась «она».</p><h2>И чтобы не заруинить общение, была создана ChatGPT V3</h2><p>Парень настроил V3, как «наблюдателя», который общается, когда Жадан долго не отвечает, дает советы. И пишет, если беседа накаляется.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/88fb4d07-e981-45c8-b8e9-2fbfacbd3649.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><p>Наконец, ChatGPT V3 прислал очередное саммари бесед и предложил жениться на девушке.</p><blockquote>На разработку проекта ушло ~120 часов и $1432 на API. На счета в ресторанах вышло до 200тр. Бтв, затраты отбил и заработал на рекомендациях. Если знакомиться самому и ходить на свидания, то на то же самое ушло 5+ лет и 13м+ рублей. Спасибо ChatGPT за экономию денег и времени</blockquote><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/e1d4876d-b55a-4108-b0a8-74084f72ec47.jpeg" alt="" /><figcaption>Источник: Александр Жадан</figcaption></figure><h2>И, возможно, это все пиар-ход</h2><p>История завирусила в Х, и пользователи, разумеется, запостили много шуток и мемов. Одни предложили теперь проверять пары в Тиндере капчей (кто-то и вовсе решил что некоторые уже это делают с помощью дикпиков).</p><p>Кто-то делал отсылки к Терминатору и Черному зеркалу (по сюжету одной из серий люди ищут себе пары с помощью ИИ). Кто-то предлагал завести отношения со Скрепышом.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2024-02-01/47eca5de-9028-46c2-90bd-aa0569af4b8f.png" alt="" /></figure><p>Наконец, героя заподозрили в обмане (и прогреве перед запуском курса). Программист Коля Шваб <a href="https://twitter.com/NikoStolz/status/1752659252320117209">изучил</a> алгоритм и сказал, что это похоже на «фулл-тайм проекту на несколько месяцев в разработке и эксплуатации». Кроме того, он напомнил, что OpenAI позволила обучать модели ChatGPT в марте 2023 года. Но уже в апреле ChatGPT V1 работала «на полную».</p><p>Также, по мнению Шваба, больше пяти тысяч мэтчей — нереалистичный результат для человека с такими серьезными критериями отсева. Наконец, пользователь добавил, что если Жадан солгал, то «очень красиво», а если рассказал правду, то он «гениально быстро обучаемый разработчик».</p>]]></content:encoded>
    </item>
    <item>
      <title>Лучший пет-проект 2023: голосование</title>
      <link>https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie</link>
      <comments>https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie</guid>
      <description><![CDATA[<p>Запустили голосование за лучший пет-проект, представленный на конкурс Tproger. В голосовании участвуют 10 проектов.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie">Лучший пет-проект 2023: голосование</a>»</p>]]></description>
      <category><![CDATA[Конкурс Tproger]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 06 Nov 2023 12:54:15 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет! Tproger запустил новый конкурс на лучший пет-проект среди наших читателей.</p><p>10 октября стартовал <a href="https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs">первый этап конкурса</a>, в ходе которого авторы проектов присылали статьи с их описанием.</p><p>Сегодня, 6 ноября, стартует второй этап, в ходе которого вы сможете проголосовать за проект, который нравится вам больше всего.</p><p>Все участники, которые прошли первый этап, получат призы.</p><ul><li>С 1 по 5 место: худи с логотипом Tproger и стикеры от редакции.</li><li>С 6 по 10 место: футболки с логотипом Tproger и стикеры.</li></ul><p>Какие пет-проекты участвуют в голосовании:</p><ol><li><a href="https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov">Senior Junior. Курсы от программистов для программистов</a></li><li><a href="https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke">Как я создал змейку на Python</a></li><li><a href="https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov">Бета-версия вычислителя суммы постройки дома с указанием параметров</a></li><li><a href="https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov">Локальный деплой проектов в пару кликов</a></li><li><a href="https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195">Как я сделал карточный баттлер без конструктора колод</a></li><li><a href="https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov">Менеджер паролей, который не хранит пароли</a></li><li><a href="https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu">Hunt job. Как отвлечься, пока ищешь работу</a></li><li><a href="https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov">Очередной фреймворк на PHP DeltaFramework</a></li><li><a href="https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov">Три библиотеки для React по цене одной</a></li><li><a href="https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov">Ретранслятор СМС-сообщений для релокантов</a></li></ol><p>Подпишитесь на тэг <a href="https://tproger.ru/tag/pet-projects-2023">Лучший пет-проект 2023</a>, чтобы не пропустить результаты конкурса и следить за обновлениями в личной ленте.</p><p>Желаем удачи!</p>]]></content:encoded>
    </item>
    <item>
      <title>Как я создал свою RPG-игру FALDOR. Части 1 и 2</title>
      <link>https://tproger.ru/articles/faldor-hroniki-chast-1-2</link>
      <comments>https://tproger.ru/articles/faldor-hroniki-chast-1-2?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[FANTASY UNIVERSE]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/faldor-hroniki-chast-1-2</guid>
      <description><![CDATA[<p>Рассказ о 2D-RPG игре FALDOR, которая разрабатывается с августа 2023-го года в качестве пет-проекта. Говорим о сюжете и визуале.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/faldor-hroniki-chast-1-2">Как я создал свою RPG-игру FALDOR. Части 1 и 2</a>»</p>]]></description>
      <category><![CDATA[Разработка игр]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 30 Oct 2023 13:08:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Сегодня я вам расскажу о своём проекте, который разрабатываю с недавних пор (С августа 2023-го года). Я – инди-разработчик игр, и это – мой проект FALDOR, который представляет из себя 2D-RPG с открытым миром.</p><p>Давайте вкратце дам вам понять, что это вообще за проект.</p><h2>Сюжет</h2><p>Блуждая миллионы лет в открытом космосе, магический и величественный артефакт Фалдор, с заключенной внутри себя душой некогда могущественного Бога Хаоса, попадает на маленькую планету Антар, где по счастливой случайности ему и суждено пробыть еще не один антарский век. Боги узнают о местонахождении Фалдора и стремятся заполучить его. Многие от него хотят избавиться, но только не боги Туленонда: Жестокие и безумные владыки, чья армия настолько велика и беспощадна, что ей нет равных; боги, чьё безумство и гордыня так сильны, что лишь корысть и злоба движут ими в их неугомонных и жадных планах. По крайней мере, так говорят боги Удгара, истинные и древние соперники Туленонда, владыки старых порядков и нынешних миров.</p><p>Главный герой, житель Антара, вскоре узнаёт, что ему выпала возможность принять участие в конфликте богов на своей собственной планете. Но, к сожалению, это история не о великом герое, не об избранном и не о сопернике богов. Это история о простом смертном создании, который оказался случайно на переплети двух идейных гигантов. Но станет ли главный герой вообще принимать участие в этом? Сможет ли он пожертвовать мирной жизнью в угоду захватывающих и опасных приключений? Это и предстоит решить Вам.</p><h2>Концепт, визуал и графика</h2><p>И вот как всё начинается. Перед вами здесь инвентарь (вернее его скелет) из моей игры.</p><figure><img src="https://media.tproger.ru/user-uploads/91769/2023-10-25/b9ffc3ff-fa2b-4b72-8cdc-a9f3b750d4ef.png" alt="" /></figure><p>Я посчитал, что нынешние РПГ игры немного потеряли суть понятия “РПГ”. Я подумал, что было бы круто, если бы игрока не вели по однотипной стороне прокачки или концепции игры.</p><p>Скажу сразу: я НЕ пытаюсь создавать заново велосипед, делать какой-то мастхев-проект или что-то в этом роде. Это просто игра в жанре РПГ, которая представляет из себя моё видение РПГ игр. Не стоит думать, что я что-то там копирую, пожалуйста.</p><p>В общем, с таким подходом к концепту, мне пришлось немного <i>переобдумать </i>концепт своей игры. Как минимум, я никогда не понимал, почему “Вор” и “Лучник” в законах РПГ-жанра – это один и тот же класс? Ну, как правило. В Фалдоре я решил эти классы разделить, и даже более того, внедрив систему “Кармы” в игру, пришлось разделить и классы почти что надвое.</p><p>Чтобы понимать лучше:</p><ol><li>В стандартных РПГ принято наблюдать 3 класса: Воин, Вор и Маг.</li><li>В Фалдоре же, грубо говоря, основными являются 7 классов: Паладин (добрый воин), Тёмный воин (тут понятно), Вор, Лучник (добрый или злой), Чародей (добрый маг), Оккультист, Нейтральная профессия (не боевая специализация).</li></ol><p>Таким образом в игре можно будет отыгрывать боевой класс, либо же не воевать ни с кем вовсе. То есть… эта РПГ, то есть Ролевая игра, даёт возможность отыгрывать именно роль практически любого человека, который вам может прийти в голову: какой-то воин, искатель приключений, маг, вор, охотник, разведчик, лесоруб, шахтёр, торговец, кузнец либо же кто-то еще – выбор, очевидно, только на стороне игрока.</p><p>К слову говоря, в Фалдоре я даже постарался убрать такое понятие, как “класс”, заменив его близким по смыслу словом – “предрасположение”, которое игрок выбирает вначале игры, и, к его сожалению, не сможет больше никогда поменять (А может быть и сможет каким-нибудь заклинанием или ритуалом, кто знает)…</p><p>Кстати, о выборе… Вот так, теперь, выглядит игра:</p><figure><img src="https://media.tproger.ru/user-uploads/91769/2023-10-25/67242ded-8b6c-4196-8399-d2c4876f27b7.png" alt="" /></figure><p>За это время было множество изменений: Добавлялись какие-то механики, перерисовывалась графика, ну и всё такое.</p><p>Например, вот такие были изменения:</p><figure><img src="https://media.tproger.ru/user-uploads/91769/2023-10-25/13dcdf55-1a37-41f6-84b3-2331ad66feb8.png" alt="" /></figure><figure><img src="https://media.tproger.ru/user-uploads/91769/2023-10-25/f329dc52-357f-47d7-b944-4b6fc26311dc.png" alt="" /></figure><p>На сегодня, думаю, это и всё. Про сюжет рассказал, игру показал, думаю, информация вышла не шибко компактной, простите. И как бы не хотелось рассказывать еще, но я не могу писать обо всех нововведениях в одном посту, потому что это будет тупо, неправильно и многословно.</p><p>Хотелось бы посмотреть как сильно вам понравится мой проект и его составляющие, если вообще понравятся, хотелось бы увидеть ваши фидбеки, реакции, и, думаю, в случае, если кому-то зайдет – напишу отдельный, вскоре, пост и более подробным списком механик.</p><p>Также, есть идея здесь вести девблог, чтобы уведомлять вас о нововведениях в игре и обо всём прочем.</p><p>Спасибо за уделенное время! До скорых встреч!</p>]]></content:encoded>
    </item>
    <item>
      <title>Лучший пет-проект 2023: голосование начнётся 6 ноября</title>
      <link>https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie-nachnyotsya-6-noyabrya</link>
      <comments>https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie-nachnyotsya-6-noyabrya?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie-nachnyotsya-6-noyabrya</guid>
      <description><![CDATA[<p>Перенесли голосование за лучший пет-проект на 6 ноября, на неделю вперёд, чтобы все успели ознакомиться с работами.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/luchwij-pet-proekt-2023-golosovanie-nachnyotsya-6-noyabrya">Лучший пет-проект 2023: голосование начнётся 6 ноября</a>»</p>]]></description>
      <category><![CDATA[Конкурс Tproger]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 30 Oct 2023 12:19:25 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет! Сейчас на нашем сайте проходит <a href="https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs">конкурс на лучший пет-проект читателей</a>. Сегодня, 30 октября, завершился первый этап конкурса, и приём статей о пет-проектах для участия в конкурсе остановлен.</p><p>Также с 30 октября должен был начаться второй этап конкурса — голосование читателей за лучший пет-проект, статьи для которого отбираются по количеству просмотров, лайков и комментариев под статьями участников на сайте.</p><p>Мы решили перенести старт голосования на 6 ноября: работ оказалось очень много, а некоторые из них прислали прямо к завершению первого этапа.</p><h2>Почему голосование стартует позже</h2><p>Кажется нечестным, что опубликованные прямо перед голосованием статьи не смогут пройти во второй этап потому, что не набрали достаточное количество просмотров, даже если у них есть все шансы выиграть.</p><p>За эту неделю читатели смогут ознакомиться со всеми работами на конкурсе.</p><h2>Список пет-проектов, которые участвуют в конкурсе</h2><ol><li><a href="https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke">Как я создал змейку на Python</a></li><li><a href="https://tproger.ru/articles/kak-ya-zapustil-agregator-festivalnogo-kino-konkurs-pet-proektov">Как я запустил агрегатор фестивального кино</a></li><li><a href="https://tproger.ru/articles/bginfo-lomaet-tvoi-oboi-napiwi-svoj-i-sdelaj-ego-luchwe-konkurs-pet-proektov">Bginfo ломает обои? Напиши свой и сделай его лучше</a></li><li><a href="https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov">Очередной фреймворк на PHP</a></li><li><a href="https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov">Локальный деплой проектов в пару кликов</a></li><li><a href="https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov">Три библиотеки для React по цене одной</a></li><li><a href="https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu">Hunt job. Как отвлечься, пока ищешь работу</a></li><li><a href="https://tproger.ru/articles/kvest-bot-konkurs-pet-proektov">Квест-бот для Telegram</a></li><li><a href="https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov">Ретранслятор СМС-сообщений для релокантов</a></li><li><a href="https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195">Как я сделал карточный баттлер без конструктора колод</a></li><li><a href="https://tproger.ru/articles/konstruktor-plejlista-dlya-ip-tv-konkurs-pet-proektov">Конструктор плейлиста для IP-TV</a></li><li><a href="https://tproger.ru/articles/oblachnaya-operacionnaya-sistema-konkurs-pet-proektov">Облачная операционная система</a></li><li><a href="https://tproger.ru/articles/meowsql-gui-klient-dlya-mysql-pod-linux-i-ne-tolko-konkurs-pet-proektov">MeowSQL: GUI-клиент для MySQL под Linux и не только</a></li><li><a href="https://tproger.ru/articles/mlup-machine-learning-as-api">MLup: как создавать веб-приложение с машинными обучением за один взмах волшебной палочки</a></li><li><a href="https://tproger.ru/articles/kak-ya-sozdayu-analiticheskij-instrument-dlya-gruppovyh-chatov-telegram-konkurs-pet-proektov">Как я создаю аналитический инструмент для групповых чатов Telegram</a></li><li><a href="https://tproger.ru/articles/kak-ya-piwu-kompilyator-c-podobnogo-yazyka-s-nulya-i-zachem-konkurs-pet-proektov">Как я пишу компилятор C-подобного языка с нуля и зачем</a></li><li><a href="https://tproger.ru/articles/telegram-bot-api-na-kotlin-kak-ono-bylo">Telegram Bot API на Kotlin</a></li><li><a href="https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov">Senior Junior. Курсы от программистов для программистов</a></li><li><a href="https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov">Менеджер паролей, который не хранит пароли</a></li><li><a href="https://tproger.ru/articles/brauzernaya-mmorpg-konkurs-pet-proektov">Браузерная MMORPG</a></li><li><a href="https://tproger.ru/articles/kak-ya-globalnye-chaty-v-2023-godu-predstavlyal-konkurs-pet-proektov">Как я глобальные чаты в 2023 году представлял</a></li><li><a href="https://tproger.ru/articles/gradcit-ai-fotoredaktor-konkurs-pet-proektov">GradCit: AI фоторедактор</a></li><li><a href="https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov">Бета-версия вычислителя суммы постройки дома с указанием параметров</a></li><li><a href="https://tproger.ru/articles/kak-razrabatyvalos-mobilnoe-prilozhenie-novyj-treker-podpisok-nocta-konkurs-pet-proektov">Как разрабатывался трекер подписок Nocta</a></li><li><a href="https://tproger.ru/articles/testament-powagovaya-takticheskaya-rpg-v-unikalnom-settinge-pro-mifologiyu-v-sci-fi-konkurs-pet-proektov">TESTAMENT: пошаговая RPG про мифологию в sci-fi</a></li></ol><h2>Заключение</h2><p>Подпишитесь на тэг <a href="https://tproger.ru/tag/pet-projects-2023">Лучший пет-проект 2023</a>, чтобы не пропустить голосование и следить за обновлениями в личной ленте.</p><p>Желаем удачи!</p>]]></content:encoded>
    </item>
    <item>
      <title>TESTAMENT: пошаговая RPG про мифологию в sci-fi — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/testament-powagovaya-takticheskaya-rpg-v-unikalnom-settinge-pro-mifologiyu-v-sci-fi-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/testament-powagovaya-takticheskaya-rpg-v-unikalnom-settinge-pro-mifologiyu-v-sci-fi-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Pavel Kurkutov]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/testament-powagovaya-takticheskaya-rpg-v-unikalnom-settinge-pro-mifologiyu-v-sci-fi-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Рассказали о разработке пошаговой тактической RPG-игры TESTAMENT, о сложностях и о том, как они породили более интересные решения.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/testament-powagovaya-takticheskaya-rpg-v-unikalnom-settinge-pro-mifologiyu-v-sci-fi-konkurs-pet-proektov">TESTAMENT: пошаговая RPG про мифологию в sci-fi — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Разработка игр]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 30 Oct 2023 11:15:03 GMT</pubDate>
      <content:encoded><![CDATA[<p>Типичные, доброго времени суток! Меня зовут Павел. Я – автор и программист игры TESTAMENT, которая еще в разработке. Игра делается небольшой командой на энтузиазме. Какие-то работы выполняются наемниками-аутсорсерами. У нас нет больших бюджетов, мощного издателя и богатого опыта в игрострое. Вроде бы это называется независимой разработкой. Пройден уже довольно длинный и тернистый путь, но все приметы говорят о том, что это – только начало приключения. Но обо всем по порядку.</p><p>В этой статье мы поговорим, внезапно, про саму игру. Я расскажу, как зародилась и мутировала идея. О сложностях, которые я встретил и о том, как они породили более интересные решения. И о важности дисциплины, дедлайнов и документировании как в больших корпоративных, так и в мелких пет-проектах. Добро пожаловать под кат.</p><h2>Зарождение идеи</h2><p>С самого детства я мечтал создать собственную игру. Интернет был недоступен, информацию приходилось искать в книгах и обращаться к инженерам. Я начал с TurboPascal и носил с собой 3.5” с компилятором и исходным кодом игр. Кто еще помнит, что такое 3.5”?! Сегодня компьютерные игры стали неотъемлемой частью нашей культуры и имеют огромное влияние на развлекательную индустрию. Они объединяют игроков разных возрастов и культур, позволяют нам погрузиться в виртуальные миры и испытать эмоции, недоступные в реальной жизни. Создание игр – это увлекательное приключение, которое никогда не прекращает меня вдохновлять.</p><p>Несколько лет назад у меня родилась идея создать игру с про различную мифологию в мире sci-fi. Я объединил вокруг проекта небольшую группу энтузиастов-любителей на хобби-основе и мы, полные сил и решимости, начали делать прототип. Моей главной целью было пройти весь путь игростроя – от идеи до продаж на Steam. Но в то же время вроде бы как хобби – нужно отдыхать от основной работы. Поэтому у нас толком не применялись процессы и инструменты промышленной разработки. Сразу после первого прототипа мы поехали на локальную выставку игр. Публика тепло приняла игру про мифологию в sci-fi, но удержать игроков оказалось невозможно. После красивой картинки и прикольной идеи игра казалась не интересной. Первый показ больше демотивировал, вместо того чтобы придать силы. Все работы были остановлены. Мы оказались в классической ситуации инди-команды, которая полагается только на энтузиазм. Все, как по учебнику.</p><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/b5338640-31cd-461f-89ba-3f60256c6625.png" alt="" /><figcaption>Случайная тактическая потасовка в мрачнейшем лесу</figcaption></figure><p>Из своего профессионального опыта я знал несколько ключевых правил проекта, который хочется довести до конца. Первое – это то, что дисциплина важнее мотивации. Потому что когда запал проходит, важно все равно продолжать работу. На тему мотивации и дисциплины на самом деле есть множество выступлений с разных конференций. Я, в свою очередь, крайне рекомендую выдерживать это правило всем профессиональным разработчикам. Второе правило – это планы и сроки. Как-то раз на работе наставник мне сказал довольно умную вещь “Чтобы оценить прогресс движения к целям, нужно составить хороший план. Если план выполнен, значит цели достигнуты.” Тогда я в очередной раз пренебрег этим правилом и в очередной раз убедился в его глубине. Даже для себя и своего домашнего хобби-проекта нужно составлять какой-то набор шагов и приурочивать их к какому-то событию. Иначе вы рискуете сделать ничего к неопределенному времени.</p><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/dff4ed3c-9fa2-4597-ae83-89be4698a2af.png" alt="" /><figcaption>Китайский мудрец кое-что знает про управление проектами</figcaption></figure><p>Сейчас игра полным ходом движется к публичной демке.</p><ul><li>Я собрал и полирую внутреннюю версию игры.</li><li>Было отрисовано просто дикое количество концептов монстров, персонажей, локаций, элементов окружения и прочего. На самом деле тема совмещения культурных атрибутов и sci-fi оказалась не такой простой, как представлялась на старте. Да это самая сложная часть проекта! Если судить по времени и людям, которые в этом поучавствовали. Кстати, спасибо всем, кто помогал и помогает в этом нелегком, но интересном деле.</li><li>У проекта появилось множество страниц в соц.сетях. У нас есть небольшое сообщество, но я им очень горжусь! Конечно, для этого пришлось научиться хоть немного презентовать и продвигать игру. И мы все еще совершаем открытия в области маркетинга, пока этим занимаемся.</li><li>Так же развивается страница в магазине Steam.</li></ul><p>Где-то здесь я уже сам осознаю себя участником приключения по законам драматургии. Небольшая завязка после придумывания идеи. Точка невозврата после сбора команды. Ложная надежда на выставке. Я верю, что дальше будет предрелизная подготовка, как кульминация. И катарсис после первых скачиваний и отзывов. И обязательно завязка, в которой я постараюсь рассказать о результатах.</p><h2>О самой игре</h2><p>TESTAMENT – это пошаговая тактика с элементами RPG про мифологию в мрачном футуристичном будущем. В игре героические воины противостоят монстрам из мифов и сказок разных культур. В сеттинге игры совмещаются аж четыре древних культуры – славянская, китайская, греческая и египетская! Эти культуры казались самыми богатыми на мифы и легенды и интересными для использования в игре. В каждой культуре есть по 3 героя с разными ролями, пяток монстров с уникальным поведением и несколько тематических локаций. Так вполне себе можно попасть в ситуацию, когда славянский ратник в силовой броне, шаолиньский монах с энерго-посохом и темный жрец Анубиса сражаются с мото-кентаврами возле Сциллы и Харибды!</p><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/62035c79-ef4b-4f05-a8aa-7ea46c5a66c2.png" alt="" /><figcaption>Есть множество путей потерять тактическое превосходство</figcaption></figure><p>Весь игровой цикл строится вокруг того, что игрок отправляет группу героев в небольшую кампанию по определенной локации. Чтобы завершить кампанию в локации, героям нужно пройти через набор рандомно сгенерированных событий. Это могут быть не только сражения с монстрами, но и небольшие кризисные ситуации, сюжетные диалоги, точки для отдыха, улучшения героев и обмена ресурсов. После завершения кампании игрок, в качестве награды, получает доступ к новой локации, герою, сюжету или просто уникальный ценный ресурс. Постепенно раскрывая контент, игра приводит игрока к сюжетной кульминации.</p><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/b383684f-92a1-4a19-9689-2336c5b91ca8.png" alt="" /><figcaption>Та самая хваленая раскладка графа в плоскости</figcaption></figure><p>Мы стараемся наслаждаться разработкой игры. А наслаждение делом приходит, когда получается хорошо. Поэтому, например, мы делаем множество концептов монстров, чтобы подобрать наиболее интересные образы, в которых бы читался и сам монстр из мифологии и элементы sci-fi. В коде я поддерживаю чистоту и аккуратность. Некоторые общие части игры я вынес в отдельные Nuget-пакеты с открытым исходным кодом. О части из них я уже рассказывал.</p><p>Это полезная привычка, требующая тренировки, чтобы было проще заниматься кодированием на основной работе. Тем не менее, иногда приходится форсировать разработку, чтобы успеть к какому-то событию вроде очередного шоукейса.</p><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/d6389f5a-b6be-43e6-a08b-9f34a8a668a1.png" alt="" /></figure><p>За новостями проекта можно сделать в соц.сетях. Обязательно подписывайтесь, оставляйте обратную связь и критику. Ваша поддержка и внимание – это пока что основной бюджет проекта. ?</p><ul><li>VK <a href="https://vk.com/testament_rpg">https://vk.com/testament_rpg</a></li><li>Telegram <a href="https://t.me/testament_rpg">https://t.me/testament_rpg</a></li></ul><h2>Вместо заключения немного о пользе пет-проектов</h2><figure><img src="https://media.tproger.ru/user-uploads/82597/2023-10-27/6e5e0519-67eb-4cbe-9591-ccf392c79e6b.png" alt="" /><figcaption>Случайное событие в игре. Герои пробудили жуткие силы!</figcaption></figure><p>В своей работе я постоянно встречаю людей, провожу собеседования и помогаю составлять планы обучения. В IT-индустрии необходимо постоянно развиваться, чтобы оставаться востребованным. Но иногда я слышу от людей: “Зачем что-то делать еще и дома? Старшие все покажут и расскажут.” Я не согласен с таким подходом. Любые домашние проекты позволяют нам узнавать новое, проверять гипотезы и развивать профессиональные навыки. Это – инвестиция в профессиональный рост. Не зря на собеседованиях часто просят ссылки на GitHub.</p><p>Вот лишь небольшой набор полезностей, которые дает вскармливание любого своего проекта:</p><ol><li>Позволяют узнать что-то новое или отточить существующие профессиональные навыки. Банально, попробовать новую платформу или инструменты разработки. Более интересно, попробовать новые компетенции. Например, будучи программистом, поиграть в девопса в CI воего репозитория. Возможно уже сейчас есть какие-то проблемы на работе, но для их решения никто не выделяет ресурсы.</li><li>Обкатать гипотезы. Например, проверить, что 100% покрытие кода тестами – не эффективно и не гарантирует отсутсвие багов.</li><li>Попробовать собрать и замотивировать команду. На работе, когда команда состоит из высокооплачиваемых специалистов, скованных трудовыми договорами и ипотеками, совместно работать сильно проще, чем с энтуастами-новичками, уже уставшими после смены. Все эти преславутые софт-скиллы, которые все пишут у себя в резюме, начинают сиять совершенно иначе.</li><li>Культивируют творческую жилку, всеми искомый креатив и критическое мышление. Что несколько помогает при выгорании на основной работе.</li></ol><p>Всем удачи, гладкого кода и прекрасных команд! Увидимся в игре!</p>]]></content:encoded>
    </item>
    <item>
      <title>Как разрабатывался трекер подписок Nocta — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-razrabatyvalos-mobilnoe-prilozhenie-novyj-treker-podpisok-nocta-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kak-razrabatyvalos-mobilnoe-prilozhenie-novyj-treker-podpisok-nocta-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Inna N]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-razrabatyvalos-mobilnoe-prilozhenie-novyj-treker-podpisok-nocta-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Рассказали о разработке пет-проекта на Android — мобильного трекера подписок Nocta, который уже выложен в Google Play.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-razrabatyvalos-mobilnoe-prilozhenie-novyj-treker-podpisok-nocta-konkurs-pet-proektov">Как разрабатывался трекер подписок Nocta — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Мобильная разработка]]></category>
      <category><![CDATA[Android]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 30 Oct 2023 11:10:01 GMT</pubDate>
      <content:encoded><![CDATA[<p>Nocta Pro – приложение трекер подписок под Android. Много возможностей, уникальные функции, бесплатно и никакой рекламы.</p><p>Добрый день, меня зовут Инна, я андроид-разработчик, хочу написать о своем приложении Nocta Pro. Создание его началось осенью прошлого года, а опубликовано в Google Play оно в конце августа. Возможно, статья получится интересной для тех, кто пишет свой проект или задумывается о нем. Она о том, как проходила разработка.</p><h2>Идея</h2><p>У меня большой опыт в разработке. Больше всего нравилось писать под Android. Но жизнь сложилась так, что в последние полтора года на работе вначале попросили писать под iOS, потом освоился React Native. Но мне захотелось вернуться обратно в Android мир. Вначале отдохнуть от работы, т.к. она в то время была достаточно тяжелой, а потом подкачать свои устаревшие знания. И это лучше всего делать на реальном проекте.</p><p>Мой опыт показывает, что самое главное в приложении — это UI и UX. Будь оно сто раз полезно, но если будет выглядеть коряво, то обречено на провал (потом я подкорректировала это мнение, но об этом позже). И мне очень повезло с тем, что нашелся человек, его зовут Ярослав, он начинающий продуктовый дизайнер, у которого была идея и который уже набросал свою задумку в Figma. Мне оставалось только спросить — не хотел бы он, чтобы его проект был реализован? По ходу рассказа привожу комментарии Ярослава ниже курсивом.</p><h2>Приложение</h2><p>Nocta представляет собой трекер подписок. Сейчас почти у каждого есть какие-то регулярно оплачиваемые подписки. Некоторыми мы пользуемся всего один раз в пробный период (их необходимо вовремя отключить), а некоторые используем постоянно. Также у поставщиков подписок бывают разные тарифные планы (еженедельные, ежемесячные, годовые, да хоть каждые два дня) — их можно прикинуть и сравнить, какой выгоднее использовать и посмотреть сколько ты в результате экономишь, сколько будет заплачено денег всего и по каждой подписке, и можно легко переключаться на другие планы.</p><p><i>Ярослав: </i><i>Идея такого приложения мне пришла в голову еще в далеком 2020 году, однако реализовать его не представлялось возможным из-за нехватки опыта, знаний и ресурсов. Что тогда, что сейчас, все представленные продукты на рынке содержат хотя бы один критический недостаток, который сводит на нет вообще весь смысл пользования таким трекером. Я горжусь Nocta потому, что в этом продукте решены сразу все известные недостатки и проблемы, и, более того, представлен ряд классных и полезных функций, которых вообще нигде нет. </i></p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/f0cb269d-d35c-430d-8a8c-8009bd01ec13.png" alt="" /><figcaption>Nocta Pro – имеет темную и светлую темы</figcaption></figure><p>Некоторые подписки могут быть в другой валюте. Есть Pay Upfront (Предоплата), что означает оплату подписки вперед на несколько циклов.</p><p><i>Ярослав: Pay Upfront – это классная и уникальная фича, которой нет ни в каком другом трекере. Она нужна, чтобы посчитать сколько денег нужно для того, чтобы оплатить подписку вперед на какой-то период. Особенно, когда бывают странные циклы списания – раз в две недели или раз в 30 дней. Ты оплачиваешь эту подписку и последующие уведомления приходят тогда, когда подходит следующая дата списания. Это удобная фича, которой лично я часто пользуюсь.</i></p><h2>Как быстро попробовать приложение в действии</h2><p>Нет ничего проще. Устанавливаете Nocta Pro и добавляете тестовые подписки. Проверить подходит оно или нет — можно за минуту, ничего не нужно делать сложного или разбираться как добавить подписку.</p><p><i>Ярослав: </i><i>Когда я просматривал приложения, которые уже были, то каждый раз после установки я видел пустой экран, и для того, чтобы понять как им пользоваться, мне нужно было создавать подписки со множеством полей (это у нас в Nocte можно заполнить всего два поля – название подписки и ее стоимость). Поэтому пришла в голову идея для тех, кто только что установил приложение и хочет понять, подойдет оно ему или нет. Одним кликом добавляешь тестовые подписки и все – можешь рассматривать приложение со всех сторон. Таким образом, мы сэкономили много времени тем, кому приложение не подойдет.</i></p><p>Подобных интересных вещей в приложении еще много. Все максимально продумано.</p><h2>Реализация</h2><p>Я решила затянуть в приложение все новое, что было на тот момент — конечно же kotlin (до этого все мои больше 20 проектов были на java), современную архитектуру (MVVM), Jetpack Compose, Hilt, Compose Navigation, WorkManager, Glance Widget, Room, SqLite и т.д.</p><p>Начинать было тяжело. Экранов и логики нарисовано еще до начала реализации очень много. И чтобы преодолеть этот барьер — я просто решила попробовать сделать самый первый экран со списком. Это было ошибкой, нужно было рассмотреть все, что есть, и принять обдуманные решения. Потом, когда процесс уже встал на рельсы, я поменяла структуру базы данных, кое-что переделала, доработали requirements — автор идеи написал больше 30 страниц описывающих user flow и всяких расчетов, таблиц и правил, а также несколько таблиц в Excel, которые рассчитывали несколько сценариев с подписками, это очень помогло.</p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/3ef4f0a8-fe63-42ee-ae22-0e90c7b89932.png" alt="" /><figcaption>Дизайн спецификации</figcaption></figure><p><i>Ярослав: Мне пришлось написать документ, который я назвал – дизайн спецификации. Это сложная штука, в нем мне пришлось вводить такой язык – собственные термины и использовать их на протяжении всего документа, в формулах и т.д. Например, ППСГ – потенциально потраченная стоимость за год, которая для каждой подписки считается по своему. И оперируя этим словариком терминов я создавал этот документ, который получился объемным, мне понравилось над ним работать, хотя наверное его можно было бы сделать сильно лучше.</i></p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/aca8269b-1a71-4f29-8c8f-acfbbc1a0a6b.png" alt="" /><figcaption>Расчеты по подпискам</figcaption></figure><p><i>Ярослав: </i><i>Еще пригодился Excel – файл. В нем были примеры подписок и все расчеты. Я его создал еще до реализации для того, чтобы использовать в эскизах экранов, чтобы они выглядели как можно правдоподобнее и были связаны друг с другом общей логикой. Позднее мы проверяли все данные с помощью этих расчетов.</i></p><p>Разработка достаточно сложная вещь, каждый день мы сталкиваемся с какими-то проблемами, которые нужно решать, недостатком знаний, которые нужно восполнять и т. д. У меня специфика работы была такая, что заказчик долго ждать не будет, поэтому если например задача не решается за 2 часа — я переключаюсь на что-то другое (а потом приходит решение) или принимаю решение делать не совсем оптимально, чтобы посмотреть на результат, а уже далее действовать в зависимости от общего мнения. Поэтому в некотором смысле — все приложение получилось таким компромиссом между попытками сделать хорошо и правильно, и продвижением вперед. Когда работаешь один — сложно сделать правильно с первого раза, что-то не получается, или просто пока не знаешь как сделать. Затем, уже спустя время, где-то находишь эти знания и рефакторишь код, исправляешь ошибки — когда это уже очевидно. Если буксовать и все время сомневаться — то весь проект рискует остаться недоделанным. У нас же была цель — Google Play Market — финальная точка, после которой можно выдохнуть.</p><p>Во время реализации дизайн в Figma был переработан, дополнен, уточнен и перепроверен.</p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/610d230b-9499-4c6b-bf4a-45692ec70533.png" alt="" /><figcaption>От варфрейма до итогового экрана</figcaption></figure><h2>Столкновение с реальностью</h2><p><i>Ярослав: </i><i>Как изменилась идея в начале разработки? Я столкнулся с тем, что разработчик пришел и сказал “нельзя”. В первую очередь это было связано с курсом валют. Первоначальная идея была такая, что курс валют приходит автоматически с накидыванием сверху полутора процентов банковских комиссий, потому что актуальный курс списания выше чем курс обменников. И тогда я подумал, что все, приложение не имеет смысла, но мы потом придумали, что можно заносить эти курсы вручную и даже напоминать обновить эти курсы.. и при этом убили двух зайцев – у пользователя всегда будут актуальные курсы валют и мы отказались от сервера. И даже я считаю это наверное плюс нашего приложения,  т.к. если подумать , то автоматический курс валют не отвечал бы потребностям пользователя.</i></p><p><i>Ярослав: </i><i>Еще один момент, который пришлось учесть, это использовать “темные паттерны”, к примеру уведомления, чтобы пользователь их не смахивал, а открывал и использовал приложение, чтоб Google не отозвал разрешение у приложения, нужно туда помещать интригу. Вначале было задумано уведомление “Через 3 дня спишется 100 рублей за подписку ХХХ”, а теперь “Скоро платеж” и чтобы узнать какой платеж пользователь должен нажать на уведомление и перейти в приложение, и таким образом поддерживается активность, в результате которой у нас с меньшей вероятностью отзовут разрешения.</i></p><p>А еще, когда пишешь свой проект, то ты сам себе начальник и неизбежно сталкиваешься с тем, что где-то хочешь упростить реализацию, что-то не делать, т. к. это сложно или долго. Но этот проект имел большую цель — попробовать на практике как можно больше сложных вещей.</p><p>Проект сейчас имеет 24 модуля. Для одного разработчика пет-проекта — это даже много, а когда хочешь попробовать, как оно получится — то вполне нормально для такого размера приложения.</p><h2>UI</h2><p>Приложение в классическом материальном дизайне. Я использовала библиотеку androidx.compose.material3. Для рисования интерфейса – Jetpack Compose. Сам дизайн продуман до мелочей, аккуратные отступы между элементами, паддинги тоже разные для оптической компенсации элементов в списке с точностью до пункта. Нами продумана вся дизайн система, она одинаковая — в Figma и перенесена в один из модулей приложения, легко найти и поправить, легко добавлять и использовать в любом месте. Есть система шрифтов, цветовая схема. Темная и светлая темы. Аккуратные картинки к каждой подписке пользователя. Иконки приложения для Monet в Android.</p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/9f380bb7-4802-4f59-abd3-488cdee15441.png" alt="" /><figcaption>iOS версия приложения</figcaption></figure><p><i>Ярослав: </i><i>В самом начале Nocta планировалась как кейс для iOS и там было основных 20 экранов. Потом пришлось переделывать все экраны с учетом не только дизайна, но и с учетом логики того, как взаимодействуют окна, структура. iOS версия раньше смотрелась как-то прикольно, но теперь она устарела и Android версия выглядит значительно лучше. Кроме того, у меня прибавилось опыта, если я раньше мог пропускать экраны, которые содержат определенный стейт, то сейчас я сразу вижу, что экран должен содержать, какой стейт и как с ним взаимодействовать.</i></p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/bb1cab93-65cf-4d3c-adec-8d8bb9a33deb.png" alt="" /><figcaption>UI kit</figcaption></figure><p><i>Я разработал UI kit, в нем содержатся – цветовая схема (светлая и темная), шрифты, и элементы дизайна, это как будто кирпичи, из которых формируются экраны.</i></p><p><i>Картинки к подпискам я пытался сделать лаконичными, чтобы не приходилось в них копаться, пытаясь выбрать то, что нужно. Я внимательно пролистал список иконок к андроиду в плагине Figma и выбрал те, который наиболее подходят для подписок.</i></p><h2>Функционал</h2><p>Это одна из самых сложных основ приложения. Оно содержит много расчетов с датами, много разных строк, которые обозначают эти даты, периоды. Для того, чтобы правильно их сделать – нам пригодился документ, где была бы описана вся логика, а также тестовые примеры</p><h2>База данных</h2><p>Самая легкая часть. Обожаю базы данных, делать их структуру и особенно — писать запросы. Поэтому у меня очень много что сделано запросами, а не простым вытаскиванием данных из таблицы и последующей обработкой с полным перебором. Sqlite классная быстрая база данных, возможности которой нужно использовать.</p><h2>Уведомления</h2><p>Ни для кого не секрет — Google с каждым выходом новой версии операционной системы ужесточает правила для приложений в плане потребления энергии или безопасности. И получается, что приложения, которыми пользуется владелец устройства — те имеют зеленый свет, а у остальных понемногу отбирают разные полученные ранее права. Наше приложение задумывалось так, чтобы пользователь вложил свое время вначале — заполнил данные по своим подпискам, установил нужные уведомления и в общем-то больше не обращался к приложению, просто получал уведомления о будущих платежах, чтобы оно его не беспокоило лишний раз, не надоедало, не раздражало. Но увы, такие приложения обречены на фактическое сокращение функциональности. Не будешь пользоваться — через месяц (а ведь есть подписки, которые оплачиваются раз в год!) не увидишь уведомления — ОС забирает разрешение и все. Открывать настройки, искать нужный пункт меню и приложение, включать уведомления — только одно перечисление этого уже вызывает раздражение.</p><p>Пришлось изменить текст уведомления. Вначале мы думали выводить текст «Следующий платеж 100 рублей через 2 дня по такой-то подписке». Теперь просто выводится «Следующий платеж через 2 дня». И нужно кликнуть на уведомление и откроется окно с подпиской. Увы, это неизбежная реальность.</p><p>Есть еще второй вид уведомлений – это напоминания пользователю уже в самом приложении. Напоминание сделать бэкап, или напоминание о том, что нужно разрешить системные уведомления.</p><h2>Виджет</h2><p>Еще один вариант решения проблемы с уведомлениями — сделать виджет, который будет показывать список нескольких ближайших платежей на экране. Если пользователь его поставит, то приложение будет периодически работать, пользователю не нужно будет в него даже заходить. Сделать виджет, который одобрит дизайнер, достаточно сложно, а сделать Glance Widget, по которому очень мало информации даже в документации — еще сложнее. Сделать его приемлемого размера на экране — уже задачка со звездочкой, т. к. в определенных версиях действуют одни правила, в более новых — другие и т. д. У нас виджет двух типов. Вначале я сделала более простой вариант — там кнопки быстрого доступа для открытия приложения, создания новой подписки или открытия календаря. А затем виджет с самыми ближайшими подписками.</p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/72b3dc92-1646-4d4a-b348-11aaa1e4ca35.png" alt="" /><figcaption>Работа над дизайном виджетов, у нас их два вида.</figcaption></figure><p>Для виджета пришлось делать свою дизайн систему, т. к. используемый там «jetpack compose», на деле им не является, и пока что там нельзя сделать полноценную дизайн систему, т. к. он находится в разработке. Также там есть ограничения по использованию шрифтов и размеров, управлять ими как в приложении не получится, да и выглядит он в итоге на разных устройствах по-разному.</p><p>Как-то прочла замечание одного разработчика (спасибо ему), что после добавления кнопки установки виджета в самом приложении, его использование значительно возросло. Мы добавили такую же кнопку. Это и напоминает о том, что у нас есть виджет, и значительно облегчает его установку, сравните сами – легко ли найти виджет в длинном списке всех виджетов устройства, а затем искать ему место, или просто нажать на кнопку?</p><h2>Перевод на русский язык</h2><p>Это тоже было достаточно сложной частью. В приложении очень много различных фраз, которые отображаются на экране, обозначающих, например, период времени или количество чего-то («в следующем месяце», «через 2 года», «скоро», «каждый год») и очень много нюансов когда и что отображается. В английском языке все достаточно просто, там нет падежей, фразы строятся однотипно. При переводе на русский я пересмотрела многое, чтобы все правильно отображалось, но уже с целью на будущее, чтобы можно было переводить на другие языки.</p><h2>Бэкапы</h2><p>Как вы уже поняли, сервера у нас нет, поэтому отвечать за сохранность своих знаний должны сами пользователи. Я добавила удобную функциональность по создании бэкапа с данными, и восстановление данных из файла, так же приложение напоминает (как можно более ненавязчиво) что неплохо сделать бэкап. Некоторые операционные системы сами делают бэкап и при установке приложение — данные уже там.</p><h2>Справочная система</h2><p>У нас реализована и продумана справочная система, то есть в местах, где пользователю нужна поддержка в плане “что это такое?” – реализованы небольшие диалоги с подсказками, но есть и экраны, где объясняются фичи и концепции, что и для чего это нужно, как это работает, например, о функции Предоплаты.</p><h2>Публикация в Google Play</h2><p>Это тоже достаточно нетривиальная задача для человека, который давно там ничего не публиковал, т. к. все постоянно меняется. Я вначале решила, что опубликую приложение в Open Testing части. Она по сути ничем не отличается от Production, кроме того, что отзывы приватные, видны только владельцу.</p><p>Очень волнительно было ждать вердикта Google (и сейчас тоже волнительно). Интересный факт в том, что во время проверки приложения, Google также тестирует приложение и публикует его результат. Если находит баг — то предоставляется видео тестирования, при котором произошло падение. И один из интересных багов был найден и исправлен. Также, он проводит глубокий анализ со скриншотами на разных устройствах и широкий анализ приложения на адаптивность к пользователям с особыми потребностями.</p><h2>Реклама</h2><p>Ну а теперь о том, как изменилось мое мнение что важно для приложения. Увы и ах, без вложений в рекламу ничего не получается. Nocta получилась большое и красивое приложение, законченное, которым приятно пользоваться, со мной связалось несколько разработчиков (удалось «прорекламировать» только в чатах по разработке) и мы даже стали друзьями и делимся чем-то полезным.</p><p>Но реальность такова, что денег на это больше нет.</p><figure><img src="https://media.tproger.ru/user-uploads/91432/2023-10-26/af575d6b-897b-47c0-8393-c094f1c4e46a.png" alt="" /></figure><h2>Планы</h2><p><i>Ярослав: Не знаю насчет планов.. внутри приложения всегда можно добавлять, докручивать какие-то интересные фичи, тот же самый max-концепт, разделение на профили, теги, wizards, даже что-то безумное, какие-то сториз “а вы знаете, чтобы сэкономить на подписках, можно применить вот эту тактику”, добавить notification hub, с ним поработать, т.к. они у нас в разных местах возникают, разделить приложение max, basic, pro. Это в сторону фич, в сторону платформы – хотелось бы видеть приложение на iOS.</i></p><p>Вообще в планах у нас были две или три версии приложения. Одна — самая простая, для тех, кому нужна базовая функциональность. Вторая — Pro, платная, которая и была реализована и была выложена бесплатно. Но уже есть планы на дальнейшее развитие, продуманные фичи для добавления. Однако пока не знаю, будет ли продолжение (добавление крупных фич) в связи с тем, что сейчас получать доход от приложения уже сложно.</p><p>Конечно, было бы неплохо иметь сервер, сделать регистрацию пользователей и синхронизацию их данных, или, к примеру, автоматические курсы валют. Но освоение мною этих вещей это too much.</p><p>Небольшие доработки и добавления, изменения, конечно же будут. Сейчас, когда исправлены основные баги, я занята поиском новой работы.</p><p>Надеюсь, наше приложение понравится тем, кто любит такое ? Пожалуйста, пользуйтесь, присылайте нам свои пожелания, оставляйте оценки в Google Play Store, передайте ссылку своим друзьям, если знаете, что оно им понравится, мы благодарны вам за это.</p><ol><li><a href="https://play.google.com/store/apps/details?id=com.cordylussoftware.nocta">Ссылка на Google Play Store</a>;</li><li>Связаться с нами можно в <a href="https://t.me/noctatracker">телеграм</a>;</li><li>Мой <a href="https://www.linkedin.com/in/inna-n-775457a2/">профиль </a>и резюме.</li></ol>]]></content:encoded>
    </item>
    <item>
      <title>Бета-версия вычислителя суммы постройки дома с указанием параметров — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Denis Markin]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>В 11 лет написал бета-версию приложения для строителей.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/beta-versiya-vychesleniya-summy-postrojki-doma-s-ukazaniem-porametrov-konkurs-pet-proektov">Бета-версия вычислителя суммы постройки дома с указанием параметров — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Sun, 29 Oct 2023 17:26:30 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет всем! Мне 11 лет, меня зовут Денис. С 9 лет я увлекаюсь созданием игр, но это не игра, а бета-версия приложения. Как подросту, зная C#, я переделаю эту программу уже с интерфейсом.</p><p>Этот проект я начал вчера, а на идею меня подтолкнуло то, что можно упростить работу кровельщикам и строителям с помощью этой программы. В дальнейшем я буду добавлять еще больше параметров. Также будет производиться подсчет всей стоимости в зависимости от параметров.</p><p>Кратко говоря, здесь есть два выбора в начале: эконом и премиум классы домов, и в зависимости от выборов появляются соответствующие вопросы. Пожалуйста, оставляйте свои комментарии и лайки под постом.</p><p>Ссылка на реплит проект:</p><p>https:\/\/replit.com\/@DenisMarkin\/piet-proiekt#main.py</p><p>Сам проект (●’◡’●)</p><figure><img src="https://media.tproger.ru/user-uploads/91886/2023-10-27/8090c009-4025-48fd-8887-608a106eeebd.jpeg" alt="" /></figure><figure><img src="https://media.tproger.ru/user-uploads/91886/2023-10-27/4ec1934a-3934-460f-ad00-2b76e52e8e97.jpeg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>GradCit: AI фоторедактор — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/gradcit-ai-fotoredaktor-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/gradcit-ai-fotoredaktor-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Виталий Монастырев]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/gradcit-ai-fotoredaktor-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Сделал свой фоторедактор с AI — для разных платформ.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/gradcit-ai-fotoredaktor-konkurs-pet-proektov">GradCit: AI фоторедактор — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Мобильная разработка]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Приложение]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Sun, 29 Oct 2023 14:22:30 GMT</pubDate>
      <content:encoded><![CDATA[<p>Всем привет!</p><p>Меня зовут Виталий Монастырев и в статье расскажу о процессе разработки AI фоторедактора <a href="https://gradcit.com/">GradCit</a>, который умеет дорисовывать фон, позволяет редактировать черты лица, может создавать стикеры, заменять небо на фото и многое другое.</p><h2>Идея проекта</h2><p>Я достаточно давно занимаюсь программированием и мне хотелось попробовать свои силы в разработке собственного продукта. Считаю это достаточно полезным занятием, так как в процессе приходится развивать не только навыки разработки, но и маркетинга для продвижения приложения, планирования при принятии решений о добавлении нового функционала, тестирования и так далее.</p><p>Мне всегда нравилось делать фотографии на смартфон и я задумался, что можно попробовать сделать свой фоторедактор. С одной стороны, фоторедакторов в магазинах приложений сейчас и так много, но с другой — идея создания простого фоторедактора не выглядит суперсложной и кажется вполне реализуемой. Кроме того, можно для начала добавить какие-нибудь базовые фильтры для MVP-версии и далее наращивать функционал.</p><h2>Базовая архитектура</h2><p>Итак, с тематикой приложения определились. Теперь самое время подумать, что мы хотим в него добавить и какие компоненты нам нужны. Как я упомянул выше, для совсем базового функционала достаточно сделать обычные фильтры, которые можно накладывать на изображение. Однако, если мы хотим добавить приложению фишки, которые бы выделяли его на фоне конкурентов, то усилий потребуется чуть больше.</p><p>Сейчас очень активно развивается направление машинного обучения, с его помощью можно редактировать фотографии намного проще, чем раньше. Например, мы можем определять при помощи ML-алгоритмов различные элементы на фото автоматически и затем применять алгоритмы обработки. Но здесь стоит оговориться, что некоторые ML-алгоритмы достаточно ресурсозатратны и их не запустить на большинстве смартфонов. Для этих целей может потребоваться обработчик на стороне сервера, поэтому стоит предусмотреть этот момент в нашей архитектуре.</p><p>Следующий момент, который показался мне важным, это возможность делиться фотографиями. Безусловно, у нас есть различные мессенджеры и социальные сети, где мы можем публиковать свои фото, сторизы и прочее, но возможность публикации фотографий можно использовать в дальнейшем, чтобы проводить на основе приложения различные интерактивные конкурсы с аудиторией. Кроме того, мы получаем собственную независимую платформу, что в современном изменчивом мире является совсем не лишним.</p><p>Базовая архитектура в моем случае выглядит следующим образом:</p><p>Пройдемся по компонентам:</p><ul><li><b>Client</b> — приложение, которое запускается на устройстве пользователя. В моем случае в качестве клиентов выступают приложения для iOS, iPadOS и macOS. Первая версия создавалась исключительно под iPhone и использовался язык Swift. Предвижу вопрос, почему не использовались языки для кросс-разработки, чтобы писать одно приложение под iOS и Android. Меня всегда смущала производительность таких приложений и возможность использования новейших инструментов. Также на выбор в пользу нативного языка повлияло и наличие различных инструкций и туториалов.</li><li><b>Backend server —</b> набор API, который отвечает за общение с клиентским приложением. Включает в себя методы аутентификации, работы с базами данных и ML server’ом. Backend server реализован на Spring.</li><li><b>ML server</b> — включает в себя ресурсоемкие ML-расчеты, которые невозможно провести на устройстве пользователя. Так как большинство ML-алгоритмов работают на Python, то сервер был реализован на Flask.</li><li><b>Kafka</b> — была использована, чтобы отгружать в нее информацию об уведомлениях, которые необходимо выслать на устройства пользователей. Это могут быть уведомления о том, что кто-то оценил фотографию, подписался на профиль, оценил фотографию и другое.</li><li><b>Notification server</b> — занимается отправкой уведомлений на устройства. Данные об уведомлениях забираются из топика Kafka. Реализован также на Spring.</li><li><b>Redis</b> — хранит кэшированную информацию о недавних запросах в оперативной памяти. Это позволяет быстрее возвращать ответ клиенту.</li><li><b>MySQL</b> — выступает в роли основной базы данных для хранения информации. Скорее всего в дальнейшем придется переезжать на что-то другое, но пока она справляется.</li></ul><h2>Интерфейс</h2><p>Первая версия приложения разрабатывалась исключительно под iPhone, поэтому интерфейс был не заточен под перевороты и масштабирование экрана. В связи с этим на оптимизацию под iPad и Mac ушло несколько месяцев. Необходимо было предусмотреть повороты экрана, режим Split View, а также другие пропорции экрана.</p><p>Пользователю на главном экране доступны следующие вкладки:</p><ul><li><b>Камера.</b> Позволяет сделать или выбрать фото из галереи и перейти к его редактированию.</li></ul><ul><li><b>Карта.</b> Выложенные фото при желании можно отметить на карте мира, которая является общей для всех пользователей приложения. Более того, для таких фотографий становится доступен режим AR. Если его выбрать, то на экране в режиме навигатора появляется расстояние и направление до места съемки.</li></ul><ul><li><b>Лента.</b> Доступны вкладки «Новое», «Топ» и «Подписки». Во вкладке «Новое» отображаются последние публикации, которые набрали минимальный рейтинг; в «Топе= отображаются недавние публикации с сортировкой по рейтингу; в «Подписках» соответственно подписки.</li></ul><ul><li><b>Поиск.</b> Позволяет находить пользователей, либо записи по хэштегу.</li></ul><ul><li><b>Профиль.</b> Здесь отображаются опубликованные фотографии, отметки на карте и опубликованные текстовые записи.</li></ul><p>Добавлю небольшой комментарий относительно одной из основных проблем, с которыми я столкнулся при проектировании интерфейса. В моем случае пользователь может переходить бесконечное количество раз из одного ViewController в другой. Например: со вкладки ленты перейти на страницу записи, затем со страницы записи на страницу профиля, оттуда на страницу подписок, оттуда снова в профиль и так далее.</p><p>Каждый ViewController потребляет определенное количество оперативной памяти и если не заняться этим вопросом, то через N-количество итераций приложение вылетет с ошибкой по памяти. Для решения данной проблемы я реализовал инструмент кэширования страниц. При переходе со страницы на страницу сохраняется информация о последовательности переходов и о вкладках, закрытая вкладка удаляется из стека контроллеров. Отображаемая информация сохраняется в кэш. Размер кэша в оперативной памяти ограничен, поэтому информация также сохраняется в постоянную память устройства. Для того чтобы работали свайпы переходов (когда мы пальцем тянем от края экрана слева направо, чтобы открыть предыдущую страницу), при открытии новой страницы формируется предыдущая.</p><p>Реализованный механизм решает проблему утечки памяти, при бесконечном переходе по вкладкам. Возможно, есть способы, как это можно реализовать по другому и более просто, но я не нашел ничего похожего. Если кто-то сталкивался с подобными трудностями, то буду рад узнать как вы решали проблему в комментариях.</p><h2>Возможности редактора</h2><p>В редакторе доступно множество самых разных инструментов. При их интеграции стояла задача того, как совместить их работу между собой. Для этого используется своеобразная логика стека, где каждый эффект применяется последовательно к изначальному фото. Расскажу подробнее про функционал, который доступен в редакторе.</p><ul><li><b>ИИ маска.</b> Позволяет отметить область на экране и задать prompt для замены фона. Дорисовка происходит на стороне сервера, так как требуется достаточно большое количество вычислительных ресурсов.</li></ul><ul><li><b>Маска.</b> Позволяет удалить лишний объект с фото. Для маски доступна возможность запуска модели прямо на смартфоне (при помощи Core ML), но при этом страдает качество изображения, поэтому пока модель работает также на сервере.</li></ul><ul><li><b>Редактор лица.</b> В данном режиме приложение распознает лица на фото и определяет отдельные элементы: глаза, губы, нос, рот и прочее. Далее происходит обработка с определенными элементами. Это может быть как добавление искажения поверх изображения, так и наложение фильтра.</li></ul><ul><li><b>Замена неба.</b> Инструмент определяет небо на фотографии и позволяет заменить его на выбранное изображение. Для большей реалистичности на фото накладывается дополнительный фильтр.</li></ul><ul><li><b>Стикеры.</b> В приложении доступны как стикеры по умолчанию, так поддерживается и добавление собственных стикеров. Добавить свой стикер можно через меню, либо нативно, перетащив его из фотогалереи.</li></ul><figure><img src="https://media.tproger.ru/user-uploads/91428/2023-10-20/41474ca7-7ec9-4b0e-a046-d117fbe41134.png" alt="" /></figure><ul><li><b>Замена фона.</b> Модель машинного обучения автоматически определяет основной объект на фото и заменяет фон на выбранный.</li></ul><ul><li><b>А также!</b> Инструменты рисования, множество самых разных фильтров, HLS-настройка, рамки и многое другое.</li></ul><figure><img src="https://media.tproger.ru/user-uploads/91428/2023-10-19/d8624ec8-e4d2-4c07-b714-97213e4b1bb3.png" alt="" /></figure><h2>Заключение</h2><p>В статье я постарался описать общую архитектуру приложения, а также поделился самыми интересными возможностями редактора на живых примерах. На данный момент я продолжаю развитие приложение и постоянно добавляю новый функционал. Если у вас возникли какие-либо вопросы, либо пожелания, то я с радостью отвечу на них в комментариях.</p><p>Скачать приложение можно вот тут для iPhone и Mac:</p><p>А вот тут для iPad:</p>]]></content:encoded>
    </item>
    <item>
      <title>Как я глобальные чаты в 2023 году представлял — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-globalnye-chaty-v-2023-godu-predstavlyal-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kak-ya-globalnye-chaty-v-2023-godu-predstavlyal-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Egor Yolkin]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-globalnye-chaty-v-2023-godu-predstavlyal-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Написал небольшой и простой глобальный чат, вдохновившись стратежкой Clash of clans.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-globalnye-chaty-v-2023-godu-predstavlyal-konkurs-pet-proektov">Как я глобальные чаты в 2023 году представлял — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Приложение]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 27 Oct 2023 15:20:07 GMT</pubDate>
      <content:encoded><![CDATA[<p><b>Egor Yolkin, Python backend разработчик, 19 годиков</b></p><p>Сайтик создателя:</p><p>GitHub проекта:</p><h2>Предисловие</h2><p>Однажды, размышляя над тем, насколько изменились чаты за последние несколько лет, я внезапно вспомнил давным давно забытую стратежку — Clash of clans.</p><p>И вспомнилось мне то забытое временем чувство, когда трава была зеленее, чай чернее, а глобальный чат в данной игре ещё существовал и радовал игроков своим присутствием. Сколько ночей у меня проходило там — не сосчитать. Впрочем, это и не нужно.</p><p>Так и родилась в недрах моих нейронных связей мысь о том, что глобальные чаты в массе своей представляли крайне интересную концепцию: все ко всем. Многим (мне, порой, тоже) они приносили новые знакомства. Каждый мог извлечь какую-либо пользу для себя в подобном интерфейсе, или с радостью провести пару десятков минут за обсуждением ныне злободневного за чашечкой чая тыкая буковки.</p><p>И подумал я, а не поискать ли мне спустя стольких лет скитаний аналог подобных чатов? Да, следовало бы. И я начал поиски, но успехом они не увенчались. Не было того самого лампового чатика, где каждый мог бы найти себе собеседника по душе.</p><p>В тот самый момент я понял, что мне следует взять ситуацию под свой контроль и подарить этому миру нечто, пусть и не столь полезное, но дающее те самые забытые чувства после нескольких часов общения с абсолютно незнакомыми людьми.</p><p>Так и появился он…</p><h2>World ⚡️ Connect</h2><p>Я начал свой путь с изучения вопроса: а что вообще требуется от подобной категории цифровых продуктов?</p><p>Пришёл к выводу, что лучшей идеей будет чат с максимально простой регистрацией (банально — имя и пароль), разделением чатов на категории (далее — топики) и красивым дизайном.</p><h2>Время бэкенда!</h2><figure><img src="https://media.tproger.ru/user-uploads/91607/2023-10-21/51aaf3bc-8998-444b-9e04-021b6518feb2.png" alt="" /></figure><p>Подумал я и приступил к выбору инструментов для разработки. По душе мне пришёлся FastAPI. На нём и ехала конструкция моя. Реализовал простенькое API, которое позволяло:</p><ol><li>Производить регистрацию и авторизацию пользователей без кучи полей информации.</li><li>Отправлять сообщения.</li><li>Создавать топики и редактировать их.</li><li>Получать информацию о топиках (общее количество сообщений и несколько сотен последних сообщений с возможностью пагинации).</li><li>Использовать WebSocket’ы для реализации чат.</li></ol><p>Итог: имеем красивое RESTful API на FastAPI и WebSockets. Поспешаем не торопясь.</p><h2>Момент фронтенд-части</h2><p>Поразмыслило моё десятое «Я» и сделало шаг в сторону использования Bootstrap. В веб-дезигнах ваших я не силён, а много эстетических рыбов от проекта получить всегда рад. Также роль сыграла скорость возведения великой китайской стены №2 в виде моего чата.</p><p>Итог: имеем минималистичную вёрстку с использованием Вootstrap. Доволен как слон.</p><h3>— Так мало?</h3><p>Возмутиться кто-то.</p><p>— Да</p><p>Отвечу я.</p><p>Задумка была именно в простоте. Имея для примера глобальный чат Clash of clans, я принял решение, что моё веб-приложение не должно содержать много сотен фишек и прочего. Скажем так, это моя философия ?</p><h2>А что в итоге то?</h2><p>В итоге имею личный прекрасный пет-проект для себя и моих девяти личностей. Будем вместе общаться ? В процессе реализации проекта я проникся ностальгией о прошлом. Глобальные чаты прекрасны, а мой — так вообще (шутка юмора, конечно же).</p><p>Хочу сказать спасибо Tproger за то, что дали мотивацию написать эту статью, а также за действительно удобный редактор статей.</p><p>Всем добра (⁠◕⁠ᴗ⁠◕⁠✿⁠)</p>]]></content:encoded>
    </item>
    <item>
      <title>Браузерная MMORPG — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/brauzernaya-mmorpg-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/brauzernaya-mmorpg-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Андрей Масленников]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/brauzernaya-mmorpg-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Много лет любил игры. Захотелось сделать что-то своими руками — и получился код браузерной MMORPG.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/brauzernaya-mmorpg-konkurs-pet-proektov">Браузерная MMORPG — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Разработка игр]]></category>
      <category><![CDATA[Golang]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 27 Oct 2023 13:33:34 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет, меня зовут Андрей и я занимаюсь разработкой уже около 16 лет (если то, что я разрабатывал в 15, можно назвать разработкой).</p><p>Всё это время, меня так или иначе тянуло в геймдев, но основная работа и проекты были связаны с веб-разработкой. Мою историю в игровых проектах можно описать следующим образом:</p><ul><li>Я играю в игры. Кто-то с ностальгией вспомнит как он играл в <a href="https://ru.wikipedia.org/wiki/Heroes_of_Might_and_Magic_III">HoMM 3</a> или <a href="https://ru.wikipedia.org/wiki/Need_for_Speed:_Most_Wanted">NFS</a>, у меня же в памяти останутся преимущественно онлайн игры, от браузерных (<a href="https://ru.wikipedia.org/wiki/%D0%A2%D0%B5%D1%80%D1%80%D0%B8%D1%82%D0%BE%D1%80%D0%B8%D1%8F_(%D0%B8%D0%B3%D1%80%D0%B0)">Территория</a>, <a href="https://ru.wikipedia.org/wiki/%D0%91%D0%BE%D0%B9%D1%86%D0%BE%D0%B2%D1%81%D0%BA%D0%B8%D0%B9_%D0%BA%D0%BB%D1%83%D0%B1_(%D0%B8%D0%B3%D1%80%D0%B0)">Бойцовский клуб</a>), до реальных MMORPG (типа <a href="https://ru.wikipedia.org/wiki/Lineage_II">LA2</a> и <a href="https://ru.wikipedia.org/wiki/World_of_Warcraft">WoW</a>)</li><li>Я хочу сам написать игру. На дворе ~2007, я в восторге от браузерок, дядя показал мне что можно делать с PHP (но забыл рассказать про базы данных), и первая попытка сделать что-то своё закончилась на окне персонажа, где я через простой if переключал предметы на разных персонажах и думал, что всё так и работает. Совет себе из будущего:</li></ul><blockquote>Сохраняй всё что пишешь, потом можно поржать над тем, что делал давно</blockquote><p>Думаю неудивительно, что здесь ничего не вышло.</p><ul><li>Я пытаюсь запустить готовую игру и доработать её. На 2 или 3 курсе института я начал усиленно гуглить и искать готовые игры (ну хотелось ведь что-то запустить и развивать, а на чисто своё не хватало энтузиазма). В это время мы с друзьями играли в <a href="https://ru.wikipedia.org/wiki/OGame">OGame</a> (браузерная игра), и мне удалось откопать движок XNova (не могу найти ссылку на него сейчас), который по сути был клоном OGame. Было решено запустить его самостоятельно, и поуправлять проектом. По итогу на протяжении пары месяцев был онлайн порядка 5–10 человек, потом игру взломали, и на этом всё кончилось =)</li><li>Читаю об играх, изучаю опенсорс-движки. С работой времени на развлечения стало гораздо меньше, но мечты об игровом проекте никуда не ушли, нашёл утешение в чтении исходников открытых проектов. Наверное, основным, откуда я многое подчерпнул, в том числе для текущего проекта, является <a href="https://github.com/cmangos">CMangos</a> — опенсорс-сервер для WoW. Хотелось бы ещё иметь открытый клиент, но, думаю, мечтам не суждено будет сбыться.</li><li>Довёл игровой пет-проект до состояния, когда им можно поделиться. Сперва хотелось сделать что-нибудь в режиме реального в 3D, но, потыкавшись по разным сторонам, понял, что для освоения всех тонкостей нужно потратить очень много времени, и лучше взять то, с чем в последнее время много работал.</li></ul><h2>Как начиналось?</h2><p>Идея возникла на стыке моего игрового опыта и опыта веб-разработчика. Захотелось сделать что-то своими руками (наконец-то), а поскольку руки приспособлены только под клавиатуру — получился код. Но точно могу сказать, что формат браузерной MMORPG появился после мытарств с C/C++ и 3D (брать Unreal Engine, Unity или любой другой готовый движок не хотелось, причина банальная — хотелось по максимум своё), когда я понял, что туда надо всаживать гораздо больше времени, чем есть, и, может быть, через год-другой что-то и получится. То, что буду делать именно онлайн-игру, также было ясно с самого начала, так как под большим впечатлением от времени, проведённого в онлайн-играх, казалось, что только такие игры и должны быть.</p><p>Из того, что сделать в вебе, было несколько идей: от симулятора кота, который терроризирует хозяина (но показалось что тут лучше всё же single в 3D сделать), до переосмысления вышеупомянутой OGame, но потыкавшись по текущим браузерным MMORPG, показалось, что можно попытаться привнести что-то новое (к тому же их несколько и проще было бы найти интересные механики и референсы).</p><p>Стоит также сказать, что попыток начать в разные этапы жизни было несколько, но до чего-то большего добрался только один. Я считаю, что мне помогло правильное распределение приоритетов и точек интереса в разработке, так как все прошлые проекты начинались с самого интересного — геймплея или реализации основной идеи, а когда время доходило до того, что надо делать всю обвязку (регистрация, авторизация, сессии и прочее), энтузиазма уже не было и доделывать не хотелось. На этот раз я начал со скучного, и когда запас энтузиазма начал иссякать, переключился на геймплейные механики, что позволило вполне себе успешно поработать над проектом около полугода.</p><p>Кажется, что основные механики браузерных MMORPG особо не меняются, расскажу об их части, а также подробно остановлюсь на боевой системе, которая, на мой взгляд, получилась достаточно интересной.</p><h2>Базовые механики</h2><h3>Перемещение персонажа</h3><p>Наверное, первая механика, которую я реализовал. Строится она на том, что мир состоит из локаций, которые могут быть связаны с другими локациями. Выбираешь одну локацию для перехода и попадаешь в неё. Мне сразу же захотелось сделать функционал ограничения на вход в локацию (например, чтобы новые игроки не убегали в локации высокого уровня), и я реализовал это с помощью механизма ограничений, который позволяет создавать набор правил для игрового объекта, которые проверяются при попытке взаимодействия с этим объектом.</p><p>Для обкатки данного механизма, я реализовал простейшее ограничение — запрет перехода в определённую локацию персонажам ниже пятого уровня.</p><p>Теперь, всё что нужно сделать для проверки каких-либо ограничений (будь то переход в локацию, доступность квеста или выпадение определённого предметов с бота), нужно вставить новую запись в базу данных, и, если раньше определённой проверки не существовало, описать в коде то, как она должна происходить.</p><p>Пример кода, отвечающего за проверку состояния квеста.</p><h3>Характеристики и предметы</h3><p>В любой MMORPG важен прогресс твоего персонажа, как за счёт прокачки уровней, так и за счёт добычи новых предметов, которые можно на себя надеть. Кажется, что весь баланс, в первую очередь, отстраивается от характеристик, которые персонаж получает при прокачке, и от характеристик на предметах, и именно эти две вещи у меня реализованы.</p><p>Характеристики есть базовые, которые выдаются при регистрации, бонусные, которые вырастают в связи с ростом уровня, и характеристики на предметах, которые применяются к персонажам при использовании найденных предметов (наверное, сюда можно также добавить характеристики от усилений, но этот функционал пока не реализован).</p><p>Как и система ограничений, система выдачи бонусов (например, за повышение уровня), одна из основных в игре. Она работает по схожему с ограничениями принципу, в рамках которого мы указываем тип бонуса (например, выдача характеристики), а также значения (код и значение характеристики).</p><h3>Квесты</h3><p>Наверное, один из самых сложных функционалов после боёвки, так как необходимо учитывать множество ограничений (квест два нельзя взять раньше квеста один), цепочки диалогов (для лучшего погружения в историю), награды, проверку выполнения квеста и кучу всего ещё.</p><p>Нетрудно догадаться, что многие вещи, связанные с квестами, будут тесно переплетаться с общей системой бонусов и ограничений. Для примера можно рассмотреть простой квест, в рамках которого нам необходимо выбить десять предметов с ботом и затем сдать их, получив в награду какую-нибудь вещь. Для реализации данного квеста нам потребуется:</p><ol><li>Набор фраз для NPC (для получения квеста, для завершения квеста, для промежуточного состояния квеста). Все их нужно перелинковать между собой и разработать систему, которая будет подставлять определённые реплики в разные моменты времени.</li><li>Бонус на выпадение квестовых предметов, с ограничением на них: квест должен быть взят, а предметов в инвентаре должно быть меньше десяти (зачем нам выбивать и плодить больше предметов, чем нужно).</li><li>Ограничение на сдачу квеста (должно быть десят квестовых предметов в инвентаре).</li><li>Бонус за сдачу квеста.</li></ol><p>А если квест подразумевает большое количество таких связей и условий, то это большая и кропотливая работа.</p><h3>И всё остальное</h3><p>Если описывать все остальные реализованные возможности игры так же полно, как и предыдущие 3, то будет слишком много текста. Поэтому небольшой список того, что ещё есть:</p><p>1. Чат (с сообщениями от пользователей и системными, о разных событиях)</p><p>2. Аукцион (с возможность покупки и продажи предметов)</p><p>3. Почта (на которую приходят покупки и деньги после завершения сделки на аукционе)</p><p>4. Группы (с автоматическим или ручным распределением лута)</p><p>5. Подземелья (в которые можно войти только группой с нападением монстров на каждом переходе и босом в конце)</p><p>6. События (поэтапные, с появлением новых монстров или добычей специальных предметов и наградами за это)</p><p>7. Профессии (добывающие и крафтовые, их можно прокачивать, изучать новые рецепты)</p><p>Ну и конечно же, боевая система, которую мне хотелось бы описать наиболее подробно</p><h2>Боевая система</h2><p>То, чего хотелось достичь в боевой системе — это некое приближение к привычной мне системе из WoW, а именно: таргетная система боя, использование заклинаний со временем восстановления и позиционирование для избегания различных атак. В первую очередь, я решил посмотреть на реализацию боевых систем в существующих браузерках. По большей части, все они сводились к тому, что система выбирает тебе противника и ты с ним сражаешься. Иногда можно было выбрать цель для специальной способности среди всех противников или союзников. В одной из игр даже была возможность позиционирования, но всё было не тем, чего бы мне хотелось.</p><p>В итог, сперва я попробовал сделать 2D-поле, состоящее из квадратов. Вдоволь наигравшись с ним, я понял что визуально мне не очень нравится. После долгих размышлений я вспомнил ещё одну игру, где поле было реализовано с помощью шестиугольников. Реализовал, понравилось, на том и решил остановиться. В кратчайшие сроки я нашёл реализацию поля с шестиугольниками на ThreeJS в 3D, а также очень крутую статью с описанием математики работы с такими полями.</p><p>На базе всего вышесказанного удалось создать с помощью <a href="https://threejs.org/">ThreeJS</a> и 3D-поле, и добавить на него объекты персонажа и ботов и реализовать управление.</p><p>После реализации передвижения пришлось заняться навыками и их реализацией. На данный момент готово по пять навыков для каждого из трёх классов в игре, которые могут наносить урон не только по цели, но и по области. Или на линии движения, снижать или увеличивать наносимый урон, оглушать врагов (пока писал понял, что, скорее всего, действие, растянутое по ходам, не прервётся оглушением), исцелять и вешать дебафы, наносящие периодический урон.</p><p>Самыми интересными в реализации оказались навыки, которые добавляют новые возможности в интерфейс, например, навык рывка, который давал возможность выбора позиции, в которую перенесётся игрок после использования навыка, а все цели на его пути получат урон и, с небольшой вероятностью могут быть оглушены.</p><p>Код навыков выглядит всегда примерно одинаково (за исключением случаев, когда он не укладывается в существующие реалии), например код навыка «Рывок» представлен ниже.</p><p>В целом практически все действия и эффекты сделаны по схожему принципу: выбираем тех, кого должен затронуть эффект, добавляем его в ответ для движка, который применит данные эффекты на нужные цели, проведя дополнительные валидации. Как нетрудно догадаться, можно было бы применить эффект AddMovement для вражеских задетых персонажей и разбросать их по полю.</p><p>Немаловажной частью боевой системы является спавн на поле негативных зон, стоя в которых, игрок либо сразу получит урон, либо через какое-то время. Сделано это путём расширения системы эффектов, в рамках которой можно добавить на поле проходимый объект со своей функцией отсчёта до нанесения урона.</p><p>Любая такая зона может совершать все те же действия, что и бот или персонаж. Она может просканировать поле боя и заспавнить новые зоны, или применить оглушение к стоящему на ней игроку. Путём смены логики, можно наносить урон всем игрокам в определённом радиусе, если на самой зоне никто не стоит.</p><p>Ещё одной составляющей боевой системы является, как не трудно догадаться, AI-боты. И в данном случае они просто заскриптован. Для каждого бота вызывается метод DoTurn, который так или иначе вызывает какой-нибудь из навыков и порождает применение эффектов.</p><p>Базовый AI позволяет просто преследовать ближайшего игрока, и если радиус навыка позволяет, ударить персонажа этой способностью.</p><p>Данный AI нужен для самых простых ботов, что бы не разрабатывать AI под каждого, но если речь идёт о сложных механиках, тут не обойтись без описания конкретных взаимодействий. Например, у меня есть реализованное подземелье, в рамках которого есть босс-дракон, он умеет использовать разные способности в зависимости от общего таймера боя (на третьем ходу запустить определённое заклинание) или бот-призыватель, который использует предмет для призывы помощников, в случае если его здоровье опустилось ниже 50%.</p><p>Функционал использования предметов, как для игрока, так и для ботов, позволяет разнообразить бой, добавив туда возможность исцеляться или призывать себе кого-нибудь на помощь. Количество таких предметов ограничено на один бой, но есть идеи, например, для каких-нибудь затяжных боёв, что один слот может занимать предмет, пополняющий карманы новыми эликсирами =)</p><p>Помимо всего прочего для боевой системы важен баланс, в рамках которого действуют все модификаторы и мультипликаторы. Я прорабатывал его в таблицах, в рамках которых ориентировался на то, за какое количество ударов я смогу победить игрока, монстра или босса того же уровня, при этом каждые уровни балансировались под определённые типы сетов, которые давали больше характеристик.</p><p>Далее формулы, которыми я считал силу удара, я перенёс в код и потестировал на ботах — в среднем всё сошлось.</p><h2>Технологический стек</h2><p>В качестве бэкэнда используется <a href="https://go.dev/">Golang</a>, так как последние несколько лет я пишу именно на нём, а сервисы спроектированы на базе чистой архитектуры, которую мы применяем в компании, в которой я работаю.</p><p>В качестве базы данных взял <a href="https://www.mysql.com/">MySQL</a>, так как давно не с ней не работал (а опыта на Go с ней вообще не было). Это привело к страшным последствия в аукционе, когда мне пришлось составлять фильтрационные запросы в зависимости от наличия в фильтре тех или иных параметров.</p><p>Выглядит стрёмно, и, да, я понимаю что здесь можно было бы применить ORM или просто Query Builder, но, когда я писал эту часть, мне лень было заморачиваться с поиском соответствующих библиотек.</p><p>Для управления базой данных я использовал PHPMyAdmin, вспомнил былые времена, когда в базу данных ходил только через неё.</p><p>Одной из основных вещей, которые мне хотелось попробовать при реализации данного проекта, это <a href="https://grpc.io/">GRPC</a>, поэтому всё общение (и между микросервисами, и запросы с фронта) происходит через этот протокол. Главным разочарованием для меня стало то, что пакет <a href="https://github.com/grpc/grpc-web">grpc-web</a> не поддерживает stream’ы, хотя казалось бы, можно это обернуть через веб-сокеты, поэтому пришлось делать свой сервис, который занимался проксированием таких запросов. Мне также не очень нравится, как у меня организовано хранение и распространение артефактов от .proto-файлов, но что с этим делать я пока не знаю.</p><p>Выбор для фронта был не очень велик, я неплохо знаю <a href="https://vuejs.org/">Vue</a>, а моё общение с <a href="https://react.dev/">React</a> не задалось ещё очень давно (когда я не смог развернуть его без create-react-app). Поэтому я выбрал React, в конце концов, все мои пет-проекты так или иначе связаны с познанием чего-то нового. Написание React-приложения с помощью хуков мне зашло куда больше, чем старые классовые компоненты. Я использовал библиотеку <a href="https://mui.com/">MUI</a> для основной части интерфейса, и написанные самостоятельно компоненты для того, чего нет в библиотеке.</p><p>Самое интересное в этой части кода связано с потребностью сделать всплывающие подсказки к предметам. Мне не хотелось запрашивать данные каждый раз при наведении, и знающие люди подсказали, что для локального кеширования можно использовать <a href="https://react.dev/reference/react/useContext">useContext</a>.</p><p>Всё окружение (включая наполнение БД первичными данными), сейчас поднимается с использованием <a href="https://docs.docker.com/compose/">docker-compose</a>, в котором нет чего бы то ни было интересного.</p><h2>Статус проекта</h2><p>На данный момент проект находится в вялотекущей стадии поиска дополнительной мотивации. То что я хотел получить от проекта первоначально (играбельный прототип, изучение новых технологий), я уже получил, но, после такого большого количества времени, не хотелось бы просто его положить на полку, как все предыдущие.</p><p>Сейчас в спокойном режиме стараюсь работать над проработкой мира и его дизайном, для дополнительной — визуальной — мотивации писать код дальше.</p><p>К сожалению, ссылку на Github оставить не могу, так как надеюсь, что из этого проекта сможет вырасти что-нибудь коммерческое. Но рад буду пообщаться и обсудить что со всем этим делать дальше в телеграме</p>]]></content:encoded>
    </item>
    <item>
      <title>Менеджер паролей, который не хранит пароли — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Artem]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Написал свой удобный и безопасный менеджер паролей, который могут протестировать все.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/menedzher-parolej-kotoryj-ne-hranit-paroli-konkurs-pet-proektov">Менеджер паролей, который не хранит пароли — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Безопасность]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Vue]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 26 Oct 2023 12:14:55 GMT</pubDate>
      <content:encoded><![CDATA[<p>Всем привет! Меня зовут Артем (Nelkor) и я всем сердцем увлечён программированием. Занимаюсь этим на работе и время от времени создаю пет-проекты.</p><h2>Вступление</h2><p>Все мы пользуемся паролями. Мы хотим, чтобы наши пароли были сложными, уникальными для каждого аккаунта и не хотим хранить их на бумажке. Однако, помнить десятки разных и сложных паролей попросту невозможно, и мы идём на компромисс. Например, пароли начинают повторяться. Мы понимаем, что это уязвимость, но как иначе удержать свои доступы в голове?</p><p>В начале этого года я решил — хватит! Я перейду на один из менеджеров паролей. Все крутые парни пользуются менеджерами паролей. И я стал изучать их.</p><p>Неочевидная проблема заключается в том, что менеджеры паролей… хранят пароли. Как правило, это зашифрованный файл на устройстве. Если доступ к этому файлу будет утерян, мы потеряем доступ ко всем своим аккаунтам. Если мы купили новое устройство, на нём этого файла нет. Если мы завели новый аккаунт на одном устройстве, а войти хотим с другого, на нём этого пароля нет. Файл необходимо синхронизировать и следить за его версиями.</p><p>В критически важный момент мы можем не получить доступ к своему аккаунту.</p><p>Эту проблему, якобы решает облачное хранение. Но облачное хранилище — это всегда чей-то сервис. Мы не можем быть уверены, что этот сервис не сломается или не откажет нам в доступе по любой причине.</p><h2>Идея</h2><p>Ни один из популярных менеджеров паролей не предоставляет той функциональности, которая мне нужна. И я решил сделать свой.</p><p>Принцип простой — придумать и запомнить один надёжный пароль не так уж трудно. Этот пароль может играть роль источника энтропии для криптографической функции, которая вычисляет пароль для конкретного аккаунта. Все данные аккаунтов можно безопасно сохранять на устройстве для удобства пользователя.</p><p>Зная свой исходный пароль, <b>мы можем получить доступ к любому своему аккаунту откуда угодно, хоть с совершенно нового устройства</b>. Чистая функция вычислит оба раза одинаковый результат, если передавать ей на вход одинаковые данные.</p><p>В качестве варианта реализации я выбрал PWA. Во-первых, PWA — это, прежде всего, веб-сайт. То есть получить доступ к нему максимально просто. Во-вторых, PWA — это приложение, которое можно установить на любое устройство. Буквально одни плюсы и нет минусов.</p><p>В начале года как раз узнал про методологию Feature-sliced design и решил распробовать её на своём новом пет-проекте. В качестве реактивной библиотеки выбрал свою любимую третью Vue. Итак, дамы и господа, встречайте…</p><h2>Passcryptum</h2><figure><img src="https://media.tproger.ru/user-uploads/91563/2023-10-20/9257af88-4b14-4c4d-89a0-54a01b0c0edc.png" alt="" /></figure><p><a href="https://github.com/nelkor/passcryptum">GitHub — Passcryptum</a></p><p>Исходный пароль обрабатывается функцией PBKDF2 SHA-512 262144 итераций. Это серьёзное препятствие на пути у тех, кто захочет получить доступ к нашим аккаунтам путём перебора исходного пароля.</p><p>Приложение не хранит пароли, но хранит список сервисов и логинов в зашифрованном виде. Без нашего исходного пароля никто не сможет прочитать даже список сервисов, которыми мы пользуемся. В свою очередь мы, заходя в Passcryptum, сразу видим свои сервисы и можем сразу скопировать логин/пароль.</p><p>Список сервисов можно безопасно хранить где угодно и передавать на другие устройства. Даже если у нас новое устройство, а список сервисов потерян — ничего страшного, можно просто ввести свои сервисы и логины заново и получить свои пароли.</p><p>Если есть нужда сменить пароль на аккаунте — у каждого логина есть версия. Инкрементируем версию и получаем новый совершенно уникальный пароль.</p><p>Чтобы не вводить каждый раз свой суперсекретный исходный пароль (мало ли где кто подсмотрит), существует возможность задать PIN. Хеш исходного пароля шифруется значением PIN, а также отпечатком системы устройства. PIN можно сколько угодно раз забыть, удалить и установить новый. Главное — помнить свой исходный пароль и вводить его исключительно осторожно.</p><h2>Заключение</h2><p>Passcryptum решил мою проблему и я с радостью готов поделиться со всем миром этим инструментом. В Passcryptum нет ничего платного и весь код открыт.</p><p>Помимо README.md, я добавил несколько полезных инструкций:</p><ul><li><a href="https://github.com/nelkor/passcryptum/blob/main/docs/password-generation.md">Алгоритм генерации паролей</a>;</li><li><a href="https://github.com/nelkor/passcryptum/blob/main/docs/pin.md">PIN</a>;</li><li><a href="https://github.com/nelkor/passcryptum/blob/main/docs/recommendations.md">Рекомендации по использованию</a>.</li></ul><p>Для инструкций выбрал английский язык как международный. Надеюсь, это никому не помешает прочитать, ведь средства автоматизированного перевода сейчас уже на очень высоком уровне.</p><p>Спасибо за внимание! Каждому человеку, который пользуется паролями (ну то есть просто каждому), искренне советую попробовать Passcryptum.</p>]]></content:encoded>
    </item>
    <item>
      <title>Senior Junior. Курсы от программистов для программистов</title>
      <link>https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov</link>
      <comments>https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Serine]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov</guid>
      <description><![CDATA[<p>Сделали свою платформу курсов для программистов — с актуальной теорией и множеством практики. Сейчас доступны Python и Rust.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/senior-junior-kursy-ot-programmistov-dlya-programmistov">Senior Junior. Курсы от программистов для программистов</a>»</p>]]></description>
      <category><![CDATA[Обучение программированию]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 25 Oct 2023 09:07:50 GMT</pubDate>
      <content:encoded><![CDATA[<p>Признавайтесь, кто ведет секретный бэклог фреймворков и языков, в которых бы разобраться, но никак не доходят руки? Изучение нового кажется интересной идеей, но ровно до того момента, пока этим не займешься. То времени не хватает, то мотивации.</p><p>Какие вообще есть варианты?</p><ul><li><b>Курсы</b> из разряда «%lang_name% с нуля». Имя им легион. Но многие ли из них ориентированы на разработчиков, а не вайтишников? Снова слушать про класс Employer и отличие цикла for от while как-то непродуктивно.</li><li><b>Книги.</b> Серьезные, профессиональные книги. Проблема не в том, что они толстые и скучные. Просто нужно обладать воистину железной силой воли, чтобы не только дочитать до конца, но и прорешать задачи. Отдельный вопрос, как убедиться, что закодил решение без багов.</li><li><b>Документация</b> и, опционально, заныривание в <b>исходники.</b> Отличный подход, хоть и не самый эффективный. Жаль, он не дает представления о распространенных в сообществе лучших практиках, о нюансах, на которые наталкиваешься в промышленной разработке.</li></ul><p>Итак, однажды вечером собрались четыре разработчика и задались вопросом: как в идеале должна выглядеть площадка для изучения новых языков и технологий? Сошлись на следующем:</p><ul><li>Самое важное — это <b>практика.</b> Ее нужно много. Но маленькими порциями. Пусть теория чередуется с емкими задачами в <b>online IDE</b> на этой же странице.</li><li>Задачи должны быть разноплановыми. Писать код. Рефакторить код. Анализировать, как отработает код. Все как в жизни.</li><li>Концентрированная, свеженькая <b>теория.</b> Без лирических отступлений, опасных упрощений, академеческих дебрей. Прочитать и смочь ревьюить реквесты!</li><li>Курсы должны быть <b>опенсорсными.</b> Чтобы любой желающий мог сообщить об ошибке, предложить реквест с исправлением, заменить скучную задачу на более жизненную. И даже опубликовать собственный курс!</li></ul><p>…Так и родилось описание проекта <a href="https://senjun.ru">Senior Junior,</a> который мы в свободное время пилим почти полтора года. Эхееей, на прошлой неделе мы выкатили альфа-версию!</p><h2>Что из себя представляет Senior Junior?</h2><p><a href="https://senjun.ru">Senior Junior</a> — это площадка с опенсорсными курсами для разработчиков. Повторю, для разработчиков. Вайтишники, осторожно! У нас нет сертификатов, гарантий трудоустройства и лозунгов «освойте с нуля». Зато у нас есть актуальная теория в связке с непрерывной практикой в online IDE.<a href="https://media.tproger.ru/user-uploads/91482/2023-10-19/e17d56ed-2e20-48f2-aabf-6ce7df6635ba.jpeg"></a></p><p>Тексты курсов и задачи <a href="https://github.com/senjun-team/senjun-courses/tree/main">выложены на гитхаб.</a> На данный момент мы почти дописали курс по Python и приступили к курсу по Rust.</p><p>Курсы можно проходить на сайте и в <a href="https://t.me/sen_jun_bot">Telegram-боте.</a> Между ними легко синхронизировать прогресс! А что, очень удобно: дома начал главу на сайте с десктопа, продолжил уже в метро из бота.</p><figure><img src="https://media.tproger.ru/user-uploads/91482/2023-10-19/35a789da-b327-4b18-b84d-e2609b740d49.jpeg" alt="" /></figure><h2>Как устроен проект</h2><p>Мы публикуем главы курсов в формате <a href="https://docs.github.com/en/get-started/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax">md.</a> Тексты размечаем через <a href="https://github.com/arve0/markdown-it-attrs">markdown-it-attrs. </a></p><p>На фронтенде md рендерится в HTML с помощью библиотеки <a href="https://github.com/markdown-it/markdown-it">markdown-it.</a> В Telegram-боте форматированный текст подготавливает самописный парсер. <a href="https://codemirror.net/">CodeMirror</a> используется для интегрирования online IDE в веб-страницу.</p><p>Бэк выглядит примерно так:</p><figure><img src="https://media.tproger.ru/user-uploads/91482/2023-10-19/befe9f45-ecc8-4b48-b96c-42af79b76bb1.jpeg" alt="" /></figure><p>На данный момент у нас есть:</p><ul><li><a href="https://senjun.ru/courses/python/">27 глав</a> по Python и <a href="https://senjun.ru/courses/rust/">2 главы</a> по Rust. 160 задач. Все они в открытом доступе.</li><li>Площадка <a href="https://senjun.ru">senjun.ru</a> и <a href="https://t.me/sen_jun_bot">Telegram-бот</a> для прохождения курсов. Согласно принципу «подчеркивай достоинства, скрывай недостатки» все исходники <i>пока</i> надежно спрятаны.</li><li>4 разработчика, вложившихся в проект и готовых его развивать: <a href="https://www.linkedin.com/in/anna-bekker-938070252/">Аня Беккер,</a> <a href="https://www.linkedin.com/in/dmitry-shipilov-2a2b8b218/">Дима Шипилов,</a> <a href="https://www.linkedin.com/in/vladimir-khatzkevich-31387037/">Володя Хацкевич</a> и <a href="https://www.linkedin.com/in/olga-khlopkova-3a920b204/">Оля Хлопкова.</a></li></ul><h2>О настоящем и будущем</h2><p>Позади полтора года работы. За это время мы запилили бэкенд и клиент-сайд, выкатились на прод и пережили пару итераций тестирования, сбора фидбэка и фиксов.</p><p>За нашими спинами не стоят многомиллионные бюджеты корпораций. И это восхитительно. Потому что корпоративные рамки, требования и бизнес-цели нас не сковывают. Не ждите от нас навязчивых фичей, которые бесят аудиторию, зато помогают менеджеру закрыть KPI. Вместо пуш-уведомлений и автоматических подписок мы с удовольствием добавим фичи, которые будут полезны пользователям.</p><p>Не скромничайте, выходите на связь:</p><ul><li>Оставляйте фидбэк. Форма для заполнения есть в конце каждой главы курсов <a href="https://senjun.ru">senjun.ru.</a></li><li>Добавляйтесь <a href="https://t.me/+P6mKBuFC9pQwNTk6">в группу в Telegram.</a></li><li>Заводите баг-репорты, открывайте пул-реквесты <a href="https://github.com/senjun-team/senjun-courses/tree/main">на GitHub.</a></li></ul><p>Какие у нас планы?</p><p>Допишем главы по Python и Rust. Параллельно будем добавлять новые курсы. Golang, линуксовый shell script, Kotlin? C++ за 21 год, почему бы и нет? Carbon, как только появится первый релиз языка? А как насчет узкоспециализированных тем вроде теории компиляторов?</p><p>Итак, кто что заказывает?</p>]]></content:encoded>
    </item>
    <item>
      <title>Telegram Bot API на Kotlin — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/telegram-bot-api-na-kotlin-kak-ono-bylo</link>
      <comments>https://tproger.ru/articles/telegram-bot-api-na-kotlin-kak-ono-bylo?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Алексей Овсянников]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/telegram-bot-api-na-kotlin-kak-ono-bylo</guid>
      <description><![CDATA[<p>Написал на Kotlin библиотеку с поддержкой WebApp в JS таргете и множеством разных DSL.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/telegram-bot-api-na-kotlin-kak-ono-bylo">Telegram Bot API на Kotlin — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Kotlin]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 25 Oct 2023 07:11:19 GMT</pubDate>
      <content:encoded><![CDATA[<p>Добрый день 🙂 Я Алексей Овсянников, автор библиотеки <a href="https://github.com/InsanusMokrassar/ktgbotapi">KTgBotAPI</a>, о которой и хотел бы рассказать в рамках конкурса пет-проектов.</p><h2>Что за библиотека такая</h2><p>Изначально задачей библиотеки была строгая типизация работы с <a href="https://core.telegram.org/bots/api">Telegram Bots API</a>. Так уж вышло, что со временем это переросло в нечто большее, теперь это — мультиплатформенная библиотека с поддержкой WebApp в JS таргете и кучей разных DSL.</p><h3>О зарождении</h3><p>По счастливому стечению обстоятельств, на момент начинания библиотеки я уже имел опыт публикации JVM-библиотек, работы с Kotlin и работы с Telegram Bots API. Понятное дело, что тогда (около пяти лет назад) уже были какие-то решения для этих задач, но:</p><ul><li>Как минимум, бОльшая часть была написана на Java для JVM — ни о какой null-safety и других фишках Kotlin не шло речи.</li><li>Ни одна из изученных мной библиотек не обладала хотя бы намёком на какую-то безопасность при работе — поля запросто могли отсутствовать, а методы не применяться.</li><li>Тогда еще не так популярны были всякие DSL + поскольку библиотеки были на JVM, очень много чего скрывалось в документации или в лучшем случае в JavaDoc’ах</li></ul><p>Самой большой болью было то, что библиотеки калькировали API, из-за чего постоянно происходили выстрелы в ногу: то поле отсутствует для какого-то типа, то метод не применим для чата.</p><h3>Трудности по-пути</h3><p>Трудностей было много. Например, на первую версию ушел месяц, без учёта тестов. На входе у пользователей библиотеки до сих пор сохраняются сложности в связи со строгой типизацией и тем, что за ней следует, например, базовый <a href="https://tgbotapi.inmo.dev/tgbotapi.core/dev.inmo.tgbotapi.types.chat/-chat/index.html">Chat</a> имеет только идентификатор, все остальные параметры для общей абстракции чатов просто отсутствуют.</p><p>Также, каждая итерация поддержки <a href="https://core.telegram.org/bots/api">Telegram Bots API</a> вносила свои приколы: например, форумы — это просто группы с галочкой форумов, у которых для сообщений есть поле threadId. Само собой, каждое обновление заставляло перелопачивать иерархию типов, что иногда приводило к болючим изменениям. Цена прогресса, так сказать 🙂</p><p>Из забавностей, в одном из обновлений ребята из команды Telegram толи вывалили наружу, толи подглядели в либу и почти скопировали какую-то иерархию типов (кажется, для прав) — это было очень интересно видеть почти 1-в-1 названия для типов и их отношения друг к другу в официальном API и моей либе 😀</p><h3>Сообщество</h3><p>Отдельное спасибо я хочу сказать сообществу. Новые идеи, репорты багов, а иногда даже и самостоятельный вклад — многое произошло благодаря сообществу. Например, текущая <a href="https://docs.inmo.dev/index.html">дока</a> появилась в том виде, в каком она есть, благодаря одному из <a href="https://t.me/m_a_d_h_e_a_d">пользователей</a> либы — он подсказал, куда можно смотреть, чтобы получить доку, в которую можно будет предлагать правки и которая будет удобна в использовании.</p><h3>К чему я (мы) пришел</h3><p>Я начинал работу над библиотекой один. Со временем приходили люди и привносили идеи. Так появилось много всего:</p><ul><li>удобный API, вроде как дублирующий методы в оригинальном API, но на самом деле также разделённый по типам и строго декларирующий, какие параметры с какими можно сочетать;</li><li>различные DSL вроде <a href="https://docs.inmo.dev/tgbotapi/dsls/keyboards.html">Keyboards DSL</a> и <a href="https://docs.inmo.dev/tgbotapi/dsls/text.html">Text Entities DSL</a>;</li><li>некоторые библиотеки вокруг: <a href="https://docs.inmo.dev/plagubot/index.html">PlaguBot</a> для унификации частей ботов (плагинов), различные FSM и <a href="https://docs.inmo.dev/tgbotapi/logic/behaviour-builder.html">BehaviorBuilder</a>.</li></ul><h2>Вместо выводов</h2><p>Библиотека жива. Сейчас во многом она в ситуации поддержки — возможности целенаправленно развивать её и её экосистему особо нет, но тем не менее всё время появляются какие-то классные штуки, как то отдельная абстракция для <a href="https://t.me/ktgbotapi/354">предварительной информации о чатах</a> или различные дополнения документации.</p><h4>Спасибо за внимание 🙂</h4>]]></content:encoded>
    </item>
    <item>
      <title>Как я пишу компилятор C-подобного языка с нуля и зачем — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-piwu-kompilyator-c-podobnogo-yazyka-s-nulya-i-zachem-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kak-ya-piwu-kompilyator-c-podobnogo-yazyka-s-nulya-i-zachem-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Вячеслав Корепанов]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-piwu-kompilyator-c-podobnogo-yazyka-s-nulya-i-zachem-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Пишет компилятор своего языка и параллельно набирает базу: процесс компиляции, оптимизации и исполнения кода</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-piwu-kompilyator-c-podobnogo-yazyka-s-nulya-i-zachem-konkurs-pet-proektov">Как я пишу компилятор C-подобного языка с нуля и зачем — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Golang]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 23 Oct 2023 15:59:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Всем привет! Меня зовут Вячеслав!</p><p>Я являюсь разработчиком на языке Go в течение трех лет. Также вот уже в течение трех лет я пишу пет-проект компилятора C-подобного языка.</p><p>Изначально появилась идея написания компилятора C-подобного языка в промежуточный код, который затем бы защищался от несанционированного использования и интерпретировался только лицом, обладающим ключом. Однако сейчас эта идея устарела, поскольку я больше увлекся уже компиляцией промежуточного программного кода в машинный (бэкэндом компилятора).</p><p>На самом деле, проект все более перерастает в учебный и позволяет глубже понять процесс компиляции, оптимизации и исполнения программного кода. Мне известны такие инструменты как LLVM, Lex, Bizon и тому подобные, но целью данного проекта сейчас является понимание основ того, как устроены компиляторы. Поэтому мною было принято решение от этих средств отказаться и реализовать компилятор без них. Кто-то упрекнет меня в написании велосипеда, но я считаю, что без написания велосипеда понять его устройство по-настоящему, порой, невозможно. Итак, обо всем по порядку.</p><p>Процесс компиляции состоит из нескольких фаз. Укрупненно, это лексический и синтаксический анализы, а также генерация промежуточного представления и перевод этого представления в целевой язык. На разных этапах целевой язык моего проекта менялся. Изначально, как я уже говорил, использовалось промежуточное представление с последующей защитой и интерпретацией. Однако процесс выполнения в этом случае достаточно медленный, поэтому я быстро пришел к пониманию того, что для реализации новых конструкций языка посредством старых нужно формировать исполняемый файл.</p><p>Таким образом, я сменил целевой язык на язык Go, получив таким образом транспилер. Тем не менее язык Go и мой C-подобный язык плохо совместимы. Например, в Go нельзя объявлять переменную, которая затем не будет использоваться, а в моем языке можно. В конце концов целевым языком стал для меня классический GNU Assembler, ведь я компилирую программы под ОС Ubuntu x64. В настоящее время он и остается целевым языком. После компиляции программ с языка GNU Assembler я получаю исполняемые файлы.</p><p>Лексический анализ предполагает разбиение входного потока символов на осмысленные группы (лексемы), а также выделение токенов (лексемы и ее типа). Например, “AND”, “11”, “(” — это лексемы моего языка). Я выделяю, например, следующие типы лексем: OP — операция, VAL — значение, VAR — переменная, BR — скобка. Так, для приведенных лексем можно назвать следующие токены: “OP AND”, “VAL 11”, “BR (“. Когда код команды (символы до “;”) разбит на лексемы, наступает фаза синтаксического анализа — выявление того, в каких отношениях состоят сущности (токены). Результатом синтаксического анализа обычно является либо абстрактное синтаксическое дерево (АСД), либо трехадресный код. Я строю АСД. Вот пример такого дерева.</p><figure><img src="https://media.tproger.ru/user-uploads/23823/2023-10-23/3084eed3-3da7-4ca6-be15-23fc8a474d42.jpeg" alt="" /><figcaption>Рисунок 1. Абстрактное синтаксическое дерево для выражения</figcaption></figure><p>Для построения таких деревьев, визуально понятных для человека, я использую GoCV — обертку на Go для библиотеки OpenCV.</p><p>В конечном итоге каждая вершина дерева нумеруется в глубину, и мы получаем массива токенов в соответствии с их расположением в дереве:</p><p>Пустые кружки означают тот факт, что у узла нет потомков.</p><p>После прохождения фазы синтаксического анализа команда может быть выполнена, либо преобразована в промежуточное представление. Смысл защиты программы состоял в том, чтобы дописать лишние команды в промежуточное представление программного кода и запомнить смещения, по которому лежат реальные команды. Файл со смещениями являлся ключом. Вот, как схематично можно представить этот процесс</p><figure><img src="https://media.tproger.ru/user-uploads/91327/2023-10-16/991cf7c3-d2ab-4868-85a1-ab45171a1460.jpeg" alt="" /><figcaption>Рисунок 2. Процесс получения защищенной программы и ее исполнения</figcaption></figure><p>К сожалению, я быстро понял, что такой подход мало чем отличается от программы, положенной в архив с паролем. Поэтому мною было принято решение от данного процесса отказаться и реализовать классический компилятор с целью самообучения и возможностью делиться полученными знаниями с окружающими.</p><p>Также в настоящее время на основе регулярных выражений мной реализованы статический и динамический валидаторы программного кода. Перед тем, как пойти в обработку, программа проверяется без ее запуска на правильность по формальным признакам (число открытых скобок равно числу закрытых, сигнатура функции объявлена в соответствии с синтаксическими правилами языка и тому подобное), а также с запуском в виртуальной среде, где происходит проверка, например, на соответствие типов и т.п.</p><p>В компиляторе реализованы условные конструкции, циклы, функции, рекурсия, возможность подключения сторонних файлов на том же языке, работа с файлами и регулярными выражениями.</p><p>Программа на C-подобном языке преобразуется в промежуточное представление, похожее на язык Assembler с тем, чтобы в последующем реально получить программу на языке GNU Assembler и скомпилировать ее.</p><p>В настоящее время мной написан чат-бот на языке Go ВКонтакте, но я мечтаю переписать со временем этого бота на собственном языке. Любимый кусочек кода:</p><figure><img src="https://media.tproger.ru/user-uploads/91327/2023-10-16/38277a52-3232-4305-a7cb-a5f8f3501420.jpeg" alt="" /><figcaption>Функция DrawTree, выполняющая первичную подготовку данных и изображения АСД</figcaption></figure><p>Функция makeTree, выполняющая основную работу по построению АСД, достаточно объемная, поэтому мне не хотелось бы приводить здесь ее код. Весь код может быть найден на GitHub.</p><p>Более подробно о процессе реализации компилятора я рассказываю в своей группе ВКонтакте. Также прикрепляю ссылку на репозиторий GitHub.</p><ul><li>GitHub: https://github.com/korepanov/bint</li><li>ВКонтакте: https://vk.com/repaschool</li></ul>]]></content:encoded>
    </item>
    <item>
      <title>Как я создаю аналитический инструмент для групповых чатов Telegram — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-sozdayu-analiticheskij-instrument-dlya-gruppovyh-chatov-telegram-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kak-ya-sozdayu-analiticheskij-instrument-dlya-gruppovyh-chatov-telegram-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[MacArty]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-sozdayu-analiticheskij-instrument-dlya-gruppovyh-chatov-telegram-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Делаю на Python инструмент, который позволяет анализировать эффективность работы сотрудников в Telegram-чатах.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-sozdayu-analiticheskij-instrument-dlya-gruppovyh-chatov-telegram-konkurs-pet-proektov">Как я создаю аналитический инструмент для групповых чатов Telegram — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Аналитика]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 23 Oct 2023 12:05:35 GMT</pubDate>
      <content:encoded><![CDATA[<h2>Обо мне</h2><p>Привет ✌</p><p>Я аналитик в IT и телекоммуникационной компании. Так сложилось, что в текущий момент работаю над своим проектом, который позволяет анализировать эффективность работы сотрудников в Telegram-чатах. И, возможно, местная аудитория даст полезные советы для развития инструмента.</p><p>Ну и еще было бы здорово получить худи от Tproger)</p><h2>Идея проекта</h2><p>Не нужно рассказывать о популярности Telegram и постоянном увеличении аудитории. В РФ используется порядка 60к групповых чатов, по статистике TGStat на август 2023.</p><p>Групповые чаты использует и бизнес для коммуникации со своими клиентами, по опыту, больше для поддержки продукта, чем для продажи. Соответственно руководителю отдела поддержки важно понимать, как эффективно сотрудники работают в Telegram, а именно интересуют метрики:</p><ul><li>время ответа сотрудника на сообщения клиента;</li><li>время, которое сотрудник тратит на общение в чатах с клиентами;</li><li>качество работы сотрудников, то есть насколько предоставленные ответы сотрудником закрывают вопросы клиентов;</li><li>сегментация обращений от клиентов;</li><li>какие клиенты больше генерят обращений.</li></ul><p>Это только часть метрик, которые необходимы для анализа.</p><p>Моя коллега — руководитель отдела поддержки, пришла ко мне с задачей разработки инструмента, который позволит анализировать эффективность сотрудников в чатах Telegram.</p><p><b>Первоначальная и основная задача:</b> быстро и дешево запустить инструмент + проверить, а точно ли он приносит пользу. Так как на рынке нет подходящих решений*, то я решил создать такой инструмент самостоятельно. Который на текущий момент и является моим пет-проектом.</p><h2>Развитие проекта.</h2><p>Быстро и бесплатно запускаем MVP инструмента.</p><p>Чтобы собирать данные, нужно создать обычный Telegram-бот. Также нужно хранилище для собранных данных. Для этой цели использовал Google Sheets. Чтобы подключить Telegram-бота к гугл-таблицам и собирать данные, нашел в открытом доступе код:</p><p>Для получения необходимых руководителю метрик, использовались формулы в гугл-таблицах. И чтобы делать какие-то выводы на основе собранных данных, их нужно визуализировать. Для этой задачи используется <a href="https://datalens.yandex.ru/">Yandex DataLens</a>.</p><p><b>Итог — MVP</b></p><p>В течение полного месяца протестировали на семи групповых чатах Telegram. Все работает корректно, и только одна ошибка при загрузке данных. Удалось вывести следующие метрики:</p><ul><li>Количество всего сообщений в разбивке по чатам, чтобы понимать, какой клиент генерирует наибольшее количество обращений.</li><li>Количество сообщений в рабочее и нерабочее время.</li><li>Время ответа клиенту в чате, в разрезе по сотрудникам и по отделу.</li><li>Время, потраченное сотрудниками на переписку с клиентом.</li><li>Количество сообщений по часам, чтобы оптимизировать график сотрудников, в зависимости от пиковых часов.</li><li>Количество пропущенных чатов. В формулах задается определенное время ответа клиенту. Если время было превышено, то руководитель в дашборде увидит какому клиенту долго не отвечают.</li></ul><p>И самое главное, что руководитель может видеть информацию почти в реалтайм (лаг обновления данных в Yandex DataLens — 30 минут) и на мобильном устройстве.</p><p><b>Вывод:</b> продукт закрывает потребности, но, разумеется, требует доработок.</p><h2>Возникшие трудности</h2><p>После тестирования MVP, решили использовать инструмент на всех клиентах отдела, с которыми ведется коммуникация в групповых Telegram-чатах.</p><p>Добавили бота в 100+ чатов, начали собирать новые метрики, то есть усложнять формулы в гугл-таблицах. Объем собираемых данных вырос в разы, а сложные формулы увеличивали скорость обработки запросов. Это привело к тому, что данные могли подгружаться с некоторой задержкой, что в итоге сказывалось на вычислении метрик, и у руководителя в дашборде формировались неточные данные.</p><p>Изначально было понятно, что для большого объема данных такое костыльное хранилище в виде гугл-таблиц рано или поздно приведет к ошибкам. Как раз в текущий момент, мой пет-проект в стадии трансформации, чтобы избавиться от возникших трудностей:</p><ul><li>Создалась БД на MySQL.</li><li>Telegram-бота пишу на Python, не только для наполнения БД, но и для формирования необходимых метрик. Пользуюсь наиболее популярной библиотекой telebot.</li><li>В планах еще разработать GUI для управления и контроля работы ботом.</li></ul><h2>Заключение</h2><p>Я ввязался в ту еще авантюру с разработкой данного проекта. Однако с его помощью я повышаю свои скиллы в разработке на Python, продуктовому менеджменту и аналитике данных. Самое главное, что все это меня драйвит и заряжает, поэтому я и считаю это своим пет-проектом.</p><p>Буду рад любым комментариям, лайкам и вопросам. Спасибо за внимание)</p>]]></content:encoded>
    </item>
    <item>
      <title>MLup: как создавать веб-приложение с машинными обучением за один взмах волшебной палочки - конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/mlup-machine-learning-as-api</link>
      <comments>https://tproger.ru/articles/mlup-machine-learning-as-api?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Timofey]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/mlup-machine-learning-as-api</guid>
      <description><![CDATA[<p>Написал библиотеку на Python , которая позволяет создавать и запускать приложения с любой моделью машинного обучения.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/mlup-machine-learning-as-api">MLup: как создавать веб-приложение с машинными обучением за один взмах волшебной палочки - конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Машинное обучение]]></category>
      <category><![CDATA[Data Science]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 19 Oct 2023 15:02:32 GMT</pubDate>
      <content:encoded><![CDATA[<p>Я с самого начала своего пути в IT полюбил machine learning (машинное обучение). И мой пет-проект связан с этим. Я сделал небольшой фреймворк, который позволяет создавать и запускать веб-приложение с любой моделью машинного обучения без необходимости привлекать программиста.</p><h2>Про проблему веб-приложений с машинным обучением</h2><p>Модель – это какой-то исполняемый код, которому можно отдать данные в определенном формате (подать на вход) и получить ответ (получить выход). Как правило, это массивы чисел: массивы numpy, тензоры, спарс-массивы и другие.</p><p>Пользователям вашей модели недостаточно знания о том, какой массив им нужно отдать вашей модели машинного обучения. Им нужен интерфейс взаимодействия с ней: сайт, телеграм-бот, мобильное приложение.</p><p>В больших компаниях есть ресурсы для создания таких интерфейсов, их оптимизации и поддержки. Но также есть много небольших компаний и просто исследователей, которым нужно создавать этот интерфейс самостоятельно. Мой пет-проект должен, если не избавить, то сильно упростить этот процесс.</p><p>Библиотека, про которую я пишу, создает веб-приложение с API для модели машинного обучения. Я назвал ее <b>mlup</b>. Чтобы запустить ваше веб-приложение, нужна только модель.</p><p>В связи с тем, что основные ЯП в машинном обучении — Python и C++, я написал библиотеку на Python. Хочу в будущем сделать реализацию на С++. Название mlup было уже занято в pypi, поэтому я загрузил библиотеку под названием pymlup.</p><p>Установить библиотеку на Python можно через pip: pip install pymlup.</p><h2>Про решение</h2><h3>Как пользоваться</h3><p>Самый простой вариант — запустить веб-приложение со всеми стандартными настройками:</p><p>Эта команда создаст и запустит сервис c API, в котором можно вызывать предсказание вашей модели. Сам сервис запустится на 8009 порту. Вы можете открыть документацию API и потестировать ваш сервис в ней по адресу <i>http://localhost:8009/docs</i>.</p><p>Вы можете написать свой конфигурационный файл в yaml/json формате и запускать из него:</p><p>Или сгенерировать код веб-приложения в Python-файл. Созданное приложение можно дорабатывать собственным кодом и запускать любым удобным способом:</p><p>Также можно использовать все возможности из кода, импортируя библиотеку mlup и создавая объект mlup.UP.</p><p><i>EmptyModel</i> ничего не возвращает, когда ее просишь что-то предсказать. Это просто заглушка, которая используется для внутренних целей и для пустой инициализации.</p><p>Каждая модель машинного обучения занимает какой-то объем памяти, поэтому ее загрузка в память должна быть явной. А без загрузки модели в память невозможен ее анализ и создание веб-приложения. Когда вы создаете объект mlup.UP, ничего в память не грузится. Для загрузки модели и ее анализа нужно вызывать метод up.ml.load().</p><p>Код up.run_web_app(daemon=True) запускает веб-приложение. Под капотом используется FastAPI.</p><h3>Архитектуры веб-приложения</h3><p>На момент написания статьи, в mlup есть три архитектуры веб-приложения:</p><ol><li>Прямое использование модели (<i>directly_to_predict</i>)</li><li>Очередь и воркер (<i>worker_and_queue</i>)</li><li>Батчинг данных из запросов (<i>batching</i>)</li></ol><h4>Архитектура веб-приложения: прямое использование модели</h4><p>Самая простая и очевидная на первый взгляд архитектура. Для каждого запроса пользователя вызывается предсказание модели.</p><figure><img src="https://media.tproger.ru/user-uploads/90935/2023-10-17/de6f27f9-bab4-4a3e-9808-31422490e245.png" alt="" /></figure><p>Модели машинного обучения, во время предсказания, выполняют CPU bound операции. Каждый запрос пользователя будет запускать предсказание модели независимо от других. Получается параллельные предсказания. В таком случае ресурсы потребляемые моделью будут множится для каждого запроса и могут закончится. <b>Приложение зависнет.</b></p><p>Но эта архитектура самая быстрая для предсказания. Она подходит для случаев: когда у вас маленькая модель, быстрая модель, мало запросов к ней.</p><h4>Архитектура: очередь и воркер</h4><p>Когда у вас недостаточно ресурсов для запуска несколько параллельных предсказаний модели, вы можете обеспечить доступ к модели через очередь. Тогда ваша модель машинного обучения будет выполнять только 1 предсказание (CPU bound операцию) в момент времени. И все запросы пользователей будут обработаны в том порядке, в котором пришли.</p><figure><img src="https://media.tproger.ru/user-uploads/90935/2023-10-17/f4b6b800-3735-4576-a952-bf612ad0b2e4.png" alt="" /></figure><p>Эта архитектура поддерживает долгие предсказания (long predict) – когда ваша модель машинного обучения вычисляет ответ дольше, чем клиент может ждать. Клиент может отправить запрос на предсказание, получить в ответе predict_id (uuid) и вернутся за ответом позже.</p><h4>Архитектура веб-приложения: батчинг данных из запросов</h4><p>Доступ к модели через очередь не всегда бывает эффективным. <i>Архитектура батчинга данных из запросов</i> обеспечивает такой же доступ к модели через очередь, как <i>архитектура очередь и воркер</i>. Но в модель попадают на предсказание уже не один запрос в момент времени, а несколько.</p><p>Воркер с моделью читает очередь запросов, пока не наберет определенное число данных для предсказания (батч). Собранную пачку данных из нескольких запросов отправляет в модель, а результаты раскладывает в хранилище результатов по ключу <i>predict_id</i>. В случае mlup, все это происходит в памяти, без привлечения сторонних хранилищ.</p><figure><img src="https://media.tproger.ru/user-uploads/90935/2023-10-17/ffa5a51a-5a1f-404d-a8e6-340a1d881d00.png" alt="" /></figure><p>Эту архитектуру можно использовать, когда пропускная способность вашей модели машинного обучения предсказуема. Нет никакого смысла использовать архитектуру батчинга данных из запросов, если ваша модель может предсказывать одновременно только для маленького количества объектов.</p><p>Какую архитектуру выбирать, зависит от многих факторов: модели, ожидаемой нагрузки, количества ресурсов. Но эта тема заслуживает отдельной статьи.</p><p>Более подробно про весь процесс запуска и работы доступных архитектур веб-приложения написано в документации:</p><h3>Кастомизация</h3><p>Если стандартных алгоритмов <b>mlup</b> вам недостаточно, вы можете создавать свои. Все возможные кастомизации процесса загрузки и работы можно написать самостоятельно и подключать как модули. Например, вы можете реализовать собственную архитектуру веб-приложения с моделью и подключить ее в файле конфигурации, указав путь для импорта вашего кода.</p><p>Если API веб-интерфейс, созданный <b>mlup</b>, вам не подходит, вы можете создать любой другой интерфейс. Вам нужно просто загрузить вашу модель с помощью mlup и использовать ее. Обращаться к модели, как к черному ящику, через метод mlup.UP.predict, используя привычные Python-типы и не думая о внутренних преобразованиях данных в формат модели машинного обучения и ее работе.</p><p>Чтобы не дублировать документацию, не стану останавливаться на всех возможных вариантах использования фреймворка и всех конфигурациях. Про это подробно я написал в документации.</p><h2>Про производство</h2><p>Я написал десятки сервисов, в которых использовались модели машинного обучения. Это были как простые приложения с одной моделью, так и более сложные приложения, в которых модели были лишь кусочком бэкенда. И все они загружались и работали по одному сценарию:</p><ol><li>Загрузка модели в память.</li><li>Инициализация модели и ресурсов под нее (GPU).</li><li>Запуск интерфейса взаимодействия с моделью.</li><li>Принятие запроса к модели от клиента.</li><li>Преобразование данных от пользователя в формат модели.</li><li>Вызов модели с преобразованными данными и ожидание ответа от нее.</li><li>Преобразование ответа модели в формат понятный пользователю.</li><li>Ответ пользователю.</li></ol><p>В большинстве случаев мне приходилось создавать приложение для каждого сценария заново. Даже если они были однотипные и создавались через Ctrl+C, Ctrl+V. Однажды я захотел консолидировать создаваемые мной приложения в одно, работу которого можно настраивать.</p><p>Я планировал сделать MVP за месяц. <b>Это было наивно!</b> Впрочем, я же программист: проваливать дедлайны — часть моей профессии. По часику в день я за месяц собрал приложение с разными архитектурами. Начал создавать разные модели машинного обучения, чтобы протестировать мой код. <b>И тут меня осенило!</b> Data Science специалисты не любят использовать библиотеки для разных задач, которые можно импортировать в свои исследования. А также в 1–2 строчки кода решать свои проблемы: сделать красивый график из массивов данных, красивый прогресс бар для обучения, обучить модель машинного обучения и другие.</p><p>Я понял, что созданное мной приложение неудобное для использования. Для его использования нужно клонировать Github-репозиторий, что-то прописывать в конфигурационный файл, собирать докер. Это все сложно и не подходит для главной цели — упростить создание веб-приложения с моделью. Было решено: обернуть написанный сервис в библиотеку. И на это ушло еще пару месяцев. Еще месяц я писал документацию, все оформлял и заливал в интернет.</p><p>В итоге я получил фреймворк для создания любого интерфейса взаимодействия с моделью с собственной реализацией веб-приложения. Мне нравится, что получилось сделать взаимодействие с фреймворком удобным и привычным для всех ролей, участвующих в создании приложения с моделью машинного обучения:</p><ol><li>Для Data Science специалиста можно использовать как библиотеку. В том числе запускать веб-приложение, тестировать его и сохранять в файл проверенный конфиг для будущего приложения.</li><li>Для программиста можно использовать из bash или прямо из кода. Можно брать созданное Data Science специалистом приложение с настройками для его модели и навешивать свою инфраструктуру.</li><li>Для DevOps-специалиста — это привычная работа с конфигами приложений и bash-командами для запусков процессов и приложений.</li></ol><p>Я очень надеюсь, что предлагаемый фреймворком <b>mlup</b> формат создания приложений будет удобным для всех участников этого процесса.</p><h2>Какие планы</h2><p>Я хочу добавить несколько модулей в коробку, поддерживающих популярные площадки по хранению моделей. Также улучшить валидацию входящих данных и доработать саму документацию.</p><p>Но самая желанная идея — добавить реализацию на C++, которая будет использовать тот же конфиг. Но не все модули из Python реализации можно реализовать в C++. Например, работу с <b>Pickle</b> моделями. Но если вам нужно C++ приложение с моделью машинного обучения, значит вы, скорее всего, знаете, что делаете, и можете сохранить вашу модель в нужном формате.</p><p>Спасибо, что дочитали эту статью до конца. Буду рад любой обратной связи, особенно на GitHub.</p><h2>Ссылки</h2><ol><li>Github — https://github.com/nxexox/pymlup</li><li>Документация — https://mlup.org</li></ol>]]></content:encoded>
    </item>
    <item>
      <title>Облачная операционная система — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/oblachnaya-operacionnaya-sistema-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/oblachnaya-operacionnaya-sistema-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Ильдар]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/oblachnaya-operacionnaya-sistema-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>За три года написал свою облачную операционную систему на собственном языке программирования.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/oblachnaya-operacionnaya-sistema-konkurs-pet-proektov">Облачная операционная система — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Docker]]></category>
      <category><![CDATA[Облачные технологии]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 17 Oct 2023 12:57:42 GMT</pubDate>
      <content:encoded><![CDATA[<p>Идея создать облачную операционную систему у меня возникла давно. После знакомства с докером, я понял, что это очень перспективная технология. Но есть несколько нюансов:</p><ol><li>Непонятно, как сделать HTTP-маршрутизацию. Нужно ставить отдельно Traefik или аналог и с ним разбираться. А так, чтобы из коробки, такое не поддерживается.</li><li>Не хватает правильного веб-интерфейса. Чтобы мышкой можно было тыкать и быстро запускать докер-среду с нужными контейнерами. Есть Portainer, но мне он не понравился. Там по сути мышкой создается yaml-файл. Но это неудобно. Хочется просто взять и сказать докеру: «Запусти MySQL, а вот c этими yaml-файлами сам разберись».</li><li>Я тогда занимался автоматизацией бизнес-проектов, ставил разные CRM, настраивал сервера, поднимал корпоративные почты. Поднять свою почту еще та задача. Обычно это несколько недель работы. А вот есть ли нормальная готовая сборка почты под докер?</li></ol><p>Помимо почты, бизнес хотел еще CRM, свою вики, таск-менеджер, и все это на одном домене, на своем сервере, с единой авторизацией. И как такое сделать? Есть ли готовые opensource решения? У меня появилась идея. Давайте создадим такую систему.</p><p>На протяжении последних трех лет я разрабатывал ее один, в свободное от работы время. И спустя годы разработок, тестирования и апробации, я создал облачную ОС и назвал ее BAYRELL Cloud OS.</p><p>Облачная ОС разработана на языке Bay Lang, который я создал до этого. Идея создать Bay Lang появилась еще раньше, в далеком 2016 году, когда я задался вопросом, а как запустить React на PHP? Варианта два: либо делать бэкенд на PHP как микросервис, либо V8js.</p><p>Но меня эти два варианта не устраивали, и я решил разработать шаблонизатор для PHP, который также умеет в реактивность в JS. И вскоре шаблонизатор превратился в язык программирования Bay Lang. На разработку языка программирования ушло примерно семь лет. В нем было около 11 версий.</p><p>Сейчас Bay Lang является тьюринг-полным языком программирования. Он умеет:</p><ol><li>Конвертировать программу в PHP для бэкенда и JS-фронтенда.</li><li>В реактивность, как у современных фреймворков Vue.js и React.</li><li>Server Side Render.</li></ol><p>Свой язык программирования я апробировал, разработав саму облачную ОС и сайт для нее.</p><p>Облачная ОС, на сегодняшний момент:</p><ol><li>Управляет докер-контейнерами на сервере.</li><li>Обладает веб интерфейсом, где можно мышкой запускать WordPress, MySQL, PHP и т.п.</li><li>Может использоваться как облачный аналог Denwer, XAMPP.</li><li>Обладает маркетплейсом, в который я собрал различные контейнеры, которые использую у себя на тестовом сервере.</li><li>Также сейчас активно используется в качестве среды разработки. В облачной ОС есть веб-версия VSCode, которую можно установить себе на сервер, и прямо на там вести разработку микросервисов.</li><li>Можно взять игровой компьютер, установить туда облачную ОС, и через браузер с планшета обучать модели ИИ на PyTorch. Это такой собственный локальный аналог гугл-колаба на минималках.</li></ol><p>Я рассказывал об облачной ОС своим друзьям и знакомым, и давал им ее попробовать. Они отмечают, что с помощью нее удобно управлять докер-контейнерами, но не хватает пошаговых инструкций по установке и использованию. А также побольше софта в маркетплейсе.</p><p>Я планирую их создать в ближайшем будущем.</p><p>Облачная ОС доступна на гитхабе <a href="https://github.com/bayrell-os">https://github.com/bayrell-os</a></p><p>Сайт проекта: <a href="https://cloud.bayrell.org/ru/">https://cloud.bayrell.org/ru/</a></p><p>На сайте находится маркетплейс и базовые инструкции как установить Облачную ОС.</p><p>Пожалуйста, расскажите в комментариях, что вы думаете по этому поводу, и что еще можно добавить в Облачную ОС?</p>]]></content:encoded>
    </item>
    <item>
      <title>Конструктор плейлиста для IP-TV — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/konstruktor-plejlista-dlya-ip-tv-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/konstruktor-plejlista-dlya-ip-tv-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Алексей Старовойтов]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/konstruktor-plejlista-dlya-ip-tv-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Сделал небольшое приложение, которое позволит сконструировать нужный для пользователя IP-TV плейлист в формате M3U.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/konstruktor-plejlista-dlya-ip-tv-konkurs-pet-proektov">Конструктор плейлиста для IP-TV — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Dart]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 17 Oct 2023 09:03:53 GMT</pubDate>
      <content:encoded><![CDATA[<p>Меня зовут Алексей, и я типичный программист, которого прёт от разработки.</p><p>Мне пришла идея реализовать приложение, которое позволит сконструировать нужный для пользователя IP-TV плейлист в формате <a href="https://ru.wikipedia.org/wiki/M3U">M3U</a>.</p><p>Мне нужно было от приложения следующее:</p><ul><li>Задать каналы и их порядок в плейлисте. Канал — это имя, логотип и ссылки на стримы.</li><li>Сохранить заданный плейлист в БД, выбрав не протухшую ссылку на стрим либо использовав <a href="https://user-images.githubusercontent.com/15068331/163717494-6cf6b0fe-6264-4d6d-99d7-97bf27bfb925.mp4">заглушку</a>.</li><li>Сконструировать плейлист в формате M3U из плейлиста, сохранённого в БД.</li><li>Web API с 2 методами: для запуска пункта 2 (далее: метод refresh_channels) и для получения плейлиста в формате M3U (далее: метод ip_tv_playlist.m3u), чтобы телевизор мог его получить и обработать.</li></ul><p>Чтобы добавить процессу разработки ценности, я решил выбрать язык программирования Dart. Мне было интересно, насколько он удобен для такой задачи и как язык в целом.</p><p>Попользовавшись своим чудом, я понял, что вручную искать рабочую ссылку на стрим — неблагодарное дело, поэтому решил внести корректировки в изначальную задумку:</p><ul><li>Метод refresh_channels принимает список ссылок на IP-TV плейлисты и множество параметров фильтрации каналов:names_to_remove[] — регулярные выражения для удаления каналов по названию канала;groups_to_remove[] — регулярные выражения для удаления каналов по названию группы;source_urls_to_remove[] — регулярные выражения для удаления каналов по ссылке на источник канала;min_resolution_width — минимальная допустимая ширина разрешения канала;min_resolution_height — минимальная допустимая высота разрешения канала.</li><li>Возможность задать каналы и их порядок в плейлисте остаётся той же, но у канала появляется дополнительное поле namePattern, в котором мы можем задать регулярное выражение для поиска этого канала в переданных плейлистах.</li><li>Все каналы, которых не коснулась фильтрация, добавляются в конец заданного списка каналов.</li></ul><p>Данная корректировка избавляет нас от ручного поиска рабочей ссылки на стрим для каждого желаемого канала, добавляет каналы, которые могут показаться интересными (кандидаты на добавление в заданный список каналов) или не интересными (причины добавления новой группы, имени или ссылки на источник в параметры фильтрации). Но мы должны вручную найти IP-TV плейлисты, из которых будет собираться наш, персонализированный. С этим неудобством я смирился, хотя можно было и это решить.</p><p>В реализации приложения мне похвастаться нечем, потому что делал на скорость, между делом. Но была одна трудность, с которой я столкнулся. Ещё в то время, как я пробовал на деле первую юзабельную версию приложения, я заметил, что некоторые каналы, хоть и работают, показываются в очень низком разрешении (720p, 480p, а то и хуже). На 75” 4К телевизоре это выглядит ужасно, поэтому среди фильтров есть возможность задать минимальное разрешение стрима. В моём случае это 1920×1080. Но единственный нормальный способ проверить разрешение стрима, который я нашёл, это использовать программу ffprobe. Её можно «попросить» вернуть некоторую информацию о стриме, в том числе его разрешение. Но делается это далеко не моментально. Поэтому обработка 14-ти плейлистов, которые я задал, проходила так долго, что я не дождался и остановил процесс. В качестве решения этой трудности я просто распараллелил проверку разрешения стримов на несколько потоков, достигнув приемлимого времени ожидания обработки 14-ти плейлистов (~5 минут).</p><p>Довольный результатом, я решил, что было бы круто помочь таким же пользователям Smart TV, которые так же как я не видят ничего удобного в онлайн-кинотеатрах, дополнительно содержащих в себе телевидение. Можно было бы сделать веб-интерфейс, который бы проксировал прямое обращение к Web API, но фильтрацию по минимальному разрешению стрима, скорее всего, пришлось бы скрыть, раз это такая долгая операция. Или сделать платной возможностью и за счёт этого позволить нормальные вычислительные мощности сервера. Но до продолжения делания чего-либо по этому проекту руки не дошли, поэтому я отделался написанием README.md, с помощью которого можно самостоятельно запустить приложение локально и сконструировать себе персонализированный плейлист.</p><p>Ссылка на репозиторий проекта в GitHub:</p><p>И напоследок: желаю всем меньше «печальных» каналов =)</p><figure><img src="https://media.tproger.ru/uploads/2023/10/276549553-205e6819-79c3-4ec9-a139-122b9cf33ef7-scaled.jpg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Как я сделал карточный баттлер без конструктора колод — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195</link>
      <comments>https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Nikita Loskutov]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195</guid>
      <description><![CDATA[<p>Я делал карточную игру-баттлер около 15 лет, но так и не нашел для нее издателя. И все же я горжусь этим проектом.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-sdelal-kartochnyj-battler-bez-konstruktora-kolod-konkurs-pet-proektov-246195">Как я сделал карточный баттлер без конструктора колод — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Разработка игр]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 13 Oct 2023 11:33:49 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет, меня зовут Никита. Я разработчик уже около 15 лет. И все эти годы в свободное время я делаю баттлер FAWE.</p><p>Все началось еще в университете с лабораторной работы по искусственному интеллекту, где надо было написать свой ИИ. Но перед этим нужно было ответить на вопрос: «Какую задачу он будет решать?».</p><p>Ответ был найден быстро. С самого детства я обожал компьютерные игры и в то время просиживал за «Космическими рейнджерами», часами загружаясь перед мини-квестами, чтобы попробовать пройти по-другому. И вот я решил сделать подобие одного из таких мини-квестов и научить ИИ выигрывать.</p><p>В моей интерпретации два мага по очереди выбирали заклинание, после чего в зависимости от атаки и защиты наносился урон. Тот, у кого закончились жизни, проигрывал. Сеттинг был самым стандартным — магия стихий. Отсюда и название: F — fire, A — air, W — water, E — earth. FAWE.</p><p>В последующие годы я занимался разработкой разного рода софта в различных компаниях, а в свободное время делал новые версии все той же игры. Параллельно я приезжал к другу, который частенько выигрывает городские турниры по настолкам. Компанией мы обычно играли в «Манчкин Квест», а вдвоем в Magic: The Gathering. Сам же я пытался играть в Hearthstone, но довольно быстро самой игре я предпочел просмотр мировых чемпионатов по ней.</p><p>Почему? Как ни странно, самый очевидный ответ уже давно был мемом: «самая сильная карта — кредитная». Но даже если ты потратишь кучу денег или времени на самые сильные карты, даже если соберешь колоду, даже если выиграешь с ее помощью мировой чемпионат, выйдет новое дополнение — и придется выкинуть львиную долю своих карт и начать собирать колоду заново. Конечно, многим именно это и нравится в карточных баттлерах. Самим компаниям наверняка тоже.</p><p>Второй момент — я не очень люблю играть 1 на 1, мне куда интереснее играть компанией или командой хотя бы из двух человек.</p><p>Долгие годы меня не покидала мысль «надо что-то менять». В конце лета 2019 года я развелся с женой, уволился из зарубежной компании и самоизолировался в квартире еще до того, как это стало мейнстримом.</p><p>Первоочередной целью было — поставить жизнь на паузу и перевести дух. Второй — сделать наконец нормальную версию своей игры. Благо, за все эти годы у меня уже сложилось хоть и примерное, но представление о том, какой она должна быть. Были даже макеты из ASCII-графики. Оставалось самое простое — сделать игру.</p><p>За многие годы в разработке у меня уже накопился кое-какой опыт по оценке трудозатрат. Поэтому я проверил положение Меркурия, сверился с фазой Луны, подкинул кубик и выяснил, что весь проект займёт 2 месяца. Ещё 1 месяц я заложил на тестирование. «Не так уж и много. Сделаю, а потом наконец отдохну», — подумал я.</p><p>Следующие 1,5 года я работал примерно по 12–16 часов в день с парой выходных в месяц. Почти все от идеи до реализации делал сам, разве что арт заказал у одной студии. Этот маневр стоил мне большую часть бюджета, после чего игру во что бы то ни стало надо было закончить до конца 2020 года.</p><p>Параллельно я начал думать о монетизации и очень скоро выяснил крайне банальную вещь: без маркетинга и рекламы шансы на успех легко и непринужденно стремятся к нулю. Сам я разработчик, а не рекламщик и не маркетолог, поэтому единственный мой шанс — паблишеры, они же издатели.</p><p>Тогда я наивно полагал, что если у тебя есть оригинальная игра с крутым артом, то и от издателей отбоя тоже быть не должно. Все оказалось совсем не так. Самой большой проблемой, как ни странно, стал элеватор питч. Когда меня спрашивали, я обычно отвечал, что делаю Hearthstone в 2 клика. Людям этот питч нравился, но с издателями не прокатило, а Google Play и вовсе запретил мне упоминать чужие бренды.</p><p>В итоге игра так и не нашла своего издателя и осела в Google Play под названием FAWE: Enchanted Forest 30 декабря 2020 года.</p><p>За все это время накопилось достаточно фидбэка, чтобы понять: пытаясь сделать игру для обычных людей, я ориентировался на хардкорных гиков, в результате чего для первых она получилась слишком сложной, а вторых и так все устраивает в существующих баттлерах. Поэтому несколько месяцев назад вышла вторая часть под названием Let’s FAWE!. В ней геймплей полностью переработан с фокусом на обычных игроков. Но издателя я пока так и не нашел.</p><p><b>Технические детали</b>: наибольший интерес представляют боты. Зачастую, чтобы сделать их интересными и сложными, разработчики просто выдают им читы, например, отсутствие тумана войны или сбор двойных минералов. В своей же игре из академического интереса я сделал честных ботов, которые пользуются только той информацией, которой обладает обычный игрок, и не отличают его от других ботов. При этом, как показывает практика, играть с ними действительно сложно и интересно. Предлагаю челлендж: выиграть хардкорных ботов 5 раз подряд в режиме 1х1х1х1.</p><p><b>Стэк проекта</b>: Golang, Lua, Defold, SQLite.</p><p><b>Любимый кусочек кода</b>:</p><p>Адаптирует картинку в режиме Projection: FIXED_AUTO под любой размер экрана/окна.</p><p>Поиграть в последнюю версии моей игры можно <a href="http://townportal.xyz/">прямо на сайте</a>.</p><p>Для истории оставлю ссылки на оригинальную FAWE: Enchanted Forest:</p><ul><li>RuStore: <a href="https://apps.rustore.ru/app/com.cnaize.fawe">https://apps.rustore.ru/app/com.cnaize.fawe</a></li></ul><ul><li>Google Play: <a href="https://play.google.com/store/apps/details?id=com.townportal.fawe">https://play.google.com/store/apps/details?id=com.townportal.fawe</a></li><li>Steam: <a href="https://store.steampowered.com/app/1760510/FAWE_Enchanted_Forest">https://store.steampowered.com/app/1760510/FAWE_Enchanted_Forest</a></li></ul>]]></content:encoded>
    </item>
    <item>
      <title>Ретранслятор СМС-сообщений для релокантов – конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Sergey]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Собрал ретранслятор сообщений, который принимает сообщения и пересылает их на мессенджер, позволяя избежать платы за роуминг за рубежом.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/retranslyator-sms-soobshhenij-dlya-relokantov-konkurs-pet-proektov">Ретранслятор СМС-сообщений для релокантов – конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Arduino]]></category>
      <category><![CDATA[Raspberry Pi]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 13 Oct 2023 10:06:08 GMT</pubDate>
      <content:encoded><![CDATA[<p>В этом году я уехал учиться в другую страну, но у меня есть аккаунты в российских банках, на госуслугах и других интернет-порталах, требующих аутентификацию по СМС-коду. Как мне зайти на госуслуги, но не платить при этом за роуминг? Решение теперь есть – собрать устройство, которое будет принимать мои СМС-сообщения и ретранслировать их в мессенджер.</p><p>Привет! Я инженер-железячник, который любит, когда умные железки целиком и полностью ему подчиняются. Сегодня я расскажу, как я сделал себе пепелац, который получает смски и пересылает их мне через Интернет.</p><p>Я выбрал Raspberry Pi 2B и модуль SIM900 для Arduino – просто потому, что смог быстро купить их на Авито. Трудности начались ещё на этапе сборки устройства, потому что для модуля SIM900 нет нормального даташита, и очень сложно было понять, куда подавать питание, где находятся выводы последовательного порта, выводы управления. Вдобавок оказалось, что на одном из устройств перепутаны выводы RX и TX, и, не имея осциллографа, я очень долго не понимал, почему я не получаю ответов от модуля SIM900.</p><p>Но в итоге я собрал устройство и приступил к построению логики кода. Я написал код на языке Python, реализовал процесс ожидания получения новых СМС-сообщений как путём периодического опроса, так и путём реагирования на событие. В процессе получения сообщений я столкнулся с ещё одной проблемой, которую решить не смог. Дело в том, что очень длинные СМС разбиваются на несколько коротких, и каждое из них отсылается отдельно. Но как собрать их воедино? В описании команды CMGL я не нашёл признаков, которые позволили бы понять, что сообщение является частью более длинного сообщения.</p><p>Следующий вопрос – выбор такого мессенджера, через который можно пропихнуть сообщения через великий китайский файрвол. Whatsapp, Telegram сразу не подходят. Китайский WeChat даже не рассматривал – наслышан о его техподдержке и глюках вроде “операция не разрешена для этого аккаунта”. В итоге выбор пал на ВК. Я получил токен VK API и задействовал функцию отправки сообщений от имени сообщества.</p><p>Всё заработало. Я оставил устройство у моего друга, где оно лежит возле роутера. Код проекта доступен по ссылке:</p><p>Есть ещё одна проблема, которую я не смог решить, и сейчас прошу совета. Система стабильно работала с симкой Мотив, но когда я её заменил на МТС, то всё сломалось. После включения модуля SIM900 (неважно, кнопкой или пином), я получаю по UART такие сообщения:</p><p>Сообщения говорят об успешной инициализации SIM-карты. Но после этого устройство сразу отключается, красный светодиод гаснет. Иногда бывает, что после полного отключения питания устройство включается и некоторое время работает, но потом снова отключается, чаще всего после получения СМС.</p><p>Я подозреваю, что не хватает мощности источника питания. Устройство питается от одного источника на 5 вольт 2,4 ампера. Питание подаётся на Raspberry, а оттуда проводами на SIM900. Подавать питание напрямую на SIM900 не пробовал, так как нет подходящего адаптера. Как считаете, есть ли смысл его приобрести? Или могут быть другие причины?</p>]]></content:encoded>
    </item>
    <item>
      <title>Квест-бот — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kvest-bot-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kvest-bot-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Лена Капаца]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kvest-bot-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Разработала игру для участников конференции, повышающую "эфирное" время стендов и проверяющую игроков на профпригодность.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kvest-bot-konkurs-pet-proektov">Квест-бот — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[JavaScript]]></category>
      <category><![CDATA[Конференции]]></category>
      <category><![CDATA[SQL]]></category>
      <category><![CDATA[Боты]]></category>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Игра]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 12 Oct 2023 16:04:05 GMT</pubDate>
      <content:encoded><![CDATA[<p>Мой пет-проект, который даже смог выйти в продакшен: коллеги оценили идею развлечь участников конференции и дали возможность людям поиграть во время делового мероприятия. Если вы хотите собрать бота на JavaScript, эта статья поможет.</p><h2>Суть игры</h2><p>Участники конференции: руководители проектов, аналитики и прочие специалисты перемещаются от стойки к стойке, получают четырехзначные коды и отвечают на вопросы вроде этого:</p><p>По прохождении игры победителям вручают пакеты с подарками: кружка, Moleskin, шоколад и другие призы от партнеров на сумму около четырех тысяч рублей.</p><h2>Состав проекта</h2><p>Для краткосрочной работы телеграм-бота на JavaScript достаточно всего трех зависимостей: node-telegram-bot-api, SQLite для хранения данных игроков и util для обработки параллельных событий. По сути для каждого игрока создается копия игры со своими изменяемыми состояниями, поэтому единовременно минимальный сервер (Ubuntu 22.04 1,5 Гб RAM) может поддерживать игру почти сотни человек:</p><p>Зададим константы — они помогут запустить личного бота, чей токен отдает BotFather, а также укажут, с каким типом СУБД предстоит взаимодействовать:</p><p>Порядок методов и функций здесь сделать естественным не получится. JavaScript — интерпретируемый язык, и читает код построчно. То есть располагать объекты предстоит в таком порядке, чтобы к моменту запуска метода, обращающегося к базе данных, конфигурация была известна.</p><h2>Переходы между стендами, победы, проигрыши</h2><p>В этом участке кода мы проверяем прогресс игрока вне зависимости от того, новичок он или нет. Здесь же содержится обработчик для событий: «переход к следующему вопросу», «победа», «проигрыш», «изменение числа попыток».</p><p>Когда игрок вводит верный код, получает очередной вопрос:</p><h2>Проверка игрока</h2><p>Начинается игра с проверки пользователя. Если запись с таким ID Telegram уже есть в БД, то мы извлекаем число пройденных этапов. И затем высылаем новый вопрос:</p><p>Ниже привожу участок кода, отвечающий за запись данных игрока во время регистрации. Мы собираем имена, номера телефонов и Telegram ID. Стойки и вопросы миксуются, то есть у каждого игрока их набор индивидуальный. Это предотвращает игру толпой и минимизирует слив ответов:</p><p>Ппредусматриваем вывод ошибок в консоль:</p><p>Когда настало время игры, в мои обязанности входила лишь поддержка игроков. Проблем было немного, лишь три раза бот прекращал отвечать из-за ошибки, которую не удалось воспроизвести. В большинстве случаев перезапуск командой /start позволял продолжать квест.</p><h2>SQL через командную строку</h2><p>Я мониторила игроков, вычищала тестировщиков по окончании квеста через консоль (потому что было интересно освоить CLI-версию sqlite3).</p><p>Для чтения, записи, обновления и удаления было достаточно проложить путь к файлу.db:</p><p>И запустить предварительно установленную библиотеку:</p><p>Если нужно было проверить число игроков и донести призы впоследствии, подходил SQL-запрос, выдающий число победителей (stake – число пройденных вопросов от 0 до 10):</p><p>Хранилище отдавало такой результат:</p><p>Если речь шла о помощи игроку, застрявшему с ботом-молчуном, я пару раз дарила прохождение раунда:</p><p>Если в основной код проекта внедрялись изменения (с помощью Vim, прямо на месте), то с помощью process manager бот перезапускался:</p><h2>Заключение</h2><p>В мае 2023 года этот квест прошло около 150 человек, что весьма здорово, учитывая нулевые затраты на продвижение. И это увеличило время пребывания на стендах примерно на 11 часов.</p><p>Получается, людям действительно интересно проверять себя на прочность, отвечать на непростые, специфические вопросы и даже находить лазейки в моей логике. Нашлись игроки, которые увидели уязвимость в системе проверки победы. Мы решили оставить в качестве проверки демонстрацию скриншота с поздравлением о победе, и на этом сыграли два игрока: второпях проверять, реальный ли интерфейс Telegram, или просто скриншот, наши администраторы не стали. Прямо как на автомойке про 500 рублей: люди показывают мойщику лишь скриншот об оплате.</p>]]></content:encoded>
    </item>
    <item>
      <title>Hunt job. Как отвлечься, пока ищешь работу — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu</link>
      <comments>https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Little Fox]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu</guid>
      <description><![CDATA[<p>Написала приложение, которое помогает вести учет по всем компаниям, на вакансии которых я откликнулась, и отслеживать статус переговоров.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/hunt-job-ili-kak-otvlechsya-poka-ishhew-rabotu">Hunt job. Как отвлечься, пока ищешь работу — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Приложение]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 12 Oct 2023 12:33:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Сейчас нахожусь в поиске работы, ищу уже не первый месяц, и от этого немного депрессивно. Сразу скажу, что ищу не как разработчик, а как QA. В жизни и в душе я QA, а темными вечерами — адепт Python.</p><p>Для того, чтобы как-то отвлечь себя от неудач на фоне поиска работы, я решила написать небольшую программу. Она должна была не только помочь отвлечься, но и в целом помочь в поиске работы. Не знаю, есть ее аналоги или нет, не искала.</p><p>Суть программы очень проста: она помогает вести учет всем компаниям, на вакансии которых я откликнулась. Можно заносить данные, где была найдена вакансия, какой статус отношений – тех.собес, тестовое и т.п., также добавлять комментарии.</p><p>Кратко о том, что умеет программа:</p><ol><li>Добавлять новую компанию с данными: название, статус, где нашла вакансию, сколько раз откликалась, комментарий;</li><li>Обновлять данные по уже добавленной компании;</li><li>Удалять компании;</li><li>Искать компанию по названию;</li><li>Искать по статусу и количеству откликов;</li><li>Показывать все компании, которые занесены в БД.</li></ol><p>Реализовала проверку от дурака: прежде чем добавить компанию, программа проверяет, что ее еще нет.</p><p>Есть несколько всплывающих информационных окон: об успехе обновления/сохранения/удаления; предупреждение, что такая компания уже есть.</p><p>Есть дефолтные значения для селекторов и полей.</p><p>Для реализации UI использовала tkinter, данные хранятся во встроенной в Python БД – SQLite.</p><p>Так как при первом тестировании программы я случайно удалила все данные, которые уже занесла для тестов, то в итоговой версии программы я настроила бэкапы.</p><p>Программа пишет основные данные в основную БД, а когда работа с программой завершается, она проводит проверку данных основной таблицы с данными из последнего записанного бэкапа. Если они различаются, программа создает новый бэкап, а если нет, то ничего не делает. Ну и при первом завершении работы, конечно, создает первый бэкап.</p><p>Программа работает не из среды, собрала для нее билд, чтобы каждый раз не запускать PyCharm. Поэтому теоретически программой может пользоваться любой, кто захочет.</p><p>Есть еще пара идей, что можно добавить в программу, но в целом она и так уже выполняет свою функцию. Плюс, я запускаю ее уже как exe-файл, а не из среды, это позволяет мне не потерять все данные при манипуляциях с логикой.</p><p>В процессе написания кода мне помогал ChatGPT (у меня бесплатная версия) советом, вредным советом или просто обсуждением. На самом деле, как собеседник для обсуждения проекта и его нюансов ChatGPT очень даже ничего. Особенно если учитывать, что Python я учу не регулярно и с большими перерывами, а начала учить только где-то в прошлом году.</p><figure><img src="https://media.tproger.ru/user-uploads/91071/2023-10-12/89a74348-ec33-4da0-bd8c-4a464033d257.png" alt="" /><figcaption>Стартовое окно с подсчетом общего количества компаний в БД</figcaption></figure><figure><img src="https://media.tproger.ru/user-uploads/91071/2023-10-12/961d215c-4da9-4bef-8676-eaf0bf07a5d7.png" alt="" /><figcaption>Окно добавления компании<br /></figcaption></figure><figure><img src="https://media.tproger.ru/user-uploads/91071/2023-10-12/8bad6474-c0c9-4543-964a-fe52f0ae5ebe.png" alt="" /><figcaption>Окно поиска информации по параметрам</figcaption></figure><figure><img src="https://media.tproger.ru/user-uploads/91071/2023-10-12/e11aa872-75eb-4ea0-9b0f-de0be83200d2.png" alt="" /><figcaption>Окно поиска компании по названию<br /></figcaption></figure><p>Вот как-то так, спасибо всем, кто прочитал!</p><p>PS: ссылка на GitHub</p>]]></content:encoded>
    </item>
    <item>
      <title>Три библиотеки для React по цене одной — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Sultan]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Написал три библиотеки для React, используя JavaScript: функции вместо JSX, управление приложением с использованием хуков и CSS в React.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/tri-po-cene-odoj-konkurs-pet-proektov">Три библиотеки для React по цене одной — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[JavaScript]]></category>
      <category><![CDATA[React]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Библиотеки]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 12 Oct 2023 11:39:01 GMT</pubDate>
      <content:encoded><![CDATA[<p>Мне кажется, что я начинаю свои проекты только из-за редмишек (read me). Ну знаете, как в начале придумать проблему, а потом её героически победить. Это как TDD, но только здесь не тесты, а редми вперед, прямо как функциональщики программируют, задом наперед.</p><p>Короче говоря, README — это своеобразный план, примерно как бэкендеры и фронтендеры согласовывают интерфейс до начала разработки. Здесь то же самое, но только договор с самим собой. План нужен для уверенности, что всё продумано и схвачено. Не могу не <a href="https://www.youtube.com/clip/UgkxPXwtHsFm3oSpMpA_E2gpUu0UYWvW5D4K">процитировать Лапенко</a>:</p><blockquote>Я на сто процентов уверен, что этот план должен сработать. Я вот когда его придумал, потом так в зеркало посмотрел на себя и подумал какой же я молодеец, какие же плааны я придумываю…</blockquote><p>А мой план таков: в рамках этой статьи я хочу поделиться с вами своим личным опытом освоения этого подхода.</p><p>Пет-проекты отличаются от обычных тем, что их делают с любовью. Пет-проекты — это не про количество, а скорее про качество. Именно поэтому я решил представить вам сразу три своих проекта. Согласен, не бьется с логикой, но это просто попытка продать три продукта по цене одной.</p><p>Прежде всего, хочу представиться. Меня зовут Султан, хотя это и звучит словно из какой-то сказки, но это моё настоящее имя. Вашему вниманию предлагаю библиотеки, написанные мной на JavaScript для React. Если вам это интересно, прошу под кат.</p><h2>Stylin</h2><figure><img src="https://media.tproger.ru/user-uploads/90257/2023-10-11/6f1bb383-3c9b-4518-aac3-2f0d6ca229b8.gif" alt="" /></figure><p>Это, наверное, самый быстрый и элегантный способ создания стилизованных компонентов React. С помощью этой библиотеки можно импортировать компоненты непосредственно из файлов CSS:</p><p>На входе получаем компонент, который полностью стилизован и типизирован, а его внешний вид (стили CSS) управляется через свойства компонента.</p><p>И тут самое место задать вопрос: “Карл, как?! Как эта магия работает?”.</p><p>Одно дело — это написать в редми, другое дело — это реализовать. Благо, у меня есть фантазия и большой опыт разработки. Мне удалось найти решение в виде CSSDoc, это как <a href="https://ru.wikipedia.org/wiki/JSDoc">JSDoc</a>, но только для CSS. Так вот такие аннотации необходимо добавить перед стилями компонента:</p><p>А чтобы всё это заработало, мне пришлось написать специальные загрузчики для Webpack:</p><p>Загрузчики преобразуют аннотации в компоненты React и генерируют типы TypeScript. В зависимости от значения свойства компонента, соответствующий CSS класс будет присвоен значению className. Ниже приведенный код – это упрощенный результат конвертации для общего понимания.</p><p>Все эти преобразования и извлечение CSS стилей происходят во время сборки проекта. Это означает, что стили не создаются динамически во время выполнения приложения, как это делается в библиотеках css-in-js. Отсюда и скорость: отрисовка компонентов происходит быстро.</p><p>В целом, как всё это работает, можно посмотреть в этой <a href="https://codesandbox.io/p/sandbox/github/sultan99/cards/tree/main">демке</a>. Более подробную информацию об этой библиотеке можно получить в <a href="https://github.com/sultan99/stylin">README</a> или в этой <a href="https://habr.com/ru/articles/545994/">статье</a>. Однако статья написана в пафосной форме, я был молод и не совсем понимал, что писал, в общем я предупредил.</p><h2>Holycow</h2><figure><img src="https://media.tproger.ru/user-uploads/90257/2023-10-12/97bbf43f-3d87-4ed7-a1f5-50d58a63f854.gif" alt="" /></figure><p>Если предыдущая библиотека блестела своей новизной идеи, то эта весьма банальная. Однако техническая сторона гораздо сложнее, от меня потребовалось очень много умственных усилий, чтобы сбалансировать небольшой размер пакета, с изобилием фич, производительностью и удобством использования.</p><p>Итак, представляю вашему вниманию библиотеку <a href="https://github.com/sultan99/holycow">holy state</a> для управления состоянием React-приложения с использованием хуков. Эту библиотеку можно рассматривать как утилитку по созданию хуков, которые могут хранить состояние вне компонентов React. Самая интересная часть заключается в том, что она работает без использования провайдеров контекста, observables, селекторов или HOC-коннекторов.</p><p>Основные особенности</p><ul><li>Библиотека не имеет внешних зависимостей. <a href="https://bundlephobia.com/package/@holycow/state@1.1.0">Размер Gzip: ~1.6kb</a>.</li><li>Хуки могут быть использованы за пределами компонентов React.</li><li>Жадная отрисовка. Компоненты перерисовываются только при обновлении значений.</li><li>Вычисляемые значения с кэшированием и вложенностью хуков.</li><li>Асинхронные экшены.</li><li>Подписка на изменения состояния.</li><li>Поддержка событийно-ориентированной архитектуры.</li><li>Гармония с функциональным программированием.</li><li>Полная типизация TypeScript.</li></ul><p>При создании этой библиотеки я стремился сделать умный рендеринг, при котором компонент будет отрисован только в случае изменения используемых им переменных из хука. В противном случае, отрисовка не должна произойти. Следующим важным шагом было предоставить удобный механизм обновления состояния хука без необходимости в спредах объектов и клонировании.</p><p>А для более сложных задач по обновлению состояния, доступны экшены – место для размещения бизнес-логики, такой как валидация, сетевые операции и прочего:</p><p>Вычисляемые значения с поддержкой кэширования:</p><p>Поддержка событийно-ориентированной архитектуры позволяет разделять код и загружать его с помощью ленивой загрузки. Такой Redux way подход, но в более простой форме.</p><p>Следующая библиотека предназначена для очень специфичных кейсов. Если вам не нравится JSX или по каким-то причинам вы не хотите использовать его в своих проектах, то следующая библиотека создана специально для вас.</p><h2>React on lambda</h2><figure><img src="https://media.tproger.ru/user-uploads/90257/2023-10-12/17375db2-77d8-4d47-8ce7-96a46e4afbd5.png" alt="" /></figure><p>Всё очень просто, вместо JSX используем функции. Чтобы что?</p><p>А просто, для фана:</p><p>Конечно, не стоит серьезно относиться к использованию символа λ (лямбды). Он был использован для привлечения внимания и создания шума вокруг. Вместо него можно использовать любой другой допустимый символ. Основное отличие этой библиотеки от подобных заключается в том, что все функции каррированы и удобно программировать в <a href="https://medium.com/dailyjs/functional-js-7-point-free-style-b21a1416ac6a">point free</a> стиле.</p><p>Если эта библиотека вас заинтересовала, то можно глянуть <a href="https://codesandbox.io/s/jjlo9m5jq5">демку</a> или сходить на <a href="https://github.com/sultan99/react-on-lambda">репозиторий</a>.</p><p>Тех, кого я еще не сбил с толку своими проектами, относительно RDD. Ну, о том, как я начинаю пет-проекты через README, то боюсь вас огорчить. Я, как и любой программист, не люблю писать редмишки и делаю это на последнем этапе (за <a href="https://github.com/sultan99/sql-fns">редким исключением</a>).</p><blockquote>Мне один доктор все объяснил,RDD – это миф о загробной жизни. Кто туда попадает, тот не возвращается.</blockquote><p>Берегите себя и прошу вас: не ешьте на ночь сырых помидоров!</p>]]></content:encoded>
    </item>
    <item>
      <title>Локальный деплой проектов в пару кликов — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Sergey Voloshin]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Разработал консольную программу для автоматизированного локального деплоя проектов в пару команд, использующую Docker.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/lokalnyj-deploj-proektov-v-paru-klikov-konkurs-pet-proektov">Локальный деплой проектов в пару кликов — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Docker]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 12 Oct 2023 10:31:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Как можно быстро развернуть сайт на своем компьютере и использовать все преимущества локальной разработки?</p><p>“Но ведь есть же Docker!”, — скажете вы. И будете совершенно правы, речь пойдёт именно о контейнеризации проектов. Только добавим немного автоматизации. =)</p><h2>Как это было</h2><p>Да, сначала был Docker. И было здорово, создаём docker-compose файл с php+mysql+nginx, пробрасываем файлы в контейнер, заливаем базу данных и кодим новые фичи для нашего проекта.</p><p>Но на весь этот процесс при первом локальном развороте сайта уходило слишком много времени. Да ещё и одновременно можно запустить только один сайт (либо настраивать постоянно конфигурацию Nginx).</p><h2>Автоматизируем</h2><p>Как и большинство разработчиков, я ленив, и если есть возможность что-то автоматизировать, я обязательно это сделаю.</p><p>Так и родился мой pet-проект, который по задумке должен был в пару команд в терминале развернуть сайт локально.</p><p>Назвал я его <b>DL</b> (Deploy Local). И представляет он из себя небольшую консольную утилиту, написанную на Go — обёртку над docker, которая скачивает по SSH типовой проект с сервера и поднимает всё локально в контейнерах. Правда, получилось чуть больше, чем пара команд, но раз уж автоматизировать, то делать это на максималках. =)</p><h2>Что умеет</h2><p>На данный момент программа при запуске деплоя с сервера умеет автоматически определять CMS WordPress, Bitrix и фреймворк Laravel. Но при небольшой настройке будет работать с чем угодно.</p><p>DL может запускаться на Linux, MacOS и Windows (через WSL2), позволяет одновременно поднять локально несколько проектов, умеет перехватывать почту, отправленную через PHP, генерирует самоподписанные ssl-сертификаты для локальных доменов и очень легко кастомизируется обычными docker-compose.yaml файлами.</p><h2>Пару команд</h2><p>Для работы нужен только Docker Engine и docker-compose (v2). Вся конфигурация настраивается через .env файл в несколько строк.</p><p>Проще всего установить dl через запуск bash-скрипта, но для Linux есть также <a href="https://local-deploy.github.io/ru/getting-started/install">варианты установки</a> через apt и pacman.</p><p>После установки запускаем необходимые для работы локальные сервис-контейнеры (portainer, traefik, mailhog):</p><p>И вот пример самой простой конфигурации в .env файле:</p><p>Сохраняем файл, запускаем скачивание проекта (должен быть прокинут ваш публичный ssh-ключ на сервер): dl deploy.</p><p>Поднимаем его локально: dl up.</p><p>Вы великолепны!</p><p>Теперь ваш сайт можно открыть в браузере по ссылкам, которые отобразяться в консоли. В примере выше это будет два варианта: либо site.com.localhost, либо site.com.127.0.0.1.nip.io.</p><p>На данный момент мой pet-проект все ещё обрастает новыми функциями, но уже имеет стабильные релизы и готов к использованию.</p><p>Буду рад, если эта утилита сделает вашу локальную разработку простой и продуктивной. =)</p><ul><li><a href="https://github.com/local-deploy/dl">Github</a></li><li><a href="https://local-deploy.github.io/ru/">Документация</a></li></ul>]]></content:encoded>
    </item>
    <item>
      <title>Очередной фреймворк на PHP  — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Неопознанный программист]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Создал PHP-фреймворк для создания веб-проектов DeltaFramework, который должен облегчить жизнь верстальщикам.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/ocherednoj-frejmvork-na-php-konkurs-pet-proektov">Очередной фреймворк на PHP  — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[PHP]]></category>
      <category><![CDATA[Фреймворки и библиотеки]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 12 Oct 2023 09:35:34 GMT</pubDate>
      <content:encoded><![CDATA[<p>Всем привет. Сразу предупреждаю, что чукча не писатель, поэтому главное не потерять нить повествования.</p><p>Иногда, когда становилось скучно и рабочие проекты пилить не хотелось, я садился за разработку собственного велосипеда. Причем архитектура была выбрана не то чтобы правильная, а наиболее удобная для коротания времени за написанием кода. Где-то встречались костыли, где-то некие ноу-хау.</p><p>Мой велосипед представляет из себя некий PHP-фреймворк для создания веб-проектов.</p><p>На текущий момент он представляет следующий функционал:</p><ul><li>Авторизация;</li><li>Регистрация;</li><li>Роли пользователей;</li><li>Верификация E-Mail;</li><li>Рассылки почты;</li><li>Поддержка шаблонов почтовых отправлений;</li><li>Менеджер очереди заданий;</li><li>Шаблонизатор;</li><li>Поддержка маршрутизации;</li><li>REST API;</li><li>Кеширование;</li><li>Логирование;</li><li>Работа с файлами;</li><li>Миграции;</li><li>Captcha;</li><li>DDoS Guard (basic).</li></ul><figure><img src="https://media.tproger.ru/user-uploads/25296/2023-10-11/fa2ba81e-ed8b-4875-bda4-0a0ecb651129.png" alt="" /><figcaption>Одна из фронтовых страниц демосайта, шаблонизатор Twig</figcaption></figure><p>Пользовательская часть построена с использованием шаблонизатора Twig. Я посчитал, что это приемлемо и, вероятно, в дальнейшем облегчит жизнь верстальщикам.</p><p>Админка же, напротив, сделана без использования каких-либо шаблонизаторов (привет, Битрикс). Местами реализации ужасны, местами из глаз идет кровь, но оно работает. Сделано так, скорее, только на время альфа-версий.</p><p>Функционал пилится, некоторые идеи приходят в неудобное время, и чтобы они появились в качестве реализации, я иногда грешу простыми и топорными реализациями с надеждой на причесывание в дальнейшем. Техдолг копится, как говорится…</p><figure><img src="https://media.tproger.ru/user-uploads/25296/2023-10-11/bb9aef82-8ebb-4248-b3f9-0e47ad049bbf.png" alt="" /><figcaption>Страница авторизации в панели администратора</figcaption></figure><p>Из интересного также есть функционал обработки роутов (маршрутов) для фронтовой части сайта с поддержкой динамических составляющих.</p><p>Реализована поддержка многосайтовости с подключением локального файла конфигурации (когда мы линкуем папку с ядром к другому проекту и создаем конфиг для нового проекта). А для облегчения развертывания используются миграции через Phinx.</p><p>Для большей гибкости реализованы роли пользователей для контроля доступа к каким-либо частям проекта. Там же есть отдельные роли как для администратора с максимальными правами и базовой роли пользователя, так и для менеджера с урезанными правами (базовый доступ к админке). Накручивать можно по желанию что угодно. Кстати, имеется функционал логирования, что очень облегчает поиск виновного, когда кто-то или что-то косячит. ?</p><p>Также реализовал функционал диспетчера очереди с поддержкой приоритетов, воркеров и повторного выполнения в случае возникновения ошибок. Использоваться может, например, для рассылки писем, обработки изображений и в целом для всего, что требует времени больше, чем пользователь готов ждать при загрузке страницы (рендерим страницу, а какие-то тяжелые задачи отдаем очереди на обработку, и все счастливы).</p><p>В качестве мониторингов был выбран Сентри как основной и Телеграм как дублирующий. Функционал второго также реализован в данном проекте.</p><figure><img src="https://media.tproger.ru/user-uploads/25296/2023-10-11/2925401a-655e-4fd3-ba59-96abc5119442.png" alt="" /><figcaption>Пример уведомления о возвращении повисшего задания очереди в работу</figcaption></figure><p>Кодовая база на данный момент ведется на Гитлабе, но интереса ради продублировал репозиторий на Гитхаб с публичным доступом. Мало ли, кому-то данный велосипед зайдет. ?</p><p>Ссылка на репозиторий проекта:</p>]]></content:encoded>
    </item>
    <item>
      <title>Bginfo ломает обои? Напиши свой и сделай его лучше — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/bginfo-lomaet-tvoi-oboi-napiwi-svoj-i-sdelaj-ego-luchwe-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/bginfo-lomaet-tvoi-oboi-napiwi-svoj-i-sdelaj-ego-luchwe-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Дмитрий Беликов]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/bginfo-lomaet-tvoi-oboi-napiwi-svoj-i-sdelaj-ego-luchwe-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Как я создал аналог программы bginfo, которая выводит информацию о системе и пользователе на рабочий стол, но не ломает смену обоев.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/bginfo-lomaet-tvoi-oboi-napiwi-svoj-i-sdelaj-ego-luchwe-konkurs-pet-proektov">Bginfo ломает обои? Напиши свой и сделай его лучше — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Windows]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 11 Oct 2023 10:21:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет, уважаемый читатель! Меня зовут Дмитрий, я инженер техподдержки со стажем 10 лет. Самостоятельно изучаю Рython. Хочу сменить работу в техподдержке на разработку.</p><p>Сегодня я хочу рассказать о своем пет-проекте, который родился в голове, когда я устроился в одну крупную фирму инженером техподдержки.</p><p>Думаю, многим знакома такая программа, как BGinfo. Если не знаете, то эта программа выводит информацию о ПК на рабочий стол.</p><p>После начала работы в компании я понял, что данная программа довольно удобная: можно сразу узнать имя ПК, пользователя, домен, ip адрес и прочее, что помогает быстрее диагностировать проблемы, а также проводить инвентаризацию.</p><p>Спустя какое-то время я обнаружил у этой программки неприятный баг. Когда подключены два и более мониторов, после срабатывания BGinfo ломалось изображение, и приходилось руками менять положение с режима “Замостить” на “Заполнение”.</p><p>Но это еще полбеды. На просторах интернета я нашел программу Bing Wallpapper, которая запала мне в душу. Принцип простой: каждый день эта программа ставит на рабочий стол картинку дня, там и красивые пейзажи, и животные. Ну и какое-никакое разнообразие.</p><p>Так вот, BGinfo отключает автоматическую смену обоев. Так и родилась идея проекта.</p><p>Проект я назвал максимально “круто” — Corporate_Wallpaper_and_sys_info.</p><p>При начале разработки я подумал, что, в принципе, ничего сложного в этом проекте нет, и с места в карьер прыгнул в PyCharm.</p><h2>Параметры ПК</h2><p>Начал я с того, какие параметры выдает нам BGinfo, а именно: Host Name, Serial Number, IP Adress, Machine Domain, Logon Domain, Logon Server, User Name, OS Version, Build Number, OS Build, SCCM Client Version, Edge Version.</p><p>И тут понеслось гугление, была написана функция get_pc_info, в которой собиралась вся информация о ПК.</p><p>Часть информации получалась из командной строки, часть из реестра, часть из свойств файла .exe, как например, информация о версии MS edge.</p><p>Использовал библиотеки time, winreg, platform, socket, os, subprocess.</p><p>Приведу пример нескольких запросов, т.к. функция довольно длинная:</p><p>А самое интересное, с чем столкнулся — это вычисление аптайма. Сперва делаем запрос через powershell времени последней загрузки. Далее удаляем лишние символы и приводим к стандарту библиотеки datetime. После этого получаем текущее время и вычитаем из текущего времени время загрузки.</p><h2>Создание waterpark</h2><p>После сбора параметров встал вопрос, как же все это дело отобразить на мониторе. И тут нашлась библиотека Pillow, которая умеет редактировать изображения.</p><p>Прочитал кучу статей и документации и смог создать Watermark с информацией о ПК.</p><p>В коде выше мы создаем изображение с прозрачным фоном и записываем все полученные параметры из функции выше. После вставляем в этот watermark логотип компании, а цельное изображение вставляем в картинку для рабочего стола.</p><p>При вставке логотипа компании столкнулся с тем, что когда я вставлял  изображение .jpg в картинку с прозрачным фоном, то фон с прозрачного менялся на черный. Решилась эта задачка довольно просто:</p><p>При вставке логотипа, логотип нужно конвертировать в RGBA.</p><p>В общем итоге мы получили картинку, какая и была у пользователя, но теперь с watermark. Осталось только установить на рабочий стол. Быстрый поиск выдал простую функцию:</p><p>В зависимости от разрядности системы функции отличаются, и пришлось добавить проверку разрядности системы.</p><p>Но на этом я не остановился и решил добавить автосмену обоев: обои должны быть каждый день новые.</p><p>Как я выше писал, мне очень понравилась программа bing wallpaper. Пришлось спарсить страничку bing и сохранить изображение.</p><h2>Настройки</h2><p>А что, если пользователь не захочет менять обои? Я начал думать над созданием config файла. Сначала config сделал в формате .py. Удобно, можно его просто импортировать и работать с ним, но я отказался в пользу .ini и библиотеки ConfigParser.</p><p>В конфиг я добавил месторасположение сохранения картинки Bing и логотипа компании, добавил автосмену обоев.</p><p>Подключил все это через функцию read_config и библиотеки ConfigParser.</p><p>Тут же возникла проблема: а если не будет конфига, что делать? Написал функцию проверки конфига, и если его нет, то он будет создан.</p><p>Тут мне понадобилась функция getcwd() библиотеки os, которая возвращает путь до запущенного файла, чтобы в этой директории создать конфиг и, тем самым, сделать программу портативной.</p><p>Если у пользователя автосмена выключена, тогда нет смысла скачивать изображение, а достаточно получить путь до изображения, которое сейчас установлено у него на рабочем столе. Сделал функцию проверки автосмены:</p><p>Получаем путь до обоев пользователя:</p><p>Используем путь до обоев, чтобы вставить на него наш логотип и установить на рабочий стол, как мы это делали в коде ранее.</p><p>Для постоянной работы создал цикл while, добавив туда запуск функций и time.sleep(3600) для ежечасного обновления информации. Ресурсов потребляет не много.</p><p>Во время создания программы я сменил место работы и предложил идею своей программы руководству на новом месте, ранее подобные программы компания не использовала.</p><p>Идея руководству понравилась, и программу пообещали внедрить в компании.</p><p>Спасибо, что дочитали до конца. Это моя первая статья, прошу сильно не пинать.</p><p>Да и программировать я только учусь, в окружении разработчиков у меня нет, все писалось, тестировалось и улучшалось самостоятельно.</p><p>Возможно, я что-то сделал неправильно или неэстетично, но этот проект позволил мне поработать с файловой системой Windows, изучить новые библиотеки и столкнуться с различными нюансами разработки. После разработки я разобрался в auto-py-to-exe, чтобы запуск совершался одной кнопкой, и покопался в реестре, дабы добавить программу в автозапуск.</p><p>Если вам понравился проект, и вы хотите посмотреть его полностью, то вот ссылка на GitHub:</p>]]></content:encoded>
    </item>
    <item>
      <title>Как я запустил агрегатор фестивального кино — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-zapustil-agregator-festivalnogo-kino-konkurs-pet-proektov</link>
      <comments>https://tproger.ru/articles/kak-ya-zapustil-agregator-festivalnogo-kino-konkurs-pet-proektov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Dmitry Kuchev]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-zapustil-agregator-festivalnogo-kino-konkurs-pet-proektov</guid>
      <description><![CDATA[<p>Рассказ о разработке агрегатора фестивального кино, который помогает не ждать выхода фильма несколько лет после фестиваля.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-zapustil-agregator-festivalnogo-kino-konkurs-pet-proektov">Как я запустил агрегатор фестивального кино — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Фильмы]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 11 Oct 2023 09:31:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Я люблю кинофестивали и даже помогаю организовывать один из них — опен-эйр фестиваль анимации «Бессонница».</p><p>И опыт посетителя, и опыт организатора говорят мне одно и то же: люди хотят пересматривать фестивальные фильмы и делиться ими с друзьями. Особенно это относится к короткометражкам.</p><p>Но это практически всегда невозможно: фильмов нет в интернете, пока не закончится их фестивальный тур. То есть в течение нескольких лет фильм доступен ТОЛЬКО на фестивалях, и нет никакого способа получить уведомление о том, когда он появится в онлайне.</p><p>В общем, мне это надоело, и в этом году я запустил <a href="https://vurchel.com/">Vurchel.com</a> – пет-проект, который должен решить эту проблему.</p><figure><img src="https://media.tproger.ru/user-uploads/90966/2023-10-10/53509f41-24b6-46da-9f49-6879d4f8ca08.png" alt="" /><figcaption>Первая страница Vurchel.com</figcaption></figure><p>Наша основная цель — собрать фестивальные фильмы со всего мира на одной платформе. Мы не хостим сами видео, только встраиваем сторонние плееры или даем ссылки на стриминги.</p><p>Зайдя на страницу фильма, который пока еще недоступен, пользователь может на него подписаться, нажав на сердечко возле названия, и получить уведомление, когда этот фильм станет доступен для просмотра онлайн.</p><h2>Волонтерский проект</h2><p>Vurchel — открытый волонтерский проект. Как вики, только про фестивальное кино.</p><p>Нас никто не финансирует, все затраты идут из моего кармана. Если вы вдруг знаете хорошего человека, который бы хотел финансово поддержать этот проект в сфере культуры — свистите!</p><p>Мы ищем волонтеров: нужна помощь SEO-специалистов, backend (PHP) и frontend разработчиков, продакт-менеджеров, продакт-дизайнеров.</p><p>И, конечно, очень нужны <b>Vurchel Hunters</b>: люди, которые ищут инфу о фильмах в интернете и добавляют ее на сайт — то есть, наполняют Vurchel.com контентом.</p><p>Также <a href="https://vurchel.com/donate">накидать донатов</a> — всегда хорошая идея!</p><h2>Как организована работа</h2><p>Мы отслеживаем фестивальные новости и, как только фестиваль публикует программу показов, мы берем ее в работу: для каждого фильма фестивальной программы создается задача на доске в Coda.</p><p>Coda была выбрана из-за двух главных ее особенностей: бесконечное количество редакторов в доке (бесплатно!) и возможности по тонкой настройке всего, что надо тонко настроить. ✨</p><figure><img src="https://media.tproger.ru/user-uploads/90966/2023-10-10/59e19779-dfaa-4958-b820-78f3091a98d4.png" alt="" /><figcaption>Доска с задачами в Coda</figcaption></figure><p>Затем Vurchel Hunters добавляют информацию о каждом фильме в базу данных, а потом из этих фильмов собирается программа фестиваля на Vurchel.com.</p><p>Таким образом, Vurchel.com — это агрегатор фильмов, фестивалей и фестивальных программ.</p><p>Прямо сейчас на Vurchel доступно более 2500 фильмов. Большая часть из них — анимация, все фильмы фестиваля «Бессонница» за 10 лет.</p><p>Сейчас мы начинаем планомерную работу по добавлению свежих программ других фестивалей — не только анимации. ?</p><h2>Что под капотом</h2><p>Быстрый результат был для меня в приоритете, поэтому я взял знакомую, простую в разработке и, в то же время, богатую по возможностям CMS <a href="https://expressionengine.com/">ExpressionEngine</a>.</p><p>Вся разметка генерируется на сервере шаблонизатором от CMS. На фронтенде только чуть ванильного JS.</p><p>Кроме того, с помощью сервисов автоматизации, API и вебхуков Vurchel.com общается с другими сервисами: высылает инвайты на доску Coda только что зарегистрировавшимся волонтерам, сообщает Vurchel Hunters о достижении ими новых уровней (у нас есть геймификация с лычками в зависимости от вклада) в волонтерские чаты Discord и Telegram, отправляет уведомления подписчикам фильмов.</p><h2>Планы</h2><h3>Скоро</h3><p>Прямо сейчас первая страница сайта — это просто «бесконечная» лента недавно добавленных фильмов, доступных в онлайне, однако в ближайшем будущем там появятся редакционные материалы: рекомендации от кинокритиков, хайлайты лучших фильмов и прочее. Сайт будет говорить посетителю, что нужно посмотреть прямо сейчас и, самое главное, почему.</p><h3>Попозже</h3><p>В бэклоге — тонны идей о продуктах и сервисах, гипотез о способах продвижения фильмов среди широкой аудитории. Однако к тестированию и реализации этих идей мы приступим только когда у нас будет достаточный объем фильмов, более широкая аудитория и, конечно, ресурсы на все это.</p>]]></content:encoded>
    </item>
    <item>
      <title>Как я создал змейку на Python — конкурс пет-проектов</title>
      <link>https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke</link>
      <comments>https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Nikolay]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke</guid>
      <description><![CDATA[<p>Как я разработал змейку на Python без использования графических библиотек для участия в конкурсе по программированию для начинающих.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-sozdal-zmeyuku-na-zmeyuke">Как я создал змейку на Python — конкурс пет-проектов</a>»</p>]]></description>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 11 Oct 2023 08:53:18 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет, я – разработчик ботов для социальных сетей. Не миллиардер и не Тони Старк, просто обычный Python-разработчик.</p><p>Два года назад я решил взяться за создание своего пет-проекта. И хотя многие начинают с классического “Hello World”, я выбрал другой путь. Мой выбор пал на создание игры “Змейка”, и в этой статье, я поделюсь с вами своим опытом.</p><p>История началась давно, когда я участвовал в городском конкурсе по программированию для начинающих. Среди сложных заданий была и “Змейка”. Это задание так и осталось в моей памяти, и спустя время я решился воплотить его в жизнь, сидя дома с чашкой чая.</p><p>В то время я не был опытным программистом, поэтому идея создания игры казалась для меня сложной. Конечно, я начал с того, что загуглил, чтобы узнать, не написал ли уже кто-то подобную игру. Но оказалось, что либо никто не делал такую версию, как мне хотелось, либо существующие решения использовали стандартные средства ввода для выбора хода змейки</p><p>Моя задача заключалась в том, чтобы создать консольную версию “Змейки” без использования графических библиотек. Я хотел сделать игру доступным для всех.</p><p>Создание игры “Змейка” на Python стало для меня увлекательным и образовательным процессом. Я погрузился в мир разработки игр и научился решать разнообразные программистские задачи.</p><p>Свой проект я выложил на <a href="https://github.com/febdaynik/console-snake">GitHub</a>, можно посмотреть и пощупать всем желающим.</p>]]></content:encoded>
    </item>
    <item>
      <title>Лучший пет-проект 2023: запускаем конкурс</title>
      <link>https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs</link>
      <comments>https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs</guid>
      <description><![CDATA[<p>Tproger запускает новый конкурс на лучший пет-проект среди наших читателей. Напишите статью и получите славу, обожание и мерч от редакции.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/luchwij-pet-proekt-2023-zapuskaem-konkurs">Лучший пет-проект 2023: запускаем конкурс</a>»</p>]]></description>
      <category><![CDATA[Конкурс Tproger]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Лучший пет-проект 2023]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 10 Oct 2023 08:00:03 GMT</pubDate>
      <content:encoded><![CDATA[<p>Привет! Мы запускаем новый конкурс на лучший пет-проект среди наших читателей.</p><p>Вот, что нужно сделать, чтобы принять участие. Зайдите в <a href="https://tproger.ru/editor">редактор</a>, напишите статью о вашем пет-проекте и отправьте её на модерацию.</p><p>Взамен вы получите славу, обожание публики и мерч от редакции Tproger.</p><h2>Требования к материалу</h2><p>Статья должна включать пару слов об авторе, название и описание проекта и ссылку на GitHub.</p><p>В заголовке укажите, что ваша статья написана для участия в конкурсе, чтобы мы не упустили ее. Пример:</p><p>Будет плюсом, если вы расскажете о процессе работы: как вам пришла идея проекта, с какими трудностями вы столкнулись, как вы их решили и какую пользу извлекли из опыта по завершении работы.</p><p>Совсем классно, если вы приведете примеры кода, объясните, как тот работает, и расскажете об использованных библиотеках и инструментах.</p><h2>Этапы конкурса</h2><p>Конкурс будет проходить в два этапа.</p><h3>Первый этап</h3><p>Со 10 по 30 октября вы пишете статьи о своих пет-проектах и публикуете их на сайте.</p><p>Через три недели, 30 октября, редакция Tproger выберет проекты, которые больше всего понравились читателям. Критерии оценки — количество просмотров, лайков и комментариев под статьями участников на сайте.</p><h3>Второй этап</h3><p>30 октября стартует голосование на сайте, в ходе которого пользователи смогут выбрать лучший пет-проект.</p><h2>Призы для участников</h2><p>Все участники, которые пройдут первый этап, получат призы.</p><ul><li>С 1 по 5 место: худи с логотипом Tproger и стикеры от редакции.</li><li>С 6 по 10 место: футболки с логотипом Tproger и стикеры.</li></ul><h2>Заключение</h2><p>Не бойтесь рассказать о себе и своих достижениях, пишите легко и непринуждённо, и тогда ваши труды будут вознаграждены. 🙂</p><p>Подпишитесь на тэг <a href="https://tproger.ru/tag/pet-projects-2023">Лучший пет-проект 2023</a>, чтобы не пропустить статьи от участников конкурса и следить за обновлениями в личной ленте.</p><p>Желаем удачи!</p>]]></content:encoded>
    </item>
    <item>
      <title>От пет-проекта до научного исследования: путь к настоящей инновации</title>
      <link>https://tproger.ru/articles/ot-pet-proekta-do-nauchnogo-issledovaniya-put-k-nastoyashhej-innovacii</link>
      <comments>https://tproger.ru/articles/ot-pet-proekta-do-nauchnogo-issledovaniya-put-k-nastoyashhej-innovacii?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Mykhailo Kapustin]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/ot-pet-proekta-do-nauchnogo-issledovaniya-put-k-nastoyashhej-innovacii</guid>
      <description><![CDATA[<p>Рассказали, как страсть к программированию и пет-проекты могут привести в научное исследование с удивительными результатами.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/ot-pet-proekta-do-nauchnogo-issledovaniya-put-k-nastoyashhej-innovacii">От пет-проекта до научного исследования: путь к настоящей инновации</a>»</p>]]></description>
      <category><![CDATA[История успеха]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 05 Oct 2023 10:19:10 GMT</pubDate>
      <content:encoded><![CDATA[<p>Инновации всегда начинаются с маленьких шагов. Однако, даже самые скромные идеи могут привести к потрясающим открытиям и научным исследованиям, которые меняют наше представление о мире.</p><p>Одной из таких историй является идея, которая началась как пет-проект, но в конечном итоге переросло в научное исследование с удивительными результатами. Название этого исследования – “<a href="https://osf.io/bkfhx">Application of the ‘Banchenko Dream Synchronization Mnemonics Method’ for Joint Synchronization of Dream Elements (including Lucid Dreams) within the ‘Blokhin Dream Network Concept’ and Analysis of Results based on the ‘Kapustin Dream Match Search AI Model’</a>“.</p><p>Эта удивительная история демонстрирует, как страсть к программированию, исследованиям и научной любознательности могут привести к инновациям.</p><p>Автор: Капустин Михаил, CTO представляющий компанию ASRP (Advanced Scientific Research Projects &amp; Association of Sleep Research Projects).</p><h2>Идея, рожденная из страсти к исследованиям</h2><p>История началась с пет-проекта, идея которого казалась смелой и несколько необычной. Основатели проекта решили исследовать сон и возможность синхронизации сновидений между разными людьми.</p><p>Их гипотеза была неоднозначной и даже эксцентричной. Они предположили, что использование теории мемов и тег-мемов в сочетании с механизмами синхронизации ритмов мозга может привести к синхронизации сновидений у участников, включая случаи осознанных сновидений.</p><h2>От пет-проекта к научному моделированию</h2><p>Поначалу это казалось идеей, которая останется в рамках любительского интереса. Однако смелость и научная любознательность исследователей не знали границ.</p><p>Они разработали новую компьютерную модель “Kapustin Dream Match Search AI Model” для идентификации соответствий между снами на основе искусственного интеллекта. Эта модель стала ключевым элементом их исследования.</p><p><i>Для более подробного ознакомления с принципом работы модели можно ознакомиться с ранее опубликованной статьей “</i><a href="https://tproger.ru/articles/otkrojte-dver-v-mir-snovidenij-iskusstvennyj-intellekt-osoznannye-snovideniya-i-novyj-rynok-vozmozhnostej">Как ИИ помогает изучать осознанные сновидения</a><i>“.</i></p><h2>Гипотезы и результаты</h2><p>Исследователи сформулировали несколько гипотез.</p><p>Первая из них была не направленной и предполагала, что синхронизация сновидений через общие синхронные действия и нейропроцессы приведет к более высокой степени схожести в содержании индивидуальных снов по сравнению с случайными совпадениями.</p><p>Вторая гипотеза предполагала, что сон с синхронизированным содержанием будет демонстрировать более высокое количество взаимосвязанных тем, символов и переживаний между участниками, что указывает на уровень взаимосвязи выше случайных паттернов.</p><h2>Искусственный интеллект и анализ снов</h2><p>И вот, исследование началось. Участники были подвергнуты синхронным действиям, а их сновидения ежедневно анализировались. Результаты оказались захватывающими. Первая не направленная гипотеза подтвердилась – сон действительно синхронизировался между участниками, включая случаи осознанных сновидений.</p><p>Но настоящим открытием стала вторая гипотеза. Когда компьютерная модель была применена к анализу синхронизированных сновидений, она продемонстрировала статистически значимое увеличение точности. Это означало, что искусственный интеллект способен распознавать совпадения между снами с высокой точностью, открывая новые возможности для изучения мира снов.</p><p>Пример данного исследования также подчеркивает важность пет-проектов и стартапов для программистов. Можно начинать с маленьких идей, но, как видно из этой истории, они могут перерасти в научные исследования и привести к инновациям, которые меняют наше представление о мире. Программисты, увлеченные научной любознательностью и страстью к исследованиям, могут сделать революционные открытия, даже начиная с самых скромных идей.</p><h2>Выводы</h2><p>Исследование “Application of the ‘Banchenko Dream Synchronization Mnemonics Method’ for Joint Synchronization of Dream Elements (including Lucid Dreams) within the ‘Blokhin Dream Network Concept’ and Analysis of Results based on the ‘Kapustin Dream Match Search AI Model’” превратилось из необычного пет-проекта в научное открытие с потенциалом для дальнейших исследований в области сновидений и искусственного интеллекта.</p><p>Эта история является примером того, как страсть к программированию, науке и научной любознательности могут привести к настоящей инновации, даже если начать с самых скромных идей. Нет предела тому, что можно достичь, когда вам увлеченно и интересно.</p>]]></content:encoded>
    </item>
    <item>
      <title>Почему пет-проект для джуна лучше, чем просто диплом курсов</title>
      <link>https://tproger.ru/articles/pochemu-pet-proekt-dlya-dzhuna-luchwe-chem-prosto-diplom-kursov</link>
      <comments>https://tproger.ru/articles/pochemu-pet-proekt-dlya-dzhuna-luchwe-chem-prosto-diplom-kursov?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[МТС]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/pochemu-pet-proekt-dlya-dzhuna-luchwe-chem-prosto-diplom-kursov</guid>
      <description><![CDATA[<p>Расскажем, как найти идею для пет-проекта и усилить им ваше резюме. Бонус в конце: примеры проектов для джунов.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/pochemu-pet-proekt-dlya-dzhuna-luchwe-chem-prosto-diplom-kursov">Почему пет-проект для джуна лучше, чем просто диплом курсов</a>»</p>]]></description>
      <category><![CDATA[Для начинающих]]></category>
      <category><![CDATA[Практика]]></category>
      <category><![CDATA[Советы]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 18 Aug 2023 12:32:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Чтобы найти работу, нужен опыт. Чтобы получить опыт, нужно найти работу. Как выйти из этого круга новичку? Показать опыт разработки можно с помощью пет-проектов, которыми программисты занимаются в свободное время.</p><p>Ограничений для них не существует: можно разработать приложение для смартфона, телеграм-бота, сайт в интернете или что-нибудь ещё. В отличие от сухой строчки в резюме, пет-проект покажет, как вы можете использовать на практике разные технологии. Реальный проект будет больше интересен работодателю, чем просто диплом онлайн-школы.</p><h2>Где брать идеи для пет-проектов</h2><h3>Первый источник — ваша жизнь</h3><p>Найдите области жизни, которые хотите упростить или автоматизировать. Например, вам нужен удобный планировщик задач, чтобы организовать работу, или помодоро-таймер, чтобы меньше отвлекаться на соцсети.</p><h3>Второй источник — жизнь окружающих</h3><p>Понаблюдайте за родителями, друзьями или партнёром. Возможно, ваш друг-фотограф давно хочет сделать сайт-портфолио, а мама нуждается в приложении для ведения семейного бюджета. Работать с запросами других людей сложнее, зато вы можете сделать проект, который облегчит жизнь не только вам.</p><h2>Как создать пет-проект</h2><h3>1. Сформулируйте идею</h3><p>Подумайте, о чём будет ваш проект, какие задачи будет решать, что получат пользователи.</p><h3>2. Проведите исследование</h3><p>Выясните, кому может быть полезен ваш продукт, существуют ли похожие на него приложения и сайты, каким функционалом они обладают.</p><h3>3. Составьте план</h3><p>Этот этап может занять много времени, но он по-настоящему важен. Вы должны представить, как будет работать ваш проект, какой функционал он имеет, как действует логика в разных сценариях, какой стек технологий вы будете использовать. Рекомендуем составить документ, где вы распишете всё это по пунктам.</p><p>Если в стеке есть незнакомые технологии, нужно оценить их сложность. Так, если вы знакомы только с фронтендом, написание серверной части приложения на C# может занять долгие месяцы. И наоборот: освоение Angular или React вряд ли займёт много времени у бэкендера. Новичку лучше брать посильные задачи — так можно быстро увидеть прогресс и сохранить мотивацию.</p><h3>4. Создайте MVP — минимально жизнеспособный продукт</h3><p>Это версия проекта с базовым функционалом, которая уже готова для тестирования. Попросите друзей это сделать, чтобы выявить слабые места и узнать, насколько продукт удобен для пользователя. По обратной связи проект можно будет доработать.</p><h3>5. Добавьте кейс в резюме</h3><p>Удобнее с первых дней проекта работать с GitHub — так будущий работодатель или рекрутер сможет увидеть всю историю коммитов. В описание проекта лучше добавить скриншоты или видео работы приложения, чтобы не скачивать весь проект и не запускать его на компьютере. Для портфолио или резюме будет достаточно ссылки на репозиторий, названия проекта и описания стека технологий.</p><h2>Как лучше делать пет-проект: одному или командой</h2><p>Зависит от целей и объёма работы, который вам предстоит. Работа в команде — отличная возможность улучшить свои коммуникативные навыки и разработать более сложный продукт. Например, если вы разбираетесь в бэкенде, а ваш друг во фронтенде, то из вас получится хорошая команда и не придётся осваивать что-то новое. Но если проект небольшой и технологии вам знакомы, вполне можно справиться и одному.</p><h2>Примеры пет-проектов</h2><h3>Таск-трекер</h3><p>Таск-трекеры стали своеобразным мемом в IT-среде, так как с них начинают все программисты, но это всё ещё хороший способ получить практический опыт разработки.</p><p>Сложность таск-трекера зависит только от вас. Как вариант — создать приложение с минимальным функционалом, куда можно добавлять задачи и отмечать их выполнение. Но, возможно, вам захочется сделать продвинутый трекер с указанием дедлайнов, уведомлениями о сроках, расписанием регулярных задач и другими фишками.</p><figure><img src="https://media.tproger.ru/uploads/2023/08/4b9d546c-23bb-4348-b2e6-91144cf390ac-autoconverted.jpeg" alt="" /><figcaption>За образец для пет-проекта можно взять доски в сервисе Trello</figcaption></figure><h3>Мини-игра</h3><p>Если мечтаете о будущем в геймдеве или хотите стать фронтенд-разработчиком, создайте собственную версию популярной игры — например, тетриса, змейки или морского боя.</p><p>Представим функционал проекта на примере морского боя:</p><ul><li>генерация ссылки для входа в игру двух игроков;</li><li>возможность выводить на поле разные боевые корабли;</li><li>возможность выбирать клетки, чтобы проверить, есть ли там вражеский корабль;</li><li>чат для игроков и т. д.</li></ul><p>Пример минималистичного <a href="https://battleship-game.org/ru/">морского боя</a> для браузера:</p><figure><img src="https://media.tproger.ru/uploads/2023/08/17f693d8-70b8-4c04-b1a8-860f990c1bfb-autoconverted.jpeg" alt="" /></figure><h3>Калькулятор</h3><p>Речь не о том, который выполняет основные математические операции, а о приложении для решения узких задач. Например, студенты часто разрабатывают калькуляторы для математического анализа и линейной алгебры, моделирования физических процессов. Специализированный софт для решения таких задач очень дорогой, поэтому иногда проще создать собственный.</p><p>Если это вам не очень интересно, разработайте калькулятор для расчёта заработной платы сотрудников компании с учётом отпусков, больничных и отгулов. Это поможет на практике освоить математические операторы и преобразование типов данных.</p><p>А вот так может выглядеть <a href="https://normativ.kontur.ru/calculators/vacation">калькулятор отпускных</a>:</p><figure><img src="https://media.tproger.ru/uploads/2023/08/77cd6fd3-f0f8-427f-a5aa-ff083c873d16-autoconverted.jpeg" alt="" /></figure><h3>Социальная сеть</h3><p>Вам не нужно делать полную копию популярных соцсетей, достаточно базового функционала: возможности регистрироваться и входить в систему, редактировать свой профиль, выкладывать посты, добавлять в друзья других пользователей и комментировать их посты, отправлять личные сообщения.</p><figure><img src="https://media.tproger.ru/uploads/2023/08/eda8ac03-9969-41af-be8d-4e0865a0ca55-autoconverted.jpeg" alt="" /><figcaption>Или почему бы не сделать соцсеть для животных?</figcaption></figure><h3>Интернет-магазин</h3><p>Интернет-магазин с каталогом товаров, загружаемых из базы данных, — хорошая возможность показать свои знания для крепкого новичка в фулстек-разработке. Сделайте личный кабинет пользователя, карточки товаров с отзывами и оценками, поиск по каталогу, корзину.</p><figure><img src="https://media.tproger.ru/uploads/2023/08/38bdd255-3c94-40bc-8bb1-54700d9b7a5c-autoconverted.jpeg" alt="" /><figcaption>В качестве примера можете взять интернет-магазин МТС</figcaption></figure><p>Самое главное в разработке пет-проекта — регулярность. Старайтесь выделять ему хотя бы 30 минут в день после работы или учёбы, чтобы не потерять интерес. Тогда результат не заставит себя ждать, и завершённый проект станет важным пунктом в вашем резюме.</p>]]></content:encoded>
    </item>
    <item>
      <title>Пет-проект: Telegram-бот для изучения английского языка</title>
      <link>https://tproger.ru/articles/pet-proekt-spasaet-ot-vygoraniya-i-kachaet-mozg</link>
      <comments>https://tproger.ru/articles/pet-proekt-spasaet-ot-vygoraniya-i-kachaet-mozg?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Artem Amentes]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/pet-proekt-spasaet-ot-vygoraniya-i-kachaet-mozg</guid>
      <description><![CDATA[<p>Рассказываем о пет-проекте — боте в Telegram, который помогает изучать английский язык. Также рассказали, почему пет-проекты — это полезно.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/pet-proekt-spasaet-ot-vygoraniya-i-kachaet-mozg">Пет-проект: Telegram-бот для изучения английского языка</a>»</p>]]></description>
      <category><![CDATA[Боты]]></category>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 20 Jun 2023 09:49:40 GMT</pubDate>
      <content:encoded><![CDATA[<p>Будь ты джуном или CTO, в рутине рабочих дней современного разработчика программного обеспечения, всегда наступает момент, когда душа просит завести пет-проект (en. Pet – «домашний питомец»).</p><p>Каждый может понимать пет-проект по своему, но большинство признают, что у такого проекта нет ни дедлайнов, ни технического задания, а есть только чистая идея, мотивация и любовь разработчика.</p><p>Я, как разработчик, и как CEO проекта CVCode, считаю, что показатель высокого уровня разработчика является именно наличие пет-проектов, а также опенсорсных решений, и это важный критерий для отбора в мою команду единомышленников.</p><p>Меня зовут Артем Аментес и я хочу поделиться своим опытом создания проекта для души.</p><p>Идея, которая меня захватила, родилась весьма просто: с детства, и уже более 20 лет изучаю английский язык постоянно, и уже достиг уровня fluent (свободно владеющий). Мир, новости, технологии настолько широко используют английский, что очевидно, школьной программы конечно не хватает. Совершенствоваться необходимо постоянно.</p><p>Мне вообще нравится английский в качестве языка науки –  это позволяет мне достаточно широко охватывать мировые новости, тренды и факты. И знаю многих людей, кто хотел бы заняться <b>изучением английского</b>, чтобы чувствовать себя увереннее и свободнее, которые пытаются что-то для этого делать, но обычно откладывают до понедельника, а потом – следующего понедельника.</p><p>Итак, цель моего pet-проекта – со всеми вокруг поделиться возможностью внедрить английский в свою жизнь.</p><p><b>По опыту скажу, что есть 2 наиболее важных момента в изучении английского языка:</b></p><ol><li>Необходимо знать большое количество слов и их определений (definitions).</li><li>Регулярно практиковаться в общении, чтобы получать точный ответ и комментарии на свои вопросы и рассуждения. Второе, пожалуй, является основным.</li></ol><p>И, если с первой задачей мы можем легко справиться с помощью тетрадки, ручки и словаря, то общаться нам нужно с активным собеседником. Причем, необходимо чтобы собеседник мог поддерживать беседу нашего уровня владения языком.</p><h2>Начать следовало с архитектуры моего питомца</h2><ol><li>Главная проблема, которую решаем – это собеседник. Большая доля общения приходится на чаты в мессенджерах, а значит, мы можем создать чат-бота. Лучшим решением будет взять телеграмм. Это удобный мессенджер с открытым api и умопомрачительным числом ботов и заготовок.</li><li>В плане мозгов у «собеседника» тоже не встало много вопросов. Смело берем ChatGPT модель, и на ее базе делаем товарища для общения.</li><li>Понадобится словарь, где мы будем записывать слово, а затем его определение. Подойдет простое решение.</li><li>Повторение – мать учения, пусть по запросу бот выбрасывает слово в случайном порядке. А задача пользователя будет дать ему определение по памяти.</li></ol><p>Это проект для души, решил не сильно мудрить, быстро дойти до реализации и запустить бота в продакшн.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/94ae3b50-321e-4084-a235-74bc34cfe555.jpeg" alt="" /><figcaption>Проработка схемы проекта</figcaption></figure><h2>Шаг 1</h2><p>Для написания самого бота лучшим решением было взять язык программирования Python, и библиотеку aiogram, а модель искусственного интеллекта в виде нейросети архитектуры GPT 3.5 взял с hugging face ресурса. Причем интеграция заняла совсем немного времени. У них реализован функционал получения API подключения по токену. Иными словами, даже модель загружать не требуется ?</p><figure><img src="https://media.tproger.ru/uploads/2023/06/c916a101-9162-4b55-8779-9cad69836c05.png" alt="" /></figure><p>Для формирования толковой базы слов и определений, я использовал обычную кнопку «Add word» и 2 шаговый запрос у пользователя: в первом поле нужно внести слово, затем его определения.</p><p>По нажатию кнопки «Get word» идет простая рандомная выгрузка случайного слова из базы. Такой механизм уже по теории вероятности позволит повторять знакомые слова, при этом, предсказать порядок их выдачи не получится. Только понимать и повторять, только хардкор!</p><p>База данных слов и определений это обычная таблица, в которой 3 столбца: id, word, definition. В таблицу просто вносятся текстовые данные и ничего сверхъестественного.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/e6b6a009-7e97-48ff-9a67-d27b1a844f1c.png" alt="" /></figure><p>Вот такой изящный способ записывать свои слова в базу. Да, придется поработать, предзаписанных форм нет, для освоения языка полезнее пополнять библиотеку слов самостоятельно. Словари пользователей не пересекаются, так как каждое слово и определение привязано к id пользователя.   Возможно, что чем больше пользователей и слов, тем база данных должна быть совершеннее, но это же пет – он пока еще маленький, потом вырастет и подумаем о новой базе для него. Может и стоит сделать общую глобальную базу данных, добавить элемент челленджа?</p><h2>Шаг 2</h2><p>В чем же уникальность и использование искусственного интеллекта? Была просто добавлена кнопка «Chat», где включается режим беседы с обученной нейросетью архитектуры  GPT.  Самое приятное в этой модели, что она отвечает на все, что ты ей напишешь. Если не верно использовать слово, то и ответ скорей всего будет отвлеченный от темы. Это помогает использовать слова и конструкции верно, искать варианты, пока не добьешься взаимопонимания. Побочка обучения на векторах с учетом большой памяти контекста. Или, все таки, не баг, а фича?)</p><p>Процесс разработки занял у меня 2 дня. Да, это конечно получилось очень шустро, но я доволен своей работой. Самое главное, что этот проект можно дорабатывать бесконечно – он всегда останется любимым питомцем.</p><p>Думаю, что скоро найдется время доработать некоторые логические моменты, вычистить код, и можно публиковать бота для всех тех, кто хочет учить английский, ну или как-то тихонечко поддерживать свой уровень. Добавлю разные украшения, красиво отредактированный текст для показа слов и определений в стиле Oxford Dictionary, другие визуальные решения, но это задачка на подумать. Проект получился рабочий и механика очень простая.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/7523c7d0-0ed6-4a7c-bb70-48c02daa8944.png" alt="" /></figure><h2>Почему для меня наличие пет-проекта – такая отдушина</h2><p>Сейчас я, полностью погружен в работу над своим большим проектом cvcode.ru – это система развития интеллекта человека с помощью искусственного интеллекта.</p><p>Да, над проектом работаю не один, это 14 человек, каждый на своем участке, но каждый их кусочек деятельности нужно собрать в единую рабочую картину. CVCODE забирает гораздо больше творческих сил, чем можно подумать, а результат некоторых разработок виден только через 6-7 месяцев.</p><p>Поэтому такой быстрый проект-питомец, который буквально родился вчера в голове, а сегодня уже записывает слова, и пытается поддерживать беседу является чем-то, что поднимает настроение, помогает изучить новые приемы в программировании, но не требует от меня больших усилий и внимания.</p><p>Уверен, что такие небольшие домашние проекты спасают от стресса и выгорания. Когда все идет не так, запустил сервер, выгрузил своего питомца, подчистил ему код, и сразу на душе как-то радостнее.</p><p>Ознакомиться со страницей проекта на гитхабе можно здесь:</p>]]></content:encoded>
    </item>
    <item>
      <title>Как я страну выбирал (по 50 параметрам)</title>
      <link>https://tproger.ru/articles/kak-ya-stranu-vybiral-po-50-parametram</link>
      <comments>https://tproger.ru/articles/kak-ya-stranu-vybiral-po-50-parametram?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Виктор Волков]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-ya-stranu-vybiral-po-50-parametram</guid>
      <description><![CDATA[<p>Как IT-специалист выбирал статью для релокейта по 50 параметрам и создал сервис для выбора подходящей страны по собственному опыту.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-ya-stranu-vybiral-po-50-parametram">Как я страну выбирал (по 50 параметрам)</a>»</p>]]></description>
      <category><![CDATA[Веб-разработка]]></category>
      <category><![CDATA[Релокация]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Mon, 19 Jun 2023 09:55:36 GMT</pubDate>
      <content:encoded><![CDATA[<p>Или гугл таблица переехавщая в <a href="https://passport.help/ru">отдельный сервис</a>. Или переезд из РФ в Грузию (спойлер). Или переезд со Страпи на Директус.</p><p>В первые дни Того-о-чем-Нельзя-Говорить я упёрся в классический для многих список: Турция, Грузия, Армения, Казахстан. Потому что близко, понятно. Но нужен был анализ, в первую очередь по налогам.</p><h2>В первый раз</h2><p>Пошёл беглый анализ. Меня интересовало общее положение дел + сколько в среднем живут мужчины (ага, это важно) + условия получения паспорта и его сила.</p><p>Турция дешево, опасно, безвиз 3 месяца. Маловат безвиз, да и с языком беды. Оставил на всякий случай. С налогами дорого и гемор.</p><p>Армения не звучала как что-то интересное, может имидж для меня у неё сложился не очень. Условия по ИП не вкусные.</p><p>Казахстан уже поинтереснее, там есть виртуальная зона где можно зарегать фирму и иметь 0% на инком. Впрочем, есть и доп налоги. Сейчас уже плохо помню условия по налогам, только помню что в итоге…</p><p>Первым пунктом высадки была выбрана Грузия: 1% налога на доход + лёгкое и самостоятельное ведение налоговой отчётности. Топ-8 по лёгкости ведения бизнеса (ныне этот рейтинг упразднён авторами ввиду 2-3 скандалов со взятками).</p><p>Получение паспорта при этом отошло на второй план, ибо это дело долгое, а жить и кушать хочется сейчас.</p><p>Тут я мог бы рассказать про путь в Тбилиси, про палящее в Октябре солнце, про ощущение спокойствия, но сэкономлю время читателя. Такой информации под каждым углом. Щас еще немного истории и будет про техническую часть!</p><figure><img src="https://media.tproger.ru/uploads/2023/06/1ea7e143-23d5-4d92-afa6-ed0bac82953b.jpg" alt="" /><figcaption>Держите лучше фоточку тех мест, не мою впрочем.</figcaption></figure><h2>И во второй</h2><p>В Тбилиси было неплохо, хоть и с кучей но. Но в определённый момент Казахстан начал выгонять русских. Потом Турция. И я занервничал что Грузия поступит так же.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/108dd797-caf2-4616-a584-400036878cf0.jpg" alt="" /><figcaption>Табличка v. 23</figcaption></figure><p>Откопал свои старые записи, гугл таблицы где собирал данные по странам и начал искать куда дальше, вдруг на выход попросят. И тут меня осенило: я ведь не один такой. Нужен сервис!</p><p>Уехали мы с веб разрабом, с ним же и начали пилить. Несколько дней ушло на обсуждение. Я предлагал любимый мной друпал, но понимая что технология сильно устарела не очень-то настаивал. Он топил за strapi (позже я буду дразнить его за этот выбор, не ориентируйтесь на гитхаб-звёздочки при выборе технологии!). Выбрали именно страпи. Всё еще думаю что друпал бы не потянул задачу.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/c19540cc-2f80-4810-838e-979e12589157.jpg" alt="" /><figcaption>Админка выглядела так. Все сущности связаны, и это большой гемор.</figcaption></figure><p>От тех 3-5 параметров которые рассматривались на старте не осталось и следа. Теперь их полсотни, и это по плану только половина.</p><p>Уперевшись в очередной баг (их было много, самый смешной: слева указан максимум параметра, справа минимум) я пошёл копать как исправить этот самый страпи. Не накопал. Зато один человек (здровья ему) упомянул некий directus. Я запросил демку с сайта, немного полазил, решили попробовать. Причины такие:</p><p>1. Лучше архитектура админки. Вложенности, связи, куча всякого.<br />Сейчас я понимаю что без перехода — с таким количеством данных — я бы просто умер или сошёл с ума при заполнении.<br />2. Можно накатить прямо поверх страпи. Пару дней заняло восстановить связи.<br />3. Он ВООБЩЕ бесплатный, а не с условиями как страпи.<br />4. Директус куда больше напоминал мне друпал. Люблю друпал.</p><figure><img src="https://media.tproger.ru/uploads/2023/06/e28c2324-d011-4d23-b3b7-fce5d7961e99.jpg" alt="" /><figcaption>Почти такая же страница, но директус. Внимание на меню слева. Лучше же?</figcaption></figure><figure><img src="https://media.tproger.ru/uploads/2023/06/5304d2e1-a7db-499b-9472-930dc4f7261c.jpg" alt="" /><figcaption>А вот так выглядит страница со списком стран и их взвешенным параметром.</figcaption></figure><p>На этом моменте я окинул глазами статью и понял что хватит.</p><p>Из России я переехал в Грузию. Со Страпи на Директус. Доволен ли? Вроде да и да. На последок первая версия <a href="https://passport.help/ru">passport.help</a>:</p><figure><img src="https://media.tproger.ru/uploads/2023/06/cbc70b31-9426-4c9e-9cb0-b09afcc1fb91.jpg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Как создать первый проект с ChatGPT и Next.js без навыков кодинга</title>
      <link>https://tproger.ru/articles/kak-sozdat-pervyj-proekt-s-chatgpt-i-next-js-bez-navykov-kodinga</link>
      <comments>https://tproger.ru/articles/kak-sozdat-pervyj-proekt-s-chatgpt-i-next-js-bez-navykov-kodinga?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/kak-sozdat-pervyj-proekt-s-chatgpt-i-next-js-bez-navykov-kodinga</guid>
      <description><![CDATA[<p>В этой статье мы расскажем, как создать первый проект на Next.js и ChatGPT и собрать 10000 пользователей, не имея при этом навыков кодинга.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/kak-sozdat-pervyj-proekt-s-chatgpt-i-next-js-bez-navykov-kodinga">Как создать первый проект с ChatGPT и Next.js без навыков кодинга</a>»</p>]]></description>
      <category><![CDATA[Для начинающих]]></category>
      <category><![CDATA[Open Source]]></category>
      <category><![CDATA[Обучение программированию]]></category>
      <category><![CDATA[Node.js]]></category>
      <category><![CDATA[OpenAI]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 16 Jun 2023 08:41:29 GMT</pubDate>
      <content:encoded><![CDATA[<p>В этой статье мы расскажем, как создать первый проект на Next.js и ChatGPT и собрать 10 тысяч пользователей, и не иметь при этом никаких навыков кодинга.</p><p>Это — перевод оригинальной статьи <a href="https://dev.to/shnai0/how-i-build-my-first-open-source-project-with-chatgpt-and-nextjs-10k-users-in-24-hours-2m7n">«How I built my first Open Source project with ChatGPT and Next.js. 10k users in 24 hours»</a> автора Iuliia Shnai. Далее повествование ведётся от лица автора.</p><p>Раньше я никогда не программировал, потому что кодинг казался мне очень сложным. Два месяца назад я решился попробовать: я подумал, почему бы не начать программировать сейчас.</p><p>Друзья посоветовали мне начать с написания проектов с открытым исходным кодом и помогли мне с первыми настройками проекта.</p><p>Практически на каждом шаге я использовал ChatGPT, чтобы разобраться, как настроить что-то, как установить и подключить API или как понять, что означает код.</p><p>Теперь я расскажу немного больше о первом проекте, который я создал.</p><h2>Этапы разработки проекта</h2><ol><li>Настройка среды.</li><li>Поиск проектов с открытым исходным кодом и разработка на их основе.</li><li>Разбор кода.</li><li>Создание проекта.</li><li>Отправка проекта на GitHub.</li><li>Публикация поста о проекте в социальных сетях.</li></ol><p>Мне потребовалась неделя, чтобы разобраться во всем и запустить проект в Linkedin.</p><p>На настройку ушли 1-2 часа, для управления кодом из открытых проектов потребовалось 3-4 дня, а для размещения на GitHub и Vercel потребовался один день.</p><h2>Какой проект я создал</h2><p>Я сделал генератор постов Linkedin, который использовал ИИ.</p><p>Вот ссылка на него на GitHub:</p><p>Вы можете использовать его, чтобы создать свой собственный генератор постов.</p><h2>Почему генератор постов Linkedin</h2><p>В первое время я проводил эксперименты на Linkedin.</p><p>Я тратил много времени на написание постов на Linkedin. По крайней мере, у меня уходил час на каждый пост, и искал способ упростить написание.</p><p>Итак, я провел анализ постов более 100 разных авторов на Linkedin и 300 различных промптов, чтобы найти способы генерации эффективных постов.</p><p>Теперь я расскажу об основных шагах разработки, которые я делал поэтапно.</p><h2>Шаг 1. Настройка среды</h2><p>Прежде чем начать, мне рекомендовали установить менеджер пакетов, такой как tea, чтобы управлять средой разработки.</p><p>В этот момент слова “менеджер пакетов” были мне неизвестны.</p><p>Как я понимаю, tea помогает установить Node.js, npm, Vercel и любые другие пакеты, которые понадобятся для разработки.</p><h3>Настройка Next.js с использованием TypeScript и Tailwind CSS</h3><p>У меня было базовое представление о том, что понадобится мне для фронтенда.</p><p>Мне подсказали начать с создания нового проекта Next.js. Также я использовал TypeScript и Tailwind CSS, поэтому следовал этим шагам:</p><h2>Шаг 2. Поиск проектов с открытым исходным кодом и разработка на их основе</h2><p>Я использовал два проекта с открытым исходным кодом:</p><p><a href="https://github.com/coryetzkorn/twitter-algorithm">Алгоритм Twitter</a>, чтобы оценивать посты пользователей на Linkedin.</p><p><a href="https://github.com/Nutlope/twitterbio">Генератор био в аккаунтах Twitter</a>. Он помог мне разобраться, как подключить OpenAI и генерировать посты для Linkedin с помощью GPT. В проекте по ссылке он генерировал информацию в био для аккаунтов.</p><p>Я загрузил эти проекты в виде zip-архивов на свой компьютер.</p><h2>Шаг 3. Разбор кода</h2><p>Я был немного шокирован тем, что увидел, и сперва не мог ничего понять.</p><p>Поэтому я обратился к ChatGPT и спросил о базовой структуре моего приложения.</p><p>Я скопировал код каждой страницы и спросил, что он делает. Также я спрашивал, как вносить изменения в код.</p><p>Таким образом, я начал понимать, где находится фронтенд приложения и CSS.</p><p>Некоторые из вопросов, которые я задавал ChatGPT, были очень простыми, зато сейчас они мне полностью понятны.</p><p>В те моменты я задавал все вопросы, даже откровенно глупые.</p><h2>Шаг 4. Создание проекта</h2><p>После того, как я разобрался в базовых вещах, я приступил к изменениям в скачанных проектах и начал создавать собственное приложение на их основе.</p><p>Приложение состоит из двух частей: Ранжирование + Генератор.</p><h3>Алгоритм генерации постов для LinkedIn</h3><p>Ранжирование – это оценка вашего сообщения на основе различных критериев, которая повышает его эффективность.</p><p>Я адаптировал алгоритм ранжирования постов из Twitter для LinkedIn, использовав следующие функции:</p><ol><li>Функция для обнаружения нескольких хэштегов.</li><li>Функция для обнаружения изображений или видео.</li><li>Функция для обнаружения URL-адресов в сообщении.</li><li>Функция, которая предпочитает сообщения, содержащие эмодзи.</li><li>Функция для продвижения негативного контента.</li><li>Функция для приоритетного форматирования постов.</li><li>Функция для сокращения длины строки.</li><li>Функция для задавания вопросов.</li></ol><p>В отличие от алгоритма Twitter, алгоритм LinkedIn не является общедоступным.</p><h3>Интерфейс пользователя алгоритма</h3><p>Он обнаруживает все функции в вышеуказанном коде и показывает, как улучшить пост. Я не настроил интерфейс для всех функций.</p><h3>API OpenAI и генератор промптов</h3><p>Я использую функцию обработчика handlePrompt для создания поста. Также применяется фильтр по типам, поэтому у меня есть 5 различных промптов в зависимости от типа.</p><p>Я просто подключил свой API OpenAI для этого.</p><h3>Интерфейс генератора</h3><p>Это мой индекс-файл. Он относится к генератору постов.</p><h2>Шаг 5. Отправка проекта</h2><p>После того, как я внёс изменения в исходные проекты, я был готов к отправке собственного приложения на GitHub.</p><p>Я создал репозиторий.</p><p>Затем я создал аккаунт на Vercel, чтобы отправить проект и проверить наличие ошибок.</p><p>Каждое обновление я отправлял при помощи команды:</p><p>Для поиска ошибок я использовал ChatGPT. Он очень помог в исправлении ошибок, ведь я даже не понимал, как искать их.</p><h2>Шаг 6. Распространение в социальных сетях и сбор обратной связи</h2><p>Поскольку это был проект для LinkedIn, я <a href="https://www.linkedin.com/feed/update/urn:li:activity:7053373191133499392/">разместил пост там</a>, и он стал вирусным, набрав 200 тыс. просмотров. У него даже появились хэйтеры. 🙂</p><p>Статистика за первые 24 часа:</p><ol><li>20000 просмотров на LinkedIn.</li><li>7000 просмотров веб-сайта.</li><li>600 лайков.</li><li>Более 11000 сгенерированных постов.</li><li>3+ хэйтера.</li><li>3+ предложений о совместном проекте.</li></ol><h2>Что я делаю сейчас</h2><p>Я создаю различные микро-инструменты и вношу вклад в существующие проекты с открытым исходным кодом.</p><p>Вот один из новых проектов с открытым исходным кодом, над которым я работаю.</p><p>Это платформа для обмена документами и презентациями со встроенной аналитикой. У меня было много проблем с использованием Docsend раньше, и они меня очень раздражали. Поэтому я считаю, что будет круто иметь альтернативу с открытым исходным кодом.</p>]]></content:encoded>
    </item>
    <item>
      <title>Зачем твоему краулеру Docker</title>
      <link>https://tproger.ru/articles/zachem-tvoemu-pauku-docker</link>
      <comments>https://tproger.ru/articles/zachem-tvoemu-pauku-docker?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Лена Капаца]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/zachem-tvoemu-pauku-docker</guid>
      <description><![CDATA[<p>Рассказываем о пет-проекте — веб-пауке или краулере данных с сайтов с использованием Docker. Объясняем, при чём здесь Docker.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/zachem-tvoemu-pauku-docker">Зачем твоему краулеру Docker</a>»</p>]]></description>
      <category><![CDATA[Инструменты]]></category>
      <category><![CDATA[Python]]></category>
      <category><![CDATA[Docker]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Wed, 14 Jun 2023 10:43:57 GMT</pubDate>
      <content:encoded><![CDATA[<p>Docker — это инструмент, который позволяет создавать, развертывать и запускать приложения в контейнерах. Использование Docker для развертывания парсеров (или любых других приложений) имеет ряд преимуществ.</p><h2>Преимущества Docker</h2><h3>Изолированность</h3><p>Каждый Docker контейнер работает независимо. Это значит, что приложение будет работать одинаково в любой системе, на которой запущен Docker, независимо от установленных на этой системе библиотек и другого программного обеспечения. Это особенно полезно для парсеров, поскольку они могут требовать конкретные версии библиотек или других зависимостей.</p><h3>Переиспользование</h3><p>Docker позволяет создать образ, который затем может быть использован для создания новых контейнеров. Это означает, что вы можете настроить все необходимые для парсера зависимости один раз, а затем использовать этот образ для быстрого и легкого создания новых экземпляров парсера. В реальности многие сайты сопротивляются скрейпингу, потому умеют блокировать IP. Сменив виртуальную машину и обновив правила неактивности паука, вы потратите минимум усилий на восстановление работоспособности проекта.</p><p>Все это делает продукт идеальным инструментом для масштабирования приложений. Если ваш парсер должен обрабатывать большой объем данных, вы можете просто создать дополнительные контейнеры для распределения нагрузки.</p><h3>Безопасность</h3><p>Docker обеспечивает дополнительный уровень безопасности, поскольку контейнеры изолированы от хост-системы. Это означает, что даже если парсер станет целью атаки, атакующий не сможет вмешаться в работу хост-системы.</p><h3>Управление версиями и обновлениями</h3><p>Docker позволяет легко управлять версиями и обновлениями приложений. Вместо ручного обновления каждого экземпляра парсера вы можете просто обновить Docker-образ и затем обновить его на всех машинах.</p><h2>Недостаток Docker</h2><p>В 2023 году все же бытует мнение, что Docker – трата времени. Полагаю, в таких случаях речь шла о готовом контейнере с очень нужным кодом: его нашли на просторах сети и развернули один раз, попутно ругаясь из-за возможных ошибок при подъеме контейнера.</p><h2>Проект: паук HeadHunter на Docker</h2><p>Поисковый робот (веб-паук, краулер) — программа, являющаяся составной частью поисковой системы и предназначенная для обхода страниц Интернета с целью занесения информации о них в базу данных поисковика.</p><p>Пользователь GitHub с ником undadasea реализовал <a href="https://github.com/undadasea/headhunter-monitor">проект</a> поиска вакансий на hh.ru с помощью docker и PostgreSQL:</p><figure><img src="https://media.tproger.ru/uploads/2023/06/fa29225f-278e-4fe6-bbc6-3d17154fa3cb.png" alt="" /></figure><p>Если верить описанию, код проекта сохраняет вакансии в базу данных PostgreSQL в контейнере Docker. Так что мы определенно имеем дело с типовым пауком. Если вакансии больше нет на сайте, она помечается в базе данных как «закрытая». Мониторинг проводится раз в сутки.</p><p>Простым набором команд мы клонируем репозиторий на свою машину:</p><p>А затем разворачиваем контейнер:</p><p>И это все, как же радует такая лаконичность! Конечно, я опустила момент дотяжки алгоритма поиска под свои поисковые запросы, но об этом лучше написать отдельную статью.  Как вы уже догадались, помимо пауков в Docker упаковывают и другие категории ПО:</p><ul><li>серверы, вроде Redis, Jenkins</li><li>базы данных, например, MongoDB</li><li>фреймворки машинного / глубокого обучения, такие как PyTorch, Tensorflow</li></ul><p>Если верить <a href="https://www.datadoghq.com/docker-adoption/">статье datadoghq.com</a>, несмотря на разногласия в комьюнити, Docker все же прижился в 25% IT-компаний:</p><figure><img src="https://media.tproger.ru/uploads/2023/06/541c7175-bf55-474a-9741-f19a20478844.png" alt="" /><figcaption>dabbling – “балующиеся” [продуктом], экспериментирующие с ним вне прода</figcaption></figure><p>Более того, вероятность его использования возрастает с ростом инфраструктуры:</p><figure><img src="https://media.tproger.ru/uploads/2023/06/b273ae66-7e03-416f-84a4-91eb18802a9b.png" alt="" /></figure><p>Вывод получается “с разветвлением”: если ты работаешь над крупным проектом, тебе, скорее всего, потребуется Docker, будь то паук или другой микросервис. В случае индивидуальных экспериментов разворачивание контейнера, хоть и демонстрирует преимущество в разрезе безопасности и воспроизводимости, легко становится тратой драгоценных ресурсов разработчика.</p>]]></content:encoded>
    </item>
    <item>
      <title>Собираем умную CRM на ChatGPT, PostgreSQL и ToolJet</title>
      <link>https://tproger.ru/articles/sozdanie-intellektualnoj-crm-s-ispolzovaniem-chatgpt-postgresql-i-tooljet</link>
      <comments>https://tproger.ru/articles/sozdanie-intellektualnoj-crm-s-ispolzovaniem-chatgpt-postgresql-i-tooljet?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/sozdanie-intellektualnoj-crm-s-ispolzovaniem-chatgpt-postgresql-i-tooljet</guid>
      <description><![CDATA[<p>CRM позволит добавлять новых пользователей в PostgreSQL, создавать шаблоны писем с ChatGPT и отправлять письма через Sendinblue.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/sozdanie-intellektualnoj-crm-s-ispolzovaniem-chatgpt-postgresql-i-tooljet">Собираем умную CRM на ChatGPT, PostgreSQL и ToolJet</a>»</p>]]></description>
      <category><![CDATA[Нейронные сети]]></category>
      <category><![CDATA[Искусственный интеллект]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Приложение]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Thu, 25 May 2023 09:44:04 GMT</pubDate>
      <content:encoded><![CDATA[<p>Из этого гайда вы узнаете, как создать CRM (Customer Relationship Management) с использованием ChatGPT, ToolJet и PostgreSQL.</p><p>CRM позволит вам добавлять новых пользователей или клиентов в базу данных PostgreSQL, просматривать их данные на панели инструментов, создавать шаблоны электронной почты с помощью ChatGPT и отправлять им электронные письма через Sendinblue.</p><p>В этом руководстве мы будем использовать ToolJet для интерфейса приложения.</p><p>Дисклеймер: это — перевод оригинальной статьи <a href="https://dev.to/tooljet/building-an-intelligent-crm-using-chatgpt-postgresql-and-tooljet-4jod">Building an intelligent CRM using ChatGPT, PostgreSQL, and ToolJet</a> автора Shubhendra Singh Chauhan.</p><h2>Что такое ToolJet</h2><p>ToolJet — это low-code фреймворк и открытым исходным кодом, который позволяет нам создавать веб-приложения с полным стеком за несколько минут.</p><p>С помощью ToolJet вы можете создавать автономные полнофункциональные приложения или встраивать приложения в другие веб-сайты.</p><p>ToolJet позволяет создавать приложения, использующие реляционные и нереляционные базы данных, REST API, технологии OpenAI и облачные хранилища, такие как Google Cloud Storage, AWS S3 и Minio.</p><p>Это отличный инструмент разработки, помогающий отдельным лицам, разработчикам и предприятиям быстрее создавать и выпускать продукты.</p><h2>Настройка базы данных ElephantSQL (PostgreSQL)</h2><p><a href="https://www.elephantsql.com/">ElephantSQL</a> позволяет создавать базы данных PostgreSQL в облаке, а не на вашем локальном компьютере. Выполните следующие действия, чтобы создать базу данных PostgreSQL.</p><p>Создайте учетную запись ElephantSQL <a href="https://customer.elephantsql.com/login">здесь</a>.</p><p>Добавьте новую базу данных. Информация о банковских картах или платежных реквизитах не требуется.</p><p>После создания БД отобразится вся информация о ней. Далее создадим интерфейс приложения и подключим базу данных.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/ffbe54cf-5ed9-41ad-8ed6-efdd2d7fc53d.png" alt="" /></figure><h2>Создание приложения с помощью ToolJet</h2><p>Если вы новичок в ToolJet, и никогда не регистрировались в сервисе, <a href="https://app.tooljet.com/signup">создайте учетную запись</a>.</p><p>После этого создайте рабочую область и новое приложение под названием CRM-приложения.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/7845a14b-3fd2-4c2f-be7d-34cfb76f7a68.png" alt="" /></figure><p>Создайте пользовательский интерфейс, подобный изображенному ниже.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/14b2387a-e640-43bb-a6a9-06830606718e.png" alt="" /></figure><p>Чтобы создать пользовательский интерфейс, сначала добавьте большой контейнер, в котором будут размещены все остальные элементы интерфейса приложения.</p><p>В контейнер добавьте три элемента-контейнера поменьше в верхней части страницы: для этого нажмите кнопку «Добавить интерфейс» и выберите элемент «Таблица».</p><p>В ToolJet можно создавать интерфейсы через перетаскивание элементов на рабочую область.</p><p>После создания пользовательского интерфейса добавьте в таблицу кнопку «Действие» с текстом «Отправить электронное письмо». Мы настроим кнопку позже, она будет отвечать за отправку электронных писем пользователям.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/79295e55-9745-4323-8f3c-90afd21619bf.png" alt="" /></figure><p>Сейчас нам нужен интерфейс, который будет добавлять пользователей в базу данных. Также нужна опция для создания и редактирования адресов электронной почты пользователей.</p><p>Для этого воспользуемся <a href="https://docs.tooljet.com/docs/widgets/modal">компонентом Modal</a>. Откройте окно Modal и нажмите кнопку «Добавить лид» для добавления новых данных. После этого нажмите кнопку «Отправить электронное письмо» для ввода содержимого электронной почты для пользователя.</p><h3>Модальное окно «Добавить новый лид»</h3><p>Чтобы отобразить модуль «Добавить новый лид», вам нужно создать окно модуля и добавить событие onClick к кнопке «Добавить лид».</p><figure><img src="https://media.tproger.ru/uploads/2023/05/bae3fff8-3910-49fa-9278-d4f2fbc365f5.png" alt="" /></figure><p>Добавьте следующие компоненты в окно модуля и не забудьте закрыть его при нажатии модальной кнопки.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/d98726dc-81e5-4651-8e1a-85fcec20e612.png" alt="" /></figure><h3>Модальное окно «Отправить письмо»</h3><p>Окно «Отправить электронное письмо» позволит нам ввести адрес электронной почты пользователя, его тему и содержание.</p><p>Вы также сможете создавать содержимое электронной почты с помощью ChatGPT API. Вы узнаете, как это сделать, чуть позже.</p><p>В окне есть тумблер с событием onChange, которое скрывает подсказки от ChatGPT и кнопки с генерацией, когда они вам не нужны.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/a8fa36e5-db6c-4991-a7f7-df114b7255fa.png" alt="" /></figure><p>Не забудьте закрыть модуль перед тем, как нажать кнопку «Отправить электронное письмо».</p><h2>Как взаимодействовать с базой данных PostgreSQL в ToolJet</h2><p>ToolJet позволяет взаимодействовать с внешними ресурсами или создавать собственные функции через панель запросов. В ToolJet любая функция, которая взаимодействует с базой данных, API или облачным хранилищем и запускает код JavaScript или Python, называется запросом.</p><p>Здесь вы узнаете, как взаимодействовать с базой данных PostgreSQL в ToolJet. Во-первых, подключим базы данных PostgreSQL к ToolJet.</p><h3>Подключение базы данных PostgreSQL к ToolJet</h3><p>Выберите PostgreSQL из списка баз данных на панели «Глобальные источники данных» и предоставьте необходимую информацию.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/3abde3f8-aa46-48ae-bf80-3925c8e49f79.png" alt="" /></figure><p>На изображении выше хост совпадает с именем сервера в ElephantSQL (за исключением скобок). Имя пользователя и имя базы совпадают. Пароль нужно просто вставить в нужное поле.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/f54cff95-0fbd-4257-99ef-266e6e2ca636.jpeg" alt="" /></figure><p>Прокрутите страницу вниз и нажмите «Проверить подключение».</p><figure><img src="https://media.tproger.ru/uploads/2023/05/9d572c7b-e4e4-4549-a9bc-d2f24c7e70cd.png" alt="" /></figure><p>Если соединение проверено, мы можем делать запросы к БД.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/a1ce15db-7b1c-43a3-b76e-c1c55529ed8f.png" alt="" /></figure><h3>Запрос базы данных PostgreSQL в ToolJet</h3><p>Прежде чем мы начнем, добавим некоторые данные в базу данных.</p><p>Щелкните PostgreSQL на панели запросов, выберите режим SQL и запустите приведенный ниже фрагмент кода, чтобы создать новую таблицу с данными.</p><p>Вы можете просмотреть данные на ElephantSQL после их загрузки.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/f7bb2cf5-1143-4196-a3fb-40b7692a3d89.png" alt="" /></figure><p>Затем переименуйте запрос в getTableData и обновите редактор SQL, чтобы отобразить все содержимое таблицы. Сохраните запрос.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/e87a96e9-6901-48c8-8ae6-5d1cce07a6d3.png" alt="" /></figure><p>Обновите компонент Table, чтобы отобразить данные, полученные из запроса getTableData.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/10280974-ff24-48de-92c2-f4210ae0d421.png" alt="" /></figure><p>Теперь покажем количество клиентов, лидов и потенциальных клиентов, доступных в базе данных.</p><p>Создайте три новых запроса на основе базы данных PostgreSQL с именами getLeadsCount, getProspectsCount и getCustomersCount.</p><p>Обновите редактор SQL для каждого запроса, чтобы получить количество данных в каждой категории, как показано ниже, и сохраните их.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/029b07b9-05f3-4c93-94c1-cddff02cc826.png" alt="" /></figure><p>Отобразите количество данных, возвращенных из каждого запроса, заменив текстовое содержимое в контейнере, как показано ниже.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/0ce8f25d-2724-44d7-9335-52a665479623.png" alt="" /></figure><p>Наконец, включите переключатель «Выполнять этот запрос при загрузке приложения?» для getTableData и трех других запросов.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/b8c92b11-237f-47a9-95cf-ddc39cebc6dc.png" alt="" /></figure><h3>Добавление новых пользователей в базу</h3><p>Создайте новый запрос, связанный с PostgreSQL, который принимает значения из модуля и отправляет запрос SQL для добавления данных в БД.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/a8ed15a0-3352-4906-b337-8dd39f2a9748.png" alt="" /></figure><p>Убедитесь, что имена из фрагмента кода ниже соответствуют именам компонентов из модального окна. Скопируйте этот код в панель редактора SQL и сохраните запрос.</p><p>Теперь добавьте событие onClick к кнопке «Добавить лид», чтобы запрос выполнялся при нажатии кнопки.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/0358b3b4-fe00-488c-a480-0381d9b740d4.png" alt="" /></figure><h2>Как общаться с ChatGPT в ToolJet</h2><p>Здесь вы узнаете, как общаться с ChatGPT через OpenAI в ToolJet.</p><h3>Настройка учетной записи OpenAI</h3><p>Войдите или создайте учетную запись OpenAI <a href="https://openai.com/product">здесь</a>.</p><p>Нажмите «Personal» на панели навигации и выберите «View API keys» в строке меню, чтобы создать новый секретный ключ.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/dc5aa227-3dcc-4910-9aa9-0c368aa11b32.png" alt="" /></figure><p>Создайте новый ключ API и скопируйте его куда-нибудь. Мы используем его позже.</p><h3>Взаимодействие с API OpenAI в ToolJet</h3><p>На вкладке «Глобальные источники данных» на панели инструментов нажмите «Плагины» и выберите «OpenAI». Затем вставьте свой ключ API и идентификатор организации в поля ввода и проверьте соединение.</p><p>Теперь вы можете получить доступ к источнику данных OpenAI из панели запросов.</p><p>Если у вас нет идентификатора организации, используйте «Personal».</p><figure><img src="https://media.tproger.ru/uploads/2023/05/9e0782fb-4629-45b3-84ea-e6fbd3fa683e.png" alt="" /></figure><p>Выберите OpenAI на панели запросов и настройте его содержимое для составления электронного письма с использованием ChatGPT.</p><p>Запускайте запрос, когда пользователь нажимает кнопку «Спросить» в модуле.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/1cce49b6-be28-40f1-9df2-280bbb61964c.png" alt="" /></figure><p>Наконец, чтобы автоматически отображать адрес электронной почты пользователя в окне модуля, установите значение по умолчанию для ввода электронной почты получателя на {{components.table1.selectedRow.email}}.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/1ba3b08e-5887-4ac1-9cdc-6d04759d3b1f.png" alt="" /></figure><h2>Как отправлять электронные письма через Sendinblue API в ToolJet</h2><p>Sendinblue — это инструмент цифрового маркетинга, который предоставляет электронную почту, SMS, Facebook, чат и многое другое через одну платформу, чтобы помочь развитию бизнеса за счет укрепления отношений с клиентами.</p><p>Для начала, вам нужно войти в систему или <a href="https://www.sendinblue.com/">создать учетную запись SendinBlue</a>.</p><p>Выберите SMTP и API на панели инструментов, создайте ключ SMTP и скопируйте его куда-нибудь. Он понадобится нам в ближайшее время.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/788ba13d-ebdb-4fc5-abd8-c2fe428615ce.png" alt="" /></figure><p>Вернитесь в приложение ToolJet, добавьте новый источник данных SMTP и введите необходимые учетные данные. Ваш пароль — это сгенерированный ключ SMTP.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/82fc6fd7-3b32-4f16-8f41-e3ff09b98baa.png" alt="" /></figure><p>При успешном подключении будет отображаться «Подключение подтверждено». Затем вы можете начать отправлять электронные письма.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/5807ae88-1594-451b-8d6d-1a123837cb4d.png" alt="" /></figure><p>Затем создайте запрос для отправки писем. Укажите свой адрес электронной почты, имя, адрес электронной почты получателя, тему и компоненты заголовка.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/bc9d24f0-e9cb-4099-9b1a-af63b42f0de1.png" alt="" /></figure><p>Сохраните запрос и запустите его, когда нажата кнопка «Отправить письмо».</p><figure><img src="https://media.tproger.ru/uploads/2023/05/90c677a9-e2e1-47e9-b779-d6bd9e1c1788.png" alt="" /></figure><p>Вот рабочая демонстрация приложения:</p><h2>Заключение</h2><p>ToolJet — отличный инструмент разработки с открытым исходным кодом, и его код легко доступен для изменения и улучшения.</p><p>У него большое сообщество разработчиков, которые постоянно поддерживают и улучшают ПО. Как пользователь, вы можете быть уверены, что получите максимальную производительность при использовании ToolJet.</p><p>Вы заинтересованы в сотрудничестве с ToolJet? Не стесняйтесь проверять <a href="https://github.com/ToolJet/ToolJet">репозиторий GitHub</a> и вносите свой вклад в разработку.</p>]]></content:encoded>
    </item>
    <item>
      <title>Doom запустили на телетексте — играть можно обычным пультом</title>
      <link>https://tproger.ru/news/teletext-doom</link>
      <comments>https://tproger.ru/news/teletext-doom?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Павел Федоренко]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/news/teletext-doom</guid>
      <description><![CDATA[<p>Энтузиаст смог адаптировать Doom 1993 года к Телетексту. Графика упрощена, зато культовая игра запускается даже в Teletext 1976 года.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/news/teletext-doom">Doom запустили на телетексте — играть можно обычным пультом</a>»</p>]]></description>
      <category><![CDATA[Hardware]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Игра]]></category>
      <category><![CDATA[Новости]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 23 May 2023 13:52:04 GMT</pubDate>
      <content:encoded><![CDATA[<p>Моддер с ником Lukneu смог адаптировать Doom 1993 года к телетексту. Теперь играть в Doom можно даже с пульта от телевизора!</p><p>Вот как выглядит геймплей.</p><p>Чтобы реализовать такое, Lukneu создал мод, который запускает игру на ПК, одновременно передавая видеосигнал на телевизор и вообще на все устройства, которые умеют принимать телетекст.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/236262b3-b38a-4334-beaa-2d010ef02708.jpg" alt="" /></figure><p>Для этого пришлось изменить привычный интерфейс игры на упрощённую графику и чёрно-белые цвета. Например, лицо героя — обычный смайлик, а визуальные эффекты размыты. Так игра сможет запускаться даже через телетекст первого уровня 1976 года.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/ba45444c-8474-46de-9418-035e7105268a.jpeg" alt="" /></figure><p>Проект Teletext Doom работает на Linux, а исходники выложены на GitHub.</p><p>Телетекст — это стандарт для передачи простых информационных пакетов с текстом с помощью широковещательных сигналов через обычную антенну.</p><figure><img src="https://media.tproger.ru/uploads/2023/05/1f198630-8672-4c5b-9119-7f575021dfe0.jpg" alt="" /></figure><p>В 1970-х годах он включал несколько символов и цветов. Его пытались развивать и модифицировать, но сейчас телетекст оказался не нужен из-за ТВ-приставок и мобильных устройств. Но телетекст всё ещё по-прежнему доступен во многих странах, например в России и Европе.</p>]]></content:encoded>
    </item>
    <item>
      <title>PHPize.online - моя песочница для работы с SQL, PHP и ChatGPT</title>
      <link>https://tproger.ru/articles/phpize-online-onlajn-sreda-dlya-raboty-s-bazami-dannyh-sql-i-php</link>
      <comments>https://tproger.ru/articles/phpize-online-onlajn-sreda-dlya-raboty-s-bazami-dannyh-sql-i-php?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Slava Rozhnev]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/phpize-online-onlajn-sreda-dlya-raboty-s-bazami-dannyh-sql-i-php</guid>
      <description><![CDATA[<p>PHPize.online это онлайн-сервис, где можно быстро создать и выполнить запросы к базам данных SQL, используя любую из самых популярных СУБД.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/phpize-online-onlajn-sreda-dlya-raboty-s-bazami-dannyh-sql-i-php">PHPize.online - моя песочница для работы с SQL, PHP и ChatGPT</a>»</p>]]></description>
      <category><![CDATA[PHP]]></category>
      <category><![CDATA[SQL]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 21 Apr 2023 14:30:00 GMT</pubDate>
      <content:encoded><![CDATA[<p><a href="https://phpize.online">PHPize.online</a> – это проект, который я начал немного больше двух лет назад и продолжаю развивать его и сегодня.</p><p>Это сайт позволяющий быстро писать и исполнять SQL запросы к различным популярным базам данных, таких как MySQL, MariaDB, PostgreSQL, SQLite, Oracle и Microsoft SQL Server.</p><p>Также здесь вы можете написать и исполнить код на языке PHP, который будет обращаться к базе данных и выполнит запросы указанные в коде.</p><p>Идея проекта зародилась в процессе моего волонтёрства на Stack Overflow, где принято демонстрировать свой код онлайн с возможностью моментального запуска без дополнительной подготовки.</p><p>Существует много подобных сайтов для кодирования на различных языках программирования. Есть отличные площадки для SQL и для PHP, но ни на одной из них невозможно работать с базами данных в совместно с другими языками программирования. Я же отвечал людям, имеющим вопросы по очень популярному стеку PHP + MySQL, и не имел возможности сопроводить ответ живым примером кода. В результате я решил эту проблему, запустив свой проект. Как в анекдоте про типичного программиста который не нашёл нужный драйвер и написал его сам.</p><p>Посмотрите что получилось в итоге: <a href="https://phpize.online">PHPize.online</a> – это сайт (совершенно бесплатный)  для написания, исполнения и совместного использования кода на языках программирования PHP и SQL.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/11d08d78-fcf1-430e-8f82-bf824f66d546.png" alt="" /><figcaption>Дизайн проекта</figcaption></figure><p>Сайт имеет две панели для редактирования. Обе панели используют редактор <a href="https://github.com/ajaxorg/ace">Ace.js</a> для подсветки и автодополнения кода. Слева расположены редактор для кода SQL, элемент выбора СУБД кнопка запуска кода и блок результатов его исполнения. Изначально сайт был рассчитан только на MySQL, но позже мне удалось добавить и другие популярные СУБД (используя докерную контейнеризацию). Таким образом, чтобы протестировать какой-либо SQL запрос, вы пишете или вставляете его в редактор, выбираете версию SQL и нажав кнопку «Run SQL code» или Ctrl +Enter (если Вы поклонник горячих клавиш) и через секунду (или чуть более если Вы написали сложный запрос) получаете результат на экране.</p><p>Правая панель такой же редактор, но уже для PHP. Здесь так же можно набрать или вставить из буфера код и попытаться его исполнить в выбранной версии интерпретатора.</p><p>Если нужно поделиться своим фрагментом кода с кем-либо, вы можете просто скопировать текущий URL адрес страницы или нажать кнопку «Share» получить сокращенный адрес прямо в буфер обмена. Любой кто откроет Вашу ссылку увидит тот же код что видите Вы.</p><p>Теперь о том что делает проект уникальным — здесь в коде PHP вы можете запросить базу данных, которую вы только что создали в левой панели. Использовать библиотеки mysqli для интеграции с MySQL и MariaDB или PDO и Laravel Query builder для взаимодействия с другими СУБД. Вы также можете выбрать, версию PHP для исполнения кода (включая последний PHP 8.2).</p><p>Вторая уникальная особенность проекта PHPize.online — это интеграция с ИИ помощником на основе ChatGPT. Как в случае ошибки в SQL запросе, так и при ошибке в коде PHP вместе с кодом ошибки вы увидите кнопку и приглашение исправить ошибку автоматически. Стоит Вам нажать эту кнопку и ИИ предложит вариант исправления.</p><p>Я должен отметить что помощь не всегда идеальна, но во многих случаях помогает сократить время на отладку кода.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/c4d04dce-6033-4df4-bd51-a63c345f202f.png" alt="" /><figcaption>Ошибка в SQL запросе</figcaption></figure><figure><img src="https://media.tproger.ru/uploads/2023/03/6d7c8794-04dd-4dfe-9ae7-5c4b5bcd8492.png" alt="" /><figcaption>Результат исправления ошибки при помощи ИИ</figcaption></figure><p>Если Вам понравился проект, Вы можете <a href="https://pay.cloudtips.ru/p/60214a3d">поддержать автора</a>.</p>]]></content:encoded>
    </item>
    <item>
      <title>Что вы делали на этой неделе? Пост хвастовства за 27-31 марта</title>
      <link>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-27-31-marta</link>
      <comments>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-27-31-marta?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-27-31-marta</guid>
      <description><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе (27-31 марта). Ведь нет ничего интереснее, чем задачи коллег!</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-27-31-marta">Что вы делали на этой неделе? Пост хвастовства за 27-31 марта</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 31 Mar 2023 09:59:02 GMT</pubDate>
      <content:encoded><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег!</p><p>Вот, чем вы занимались <a href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-20-24-marta/">на прошлой неделе</a>.</p><p>Не важно, разработчик вы или тестировщик, деврел или эйчар. Расскажите, какие задачи вы героически решили, и делитесь успехами.</p><p>Кидайте всё, чем хочется похвастаться: текст, скриншоты кода и даже ссылочки на видео.</p><p>Не забывайте про NDA: не указывайте названия компании или деликатные частности.</p><p>Итак, чем вы похвастаетесь на этой неделе?</p><p>Внимание Это — зона взаимного уважения, понимания и нулевого токсика. Похвала и помощь горячо приветствуются.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/c8fda684-767b-461d-89d4-75009ddcbee8.jpg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Что вы делали на этой неделе? Пост хвастовства за 20-24 марта</title>
      <link>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-20-24-marta</link>
      <comments>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-20-24-marta?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-20-24-marta</guid>
      <description><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе (20-24 марта). Ведь нет ничего интереснее, чем задачи коллег!</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-20-24-marta">Что вы делали на этой неделе? Пост хвастовства за 20-24 марта</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 24 Mar 2023 10:10:04 GMT</pubDate>
      <content:encoded><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег!</p><p>Вот, чем вы занимались на прошлой неделе.</p><p>Не важно, разработчик вы или тестировщик, деврел или эйчар. Расскажите, какие задачи вы героически решили, и делитесь успехами.</p><p>Кидайте всё, чем хочется похвастаться: текст, скриншоты кода и даже ссылочки на видео.</p><p>Не забывайте про NDA: не указывайте названия компании или деликатные частности.</p><p>Итак, чем вы похвастаетесь на этой неделе?</p><p>Внимание Это — зона взаимного уважения, понимания и нулевого токсика. Похвала и помощь горячо приветствуются.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/f6469260-0872-463a-8093-a74727c7ec5a.jpeg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Что вы делали на этой неделе? Пост хвастовства за 13-17 марта</title>
      <link>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-13-17-marta</link>
      <comments>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-13-17-marta?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-13-17-marta</guid>
      <description><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-13-17-marta">Что вы делали на этой неделе? Пост хвастовства за 13-17 марта</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 17 Mar 2023 10:10:01 GMT</pubDate>
      <content:encoded><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег!</p><p>Вот, чем вы занимались <a href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-3-10-marta/">на прошлой неделе</a>.</p><p>Не важно, разработчик вы или тестировщик, деврел или эйчар. Расскажите, какие задачи вы героически решили, и делитесь успехами.</p><p>Кидайте всё, чем хочется похвастаться: текст, скриншоты кода и даже ссылочки на видео.</p><p>Не забывайте про NDA: не указывайте названия компании или деликатные частности.</p><p>Итак, чем вы похвастаетесь на этой неделе?</p><p>Внимание Это — зона взаимного уважения, понимания и нулевого токсика. Похвала и помощь горячо приветствуются.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/9868e876-fe6d-47dd-adf0-8873874853f9.jpg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Что вы делали на этой неделе? Пост хвастовства за 3-10 марта</title>
      <link>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-3-10-marta</link>
      <comments>https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-3-10-marta?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-3-10-marta</guid>
      <description><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/chto-vy-delali-na-etoj-nedele-post-hvastovstva-za-3-10-marta">Что вы делали на этой неделе? Пост хвастовства за 3-10 марта</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 10 Mar 2023 07:29:57 GMT</pubDate>
      <content:encoded><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы<br />работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег!<br />Вот, чем вы занимались <a href="https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-hvastovstva-za-27-fevralja-3-marta/">на прошлой неделе</a>.</p><p>Не важно, разработчик вы или тестировщик, деврел или эйчар. Расскажите, какие задачи вы героически решили, и делитесь успехами.</p><p>Кидайте всё, чем хочется похвастаться: текст, скриншоты кода и даже ссылочки на видео.</p><p>Не забывайте про NDA: не указывайте названия компании или деликатные частности.</p><p>Итак, чем вы похвастаетесь на этой неделе?</p><p>Внимание Это — зона взаимного уважения, понимания и нулевого токсика. Похвала и помощь горячо приветствуются. ?</p><figure><img src="https://media.tproger.ru/uploads/2023/03/1508f13f-b88d-43a4-9f0c-df0085c9645b.jpeg" alt="" /></figure>]]></content:encoded>
    </item>
    <item>
      <title>Умелец с Реддита сделал USB-клавиатуру в форме пениса</title>
      <link>https://tproger.ru/news/umelec-s-reddita-sdelal-usb-klaviaturu-v-forme-polovogo-organa</link>
      <comments>https://tproger.ru/news/umelec-s-reddita-sdelal-usb-klaviaturu-v-forme-polovogo-organa?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Павел Федоренко]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/news/umelec-s-reddita-sdelal-usb-klaviaturu-v-forme-polovogo-organa</guid>
      <description><![CDATA[<p>На Реддите появился тред, в котором автор похвастался изобретением — клавиатурой-пенисом. Он напечатал его на 3D-принтере.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/news/umelec-s-reddita-sdelal-usb-klaviaturu-v-forme-polovogo-organa">Умелец с Реддита сделал USB-клавиатуру в форме пениса</a>»</p>]]></description>
      <category><![CDATA[Hardware]]></category>
      <category><![CDATA[DIY]]></category>
      <category><![CDATA[3D-принтер]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Новости]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Tue, 07 Mar 2023 00:56:59 GMT</pubDate>
      <content:encoded><![CDATA[<p>Девайс напечатан на 3D-принтере и имеет форму пениса.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/0629ea4a-6ad8-41d6-a398-8f6e5590df18.jpeg" alt="" /></figure><p>Он обладает несколькими кнопками, нажимая на которые можно выбирать буквы и составлять слова. Но самое интересное, что устройство сделано так, чтобы управлять им можно было с помощью языка.</p><figure><img src="https://media.tproger.ru/uploads/2023/03/1d1dcbf5-e3c9-4ac7-86f6-6bdd859c3b59.jpeg" alt="" /></figure><p>Также автор этого чуда составил комбинации клавиш, которые можно получится «ввести». Правда, там пока нет цифр, но автор говорит, что «можно заменить на них некоторые из букв».</p><p>Теперь можно прочувствовать каждую букву всей душой.</p>]]></content:encoded>
    </item>
    <item>
      <title>Что вы делали на этой неделе? Пост хвастовства за 27 февраля — 3 марта</title>
      <link>https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-hvastovstva-za-27-fevralja-3-marta</link>
      <comments>https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-hvastovstva-za-27-fevralja-3-marta?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Рафаил Агазода]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-hvastovstva-za-27-fevralja-3-marta</guid>
      <description><![CDATA[<p>Предлагаем делиться в комментариях, над чем вы работали на этой неделе (27 февраля — 3 марта). Ведь нет ничего интереснее, чем задача коллеги!</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-hvastovstva-za-27-fevralja-3-marta">Что вы делали на этой неделе? Пост хвастовства за 27 февраля — 3 марта</a>»</p>]]></description>
      <category><![CDATA[Работа]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 03 Mar 2023 12:34:47 GMT</pubDate>
      <content:encoded><![CDATA[<p>Предлагаем делиться в комментариях под этой записью, над чем вы работали на этой неделе, ведь нет ничего интереснее, чем задачи коллег! Вот, чем вы занимались <a href="https://tproger.ru/articles/chto-vy-delali-na-jetoj-nedele-post-ljogkogo-hvastovstva-za-20-24-fevralja/">на прошлой неделе</a>.</p><p>Не важно, разработчик вы или тестировщик, деврел или эйчар. Расскажите, какие задачи вы героически решили, и делитесь успехами.</p><p>Кидайте всё, чем хочется похвастаться: текст, скриншоты кода и даже ссылочки на видео.</p><p>Не забывайте про NDA: не указывайте названия компании или деликатные частности.</p><p>Итак, чем вы похвастаетесь на этой неделе?</p><p>Внимание Это — зона взаимного уважения, понимания и нулевого токсика. Похвала и помощь горячо приветствуются. 🙂</p>]]></content:encoded>
    </item>
    <item>
      <title>Telegram-бот счётчик сообщений на Java и Spring Boot</title>
      <link>https://tproger.ru/articles/telegram-bot-schjotchik-soobshhenij-na-java-i-spring-boot</link>
      <comments>https://tproger.ru/articles/telegram-bot-schjotchik-soobshhenij-na-java-i-spring-boot?scrollTo=tproger-comments</comments>
      <dc:creator><![CDATA[Марина Александровна]]></dc:creator>
      <guid isPermaLink="true">https://tproger.ru/articles/telegram-bot-schjotchik-soobshhenij-na-java-i-spring-boot</guid>
      <description><![CDATA[<p>Пишем простой Телеграм-бот на Java, который будет подсчитывать сообщения от пользователей чата и записывать их в БД через PostgreSQL.</p><p>— Читать дальше «<a rel="follow" href="https://tproger.ru/articles/telegram-bot-schjotchik-soobshhenij-na-java-i-spring-boot">Telegram-бот счётчик сообщений на Java и Spring Boot</a>»</p>]]></description>
      <category><![CDATA[Java]]></category>
      <category><![CDATA[SQL]]></category>
      <category><![CDATA[Боты]]></category>
      <category><![CDATA[Telegram]]></category>
      <category><![CDATA[Pet-проекты]]></category>
      <category><![CDATA[Статьи]]></category>
      <slash:comments>0</slash:comments>
      <pubDate>Fri, 13 Jan 2023 09:34:00 GMT</pubDate>
      <content:encoded><![CDATA[<p>В этой статье я покажу, как написать Telegram-бот на Java с использованием Spring Boot, PostgreSQL и JPA. Также создадим исполняемый jar-файл. Сам же бот будет подсчитывать сообщения от пользователей и записывать эти данные в БД.</p><ol><li><a href="https://tproger.ru/#part1">Создаём Spring проект на Java</a></li><li><a href="https://tproger.ru/#part2">Реализация базового функционала</a></li><li><a href="https://tproger.ru/#part3">Добавление кнопок</a></li><li><a href="https://tproger.ru/#part4">Подключение Telegram-бота на Java к базе данных</a></li><li><a href="https://tproger.ru/#part5">Создание исполняемого jar-файла в Intellij IDEA</a></li><li><a href="https://tproger.ru/#part6">Выводы</a></li></ol><h2>Создаём Spring проект на Java</h2><p>Для этого воспользуемся сервисом быстрого создания <a href="https://start.spring.io/">Spring Initializr</a>: он предоставляет интерфейс для генерации заготовки проекта с добавлением стандартных зависимостей. При необходимости в дальнейшем их можно настроить под свои нужды.</p><p>Мои настройки Spring Initializr выглядят так:</p><figure><img src="https://media.tproger.ru/uploads/2022/12/03869c84-be1d-4d1b-b775-8e34b8b611fd.jpg" alt="" /></figure><p>Обратите внимание на кнопку Add Dependencies: с её помощью можно добавить важные зависимости уже на старте.</p><p>После того, как вы всё указали, нажмите Generate, разархивируйте стартовый проект и откройте его с помощью удобной IDE. У меня это <a href="https://www.jetbrains.com/idea/">IntelliJ IDEA</a>.</p><h2>Реализация базового функционала</h2><p>Для начала напишем на Java самый примитивный Telegram bot, который будет отвечать на наши сообщения.</p><h3>Создание Telegram-бота и конфигурация</h3><p>Начнём с того, что это Maven-проект. Сразу добавим в pom.xml дополнительные зависимости для работы с Телеграм ботом и базами данных:</p><ul><li><a href="https://mvnrepository.com/artifact/org.telegram/telegrambots">Telegram Bots</a></li><li><a href="https://mvnrepository.com/artifact/org.hibernate/hibernate-core">Hibernate Core Relocation</a></li><li><a href="https://mvnrepository.com/artifact/org.postgresql/postgresql">PostgreSQL JDBC Driver</a></li><li><a href="https://mvnrepository.com/artifact/org.projectlombok/lombok">Lombok</a></li></ul><p>В каталоге resources создадим файл config.properties, где будут храниться данные для подключения к боту и в будущем к БД.</p><p>Примечание Данный файл не следует включать в коммиты.</p><p>Теперь создадим бота. Для этого перейдём в Telegram в <a href="https://t.me/BotFather">BotFather</a> и создадим нового бота командой /newbot. Выбираем для него название, которое будет отображаться для всех, и его username. После этого BotFather выдаст токен для взаимодействия с бэкендом Телеграмма.</p><p>Теперь запишем в файл config.properties следующее:</p><p>Добавим в основной каталог проекта пакет config, а внутри него создадим новый класс BotConfig.</p><p>Вы наверняка заметили, что мы добавили в pom.xml <a href="https://projectlombok.org/">Lombok</a>. Это популярная библиотека для сокращения кода и расширения функциональности Java. С ней и Spring наш класс BotConfig будет выглядеть очень лаконично:</p><p>Что здесь происходит?</p><ol><li>@Configuration указывает, что класс содержит методы определения @Bean (наши @Value).</li><li>@Data на этапе компиляции генерирует для всех полей геттеры, сеттеры, toString и <a href="https://tproger.ru/articles/equals-hashcode-java/">предопределяет equals и hashCode</a>.</li></ol><p>С остальным, думаю, всё понятно.</p><h3>Класс Телеграм бота на Java</h3><p>Давайте теперь выйдем из пакета config и создадим в основном пакете проекта класс бота. Поскольку это бот-счётчик, назовём его CounterTelegramBot.</p><p>Сразу унаследуемся от TelegramLongPollingBot — класса, который позволяет взаимодействовать с Telegram. И имплементируем методы getBotUsername, getBotToken и onUpdateReceived. Создадим конструктор и добавим две аннотации перед классом: @Component (авто-создание экземпляра) и @Slf4j (для работы с логером).</p><p>На старте получаем следующий класс:</p><p>Для начала сделаем так, чтобы на команду /start Telegram-бот что-то нам отвечал и выводил в логи сообщение об успехе. Другие сообщения будут выводить в логи "Unexpected message":</p><p>И последним штрихом является инициализация бота. Добавим в пакет config класс Initializer:</p><ol><li>@Autowired обеспечивает контроль над тем, где и как осуществить автосвязывание (чтобы Spring автоматически подключил бота).</li><li>@EventListener — слушатель, который вешаем на изменение класса.</li></ol><p>Запустите и проверьте работу бота.</p><p>Примечание Если возникает ошибка Failed to configure a DataSource, измените аннотацию в исполняемом классе на @SpringBootApplication(exclude = {DataSourceAutoConfiguration.class}). Ошибка исчезнет, как только мы добавим информацию для доступа к БД в config.properties.</p><h2>Добавление кнопок</h2><p>Чтобы Telegram bot на Java и Spring Boot выглядел по-настоящему серьёзным, давайте добавим ему команду /help и пару кнопок.</p><p>Создадим в основной директории проекта пакет components. В него добавим:</p><p>1. Интерфейс BotCommands:</p><p>2. Класс Buttons:</p><p>В классе мы создаём две кнопки, которые будут расположены в одной линии. Одна из них отвечает за команду старта, а вторая — за вызов меню помощи.</p><p>Теперь немного улучшим класс CounterTelegramBot:</p><p>switch вынесли в отдельный метод, добавили обработку команд, в том числе и нажатие кнопок.</p><h2>Подключение Telegram-бота на Java к базе данных</h2><p>Перед началом работы установите <a href="https://www.postgresql.org/download/">PostgerSQL</a>, если СУБД ещё не установлена. В случае, если вы работаете с другими СУБД, просто измените настройки доступа в файле config.properties. Для тех же, кто работает с PostgerSQL, config.properties будет выглядеть примерно так:</p><p>В директорию проекта добавляем пакет database. В нём следует создать:</p><p>1. Класс User:</p><p>2. Интерфейс UserRepository:</p><p>Данный интерфейс нам нужен для удобной работы с CrudRepository — интерфейсом данных Spring для общих операций CRUD. Сюда же вшиваем запрос на апдейт нашей таблицы: добавление +1 сообщения пользователю в случае, если он написал в чат.</p><p>В классе CounterTelegramBot объявим новый интерфейс с аннотацией @Autowired, которая говорит Spring, что в это поле нужно инжектнуть бин:</p><p>Там же создаём метод добавления пользователя в базу данных, если он написал впервые, и просто обновление столбца сообщений, если пользователь уже существует:</p><p>Финально обновим метод onUpdateReceived в классе CounterTelegramBot:</p><p>Примечание Вы можете не делать ограничение по chatId, но тогда следует дополнительно прописать логику для создания отдельной таблицы под каждый чат. В моём случае бот писался под конкретный чат.</p><p>Важно Не забудьте предоставить боту права администратора чата.</p><h2>Создание исполняемого jar-файла в Intellij IDEA</h2><p>У <a href="https://core.telegram.org/bots/api">Telegram API</a> есть одно неприятное ограничение, в соответствии с которым <b>наш бот на Java позволяет достучаться только до сообщений, отправленных за последние 24 часа</b>. Всё, что было отправлено раньше, не учтётся.</p><p>Поэтому после вы можете либо создать exe-файл с установкой времени выполнения, либо воспользоваться удалённым сервером. Например, в статье о <a href="https://tproger.ru/articles/telegram-bot-create-and-deploy/">Telegram-боте на Python</a> мы рассказали, как настроить Docker и задеплоить бота на AWS.</p><p>Здесь же я просто покажу, как создать исполняемый jar-файл для ручного запуска. Костыльно, но для периодического подсчёта из конкретного чата подходит, а далее можно масштабировать по своему усмотрению.</p><p><b>Инструкция по созданию jar-файла:</b></p><ol><li>File – Project Structure – Project Settings – Artifacts – Кликаем по кнопке + – Jar – From modules with dependencies.<br /><a href="https://media.tproger.ru/uploads/2022/12/jarfile-1-step-1.jpg"></a></li><li>Выбираем главный класс проекта и жмем ОK.<br /><a href="https://media.tproger.ru/uploads/2022/12/jarfile-2-step.jpg"></a></li><li>После этого собираем Jar файл: Build – Build Artifact.</li><li>Это создаст .jar, который при двойном клике запустит JVM, если она установлена в ОС.</li></ol><p>На первом же скрине вы можете посмотреть структуру проекта.</p><h2>Выводы</h2><p>Создание Telegram-бота на Java возможно благодаря специальному классу TelegramLongPollingBot, а Spring Boot и Lombok сильно упрощают этот процесс.</p><p>Но стоит отметить, что тот же бот, написанный на Python или PHP, обойдётся вам в меньшее количество строк кода, да и туториалов по таким Телеграм-ботам значительно больше. А вот в качестве практики Java и небольшого пет-проекта, который можно представить в своём резюме, такая программа вполне подойдёт.</p><p>Остались вопросы? Задавайте их в комментариях к этой статье.</p>]]></content:encoded>
    </item>
  </channel>
</rss>