| Version 1 (modified by , 5 days ago) ( diff ) |
|---|
BuildInstructions
Содржина
Оваа страница ја опишува развојната околина, начинот на градење и начинот на тестирање на проектот Shifter Web App (гранка main).
Опис на развојната околина
Архитектура на проектот
Shifter е веб-апликација составена од два независни дела кои се пуштаат одделно:
| Компонента | Технологија | Директориум | Порта (локално) |
| Backend (REST API) | Java 17, Spring Boot 3.5.3, Spring Security (JWT + OAuth2), Spring Data JPA / Hibernate, Maven | backend/ | 8080
|
| Frontend (SPA) | React 19, TypeScript 5.8, Vite 6, Tailwind CSS 4, react-i18next | frontend/ | 5173
|
| База на податоци | PostgreSQL | – | 5432
|
Задолжителен софтвер
| Софтвер | Верзија | Зошто е потребен | Проверка |
| Git | било која | Преземање на изворниот код | git --version
|
| JDK (Java Development Kit) | 17 (Temurin / OpenJDK / Oracle) | Компајлирање и извршување на backend-от; pom.xml е фиксиран на java.version=17 | java -version
|
| Maven | не се инсталира одделно | Проектот има Maven Wrapper (mvnw / mvnw.cmd) кој сам ја презема Maven 3.9.9 | ./mvnw -v
|
| PostgreSQL | 14 или понова (драјвер 42.7.7) | База на податоци на апликацијата | psql --version
|
| Node.js | 20.19+ или 22.12+ (LTS) | Градење и пуштање на frontend-от (Vite 6 / React 19) | node -v
|
| npm | 10 или понова (доаѓа со Node.js) | Инсталација на frontend зависности | npm -v
|
| Веб-прелистувач | Chrome, Firefox, Edge или Safari (актуелна верзија) | Тестирање на апликацијата | – |
Надворешни сервиси и клучеви
Backend-от се поврзува на неколку надворешни сервиси. Клучевите се внесуваат преку променливи на околината, види Конфигурација на backend.
| Сервис | За што служи | Потребен за подигање на апликацијата? |
| PostgreSQL | Главна база на податоци | Да – без неа апликацијата не се подига |
| ZeptoMail (Zoho) | Емаил за верификација, потврди за состаноци, контакт-форма | Да – клучот мора да постои; мора да е и валиден за регистрација преку емаил |
| Google Cloud – OAuth 2.0 Client ID | Најава со Google („Sign in with Google“) | Да – вредностите мора да постојат |
| Google Cloud – Service Account + Calendar ID | Читање слободни термини од календарот на експертот | Да – види Google Service Account, инаку подигањето паѓа со грешка
|
| Amazon S3 | Прикачување и чување фајлови (слики, материјали) | Да – вредностите мора да постојат |
| Zoom (Server-to-Server OAuth App) | Автоматско креирање Zoom состанок при закажување консултација | Да – вредностите мора да постојат |
ВАЖНО: повеќето променливи во application.properties немаат стандардна вредност (пр. ${AWS_S3_REGION}, ${JWT_CONFIG_SECRET}, ${ZOOM_CLIENT_ID}). Ако некоја од нив недостасува, Spring нема да успее да ги создаде бавовите и апликацијата воопшто нема да се стартува. За локален развој е сосема во ред да се стават лажни (dummy) вредности за сервисите што нема да ги тестирате – важно е клучевите да постојат.
Инструкции за градење
Преземање на изворниот код
git clone <URL-на-репозиториумот> Shifter-Web-App cd Shifter-Web-App git checkout main
Структура на проектот:
Shifter-Web-App/ ├── backend/ # Spring Boot апликација (Maven) ├── frontend/ # React + Vite апликација (npm) └── modeling/ # модели и дијаграми
Подготовка на базата на податоци
Инсталирајте и стартувајте PostgreSQL, па креирајте корисник и празна база:
CREATE USER shifter WITH PASSWORD 'shifter'; CREATE DATABASE shifter OWNER shifter; GRANT ALL PRIVILEGES ON DATABASE shifter TO shifter;
Не е потребно рачно да се извршуваат SQL скрипти. На гранката main вредноста е spring.jpa.hibernate.ddl-auto=update, што значи дека Hibernate автоматски ги креира и ажурира сите табели при првото стартување на backend-от. Во продукцискиот профил prod вредноста е validate, т.е. шемата мора веќе да постои.
Конфигурација на backend
Backend-от при стартување чита .env датотека (библиотека dotenv-java). Датотеката не е во Git (наведена е во .gitignore), па мора рачно да се создаде на патека backend/.env:
# ===== Основно ===== SPRING_PROFILES_ACTIVE=default PORT=8080 BACKEND_URL=http://localhost:8080 FRONTEND_URL=http://localhost:5173 ALLOWED_ORIGINS=http://localhost:5173 # ===== База на податоци ===== SPRING_DATASOURCE_URL=jdbc:postgresql://localhost:5432/shifter SPRING_DATASOURCE_USERNAME=shifter SPRING_DATASOURCE_PASSWORD=shifter DDL_AUTO=update SHOW_SQL=true # ===== JWT (мин. 32 знаци, HS256) ===== JWT_CONFIG_SECRET=promeni-go-ovoj-taen-kluc-min-32-znaci!! JWT_EXPIRATION=86400000 JWT_REFRESH_EXPIRATION=604800000 COOKIE_SECURE=false COOKIE_SAME_SITE=Lax # ===== Amazon S3 ===== AWS_S3_REGION=eu-central-1 AWS_S3_BUCKET_NAME=shifter-bucket AWS_S3_ACCESS_KEY=xxxxxxxxxxxx AWS_S3_SECRET_KEY=xxxxxxxxxxxx # ===== Емаил (ZeptoMail) ===== ZEPTOMAIL_API_KEY=xxxxxxxxxxxx # ===== Google OAuth2 ===== GOOGLE_CLIENT_ID=xxxxxxxxxxxx.apps.googleusercontent.com GOOGLE_CLIENT_SECRET=xxxxxxxxxxxx # ===== Google Calendar ===== GOOGLE_EXPERT_CALENDAR_ID=expert@shift-er.com # алтернатива на service-account.json (Base64 од JSON фајлот): # GOOGLE_CALENDAR_SERVICE_ACCOUNT_JSON_BASE64=xxxxxxxxxxxx # ===== Zoom (Server-to-Server OAuth) ===== ZOOM_ACCOUNT_ID=xxxxxxxxxxxx ZOOM_CLIENT_ID=xxxxxxxxxxxx ZOOM_CLIENT_SECRET=xxxxxxxxxxxx # ===== Логирање ===== LOG_LEVEL=INFO APP_LOG_LEVEL=DEBUG
Google Service Account
Класата GoogleCalendarService се иницијализира при подигање на апликацијата. Ако не најде credentials, целата апликација паѓа со GoogleCalendarException: Service account JSON not found in classpath or environment.
Затоа мора да обезбедите еден од следниве два начина:
- Поставете ја JSON-датотеката на Service Account-от на патека
backend/src/main/resources/service-account.json(датотеката е во.gitignoreи не се комитира). - или поставете ја променливата
GOOGLE_CALENDAR_SERVICE_ACCOUNT_JSON_BASE64со Base64-кодирана содржина на истата датотека:
base64 -i service-account.json | tr -d '\n'
Service Account-от треба да има пристап (Google Calendar API scope https://www.googleapis.com/auth/calendar) до календарот наведен во GOOGLE_EXPERT_CALENDAR_ID.
Google OAuth2 redirect URI
Во Google Cloud Console, во OAuth 2.0 Client ID, додајте го овој Authorized redirect URI:
http://localhost:8080/login/oauth2/code/google
Компајлирање и стартување на backend
Сите команди се извршуваат од директориумот backend/.
cd backend # Компајлирање и градење (Linux / macOS) ./mvnw clean package -DskipTests # Компајлирање и градење (Windows) mvnw.cmd clean package -DskipTests
Резултат: извршна JAR-датотека backend/target/shifter.jar.
# Стартување во развоен режим ./mvnw spring-boot:run # или стартување на изградената JAR-датотека java -jar target/shifter.jar
Проверка дека backend-от работи:
curl http://localhost:8080/actuator/health
# очекуван одговор: {"status":"UP"}
Конфигурација и градење на frontend
Сите команди се извршуваат од директориумот frontend/.
Прво креирајте frontend/.env – frontend-от бара една променлива:
VITE_BACKEND_URL=http://localhost:8080
Потоа:
cd frontend npm install # инсталација на зависностите npm run dev # развоен режим → http://localhost:5173 npm run build # TypeScript проверка + Vite build → frontend/dist/ npm run preview # локален преглед на изградената верзија npm run lint # ESLint проверка
Содржината од frontend/dist/ се качува на статички хостинг; проектот содржи vercel.json со SPA rewrite правило за Vercel.
Цел редослед на пуштање
# 1. Стартувај PostgreSQL и создај база `shifter` # 2. Backend cd backend # создај .env и service-account.json ./mvnw spring-boot:run # → http://localhost:8080 # 3. Frontend (во нов терминал) cd frontend # создај .env со VITE_BACKEND_URL npm install npm run dev # → http://localhost:5173
Продукциско градење и пуштање
- Backend: поставете
SPRING_PROFILES_ACTIVE=prod. Профилотprodавтоматски вклучуваspring.jpa.hibernate.ddl-auto=validate(шемата мора да постои однапред),cookie.secure=trueиcookie.same-site=Strict(задолжителен HTTPS), намалено логирање и сокриени stack trace-ови. - Поставете ги
BACKEND_URL,FRONTEND_URLиALLOWED_ORIGINSна вистинските домени;ALLOWED_ORIGINSприфаќа повеќе вредности одделени со запирка. - Додајте го продукцискиот redirect URI во Google Cloud Console:
https://<backend-domen>/login/oauth2/code/google. - Frontend:
npm run buildи качете гоfrontend/dist/; поставетеVITE_BACKEND_URLна продукцискиот backend домен.
Чести проблеми при градење
| Проблем | Причина | Решение |
Could not resolve placeholder 'AWS_S3_REGION' (или слична променлива) | Недостасува променлива во .env | Додајте ја во backend/.env; за нетестирани сервиси ставете dummy вредност
|
GoogleCalendarException: Service account JSON not found | Недостасува service-account.json | Види Google Service Account
|
Connection refused кон PostgreSQL | Базата не работи или е погрешен URL | Проверете дали PostgreSQL е стартуван и дали SPRING_DATASOURCE_URL е точен
|
| CORS грешка во конзолата на прелистувачот | ALLOWED_ORIGINS не ја содржи адресата на frontend-от | Додајте http://localhost:5173 во ALLOWED_ORIGINS
|
| Мрежни грешки во frontend-от / празни податоци | Недостасува frontend/.env | Создајте .env со VITE_BACKEND_URL=http://localhost:8080 и рестартирајте npm run dev
|
WeakKeyException при најава | JWT_CONFIG_SECRET е пократок од 32 знаци | Поставете подолг таен клуч |
| Грешки „cannot find symbol“ за getter/setter методи во IDE | Исклучено annotation processing (Lombok/MapStruct) | Вклучете Enable annotation processing во IDE-то
|
| Vite не се подига | Стара верзија на Node.js | Инсталирајте Node.js 20.19+ или 22.12+ |
Инструкции за тестирање
Shifter е веб-апликација, па се тестира преку веб-прелистувач.
Каде се пушта апликацијата
| Што | Адреса |
| Frontend (корисничкиот дел) | http://localhost:5173 |
| Автоматско пренасочување со јазичен префикс | http://localhost:5173/en или http://localhost:5173/mk |
| Backend REST API | http://localhost:8080/api |
| Health check | http://localhost:8080/actuator/health |
| Најава со Google | http://localhost:8080/oauth2/authorization/google |
Кориснички имиња и лозинки
Апликацијата нема однапред креирани (seed) корисници. При првото стартување базата е празна и сметката се креира преку формата за регистрација.
| Тип на пристап | Корисничко име | Лозинка |
| Апликација (регистриран корисник) | вашата емаил адреса, пр. test@example.com | лозинка што ја бирате при регистрација, пр. Test123!
|
| Апликација (Google најава) | вашата Google сметка | управувана од Google (нема лозинка во апликацијата) |
| PostgreSQL база | shifter (или postgres) | онаа што сте ја поставиле, пр. shifter
|
Правила за лозинката при регистрација – се проверуваат во формата:
- најмалку една голема буква (A–Z)
- најмалку една цифра (0–9)
- најмалку еден специјален знак (
!@#$%^&*(),.?":{}|<>) - двете полиња за лозинка мора да се совпаѓаат
Пример за валидна тест-сметка: test@example.com / Test123!
Совет за тестирање без валиден емаил-клуч: регистрацијата преку емаил испраќа порака за верификација преку ZeptoMail и, ако клучот не е валиден, целата регистрација паѓа бидејќи трансакцијата се враќа назад. Ако немате валиден ZEPTOMAIL_API_KEY, тестирајте со Најава преку Google – тој тек не испраќа емаил и корисникот автоматски се означува како верификуван.
Мини-водич низ главните елементи
Долниот водич ги поминува главните екрани по редослед на нормално користење.
Чекор 1: Почетна страница
- Отворете http://localhost:5173 – автоматски ќе бидете пренасочени на
/en(или/mk). - Navbar (горе): линкови до
Курсеви,Менторство,Консалтинг,Академии,За Нас,Контакт,Бесплатна Сесијаи копчеНајави се / Регистрирај се. - Јазичен прекинувач (долу десно, знаменце): менува меѓу EN и MK; јазикот се одразува во URL-то (
/en/...↔/mk/...). - Footer: контакт информации и линкови до социјални мрежи.
Чекор 2: Регистрација
- Кликнете
Најави се / Регистрирај се→Регистрирај се(/en/register). - Внесете емаил, лозинка и потврда на лозинката – види
Кориснички имиња и лозинки. - Алтернативно кликнете „Continue with Google“ за најава преку Google сметка.
- По успешна регистрација, апликацијата автоматски ве носи на страницата за персонализација (
/welcome).
Чекор 3: Верификација и персонализација (/welcome)
- Страницата го чита
tokenпараметарот од URL-то и ја верифицира вашата емаил адреса. - Пополнете ги полињата: Целосно име, Работно место и Големина на компанијата (Фриленсер, Микро, Мала, Средна, Среден пазар, Голема компанија, Друго).
- Кликнете
Започни да користиш Shifter. Профилот сега е комплетен и сите заштитени страници стануваат достапни. - Ако верификацијата не успее, постои копче
Испрати нов емаилза нов линк за верификација.
Чекор 4: Најава (/login)
- Внесете емаил и лозинка, или користете
Continue with Google. - По најава access token се чува во меморија, а refresh token во
HttpOnlyколаче; сесијата се обновува автоматски при истек (401 →/api/auth/refresh).
Чекор 5: Профил (/profile)
- Мој Профил – измена на име, работна позиција и големина на компанијата; се зачувува со
Зачувај Промени. - Интереси и Стекнати Вештини – кликнете на секцијата за да отворите модал со теми и изберете барем една.
- Одјави се – ја затвора сесијата.
Чекор 6: Бесплатна сесија (/free-consultation)
Ова е најкомплексниот тек и ги користи Google Calendar, Zoom и емаил интеграциите:
- Апликацијата ги повлекува слободните термини на експертот од Google Calendar – работни денови, 08:00–16:30, во вашата временска зона.
- Изберете датум и час.
- Пополнете ги полињата: основни информации, за компанијата, предизвици и дополнителни информации.
- Кликнете на копчето за закажување. Во позадина се креира настан во Google Calendar, се отвора Zoom состанок и се испраќаат емаил потврди до вас и до експертот.
- Секој корисник има право на една бесплатна консултација – при обид за втора се појавува порака дека веќе е искористена.
Чекор 7: Контакт (/contact)
- Полињата Име и Е-пошта се автоматски пополнети од вашиот профил.
- Внесете Причина за контакт и Порака, па кликнете
Испрати. - Пораката се испраќа до експертот преку ZeptoMail; се појавува потврда на екранот.
Чекор 8: Информативни страници
- За Нас (
/about) – мисија, вредности и претставување на тимот. Јавно достапна. - Менторство (
/mentoring), Консалтинг (/consulting), Академии (/academies) – опис на услугите. Достапни само за најавени корисници. - Курсеви (
/courses) – моментално прикажува страница „Дигитални Курсеви – Наскоро“; модулот за курсеви и учење е подготвен во backend-от, но е привремено исклучен во frontend-от.
Автоматски тестови
cd backend ./mvnw test
