Debian jako serwer Javy – Serwery, bazy i routing

Po przygodach z przenoszeniem aplikacji z Jetty na Tomcata serwer ostatecznie stoi. Jest to całkowicie mój VPSik. Pierwotnie działał na nim Gentoo, jednakże nigdy nie bawiłem się z tą dystrybucją w związku z czym trochę szkoda mi było kilku tygodni na rozkminienie o co w tym wszystkim chodzi. Dlatego też decyzja o zainstalowaniu na nim Debiana, dystrybucji dojrzałej, sprawdzonej i szeroko znanej. No i jak wiadomo – support dla niej to cała rzesza linuxowych geeków.

Wstęp

Cel był prosty – stworzyć system, na którym będą działały moje aplikacyjki. Nie wymaga on zatem tuningowania jak wielkie produkcyjne serwisy, ale podstawowe kwestie dotyczące stabilności oraz bezpieczeństwa wypadałloby na nim zrobić. Docelowo na serwerze miały działać następujące usługi:

  • Apache Tomcat
  • bazy danych (MySQL na start, potem doinstaluję Postgresa)
  • języki skryptowe – choćby do wygodnego używania PHPMyAdmin, czy tego typu rozwiązań
  • no i jakiś serwer WWW, by te języki skryptowe mogły gdzieś śmigać

To był plan 0. Otrzymałem Debiana z już zainstalowanym SKD dla Javy, a także ze śmigającym Tomcatem. Instalacja samego kontenera nie jest specjalnie skomplikowana – po prostu ściągamy go poprzez apta i tyle. Jeżeli jednak musimy zaczynać z “gołym” systemem to z pewnością ten link będzie bardzo pomocny. UWAGA!!! Dodam tylko, że występuje tam mały błąd – po instalacji SDK w pliku /etc/profile należy dopisać:

export $JAVA_HOME

Zaś na listingu występuje zapis bez znaczka $. Bez tego nasze aplikacyjki dostarczone z Tomcatem nie ruszą. Wypadałoby też zobaczyć czy na pewno używamy Javy 6. W konsoli:

java -version

Jeśli mamy tam jakieś wersje <1.6 to znaczy, że można też odwiedzić wątek na pewnym forum. Na chwilę obecną zakładam, że wszystko jest dobrze poinstalowane plus używamy najnowszej wersji Javy.

W zależności od potrzeby serwer obsługujemy poleceniami:

/etc/init.d/tomcat-6 start|stop|restart

Konkretna nazwa skryptu może się różnić (w podanym przeze mnie linku jest to /etc/init.d/tomcat). Domyślnie nasz kontener działa na porcie 8080 – jego zmianą zajmiemy się za chwilkę. Uruchamiamy kontener i powinniśmy pod adresem http://localhost:8080 zobaczyć taką oto stronę:

Tomcat jest dostarczany bynajmniej nie jako ‘out-of-the-box’ i trzeba trochę pogrzebać w plikach konfiguracyjnych, aby spełniał w pełni swoją rolę. Domyślnie też jest dostarczany z 2 aplikacjami, które umożliwiają zarządzanie serwerem poprzez interfejs WWW. Pozostawianie ich dostępnych na serwerze produkcyjnym nie jest zbyt dobrym pomysłem (z powodów bezpieczeństwa), ale na etapie stawiania systemu mogą okazać się bardzo przydatne. By jednakże otrzymać do nich dostęp należy edytować plik /var/lib/tomcat6/conf/tomcat-users.xml. U mnie wygląda on tak:

<tomcat-users>
 <role rolename="manager"/>
 <role rolename="admin"/>
 <user username="nasztajnylogin" password="mojetajnehaslo" roles="admin,manager"/>
</tomcat-users>

Oczywiście user i hasło są zmyślone 🙂 W tym pliku XML mamy taki kontenerowy ACL – tworzymy jednocześnie zarówno role jak i użytkowników. Dzięki temu uzyskujemy dostęp do 2 aplikacji zarządzających kontenerem. Są one o tyle istotne na etapie tworzenia serwera, że można szybko i wygodnie poprzez stronę WWW zarządzać serwerkiem. Ja jednakże postanowiłem pobawić się plikami konfiguracyjnymi, zatem usunąłem dostęp do tych aplikacji, a je same wyrzuciłem z serwera.

Baza danych MySQL

Podstawą dla wszystkich aplikacji sieciowych jest baza danych. HowToJava powstała z użyciem MySQLa, podobnie póki co jest i z ProgramBash. Wypadało zatem zainstalować ten RDBMS by mieć na czym operować. W pakietach Debiana znajduje się najnowsza (w miarę) wersja zatem wystarczy użyć apta i jesteśmy w domu. Problemy mogą wystąpić przy próbie połączenia z bazą z zewnątrz – dla przykładu z naszego lokalnego komputera. W moim przypadku Hibernate rzucał wyjątkiem o niemożliwości połączenia się z powodu Connection refused. Innymi słowy – już sam serwer nie chciał mojego requestu. Rozwiązanie jest proste – należy edycji poddać plik /etc/mysql/my.cnf i parametrowi bind-address nie nadawać wartości localhost lub 127.0.0.1, ale IP naszego serwera. Wtedy bez najmniejszych problemów będzie można połączyć się z lokalnej maszyny. Nalezy także pamiętać o utworzeniu użytkownika z odpowiednimi prawami (łączącego się z określonego hosta). Na koniec zabaw ze zmianą uprawnień wydajemy polecenie:

flush privilages;

Bez tego można kląć na potęgę dlaczego nasze zmiany w uprawnieniach nie są widoczne.

Routing lub też proxy jak kto woli

Domyślnie Tomcat (choć dotyczy to w sumie wszystkich serwerów/kontenerów Javy z jakimi miałem okazję pracować) działa na porcie 8080 lub okolicach. Rzecz jasna w przypadku podpinania domeny pod nasz serwer takie rozwiązanie nie za bardzo wchodzi w grę – wszak nie można ustawić w routingu domen docelowego portu. Przyjęło się, że w użyciu mamy port 80 – tam przeglądarki standardowo wysyłają swoje żądania. Cóż zatem zrobić, aby wykupiona domena wskazywała na nasze pliki z aplikacjami Javy (u mnie to WARy) i wyglądało to transparentnie? Mamy kilka rozwiązań:

  • ustawienie portu w konfiguracji Tomcata na numer 80. Proste, ale absolutnie niezalecane ze względów bezpieczeństwa!!!
  • forwardować ruch poprzez odpowiednią konfigurację firewalla. Iptables to dobre narzędzie do tego.
  • postawić nasz serwer/kontener Javowy za zwykłym serwerem WWW, który będzie działał jako proxy.

Powyższe rozwiązania zostały dokładnie omówione w tym miejscu, a i z pomocą Gogla, można dowiedzieć się wszystkiego. Ja również pierwotnie myślałem o postawieniu Apache i zastosowaniu connectorów, jednakże moi mili admini wyperswadowali mi takowy pomysł i stanęło na podobnym rozwiązaniu, ale w oparciu o szybki serwer WWW – nginx. Oficjalna stronka znajduje się pod adresem http://nginx.org/. Sam serwer ma swoje plusy i minusy, by się z nimi zapoznać zapraszam do artykułu w Wikipedii. Sam serwer posłuży też do obsługi PHP – konkretniej do narzędzi zarządzających bazą danych (wygodny jestem), a także być może w przyszłości hostowania tego bloga.

Instalacja nginxa jest banalnie prosta:

sudo apt-get install nginx

I nasz serwerek jest już zainstalowany. Całkiem przyzwoity materiał o tym serwerze można znaleźć u Riklaumina, ja ograniczę się na razie do pierwszego jego uruchomienia. Tuningiem i bliższym poznaniem zajmę się w kolejnych artykułach. Przede wszystkim należy przejśc do katalogu /etc/nginx/conf.d. Cokolwiek znajdzie się w tym katalogu zostanie domyślnie potraktowane jako plik konfiguracyjny. Należy utworzyć nasz podstawowy plik konfiguracyjny:

cd /etc/nginx/conf.d
touch default.conf

Edytujemy stworzony plik i wrzucamy w niego na przykład taki oto kod:

 server {
        listen       80;
        server_name  WPISUJEMY_NASZE_IP DOMENA1 DOMENA2 DOMENA3;

        # Main location
        location / {
            proxy_pass         http://127.0.0.1:8080/;
            proxy_redirect     off;

            proxy_set_header   Host             $host;
            proxy_set_header   X-Real-IP        $remote_addr;
            proxy_set_header   X-Forwarded-For  $proxy_add_x_forwarded_for;

            client_max_body_size       52m;
            client_body_buffer_size    128k;

            proxy_connect_timeout      3600;
            proxy_send_timeout         3600;
            proxy_read_timeout         90;

            proxy_buffer_size          4k;
            proxy_buffers              4 32k;
            proxy_busy_buffers_size    64k;
            proxy_temp_file_write_size 64k;
            proxy_cache_valid 5m;
        }
    }

To baaaaardzo podstawowa konfiguracja. Ale na pewno osiągnęliśmy jedno – wszystkie requesty domyślnie lecące na port 80 zostaną przekierowane na port 8080, gdzie będzie na nie już oczekiwał nasz Tomcat. Można odpalić nginxa poleceniem:

/etc/init.d/ngninx start

Być może trzeba będzie po raz pierwszy zrobić to z poziomu konta administratora. Jak widać sam serwer zainstalował skrypt, ktory uruchamia go przy starcie systemu (w katalogu /etc/init.d/).

Tomcata musimy odpowiednio poinformować o istnieniu czegoś takiego jak subdomeny. I tutaj właśnie pobawimy się plikami konfiguracyjnymi (choć będzie to dość szybka zabawa). Docelowo mój serwerek zainstalował się w katalogu /var/lib/tomcat6/. W tymże katalogu znajduje się również podstawowy katalog dla naszych aplikacji – webapps. Dla naszych aplikacji, które zamierzamy wdrożyć należy przygotować pliki dystrybucyjne – ja pozostaję od samego początku wierny plikom WAR. Teraz musimy wyedytować plik konfiguracyjny Tomcata. W naszym ulubioym edytorku bierzemy na tapetę plik /var/lib/tomcat6/conf/server.xml.

 <Host name="SUBDOMENA_Z_DOMENA" appBase="webapps/NAZWA_SUBDOMENY" unpackWARs="true" autodeploy="true"></Host>

Restart Tomcata i należy udać się pod powyżej wpisany adres. Oczywiście serwer nie znalazł ani katalogu, ani pliku o wskazanej nazwie (jeszcze nic nie wysłaliśmy na serwer), zatem przekierował nas na główną stronę w domenie. Jednakże póki co wszystko działa poprawnie – nie dostaliśmy od serwerów po drodze błędu 404. Do testów maszyny najlepiej na szybko stworzyć maksymalnie prosty projekt w Javie (ja użyłem przykładowego projektu JSF). Generujemy dla niego plik WAR i łączymy się z serwerem dowolnym klientem FTP/SCP/SSH (w zależności co lubimy i co mamy/odpaliilśmy na serwerze). Przesyłamy do katalogu webapps nasz plik WAR i tworzymy dla niego katalog. Dla ułatwienia stworzyłem subdomenę example.chlebik.pl jak i odpowiedni katalog. Do niego wrzuciłem plik WAR. Uwaga!!! Można naciąć się na uprawnieniach do katalogów lub plików. Podążając tropem aktywności mojego Tomcata wszystkie pliki i katalogi przypisuję do użytkownika tomcat6 oraz grupy o tej samej nazwie. Przynajmniej nie dostaję ukochanego komunikatu – Permission denied.

Powyżej w pliku server.xml ustawiliśmy, że ta konkretna aplikacja ma być deployowana na starcie serwera, a także ma mieć rozpakowany plik WAR (dla zwiększenia szybkości działania). Ponownie odwiedzamy adres naszej subdomeny – i nic. Dalej jesteśmy przekierowywani na główną stronę domeny. Cóż się stało? Ano taka dziwna cecha Tomcata – wystarczy nasz plik WAR znajdujący się (u mnie) w katalogu webapps/example/, przemianować na webapps/example/ROOT.war. Restart serwera i co? Hip-Hop, hurrra. Dostajemy miły komunikat od JSF i Facelets, że nasza aplikacja działa. Można z ciekawości zajrzeć do tego katalogu – został tam rozpakowany w podkatalog o takiej samej nazwie jak plik WAR cały kod naszej aplikacji. Dlaczego w ten sposób? Uważam, że w katalogu z aplikacjami powinny być inne katalogi, a nie stado plików WAR lub inszych, które zaciemniają obraz. Każda aplikacja ma swój katalog i niech w nim dzieje się co chce.

PHP i Fast-CGI

Na koniec został mi do zainstalowania PHP. O ile w przypadku pierwotnie planowanego Apache rzecz jest banalna, o tyle nginx wymaga trochę zabawy. Należy bowiem doinstalować specjalny moduł do obsługi języków skryptowych poprzez Fast-CGI. Tutaj korzysta się z dobroci serwera lighttpd, ale o tym można już poczytać sobie w artykule. Dodam tylko by odpowiednio skroić nasz plik default.conf z nginxa – można połączyć konfig FCGI z PHP z istniejącą konfiguracją, ale można też zastosować podejście opisane w powyższym tutorialu. Co więcej – nginx jest tak fajnym narzędziem, że przy restarcie waliduje swoje pliki konfiguracyjne – jeśli coś jest nie tak wówczas od razu zostaniemy o tym poinformowani bez konieczności przeglądania logów serwera.

Co dalej?

Mam nadzieję, iż trochę ułatwiłem początkującym adminom życie (jakbym ja miał 10 lat doświadczenia :). W ramach możliwości postaram się kontynuować tak mile rozpoczęty cykl wpisów o administracji serwerem dla programistów. Jeśli znalazłeś jakikolwiek błąd w powyższym materiale lub masz jakieś sugestie – rzecz jasna zapraszam do kontaktu lub komentowania. Gdyby ktoś był zainteresowany VPSem lub hostingiem tam gdzie ja to należy pisać na ten adres email. Przy okazji możecie wspomnieć, że to dzięki mnie wiecie o usłudze 🙂

Tak na koniec

Na sam koniec dobra rada dla wszystkich programisto-administratorów 🙂 Jakiekolwiek operacje na sewerze (dedyku, VPSie czy w ogóle czymkolwiek) lepiej wpierw przetestować na VirtualBoxie. Produkt firmy SUN świetnie się do tego nadaje. Nie będę opisywał tutaj procesu instalacji i tak dalej, dam tylko kilka szybkich rad dla uruchamiania wirtualizacji systemu w Windows XP:

1. Używana przestrzeń dyskowa na system linuxowy powinna być wrzucona na partycję z systemem plików innym niż FAT32!! Inaczej dostaniemy błędy podczas instalacji, albo użytkowania, gdyż ten format nie obsługuje istnienia plików powyżej 2 GB.
2. W świetle powyższego – skonfigurować wirtualną maszynę by miała rozszerzalne miejsce na partycji. Często coś tam się doinstaluje, odinstaluje lub chce pobawić i nagle BUM – nie ma miejsca.
3. Jeżeli naszego linuxa instalujemy wraz ze środowiskiem graficznym należy ściągnąć VBoxLinuxAdditions. Jest to obraz płyty, który po instalacji naszego systemu należy podpiąć i następnie uruchomić z poziomu linuxa. U mnie wymagało to doinstalowania kilku rzeczy (nagłówków jądra linuxa i czegoś jeszcze). Kiedy to wszystko już zrobimy uruchamiamy po prostu skrypt .sh dla linuxa i stosownej architektury. Dzięki temu będziemy mogli rozszerzać ekran z wirtualizowanym systemem, grafika przestanie się ciąć i w ogóle będzie lepiej.
4. RZECZ BARDZO ISTOTNA!!! Dość często ludziom zdaża się, że uruchomienie VBoxa nawet z czystą konsolą (bez fajerwerków KDE czy GNOME) powoduje zżarcie przez VBoxa jakiś 50-90% procesora. Strasznie to wkurzające – dzieje się tak niezależnie od przydzielonej ilości RAMu. Rozwązaniem jest wyłączenie antywirusa!! U mnie działa darmowy AVG – jego wyłączenie automatycznie zredukowało zasobożerność VBoxa. Domyślam się, że chodzi o monitorowanie wirtualnego połączenia internetowego. Z tego co wyczytałem w sieci również niektóre fiewalle zachowują się w podobny sposób.

Advertisements

18 thoughts on “Debian jako serwer Javy – Serwery, bazy i routing

  1. antonijakubiak

    Mam kilka pytań do Twojej konfiguracji.

    1. Dlaczego zrezygnowałeś z Apacha i konektorów mod_proxy i mod_proxy_ajp lub mod_jk? Polecam mod_proxy_ajp.

    2. Sprawdź, czy Tomcata uruchamiasz jako root? Port 8080 jest stosowany po to, by nie uruchamiać Javy jako superużytkownik.

    3. FastCGI to znakomita technologia która wymaga jednak specjalnego programowania. Nie spotkałem się jeszcze z programem w PHP który korzysta z dobrodziejstw FastCGI. Czy na pewno potrzebujesz FastCGI?
    Aby zrozumieć FastCGI polecam ten dokument:
    http://www.sdsc.edu/~moreland/courses/IntroPerl/docs/manual/lib/CGI/Fast.html

  2. chlebik Post author

    1. Apacz jest powiedzmy “ciezszy” niz nginx to raz. Dwa – konfiguracja z tego co mialem okazje przeczytac tegoz jest bardziej skomplikowana i daje narzuty na wydajnosci.

    2. Oczywiscie, ze nie uruchamiam jako root. Nie rozumiem w tym momencie tego punktu – normalnie porty < 1024 sa portami uprzywilejowanymi – tak przynajmniej doczytalem na necie.

    3. FastCGI zostalo podpiete gdyz przy nginxie (stawiajacym na lekkosc i szybkosc) jest naturalna konsekwencja. Jest o wiele szybsze i w materialach, ktore znalazlem w necie automatycznie podpinane pod ten serwer jesli chodzi o uzywanie jezykow skryptowych. No i wygoda – jak zachce mi sie na szybko poznac Pythona to dorzucenie nowego connectora zajmie sekunde.

  3. Darek Ludera

    Mam pare pytań.

    Gdzie kupiłeś VPSa jeśli to nie tajemnica i czy poleciłbyś tego providera innym?

    Dlaczego Tomcat, a nie np JBoss, Glassfish, WAS Community albo jakikolwiek inny darmowy serwer app – przeważyła prostota rozwiązania czy za wyborem stały jakieś ograniczenia providera? Pytam bo nie mam doświadczenia z VPS, a chętnie spróbował bym czegoś godnego polecenia:)

  4. chlebik Post author

    Było to pewne ograniczenie ze strony providera – albo Jetty albo Tomcat. Choc w sumie to moj VPS zatem moge robic na nim co mi sie podoba – pewnikiem przemysle temat przy okazji nowego projektu. Glassfish kusi (chodzi u mnie lokalnie) i na razie nie sprawial mi w ogole problemow.

    Co do innych wymienionych to nie jestem pewien jak tam z nimi jesli chodzi o licencje – czy do non-profit zastosowan mozna ich uzywac w jakiejs wersji “Express” czy “Lite”. Przemawialyby za nimi tez inne wzgledy – co ostatnio przegladam ogloszenia o prace to triada: WebLogic, JBoss i WebSphere kroluja.

    Co do providera – to firma, ktora mi juz wczesniej hostowala Jetty. Jak dorwe admina to zapytam o jakas stronke ichniejsza bo ja o hostingu cynk dostalem na IRCu 🙂

  5. antonijakubiak

    1.
    Konfiguracja apache + mod_proxy_ajp jest trywialna i potężna. mod_jk daje jeszcze więcej możliwości ale jest trudniejszy do skonfigurowania. Do pełni szczęścia można używać też mod_rewrite.

    Na przykład, gdy chcesz aby strony *.jsp i *.php były obsługiwane w tym samym katalogu z pomocą przyjdzie Ci mod_jk; w różnych katalogach mod_proxy_ajp.

    2.
    Uruchamiając Tomcata jako root możesz skorzystać z portu 80 co przydaje się na serwerach deweloperskich, gdyż można zaoszczędzić kilka minut na konfigurację.

  6. amorfis

    Co do VPSa, to jeśli nie masz dużych wymagań (chodzi o moc, łącze i miejsce na dysku) to mogę polecić star-hosting.de Niewielkie, ale tanie. Są też oczywiście większe i droższe.

    A w ogóle skontaktuj się na priv (pawelstawicki [szympans] gmail [kropa] com), to mogę Ci swój udostępnić do zabawy 🙂

  7. chlebik Post author

    No moi admini obecnie niczego sie nie boja bo to moj VPS wiec robie co chce. A czym sie rozni w tym momencie uruchomienie apacza + connector od samego uruchomienia serwera (lzejszego) i puszczania wszystkich requestow na inny port na lokalnej maszynie?

    Z checia poczytam jakies dobre materialy na ten temat, jakies statystyki, benchmarki? Bede bardzo wdzieczny.

  8. chlebik Post author

    Zasadniczo mi starcza, cena tez bez przesady. A i pare ciekawych rzeczy pewnie na niego jeszcze wrzuce (blog pojdzie w pierwszej kolejnosci, ale to po swietach). Dzieki jednakze za oferte.

  9. nick

    Dzięki za ten wpis, bardzo pomógł mi przy konfigurowaniu mojego VPS-a. Okazało się, że na mojej dystrybucji nie działa redirect na iptables, a nie mogę rekompilować jądra na OpenVZ. Tomcat i nginx świetnie się sprawdzają 🙂

  10. nick

    p.s. Ja mam VPS na logout.pl za 33 zł mam 1-3 GHz procka, 512-768 MB RAM i 10 GB dysku. Jak na początek wystarczy 😉

  11. chlebik Post author

    Przy 768MB RAMu to nie wiem czy Tomcat by mi wstal z kilkoma zdeployowanymi aplikacjami 🙂 Taka dola Javowca.

  12. nick

    Nie działa mi konfiguracja subdomen w tomcacie na podstawie tego jak ty to zrobiłeś. Tobie to na pewno działa? 🙂

  13. wlodekg

    Jestem początkujący. JSF Web applications robię na WIndows pod NetBeans. Do MySQL Hibernate sięga przez com.mysql.jdbc.Driver i wszystko działa. Potem przenoszę to na serwer Debian-Tomcat 6.0 i przy wdrażaniu oczywiście pisze, że nie ma “com.mysql.jdbc.Driver”. Co i gdzie wstawić, żeby to zaczęło chodzić pod Debian’em.

  14. chlebik Post author

    Zakladam, zej estes w miare poczatkujacy zatem najlepiej (pomijajac na razie narzedzia do budowania) wrzucic tego JARa z driverem do folderu /lib w Tomcacie i powinno stykac. Pozniej jak juz sie rozeznasz co i jak to skonfigurujesz sobie tego Anta/Mavena/Ivy/Gradle by JAR byl wrzucany do docelowego WARa aplikacji.

  15. wlodekg

    Pomogło. Dziękuję bardzo ale dalej nie działa. Teraz mam komunikaty:

    2012-12-19 22:10:32 org.apache.catalina.core.StandardContext start
    SEVERE: Error listenerStart
    2012-12-19 22:10:32 org.apache.catalina.core.StandardContext start
    SEVERE: Context [/gene6] startup failed due to previous errors
    2012-12-19 22:10:32 org.apache.catalina.loader.WebappClassLoader clearReferencesThreads
    SEVERE: The web application [/gene6] appears to have started a thread named [MySQL Statement Cancellation Timer] but has failed to stop it. This is very likely to create a memory leak.

    2012-12-19 22:19:11 org.apache.catalina.core.StandardContext listenerStart
    SEVERE: Exception sending context initialized event to listener instance of class pl.com.szym.gene6.listeners.GeneContextListener
    javax.persistence.PersistenceException: [PersistenceUnit: GenePU] Unable to build

    Teraz to już całkiem nie mam pojęcia o co chodzi. Muszę jeszcze sporo poczytać. Przeszedłem daleką drogę i utknąłem o krok od mety.

  16. wlodekg

    Sorry. Już wszystko działa OK.
    Instalując Tomcat na różne sposoby żonglowałem obrazami dysku i zapomniałem, że na tym obrazie nie miałem przeniesionej bazy danych. Debian jest rzeczywiście debilo-odporny. Jeszcze raz dziękuję za pomoc.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s