Як я з Claude та ~0.001% свого коду створив TS/NextJS/React/Mongo вебпроєкт
Всі «артефакти» — визначальний опис проекту, перелік реалізованих функцій, посилання на робочу версію та на Github, відео ворк-флоу та інтерфейсу — наприкінці статті.
Останнім часом я сидів без роботи та у відчаї — що робити далі з моїм дивним резюме, яке не цікаве роботодавцям. Та і взагалі зараз начебто важко навіть найпрофесійнішим кодерам, адже скоро всіх нас замінить штучний інтелект. Я написав своєму другові і спитав, чи ніхто в його оточенні не пропонує роботу. Розмова із ним надихнула мене спробувати створити вебпроєкт, про який я давно мріяв. За допомогою коду, згенерованого ШІ, із мінімумом або взагалі без власного кодування.
Скажу, що хоч я досить непогано шарю в JS (навіть створив власну мову програмування, що компілюється у JS, типу CoffeeScript), але я взагалі не бум-бум ні в Typescript, ні в NextJS, ні MongoDB, ні в навіть React. Що таке Docker — я мав про це поверхневе уявлення. Звісно, я намагався «освоїти» React, NextJS та Mongo, але далі прочитання доків справа не пішла (добре, що більше ніколи не знадобиться цим заморочуватися!), тож я продовжував лабати на Vanilla. Для контексту — я Full Stack задрот та багато років вперто тапав на PHP, але останній великий проєкт все ж таки виконав на NodeJS/Express.
Отже, з таким бекграундом можна влаштуватися хіба шо у піхоту, тож я таки вдався до авантюри та вирішив створити проєкт, який давно уявляв. Візуалізований менеджер або планувальник проєктів, що дозволяє розбивати їх на задачі, а задачі на пізадачі за допомогою ШІ. Ви просто вказуєте назву будь-якого проєкту, його опис, та отримуєте задачі, які потрібно виконати, щоб проєкт втілився. Розбити на підзадачі можна і будь-яку задачу також. Це дозволяє менше заморочуватися над плануванням — особливо над плануванням нових проєктів.
Інтерфейс проєкту:
Так, я знав про існування Cursor та навіть Windsurf, а згодом дізнався про Cline — хайп у Твітері щодо цих речей великий, якщо у вас правильні підписки. Але щось мене втримало від занурення в ці технології, особливо враховуючи факт, що для повноцінної реалізації і досягнення мети потрібно невідомо наскільки більше, ніж $20 за місячну підписку. Тож я обрав те, що мені на той момент подобалося найбільше — ШІ від Anthropic, який до того ж був попереду всіх у кодуванні (зараз, згідно з деякими рейтингами, це Gemini 2.5, до речі).
Я почав працювати у січні і продакшн-версію релізнув в кінці березня, тож на все-про-все пішло трохи більше 2 місяців загалом, $60 та декілька сотень (близько 400) контекстних комунікацій із Claude. Спочатку це була 3.5 версія, згодом 3.7 із Deep Thinking. Різниця, скажу я вам, відчутна. По-перше, 3.5 обрізає великі bash-скрипти та великі файли (так — я генерував файли здебільшого за допомогою bash, що дозволяло створювати декілька за раз); ви маєте ввести «Continue», щоб продовжувати генерацію одного великого bash-скрипту або окремого файлу, що не зручно, бо обрізання часто буває не точно з місця обривання і трапляється весь час. Такий недолік хоч і присутній в 3.7+Thinking, але виражений не так сильно, бо в новій версії із думанням контекст відповіді набагато більший.
Найбільша технічна конфа ТУТ!👇
Claude дає певний ліміт токенів 1 раз на 5 годин. Щоб працювати в такому середовищі ефективно, мені потрібно було заводити будильник і прокидатися вночі, щоб не втрачати цінні «контекстні вікна». Якби я так не робив, то це б призвело до + 10 днів до часу на виконання.
А зараз про корисне. Як саме можна (?) реалізувати вебпроєкт «будь-якої складності» за допомогою спілкування з будь-яким ШІ, який може генерувати артефакти із кодом.
1. Максимально деталізований опис проєкту. Ключове тут «максимальна деталізація» та попередня продуманість. Орієнтовно додатковий день на планування, що втілюється в деталізованому описі, економить тиждень на реалізацію. Але навіть якщо ви почнете лише з маленького опису — це прийнятно, якщо ви знаєте, що робити далі. Утім, якщо деталізований опис не заданий визначально, це призведе до того, що AI почне видумувати функціонал: в деяких випадках він може вважатися корисним і доречним, але іноді це щось несподіване, що може перерости у зайве та внести хаос і в без того широку структуру. Адже ШІ схильний «випускати» більше, а не менше. Змусити ШІ бути лаконічним — це складна задача.
2. XML. Хоч markdown теж ок, але ви з часом зрозумієте, що XML — краще. Врешті я почав майже все намагатися оформити у XML. Якщо ви у запиті посилаєтесь на певний, часто вкладений
3. Створення і розвиток першого запиту. Перший запит має бути у вигляді високо-структурованого
<initial-prompt> <metadata> Назва проекту, короткий опис, абсолютний шлях до директорії проекту, назва бази даних, логін і пароль бази даних і таке інше. </metadata> <project-description статус="згодом видалено"> Деталізований опис проекту своїми словами </project-description> <system> Структуроване перетворення деталізованого опису проекту, що з'явилися як результат окремого запиту типу: "структуруй деталізований опис проекту в XML" </system> <technical-specification> З'явилося, як результат окремого запиту типу: "ось набір бажаних технологій та технічних умов, опис проекту, структурований опис - створи технічні специфікації" </technical-specification> <implementation-hierarchy> З'явилося, як результат окремого запиту типу: "ось набір бажаних технологій та технічних умов, опис проекту, структурований опис, технічні специфікації - створи структуру аспектів -> компонентів -> суб-компонентів -> елементів проекту у XML" </implementation-hierarchy> <some-existing-files> Деякі загальні/технічні/конфігураційні файли, наприклад .env, next.config.js, src/middleware.ts </some-existing-files> <implementation-flow уточнення="використовується на етапі створення компонентного фундаменту"> Розділення на компоненти: файлова структура компоненту, інтерфейси/типи, приклади використання та інтеграція, поради та призначення. </implementation-flow> <file-structure> XML файлова структура проекту особливого типу - не повні файли, а шляхи до файлів, їх призначення, експорти та їх призначення, приклади використання. </file-structure> <behavior> У 3.5 це були кастумні інструкції щодо попереднього думання; також інструкції щодо Problem Solving Strategy. </behavior> <file-modification-instructions> Інструкції щодо "модифікаційних артефактів" - щоб ШІ не генерував повні версії файлів, а лише інформацію достатню, щоб змінити частину: XML modificators. </file-modification-instructions> <beta-testing уточнення="використовується на другому етапі"> Опис кроків бета-тестування із фокусом на не виконаному кроці <step completed="false"> </beta-testing> <updates> Опис доповнень із фокусом на не виконаному доповненні <update completed="false"> </updates> <context-files уточнення="для другого та третього етапів"> Повні версії файлів контексту </context-files> <request> Результат еволюції великого та в свою чергу структурованого запиту: - Як треба працювати з елементами @{initial-prompt} - Як створювати bash-script для генерації - <important>, <very-important>, <most-important-tips>, <advise>, <necessities>, <before-response>, <before-starting-implementation>, <before-generating-any-file>, <before-implementation-script-generation>, <rules>, <strict-rule>, <logger> </request> <additional-request with="real examples"> 1) Solve issues action-by-action independently; do not mix solutions for several independent issues; 2) Read and learn @{context-files} </additional-request> <highest-priority-request> ... </highest-priority-request> <initial-prompt>
4. Етапи реалізації. Вийшло розділити реалізацію на три етапи:
— Формування компонентного фундаменту. Спочатку це перетворення детального опису в структуру компонентів (які є складовими частинами аспектів). З кожним окремим запитом потрібно посилатися на черговий компонент із вимогою його реалізації. Наприкінці контекстної комунікації, коли всі файли включно із тестами сформовані, потрібно узагальнити роботу та доповнити @{implementation-flow} — щоб @{initial-prompt} розвивався та містив узагальнену імплементацію. Під час цього етапу створюється статична основа проєкту. У мене вийшло 9 аспектів.
— Бета-тестування. Хоч це не «бета-тестування» у широкому сенсі, але назву для цього етапу мені запропонував ШІ. Це етап динамічної імплементації. Для мене перший крок був «Зайти на першу сторінку, перейти на сторінку реєстрації, зареєструватися». Так, по черзі ви описуєте всі кроки user-flow у структурованому вигляді. Для бета-тестування я створив другу версію темплейту @{initial-prompt}, де посилався на кожен крок бета-тестування для його імплементації. Всього у мене вийшло 25 кроків.
— Апдейти. Це вже коли ви після того, як вирішили, що проєкт готовий до продакшену, захотіли додавати нові фічі. Для цього я створив третю версію @{initial-prompt}.
5. Бекапи. Обов’язково зберігайте досягнення після кожного вдалого контекстного спілкування із ШІ. Без цього неможливо. Я навіть окрім гіту створив кастумний скрипт зберігання, типу @backup latest-fixes та @restore latest-fixes із нумерацією: backups/latest-fixes1, backups/latest-fixes2,...
6. Vscode extensions. Перелік розширень, які я створив за допомогою ШІ для автоматизації та поліпшення процесу реалізації:
— File To XML — перетворює шлях до файлу із буферу обміну в XML його контенту та шляху до нього в буфер обміну.
— Files Modificator — вносить правки у файли із XML modificator з буферу обміну.
— Open Created Files — коли файли створюються із допомогою bash-script, вони відкриваються автоматично.
— Shell Script Runner — при зберіганні sh файлу, він запускається.
— TypeScript Error Collector — збирає error hints, згенеровані Vscode/Eslint у XML структуру у буфер обміну.
— XML Compressor — компресує XML у версію без пробілів/відступів між тегами.
Історія про те, як це відбувалося на практиці
Коли я починав, то не мав найменшого уявлення, що робити. Логічно було створити опис проєкту, узагальнити думки, які формувалися впродовж тривалого часу. Потім ШІ перетворив опис проєкту в XML. Наступне, що я зробив — це на основі наявних даних та додаткового запиту створив sh-скрипт під назвою setup.sh, який згенерував мені файли, що дозволили запустити докер-контейнер із NextJS/MongoDB-проєктом. (Звісно, це вийшло не з першої, а з... третьої(?) спроби, тобто я починав роботу над імплементацією проєкту 3 рази).Почали генерувати файли перших компонентів, і я здогадався, що потрібно доповнювати @{initial-prompt}, тому доповнив його @{implemenetation-flow of initial-prompt}, де розміщував узагальнену інформацію щодо створених файлів (і відповідних можливостей) компоненту.
Ще до появи Claude 3.7 я створив кастумну інструкцію, де вказував ШІ <thinking> перед кожною відповіддю. Це покращило ефективність. Для покращення ефективності я також застосував декілька інших вигаданих мною методів.
До @{implementation-hierarchy} я додав <tree> такого виду:
1. Core Infrastructure
├──System Logging
│ └──Logger System
│ ├──LoggerConfiguration
│ └──LoggerInstance
Щоб зекономити на розмірі контексту, в @{implementation-hierarchy} розміщую лише виконані компоненти та поточний компонент до виконання (мається на увазі їхній структурований опис, який сформувала ШІ), та, по-друге, згодом почав прибирати деякі компоненти, що явно не стосувалися поточного імплементованого компоненту.
Згодом, із появою Claude 3.7, проблема розміру контексту стала менш критичною. Але з часом, коли проєкт збільшувався, ця проблема все одно поступово загострювалася, тож потрібно було весь час переглядати, що видалити із @{initial-prompt}, що зробити більш ефективно-скороченим.
Часто доводиться переносити контекст — це тому, що розмір контекстного вікна однієї розмови складає 200k токенів. Він закінчується раптово. Для перенесення потрібно створити окремий XML структурований запит, що має сумувати прогрес поточного контексту для продовження у наступному.
Для кожного компоненту створювалися jest-тести, тож підсумком реалізації компоненту було jest-тестування. Я не заглибився у подробиці того, якими саме мають бути тести, та даремно. На практиці більшість справжньої тестувальної роботи будо виконано під час бета-тестування у такому вигляді: ШІ створює *додаткові до наявних* файли, що стосуються дії кроку бета-тестування (наприклад, реєстрація користувача). я намагаюся реєструватися, якщо не виходить — описую, що саме, ШІ створює нові версії файлів — і так по колу. Постійно доводиться збирати помилки, які підказує Vscode, та ітеративно добиватися безпомилкового вигляду файлів. Але крім цих попередніх помилок є ще помилки/проблеми реалізації — щоб їх виправити, потрібно детально описувати проблему. Якщо проблема не вирішується, я або намагаюся розділити проблему на частини, або перезапускаю контекст, описуючи проблему у визначальному запиті вже більш детально із врахуванням досвіду її вирішення. Деякі складні проблеми вирішувалися з першої спроби, але деякі, здавалося б, прості — декілька днів.
Найскладніша задача — добитися від ШІ, щоб не відбувалося генерації зайвого коду. Спочатку у мене було створено багато зайвого коду, але з часом я зрозумів, як потрібно готувати визначальний запит, які файли контексту обирати, як їх обирати.
Під час бета-тестування я прийшов до створення @{file-structure} . Наприкінці роботи над дією бета-тестування за допомогою спеціального запиту я прошу ШІ сформувати порцію новоствореної файлової структури, яку додаю до файлу file-structure.xml, потім за допомогою окремого скрипта (створеного, як і всі інші, за допомогою ШІ) я обробляю file-structire.xml у file-structure-extracted.xml, намагаючися відкинути
Є різниця між @{file-structure} та @{context-files}. @{file-structure} — це не повні файли, а шляхи файлів, описи призначення/застосунку файлів, перелік їхніх експортів та приклади застосування. В той час, коли @{context-files} — це повні файли, часто *передбачені* для наступного контексту. У @{request} я прошу ШІ перед початком роботи кожного разу оцінювати наявні файли контексту та файли структури і пропонувати додаткові файли, як можуть знадобитися для максимально ефективного втілення задачі.
Логер
Першим компонентом ШІ запропонував створити логер, який є переробленим console.log, для типізації повідомлень [info/warn/error/debug]. Це корисно, бо ШІ сам формує необхідну інформацію для логів, яку треба було час від часу копіпастити у контекст для вирішення проблем. Варто використовувати саме такий logger, а не стандартний, тому що його можна доповнювати. А доповнювати є чим. Наприклад, з часом я зрозумів, як потрібно вдосконалити логінг:
1. Додати стилізацію. Хоч це є в стандартних, але у визначального logger, створеного ШІ, цього не було.
2. Додати ключові слова. Разом із файлом logger.config.json це дозволило створити можливість фільтрувати логи за ключовими словам. Це дуже корисно, бо з часом логів буде дуже багато. Наприклад у мене, можливо, 30% всього коду у файлах стосується логів. Хоч я у запиті і вказав «побільше логів», але щоб стільки... Тому щоб надавати лише потрібні логи, третім аргументом в моїх логерах є список ключових слів. Я редагую logger.config.json, вказуючи, по яким ключовим словам потрібно зараз відобразити логи. Скажу, що функції фільтрування логів, яка є у браузері, недостатньо.
3. Додати технічну інформацію про файл логу та номер рядка виклику. Взагалі другий аргумент — об’єкт на вивід можна доповнювати технічними/опціональними «фічами».
Поради
Якщо ви не розумієте, чому ШІ не виконує ваші інструкції і це вас спантеличує і ви «опускаєте руки» — не сумуйте. Просто додайте у <request> інструкцію, яку ігнорує ШІ, ще раз, бажано іншими словами, обрамлену в інший тег, накшталт <very-strict-rule>. Саме повтори інструкцій збільшують до них увагу і їхню вагу. Назви тегів мають значення.
Майте терпіння! Якщо після численних спроб ШІ ніяк не може виконати задачу або вирішити проблему — зробіть паузу і спробуйте переосмислити запит, розбийте проблему на складові частини і вирішуйте їх поступово. Уникайте спроб вирішувати декілька проблем одночасно, якщо не впевнені, що ШІ може це зробити (з досвідом інтуїція починає працювати в цьому напрямку). Не покладайтеся повністю на ШІ, розберіться в проблемі/задачі/питанні самостійно — це допоможе переосмислити. Знайдіть, що є витоком/першоджерелом проблеми, нехай ШІ проаналізує його. Нехай переробить файли з нуля, хоч це призведе до втрати вторинного функціоналу. Повторюйте спроби, поки проблема не буде вирішена — це завжди спрацьовує.
Слідкуйте за тим, які файли до якого аспекту/компоненту належать. Можна завести окремий файл, в якому асоціювати аспекти/компоненти або кроки/дії бета-тестування із списком відповідних файлів. Це допоможе швидко відновлювати роботу у певному контексті.
Перебудуйте мислення. Працюючи із ШІ, ви якби становитесь керівником, а ШІ — виконавцем. Для успіху потрібно відійти від «мислення кодера», тобто не розглядати проєкт з точки зору того, яким чином ви будете імплементувати код. Головними навичками тепер стає вміння побачити взаємопов’язане-ціле (holistic view) та вміння описати те, що ви хочете втілити.
Роздуми про майбутнє
Чи потрібно це вивчати? Через деякий час, можливо, дуже скоро або лише через пару років, програмний проєкт будь-якої складності можна буде виконувати спілкуванням із ШІ. Швидше за все, кодування більше не буде ні для кого з людей (крім якихось диваків). Адже ніхто не множить навіть двозначні числа без калькулятора, так? Чи варто одразу стрибнути в цей момент (вчора ви ще писали код, а сьогодні ШІ кодить те, що ви описуєте своїми словами) без плавного переходу? Можливо, декому і вдасться, але шлях переходу несе ризики втрат — «виживуть» не всі. Адже тепер одна людина зможе виконувати більше роботи, ніж 10 (грубо кажучи). Тож, можливо, і варто починати тренуватися взаємодіяти із ШІ, бо ця навичка стане у майбутньому основною для всіх. Після цієї роботи у мене з’явилося відчуття, що я досяг чогось дуже потрібного, можливо, не такого вираженого зараз, коли перехід ще тільки починається, але його обриси на обрії майбутнього проявляються з неодмінною впевненістю, хвилі сили трансформації розповсюджують суттєвий вплив навіть на час теперішній.
Що мені цікаво зараз? Я хотів би навчати взаємодії із ШІ — тому, що сам навчився під час виконання цього проєкту — як команди розробників, так і індивідуально. Мені цікаво взаємодіяти із підприємливою і перспективною особистістю для втілення стартапу; цікаво виконувати дуже складний проєкт за допомогою ШІ на замовлення.
Найбільше захоплює думка брати участь у стартапі, який би займався питанням повної автоматизації взаємодії із ШІ для створення вебпроєктів.
Опис проєкту AI Project Planner
— user will be defined by nickname and password, so the home page for the new user will be text-field asking to sign-up or sign-in. user data for auto sign-in and continue session will be stored in localStorage, while user’s password with nickname will be stored on backend database;
— when user signed in, this would be initially a plane area with text field offering to name and describe the project;
— when user sends a project name and description, it transferred with chosen ai api (openai by default) on frontend, requesting AI to split a described project to separate tasks. ai api is requested directly, not through backend;
— frontend receives these tasks and build svg structure: on the center of screen is rectangle with project name/description; from center rectangle arrows are drawn to other rectangles that are evenly distributed around the project rectangle, in each rectangle a description of a task appears. each task rectangle has a tangent icon, clicking on which the request is sent to the ai api which splits this task into tasks and return to the frontend. such prompt indicates parent chain of tasks up to project included for understanding context;
— when task is expanded: task rectangle itself, its child tasks and arrows to them remains visible; arrow from parent project/task rectangle and parent project/task rectangle become half-transparent and put on lower layer; all others svg elements become invisible; child tasks rectangles appeared around task’s rectangle with arrows to them from the task (similary like for project -> tasks). such functionality is the same for every ask: task is also can by expanded to its children tasks in similar way;
— if user click on already previously expanded task or project rectangle, nothing sent to ai api, its children tasks received from backend and hidden/half-transparent rule for svg elements is the same;
— task rectangle which has children tasks has tangent icon which shows number of direct children and all descendant tasks;
— name is extracted from project description as — or the first sentence neither the first line on the text;
— when project’s direct children tasks received, existing project data (these tasks specifically) is stored to backend. when a task’s children tasks are received — they stored on backend;
— children rectangles always distributed evenly around parent’s rectangle, center of each child rectangle should be on the same distance to centers of nearest/neighbour subling rectangles and distance from center of each child rectangle to center of parent rectangle should be equal to each other. child rectangles should not intersect. distance from parent task/project to task should be defined dynamically, which depends on quantity of children tasks;
— if text of task is too long, there should be reasonable maximum height of rectangle. width of a rectangle should have also reasonable maximum width;
— if full text is not fit rectangle size, there is «show more» icon shown — when user clicks on such rectangle — it increased to bottom in size and full text is shown;
— user can move working 2D area by dragging it to all directions (like it realized on maps);
— zoom is not necessary for this version;
— system will be designed for further use with any ai api, but initially it will be used with openai api;
— the backend will be used to store a project data, with it’s tasks for the user;
— the working area, which named «desk» or «deck» (choose more appropriate), will have fixed pane on the left side with icon on the top left which opens/close this pane, there will be one icon-button when pressed is opened window with text-field, where user put their openai api key which stored in localStorage and will be used for the ai api;
— task could be regenerated: for this another tangent icon is located on task rectangle; by pushing it, all children tasks hierarchy are removed and with special prompt via ai api is requested text of the new task. in such prompt indicated parent chain of tasks up to project included and sibling tasks, text of current task is not generated and asked to generate one more additional task to sibling tasks
— task could be deleted: for this another tangent icon is located on task rectangle, by pushing it, all children tasks hierarchy are removed;
— before task to be regenerated, user asked to approve regeneration request;
— on regeneration and removal db and ui are refreshed respectivelly;
— on the side pane there is icon which opens window where user can choose a project from the list of their projects. when user chooses project it’s structure is loaded from backend. when a project is loaded, project’s rectangle is shown along with direct child tasks and arrows to them on the center of the screen;
— projects and tasks are not public and visible only to user who created/own them.
Функціонал проєкту AI Project Planner, код для якого «повністю» реалізувала Claude
— Setup/файл інсталяції необхідних файлів для створення Docker container із проектом NextJS/MongoDB.
— Колекції і індекси бази даних.
— Авторизація користувача із мінімально необхідними перевірками.
— Підтримка авторизованої сесії; авторизовані запити; персональні дані.
— Перевірка валідності, зберігання ключа OpenAI API на фронтенді в localStorage.
— Фронтенд запити до OpenAI API -> completion.
— Інтерфейс створення/декомпозиції проекту.
— Першопочаткові версії необхідних запитів до AI для розбивки проекту/задачі на задачі та регенерації задачі.
— Список проектів, сортування списку, виділення та відкриття проекту.
— Бокова toggle панель.
— Видалення проекту.
— Рендерінг проекту в SVG елементи.
— Підтримка ієрархії проекту; визначення кількості children та загальної кількості задач/під-задач проекту/задачі; їх відображення.
— Геометрія, географія, правила візуалізації SVG елементів; конектори між елементами; менеджер перекриттів.
— Зум / драгінг SVG;
— Показати більше/менше тексту (опису задачі або проекту).
— Анімація центрування на елементів.
— Інтерфейс та функціонал регенерації та видалення задач.
— Обробка помилок і тост-повідомлення про помилки AI API.
— Зберігання та відновлення стану проекту (фронтенд).
— Дизайн.
— Мобільна версія.
— Девелопмент і продакшен версії.
Посилання
— Лінка на робочу версію (потрібно мати робочий OpenAI API key для повноцінного користування, API key не передається на сервер і зберігається в localStorage)
— Лінка на відео
— GitHub
— Бонус: мій список ШІ в Твіторі, що сприяє обізнаності в сучасних трендах
135 коментарів
Додати коментар Підписатись на коментаріВідписатись від коментарів