1. Wprowadzenie
1.1. Contexte
Kod PDF z dokumentu można znaleźć pod adresem |TUTAJ|.
Przykłady zawarte w dokumencie są dostępne pod adresem |TUTAJ|.
Niniejszy dokument stanowi zarówno kurs, jak i TD (ćwiczenia) na poziomie uniwersyteckim. Jest przeznaczony dla początkujących. Wykorzystuje następujące źródła:
Bibliografia:
Źródła te oznaczymy odpowiednio jako [ref1] i [ref2]. Źródło [ref1] jest stare (z 2002 r.), ale wystarczające dla potrzeb niniejszego dokumentu, w którym wykorzystano je wyłącznie w celu przedstawienia składni języka Java i jego podstawowych operacji. Pozostałe informacje niezbędne do stworzenia TD zostały przedstawione w niniejszym dokumencie w rozdziałach zatytułowanych [Cours]. Rozdziały te pochodzą bezpośrednio z [ref2] (2015) i zostały w niektórych przypadkach uproszczone.
Celem niniejszego dokumentu jest nauczanie języka Java z perspektywy zawodowej. Z tego powodu w znacznym stopniu opieramy się na frameworku Spring [http://spring.io/], szeroko stosowanym w programowaniu JEE (Java Enterprise Edition). Logicznie rzecz biorąc, po tym kursie powinien nastąpić kurs JEE. Tak właśnie jest w Istia (uniwersytet w Angers). JEE stanowi obecnie (listopad 2015 r.) główne źródło zatrudnienia dla młodych programistów z wykształceniem na poziomie Bac+5. W świecie JEE istnieje wiele innych technologii poza Springiem. Spring ma tę zaletę, że jest zrozumiały, a przede wszystkim dostarcza dobrych praktyk programistycznych, które można wykorzystać również poza ekosystemem Springa. To właśnie wyjaśnia wybór tej technologii w tym przypadku.
Ten TD jest używany od ponad 10 lat i ewoluował wraz z technologiami. Po nim (po IstiA) następują: TD, JEE i [Introduction à Java EE]. Ten ostatni, TD, pochodzi z 2012 roku (obecnie mamy rok 2015) i zasługiwałby na aktualizację. Przedstawia on ortodoksyjne podejście JEE poprzez framework internetowy JSF2 (Java Server Faces) oraz EJB3 (Enterprise Java Bean). Połączenie tych dwóch TD umożliwiło wielu studentom zdobycie staży JEE w ESN (firmach świadczących usługi cyfrowe) oraz natychmiastowe zatrudnienie w tych firmach.
W niniejszym dokumencie nie znajdziemy formalnego omówienia wszystkich aspektów języka Java. Na przestrzeni lat podejście młodszych programistów do rozwiązywania problemów znacznie się zmieniło. Obecnie niemal zawsze korzystają z Internetu, aby znaleźć fragmenty kodu, które po połączeniu tworzą program. Jeśli zapewni się im kurs, korzystają z niego raczej rzadko i ponownie wolą szukać informacji w Internecie. Choć początkowo podchodziłem sceptycznie do tego sposobu pracy, byłem jednak zaskoczony uzyskanymi wynikami. W ten sposób nawet słabsi studenci potrafili stworzyć działające programy, podczas gdy bez pomocy Internetu prawdopodobnie by im się to nie udało. Obecnie opieram się na tym sposobie pracy.
Fragmenty kodu nie dają całościowego obrazu architektury rozwiązania, a jednym z celów niniejszego dokumentu jest właśnie przedstawienie tej architektury. Studenci realizują zadanie TD tak samo jak TP, samodzielnie. Nie ma wykładów. Istnieje harmonogram, który określa oczekiwany postęp w trakcie poszczególnych sesji. Studenci mogą być opóźnieni lub wyprzedzać ten harmonogram. Ich postępy są weryfikowane poprzez szereg zadań sprawdzających, które muszą przedstawić wykładowcy. Wykładowca jest obecny zarówno po to, by udzielać wyjaśnień na prośbę studentów, jak i po to, by oceniać ich pracę. Każdy pracuje we własnym tempie. Pod koniec 36 godzin przeznaczonych na ten kurs TD niektórzy będą mieli o 50% więcej potwierdzeń niż inni, ale każdy – a taki jest przynajmniej cel – zrozumie, co wykonał samodzielnie. Kurs TD można ukończyć bez pomocy nauczyciela. Dlatego jest on dostępny na platformie [https://stahe.github.io].
Ten dokument nie będzie odpowiedni dla osób poszukujących akademickiego kursu z języka Java – takiego, w którym język ten jest wyjaśniany stopniowo i w sposób uporządkowany, a każdy szczegół składni jest wyjaśniony i uzasadniony. To, co tu proponujemy, to raczej podejście eksperymentalne. Jest prawdopodobne, że student nie zrozumie wszystkiego, co znajduje się w tym dokumencie, ale prawdopodobnie będzie potrafił właściwie wykorzystać jego treść, a zrozumienie szczegółów przyjdzie wraz z doświadczeniem.
Niniejszy dokument nie jest również kursem z algorytmiki. Algorytm TD jest prosty i może go rozwiązać każdy początkujący, który dopiero rozpoczyna naukę algorytmiki. Dokument skupia się na profesjonalnym środowisku programistycznym w Javie wraz z licznymi bibliotekami i frameworkami oraz na architekturze kodu. Większość studentów, z którymi mam do czynienia, wykazuje braki w zakresie algorytmiki, co potwierdzają następnie opiekunowie praktyk. Tak więc opanowanie algorytmów jest ważne, ale nie jest to przedmiotem niniejszego kursu z ćwiczeniami.
Wreszcie, niniejszy dokument (grudzień 2015 r.) nie uwzględnia najnowszych funkcji języka Java, w szczególności strumieni (streams) i funkcji lambda. Niemniej jednak wykorzystujemy w nim niektóre elementy najnowszej wersji JDK, czyli JDK 1.8, a poniższe kody muszą być skompilowane przy użyciu tej wersji JDK.
1.2. Contenu
Rozdział 2 poświęcony jest zagadnieniu TD, czyli obliczaniu wyników wyborów. Zadanie jest proste. W rozdziale 2 wymagane jest zaimplementowanie rozwiązania w dwóch bardzo podobnych językach: C# i Java. Implementacja odbywa się bez użycia klas. Celem jest przedstawienie składni języka Java, jego podstawowych instrukcji oraz środowiska Eclipse (IDE – Integrated Development Environment), które służy do tworzenia projektów w języku Java.
W rozdziale 3 należy zaimplementować rozwiązanie z TD w języku Java z wykorzystaniem klas. Celem jest przedstawienie pojęć klas, dziedziczenia, interfejsów i klas generycznych. Wprowadzono pojęcie testu jednostkowego JUnit.
Rozdział 4 przedstawia koncepcje leżące u podstaw kolejnych rozdziałów:
- architektury warstwowe;
- programowanie oparte na interfejsach;
- wykorzystanie biblioteki Spring do implementacji dwóch poprzednich koncepcji;

Rozdział 5 przedstawia framework Spring na przykładzie czterech projektów.
Rozdział 6 przedstawia API JDBC, który jest interfejsem dostępu do baz danych.
W rozdziale 7 zaimplementowano warstwę [DAO] (Data Access Object) w ramach TD przy użyciu API JDBC oraz Spring.

W rozdziale 8 zaimplementowano warstwę [métier] z TD:

Rozdział 9 implementuje warstwę [ui] z TD za pomocą aplikacji konsolowej:

W rozdziale 10 zaimplementowano warstwę [ui] z TD za pomocą aplikacji graficznej wykorzystującej bibliotekę komponentów Swing:


Rozdział 11 przedstawia zarządzanie bazami danych za pomocą frameworka [Spring Data], będącego częścią ekosystemu Spring. Wprowadza on specyfikację JPA (Java Persistence API), która pozwala warstwie [DAO] na operowanie obiektami zamiast na operowanie danymi SQL (Structured Query Language). Architektura warstwowa ewoluuje w następujący sposób:

W rozdziale 12 zastosowano wiedzę z rozdziału 11, implementując dostęp do bazy danych TD za pomocą [Spring Data].
Rozdział 13 pokazuje, jak udostępnić bazę danych w sieci WWW za pomocą [Spring MVC], który stanowi kolejną gałąź ekosystemu Spring. Architektura ewoluuje w kierunku architektury klient-serwer:

Rozdziały 14 i 15 przekształcają aplikację z TD w aplikację klient-serwer:

Rozdział 16 pokazuje, jak zabezpieczyć dostęp do aplikacji internetowej za pomocą [Spring Security], kolejnej gałęzi ekosystemu Spring.

W rozdziale 17 ponownie wykorzystano TD i zabezpieczono serwis internetowy poświęcony wyborom.
Rozdział 18 porusza problem żądań międzydomenowych:
![]() |
- w [1] aplikacja internetowa dostarcza strony HTML / JavaScript;
- w [2] przeglądarka uruchamia kod JavaScript osadzony na stronach HTML w celu wysłania zapytania do zabezpieczonej usługi internetowej [3-4];
Niech D1 = http://machine1:port1 będzie domeną serwera [1], a D4 = http://machine4:port4 będzie domeną serwera [4]. Jeśli serwery [1] i [4] nie znajdują się w tej samej domenie [D1!=D4], wówczas żądania z serwera [3] kierowane do serwera [4] nazywane są żądaniami międzydomenowymi. Ze względu na ograniczenia bezpieczeństwa stosowane przez przeglądarki ich wdrożenie może być problematyczne. Przyjrzymy się rozwiązaniu tego problemu.
W rozdziale 19 omówiono implementację żądań międzydomenowych w aplikacji wyborczej.
1.3. Wykorzystane narzędzia
Poniższe przykłady zostały przetestowane w następującym środowisku:
- komputer z systemem Windows 10 Pro 64-bitowym;
- JDK 1.8 (punkt 22.1);
- IDE Spring Tool Suite 3.6.3 (punkt 1);
- NetBeans 8.1 (punkt 22.4);
- przeglądarka Chrome (inne przeglądarki nie były używane);
- rozszerzenie Chrome [Advanced Rest Client] (ustęp 1);
- WampServer, które udostępnia SGBD, MySQL oraz narzędzie [PhpMyAdmin] do zarządzania nim (akapit 22.7);
Ważne jest, aby używać JDK w wersji 1.8. Niektóre przykłady wykorzystują elementy tego JDK. Większość przykładów to projekty Maven, które można otwierać zarówno w IDE Eclipse, jak i w [https://www.eclipse.org/], IntellijIDEA Community Edition, [https://www.jetbrains.com/idea/download/] oraz NetBeans [https://netbeans.org/]. W dalszej części zrzuty ekranu pochodzą z IDE Spring Tool Suite, odmiany środowiska Eclipse.
1.4. Wsparcie
Projekty Eclipse opisane w niniejszym dokumencie są dostępne na stronie [https://tahe.developpez.com/tutoriels-cours/intro-java-spring/serge-tahe-introduction-au-langage-java-et-a-l-ecosysteme-spring/].
![]() |
Aby zaimportować projekty z danego rozdziału, należy postępować w programie Eclipse zgodnie z instrukcją zawartą w [1-8]:
![]() |
Większość projektów to projekty Maven. Jeśli po załadowaniu pojawią się w nich błędy, wykonaj [Alt-F5] i postępuj zgodnie z procedurą opisaną w [9-10]. Wybrane projekty Maven zostaną ponownie skompilowane.
![]() |



