# 7. Programovanie a softvérový vývoj
Nástroje a prostředí pro softwarový vývoj rozsáhlých systémů. Základní koncepty softwarových architektur z pohledu implementace. Vícevrstvá architektura moderních informačních systémů, architektura model-view-controller. Technologie a jazyky vhodné pro frontend a backend vývoj. Persistence, ORM. Příklady z praxe pro vše výše uvedené. (PA165, PV179, volba Programování, SA200)
---
## Nástroje a prostredie pre softvérový vývoj rozsiahlych systémov
Za účelom produktivity a **Developer Experience** (DX) používame nástroje **IDE** (Integrated Development Environment) a textové editory.
- Visual Studio (IDE)
- Visual Studio Code (Editor)
- JetBrains Idea (IDE) ...
- Vim (Editor)
- Sublime Text (Editor)
Nástroje IDE poskytujú okrem textového editora aj nástroje na refaktoring, debugging, testing, statické a dynamické analýzy kódu, performance profiling, nástroje na dokumentáciu, a tak ďalej.
Na zabezpečenie **auditingu** sa používajú **verzovacie systémy VCS** (Version Control System) - Git, Subversion, Mercurial.
- V prípade chýb sa dá vyhľadávať v histórii a chybný kód vrátiť
- Využíva strom hashov zmien
- Rieši konflity, dovoľuje súbežne editovať kód z viacerých miest
- Git Workflow, Feature Branch Flow
- Conventional Commits - systém pomenovávania zmien
V prípade **agilného vývoja** je potrebné využívať **issue tracking systém** ako Jira, Azure DevOps, Trello, Linear. Tieto nástroje podporujú **SCRUM workflow**. Dajú sa použiť aj pri prediktívnom vývoji ale nie je to až tak nutné.
Pri vývoji **automatizovaných testov** používame frameworky a nástroje ako napríklad JUnit, Selenium, MS Test, Postman, Insomnia, Playwright.
V rámci programovacieho jazyka používame **package manager**, ak je nejaký dostupný.
- C# - Dotnet Package Manager, Nuget
- Java - Maven
- Rust - cargo
- C++ - vcpkg
- Python - pip, anaconda
Na zabezpečenie automatizovanej **integrácie a nasadzovania** používame nástroje CI/CD (Continuous Integration, Continuous Delivery) a cloud computing, ako napríklad GitHub Actions, GitLab CI/CD, Jenkins, Docker, Kubernetes, RedHat OpenShift, Vercel, Amazon Web Services, Microsoft Azure.
Po nasdení používame **monitorovacie a logovacie** nástroje: Grafana, Azure DevOps Logging.
Na **analýzu kódu a dokumentáciu** požívame nástroje ako: SonarQube, Roslyn Analyzers, cppcheck, MyPy, doxygen, Swagger OpenAPI.
V poslednej dobe používane nástroje "**AI**" na kontrolu kódu (reviewing) a pomoc pri programovaní (prakticky spôsob párového programovania): GitHub Copilot, ChatGPT.
Na **modelovanie požiadaviek** používame nástroje ako UML, Excalidraw, Gherkin (Cucumber), PlantUML, draw.io, Visual Paradigm.
Je dôležité zvoliť si **build systém** podporovaný pre daný jazyk. Build systém je sada nástrojov na generovanie skriptov a finálnej binárky programu.
- C++ - CMake, Make, Ninja, QMake
- C# - MSBuild
- Java - Maven, Gradle, Bazel
- TypeScript - tsc, vite, swc, esbuild
## Základné koncepty softverových architektúr z pohľadu implementácie
Softvérový vývoj sa zvyčajne skladá z **krokov**:
- Analýza
- Návrh
- Implementácia
- Testovanie
- Nasadzovanie
- Údržba, support
Proces vývoja závisí na správnej **komunikácii** medzi vývojovým tímom a stakeholdermi projektu.
Kľúčovou súčasťou analýzy a návrhu je **dekompozícia problému** na abstrakcie a komponenty. Cieľom je minimalizovať **závislosť** medzi komponentami, dosiahnuť princíp **SOLID**, High Cohesion, Low Coupling. Komponenty majú byť závislé na **abstrakciách** a **interfaceoch**, nie na konkrétnych **implementáciách**.
V závislosti na prostredí existuje viacero **spôsobov** ako robiť **analýzu a návrh**:
- DDD (**Domain Driven Development**) - vhodné na návrh komplexných, veľkých informačných systémov
- Používa Agregáty (aggregates), Udalosti (events), Domény (domains)
- Event Storming je spôsob získania požiadaviek od stakeholderov
- TDD (**Test Driven Development**) - vhodné na návrh jednoduchých problémov ale s jasnou špecifikáciou
- Základom kódu sú testy
- BDD (**Behaviour Driven Development**) - vhodné na návrh použivateľských požiadaviek
- Vzniklo z TDD, využíva druh jazyka na definíciu user stories (Gherkin, Cucumber)
Z pohľadu implementácie rozlišujeme **objektovo-orientované** jazyky (C++, C#, Java), **procedurálne** \(C) a **deklaratívne** (funkcionálne) ako napríklad Haskell, LISP, Prolog, Domain-specific languages (DSL). V dnešnej dobe však nájdeme mix rôznych **paradigmat** v jednom jazyku (PHP, C#, C++, JS, Rust).
Programujeme tak, aby sme nezvyšovali **technický dlh** (technical debt). Využívame vhodné **návrhové vzory** (design patterns), používame **konvencie**, checklisty, version control, dokumentujeme iba tam, kde to treba. Vyvarujeme sa **antipatternom** (globálne premenné, singleton). Je dôležité ale kód zbytočne **nekomplikovať**, riadime sa princípom **KISS** (Keep it simple stupid) a **DRY** (Dont repeat yourself).
## Viacvrstvová architektúra moderných informačných systémov, architektura MVC
Ak nemáme distribuovaný systém ale **monolit**, tak časti aplikácie zvyčajne delíme do **logických vrstiev** tak, aby sme oddelili biznisovú logiku od dát. Táto architektúra sa volá **vrstvená** (tiered, layered) alebo **Clean/Onion/Hexagonal** architecture. Zvyčajne sa jedná o vrstvy:
- Presentation layer (Controllers, Views, ViewModels, UI)
- Business logic layer (Services, Facades, Query)
- Infrastructure layer (DTOs, Repository, Interfaces, Configuration)
- Data Access layer (External APIs, DAOs)
Základom je **Dependency Injection** alebo **Inversion of Control** princíp.
Architektúra **Model-View-Controller** (MVC) je návrhovým vzorom, ktorý sa používa hlavne pri webových aplikáciách (ASP.NET).
- Model - dátový model (object, DTO, properties)
- View - návrh UI (HTML, XML), používa priamo Model
- Controller - aktualizuje Model a odosiela dáta do View (obsahuje biznis logiku), reaguje na požiadavky z View
Obdobou MVC je **MVVM** (Model-View-ViewModel) - používa sa ale mimo webu, napr. v C# WPF. Existuje aj **MVP** (Model-View-Presenter), kedy View nepozná Model, komunikuje iba s Presenterom.
## Technológie a jazyky vhodné pre frontend a backend vývoj
Najprv musíme určiť **platformu**:
- Desktop (Windows, Linux, Mac)
- Frontend - Qt QML, GTK, C# WPF, C# WinForms, C# Blazor, MAUI, Kotlin Jetpack Compose Multiplatform, HTML, CSS, JS (+ Electron, Tauri), Java FX, Dart
- Backend - PHP, JS, TS, C#, C++, Java, Kotlin, Rust, Python, Haskell
- Mobilné zariadenia (Android, iOS)
- Android - Java, C++, C#, Kotlin Multiplatform
- iOS - Swift, C++, C#, Kotlin Multiplatform
- Web
- Frontend - React, Tailwind CSS, Angular, Solid, Vue
- Backend - PHP, JS, TS, C#, C++, Java, Kotlin, Rust, Python, Haskell
- Embedded
- C, Rust, C++
Ďalej sa musíme zamerať na nejaké **funkčné požiadavky**.
- Akú vyžadujeme rýchlosť?
- Ako rýchlo to chceme naprogramovať?
- Koľko sme ochotní za to zaplatiť?
- Potrebujeme dokumentáciu?
- Ako sa to bude testovať?
- V akom prostredí to bude pracovať?
- Ako ľahko chceme nájsť ľudí na projekt?
Podľa týchto otázok musíme zvoliť vhodný "technological stack".
## Persistencia, ORM
V rámci skoro každého informačného systému musíme riešiť perzistenciu údajov v nejakej databáze.
Môžme zvoliť relačnú alebo nerelačnú (dokumentovú, vektorovú ...) databázu.
- Relačné - MySQL, Postgres, MSSQL, Oracle DB
- Nerelačné - MongoDB, CouchDB, Cassandra
Vždy je možnosť pripojiť sa k databáze pomocou **drivera** (JDBC) a posielať priamo SQL príkazy.
- Je to nebezpečné, môže vzniknúť problém SQL Injection, nie je nič, čo by nám sanitizovalo vstup
- Musíme manuálne riešiť problémy s pripojením
- Výhodou je nulová abstrakcia a rýchlosť
Druhá možnosť je použiť **ORM (Object-Relational Mapping) framework**, ktorý nám dáva abstrakciu nad databázou pomocou objektových modelov. Snaží sa transformovať ERD model na model tried. Zvyčajne implementuje aj návrhové vzory ako Repository pattern a Unit of work. Poznáme mnoho frameworkov a líšia sa úrovňou abstrakcie.
- C# - Entity Framework (high abstraction), Dapper (light abstraction)
- Java - Spring Java Persistence API, Hibernate (high abstraction)
- JavaScript - Prisma (high abstraction), Drizzle (lower abstraction), TypeORM (light abstraction)
- PHP - CakePHP, Symphony + Doctrine ORM (high abstraction)
- Rust - Diesel (high abstraction), Cornucopia (low abstraction)
**Cieľom** ORM je poskytnúť lepší **Developer Experience** (DX) za cenu overheadu a abstrakcie.