Web服務(Apache、Nginx、Tomcat、Jetty)與應用(LAMP、CMS-WordPress&Ghost、Jenkins、Gitlab)

Web服務和應用是目前信息技術領域的熱門技術。如何使用Docker來運行常見的Web服務器(包括Apache、Nginx、Tomcat等),以及一些經常使用應用(LAMP、CMS等)。包括具體的鏡像構建方法與使用步驟。html

兩種建立鏡像的過程。其中一些操做比較簡單的鏡像使用Dockerfile來建立,而像Weblogic這樣複雜的應用,則使用commit方式來建立。node

Apache

Apache是一個高穩定性的、商業級別的開源Web服務器。目前Apache已是世界使用排名第一的Web服務器軟件。因爲其良好的跨平臺和安全性,Apache被普遍應用在多種平臺和操做系統上。做爲Apache軟件基金會支持的項目,它的開發者社區完善而高效。自1995年發佈至今,一直以高標準進行維護與開發。Apache名稱源自美國的西南部一個印第安人部落:阿帕奇族,它支持類UNIX和Windows系統。mysql

1.使用官方鏡像nginx

官方提供了名爲httpd的Apache鏡像,能夠做爲基礎Web服務鏡像。git

編寫Dockerfile文件,內容以下:web

FROM httpd:2.4
COPY ./public-html /usr/local/apache2/htdocs/

建立項目目錄public-html,並在此目錄下建立index.html文件:Hello, Docker!sql

構建自定義鏡像:$ docker build -t apache2-image .docker

構建完成後,使用docker run指令運行鏡像:$ docker run -it --rm --name apache-container -p 80:80 apache2-imageshell

經過本地的80端口便可訪問靜態頁面。數據庫

也能夠不建立自定義鏡像,直接經過映射目錄方式運行Apache容器:

$ docker run -it --rm --name my-apache-app -p 80:80 -v "$PWD":/usr/local/apache2/htdocs/ httpd:2.4

再次打開瀏覽器,能夠再次看到頁面輸出。

2.使用自定義鏡像

首先,建立一個apache_ubuntu工做目錄,在其中建立Dockerfile文件、run.sh文件和sample目錄:

mkdir apache_ubuntu && cd apache_ubuntu

$ touch Dockerfile run.sh

mkdir sample

下面是Dockerfile的內容和各個部分的說明:

#設置繼承自用戶建立的sshd鏡像

FROM sshd:Dockerfile

#建立者的基本信息

MAINTAINER docker_user (user@docker.com)

#設置環境變量,全部操做都是非交互式的

ENV DEBIAN_FRONTEND noninteractive

#安裝

RUN apt-get -yq install apache2&&\

rm -rf /var/lib/apt/lists/*

RUN echo "Asia/Shanghai" > /etc/timezone && \

dpkg-reconfigure -f noninteractive tzdata

#注意這裏要更改系統的時區設置,由於在web應用中常常會用到時區這個系統變量,默認的ubuntu會讓你的應用程序發生難以想象的效果

#添加用戶的腳本,並設置權限,這會覆蓋以前放在這個位置的腳本

ADD run.sh /run.sh

RUN chmod 755 /*.sh

#添加一個示例的web站點,刪掉默認安裝在apache文件夾下面的文件,並將用戶添加的示例用軟連接,鏈到/var/www/html目錄下面

RUN mkdir -p /var/lock/apache2 && mkdir -p /app && rm -fr /var/www/html && ln -s /app /var/www/html 

COPY sample/ /app

#設置apache相關的一些變量,在容器啓動的時候可使用-e參數替代

ENV APACHE_RUN_USER www-data

ENV APACHE_RUN_GROUP www-data

ENV APACHE_LOG_DIR /var/log/apache2

ENV APACHE_PID_FILE /var/run/apache2.pid

ENV APACHE_RUN_DIR /var/run/apache2

ENV APACHE_LOCK_DIR /var/lock/apache2

ENV APACHE_SERVERADMIN admin@localhost

ENV APACHE_SERVERNAME localhost

ENV APACHE_SERVERALIAS docker.localhost

ENV APACHE_DOCUMENTROOT /var/www

EXPOSE 80

WORKDIR /app

CMD ["/run.sh"]

此sample站點的內容爲輸出Hello Docker!。而後在sample目錄下建立index.html文件,內容以下:Hello, Docker!

run.sh腳本內容也很簡單,只是啓動apache服務:

$ cat run.sh

#!/bin/bash
exec apache2 -D FOREGROUND

下面,用戶開始建立apache:ubuntu鏡像:

使用docker build命令建立apache:ubuntu鏡像,注意命令最後的「.」。

$ docker build -t apache:ubuntu .

下面開始使用docker run指令測試鏡像。可使用-P參數映射須要開放的端口(22和80端口):

$ docker run -d -P apache:ubuntu

64681e2ae943f18eae9f599dbc43b5f44d9090bdca3d8af641d7b371c124acfd

$ docker ps -a

CONTAINER ID        IMAGE            COMMAND     CREATED     STATUS   PORTS                                                                NAMES

64681e2ae943        apache:ubuntu "/run.sh"       2 seconds    Up 1       0.0.0.0:49171->22/tcp, 0.0.0.0:49172->80/tcp    naughty_poincare

在本地主機上用curl抓取網頁來驗證剛纔建立的sample站點:

$ curl 127.0.0.1:49172

Hello Docker!

也能夠在其餘設備上經過訪問宿主主機ip:49172來訪問sample站點。

在apache鏡像的Dockerfile中只用EXPOSE定義了對外開放的80端口,而在docker ps -a命令的返回中,卻看到新啓動的容器映射了兩個端口:22和80。

重要:可是實際上,當嘗試使用SSH登陸到容器時,會發現沒法登陸。這是由於在run.sh腳本中並未啓動SSH服務。這說明在使用Dockerfile建立鏡像時,會繼承父鏡像的開放端口,但卻不會繼承啓動命令

所以,須要在run.sh腳本中添加啓動sshd的服務的命令:

$ cat run.sh

#!/bin/bash
/usr/sbin/sshd & exec apache2 -D FOREGROUND

再次建立鏡像:

$ docker build -t apache:ubuntu .

此次建立的鏡像,將默認會同時啓動SSH和Apache服務。

來看看如何映射本地目錄。能夠經過映射本地目錄的方式,來指定容器內Apache服務響應的內容,例如映射本地主機上當前目錄下的www目錄到容器內的/var/www目錄:

$ docker run -i -d -p 80:80 -p 103:22 -e APACHE_SERVERNAME=test  -v `pwd`/www:/var/www:ro apache:ubuntu

在當前目錄內建立www目錄,並放上自定義的頁面index.html。

在本地主機上可訪問測試容器提供的Web服務,查看獲取內容爲新配置的index.html頁面信息。

Nginx

Nginx是一款功能強大的開源反向代理服務器,支持HTTP、HTTPS、SMTP、POP三、IMAP等協議。它也能夠做爲負載均衡器、HTTP緩存或Web服務器。Nginx一開始就專一於高併發和高性能的應用場景。它使用類BSD開源協議,支持Linux、BSD、Mac、Solaris、AIX等類Unix系統,同時也有Windows上的移植版本。

1.使用官方鏡像

用戶可使用docker run指令直接運行官方Nginx鏡像:

$ docker run -d -p 80:80 --name webserver nginx

34bcd01998a76f67b1b9e6abe5b7db5e685af325d6fafb1acd0ce84e81e71e5d

而後使用docker ps指令查看當前運行的docker ps指令查看當前運行的容器:

$ docker ps

CONTAINER ID IMAGE COMMAND     CREATED  STATUS PORTS                        NAMES

34bcd01998a7 nginx "nginx..."  2min ago Up     0.0.0.0:80->80/tcp, 443/tcp  webserver

目前Nginx容器已經在0.0.0.0:80啓動,並映射了80端口,此時能夠打開瀏覽器訪問此地址,就能夠看到Nginx輸出的頁面。

2.自定義Web頁面

一樣的,建立index.html文件,並將index.html文件掛載至容器中,便可看到顯示自定義的頁面。

$ docker run --name nginx-container -p 80:80 -v index.html:/usr/share/nginx/html:ro -d nginx

另外,也可使用Dockerfile來構建新鏡像。Dockerfile內容以下:

FROM nginx
COPY ./index.html /usr/share/nginx/html

開始構建鏡像my-nginx:

$ docker build -t my-nginx .

構建成功後執行docker run指令:

$ docker run --name nginx-container -d my-nginx

Tomcat

Tomcat是由Apache軟件基金會下屬的Jakarta項目開發的一個Servlet容器,按照Sun Microsystems提供的技術規範,實現了對Servlet和Java Server Page(JSP)的支持。同時,它提供了做爲Web服務器的一些特有功能,如Tomcat管理和控制平臺、安全域管理和Tomcat閥等。因爲Tomcat自己也內含了一個HTTP服務器,也能夠看成一個單獨的Web服務器來使用。

首先,嘗試在Docker Hub上搜索已有的Tomcat相關鏡像的個數:

$ docker search tomcat |wc -l 

285

能夠看到,已經有285個相關鏡像。如是我的開發或測試,能夠隨意選擇一個鏡像,按照提示啓動應用便可。

下面以Tomcat 7.0爲例介紹定製Tomcat鏡像的步驟:

1.準備工做

建立tomcat7.0_jdk1.6文件夾,從www.oracle.com網站上下載sun_jdk 1.6壓縮包,解壓爲jdk目錄。

建立Dockerfile和run.sh文件:

mkdir tomcat7.0_jdk1.6

$ cd tomcat7.0_jdk1.6/

$ touch Dockerfile run.sh

下載Tomcat,能夠到官方網站下載最新的版本,也能夠直接使用下面連接中給出的版本:

$ wget http://mirror.bit.edu.cn/apache/tomcat/tomcat-7/v7.0.56/bin/apache-tomcat-7.0.56.zip

$ ls

Dockerfile  apache-tomcat-7.0.56   jdk  run.sh

2.Dockerfile文件和其餘腳本文件

Dockerfile文件內容以下:

#設置繼承自用戶建立的sshd鏡像

FROM sshd:Dockerfile

#下面是一些建立者的基本信息

MAINTAINER docker_user (user@docker.com)

#設置環境變量,全部操做都是非交互式的

ENV DEBIAN_FRONTEND noninteractive

#注意這裏要更改系統的時區設置

RUN echo "Asia/Shanghai" > /etc/timezone && \

dpkg-reconfigure -f noninteractive tzdata

#安裝跟tomcat用戶認證相關的軟件

RUN apt-get install -yq --no-install-recommends wget pwgen ca-certificates && \

apt-get clean && \

rm -rf /var/lib/apt/lists/*

#設置tomcat的環境變量,若讀者有其餘的環境變量須要設置,也能夠在這裏添加。

ENV CATALINA_HOME /tomcat

ENV JAVA_HOME /jdk

#複製tomcat和jdk文件到鏡像中

ADD apache-tomcat-7.0.56 /tomcat

ADD jdk /jdk

ADD create_tomcat_admin_user.sh /create_tomcat_admin_user.sh

ADD run.sh /run.sh

RUN chmod +x /*.sh

RUN chmod +x /tomcat/bin/*.sh

EXPOSE 8080

CMD ["/run.sh"]

建立tomcat用戶和密碼腳本文件create_tomcat_admin_user.sh文件,內容爲:

#!/bin/bash
if [ -f /.tomcat_admin_created ]; then
echo "Tomcat 'admin' user already created"
exit 0
fi
#generate password
PASS=${TOMCAT_PASS:-$(pwgen -s 12 1)}
_word=$( [ ${TOMCAT_PASS} ] && echo "preset" || echo "random" )
echo "=> Creating and admin user with a ${_word} password in Tomcat"
sed -i -r 's/<\/tomcat-users>//' ${CATALINA_HOME}/conf/tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo "
script,manager-jmx,admin-gui, admin-script\"/>" >> ${CATALINA_HOME}/conf/
tomcat-users.xml
echo '' >> ${CATALINA_HOME}/conf/tomcat-users.xml
echo "=> Done!"
touch /.tomcat_admin_created
echo "========================================================================"
echo "You can now configure to this Tomcat server using:"
echo ""
echo "    admin:${PASS}"
echo ""
echo "========================================================================"

編寫run.sh腳本文件,內容爲:

#!/bin/bash

if [ ! -f /.tomcat_admin_created ]; then
/create_tomcat_admin_user.sh
fi
/usr/sbin/sshd -D &
exec ${CATALINA_HOME}/bin/catalina.sh run

3.建立和測試鏡像

經過下面的命令建立鏡像tomcat7.0:jdk1.6

$ docker build -t tomcat7.0:jdk1.6 .

啓動一個tomcat容器進行測試:

$ docker run -d -P tomcat7.0:jdk1.6

3cd4238cb32a713a3a1c29d93fbfc80cba150653b5eb8bd7629bee957e7378ed

經過docker logs獲得tomcat的密碼aBwN0CNCPckw:

$ docker logs 3cd

=> Creating and admin user with a random password in Tomcat
=> Done!
=======================================================================
You can now configure to this Tomcat server using:
admin:aBwN0CNCPckw

查看映射的端口信息:

$ docker ps

CONTAINER ID   IMAGE                COMMAND  CREATED  STATUS              PORTS                                                                   NAMES

3cd4238cb32a    tomcat7.0:jdk1.6 "/run.sh"   4 seconds  Up 3 seconds      0.0.0.0:49157->22/tcp, 0.0.0.0:49158->8080/tcp   cranky_wright

在本地使用瀏覽器登陸Tomcat管理界面,訪問本地的49158端口,即http://127.0.0.1:49158。(22端口是ssh的)

輸入從docker logs中獲得的密碼,成功進入管理界面。

在實際環境中,能夠經過使用-v參數來掛載Tomcat的日誌文件、程序所在目錄、以及與Tomcat相關的配置。

Jetty

Jetty是一個優秀的開源Servlet容器,以其高效、小巧、可嵌入式等優勢深得人心,它爲基於Java的Web內容(如JSP和Servlet)提供運行環境。Jetty基於Java語言編寫,它的API以一組JAR包的形式發佈。開發人員能夠將Jetty容器實例化成一個對象,能夠迅速爲一些獨立運行的Java應用提供Web服務。相對老牌的Tomcat,Jetty架構更合理,性能更優。尤爲在啓動速度上,讓Tomcat可望不可即。Jetty目前在國內外互聯網企業中應用普遍。

DockerHub官方提供了Jetty鏡像,直接運行docker run指令便可:

$ docker run -d jetty

使用docker ps指令查看正在運行中的jetty容器:

$ docker ps

CONTAINER ID  IMAGE COMMAND                CREATED  STATUS  PORTS     NAMES

f7f1d70f2773  jetty "/docker-entrypoint.b" x ago    Up      8080/tcp  lonely_poitras

固然,還可使用-p參數映射運行端口:

$ docker run -d -p 80:8080 -p 443:8443 jetty

7bc629845e8b953e02e31caaac24744232e21816dcf81568c029eb8750775733

使用宿主機的瀏覽器訪問container-ip:8080,便可得到Jetty運行頁面,因爲當前沒有內容,會提示錯誤信息。

LAMP

LAMP(Linux-Apache-MySQL-PHP)是目前流行的Web工具棧,其中包括:Linux操做系統,Apache網絡服務器,MySQL數據庫,Perl、PHP或者Python編程語言。其組成工具均是成熟的開源軟件,被大量網站所採用。和Java/J2EE架構相比,LAMP具備Web資源豐富、輕量、快速開發等特色;和微軟的.NET架構相比,LAMP更具備通用、跨平臺、高性能、低價格的優點。所以LAMP不管是在性能、質量仍是價格方面都是企業搭建網站的首選平臺。

如今也有人用Nginx替換Apache,稱爲LNMP或LEMP,但並不影響整個框架的選型原則,是彼此十分相似的技術棧。

可使用自定義Dockerfile或者Compose方式運行LAMP,同時社區也提供了十分紅熟的linode/lamp和tutum/lamp鏡像。

下面介紹後兩種方法。

1.使用linode/lamp鏡像

首先,執行docker run指令,直接運行鏡像,並進入容器內部bash shell:

$ docker run -p 80:80 -t -i linode/lamp /bin/bash

root@e283cc3b2908:/#

在容器內部shell啓動apache以及mysql服務:

$ root@e283cc3b2908:/# service apache2 start

* Starting web server apache2

$ root@e283cc3b2908:/# service mysql start

* Starting MySQL database server mysqld                                 [ OK ]

* Checking for tables which need an upgrade, are corrupt or were not closed cleanly.

此時鏡像中apache、mysql服務已經啓動,可以使用docker ps指令查看運行中的容器:

$ docker ps -aCONTAINER ID IMAGE       COMMAND     CREATED  STATUS       PORTS

NAMESe283cc3b2908 linode/lamp "/bin/bash" x ago    Up x seconds 0.0.0.0:80->80/tcp trusting_mestorf

此時經過瀏覽器訪問本地80端口便可看到默認頁面。

2.使用tutum/lamp鏡像

首先,執行docker run指令,直接運行鏡像:

$ docker run -d -p 80:80 -p 3306:3306 tutum/lamp

容器啓動成功後,打開瀏覽器,訪問demo頁面。

CMS

內容管理系統(Content Management System,CMS)指的是提供內容編輯服務的平臺程序。CMS可讓不懂編程的用戶方便又輕鬆地發佈、更改和管理各種數字內容(主要以文本和圖像爲主)。以Wordpress和Ghost兩個流行的CMS軟件爲例,介紹如何製做和使用對應的Docker鏡像。

WordPress

WordPress是風靡全球的開源內容管理系統,是博客、企業官網、產品首頁等內容相關平臺的主流實現方案之一。相似項目還有Drupal、Joomla、Typo3等。

WordPress基於PHP和MySQL,架構設計簡單明瞭,支持主題,插件和各類功能模塊。更重要的是,WordPress擁有龐大的社區,在線資源很是豐富,而且在各大網絡空間商和雲平臺中受到普遍的支持。根據2013年8月的統計數據,流量排名前一千萬的網站中其使用率高達22%。

1.使用官方鏡像

首先,經過Docker Hub下載官方wordpress鏡像:

$ docker pull wordpress

而後,就能夠建立並運行一個wordpress容器,並鏈接到mysql容器:

$ docker run --name some-wordpress --link some-mysql:mysql -d wordpress

一樣,用戶可使用-p參數來進行端口映射:

$ docker run --name some-wordpress --link some-mysql:mysql -p 8080:80 -d wordpress

啓動成功後,可在瀏覽器中訪問http://localhost:8080來打開WordPress頁面。

2.使用Compose搭建WordPress應用

可使用Compose來一鍵搭建WordPress應用。

首先,新建docker-compose.yml文件:

wordpress:
image: wordpress
links:
- db:mysql
ports:
- 8080:80
db:
image: mariadb
environment:
MYSQL_ROOT_PASSWORD: example

而後執行:

$ docker-compose up

若是提示沒有docker-compose命令,能夠經過pip install docker-compose來在線安裝。

待服務啓動後,便可打開瀏覽器訪問本地8080端口打開WordPress配置界面。

Ghost

Ghost是一個廣受歡迎的開源博客平臺,使用JavaScript編寫,以MIT協議發佈。它的設計很是簡約,使用起來體驗優異,很是適合作內容發佈,故而受到不少極客或技術工做者的喜好。能夠直接使用Docker Hub提供的官方Ghost鏡像。

直接使用docker run指令運行:

$ docker run --name ghost-container -d ghost

至此已經成功啓動了一個Ghost容器,內含Ghost實例並監聽默認的2368服務端口。

固然能夠對服務進行端口映射,以下所示:

$ docker run --name ghost-container-1 -p 8080:2368 -d ghost

df116b7d570b3456950f4d7c22ff6911124427d16635080817e884922b491a2d

還能夠掛載已有的內容到Ghost容器內:

$ docker run --name some-ghost -v /path/to/ghost/blog:/var/lib/ghost ghost

持續開發與管理

信息行業突飛猛進,如何響應不斷變化的需求,快速適應和保證軟件的質量?持續集成(Continuous integration,CI)正是針對這類問題的一種開發實踐,它倡導開發團隊按期進行集成驗證。集成經過自動化的構建來完成,包括自動編譯、發佈和測試,從而儘快地發現錯誤。CI所描述的軟件開發是從原始需求識別到最終產品部署整個過程當中,需求以小批量形式在團隊的各個角色間順暢流動,可以以較短地週期完成需求的小粒度頻繁交付。整個過程當中,需求分析、產品的用戶體驗和交互設計、開發、測試、運維等角色須要密切協做。

持續集成特色包括:從檢出代碼編譯構建運行測試結果記錄測試統計等都是自動完成的,減小人工干預。須要有持續集成系統的支持,包括代碼託管機制支持,以及集成服務器等。

持續交付(Continuous delivery,CD)則是經典的敏捷軟件開發方法的天然延伸,它強調產品在修改後部署上線的流程要敏捷化、自動化。甚至一些較小的改變也要今早的部署上線,這跟傳統軟件在較大版本更新後才上線的思想不一樣。

Jenkins

Jenkins是一個獲得普遍應用的持續集成和持續交付的工具。做爲開源軟件項目,它旨在提供一個開放易用的持續集成平臺。Jenkins能實時監控集成中存在的錯誤,提供詳細的日誌文件和提醒功能,並用圖表的形式形象地展現項目構建的趨勢和穩定性。Jenkins特色包括安裝配置簡單、支持詳細的測試報表、分佈式構建等。

自2.0版本,Jenkis推出了Pipeline as Code,幫助Jenkins實現對CI和CD更好的支持。經過Pipeline,將本來獨立運行的多個任務鏈接起來,能夠實現十分複雜的發佈流程。Jenkins官方在Docker Hub上提供了全功能的基於官方發佈版的Docker鏡像。

能夠方便地使用docker run指令一鍵部署Jenkins服務,以下所示:

$ docker run -p 8080:8080 -p 50000:50000 jenkins

Jenkins容器啓動成功後,能夠打開瀏覽器訪問8080端口,查看Jenkins管理界面。

目前運行的容器中,數據會存儲在工做目錄/var/jenkins_home中,這包括Jenkins中全部的數據,包括插件和配置信息等。

若是須要數據持久化,可使用數據卷機制:

$ docker run -p 8080:8080 -p 50000:50000 -v /your/home:/var/jenkins_home jenkins

以上指令會將Jenkins數據存儲於宿主機的/your/home目錄(須要確保/your/home目錄對於容器內的Jenkins用戶是可訪問的)下。

固然也可使用數據卷容器:

$ docker run --name myjenkins -p 8080:8080 -p 50000:50000 -v /var/jenkins_home jenkins

Gitlab

Gitlab是一款很是強大的開源源碼管理系統。它支持基於Git的源碼管理、代碼評審、issue跟蹤、活動管理、wiki頁面,持續集成和測試等功能。

基於Gitlab,用戶能夠本身搭建一套相似Github的開發協同平臺。Gitlab官方提供了社區版本(Gitlab CE)的DockerHub鏡像。

能夠直接使用docker run指令運行:

$ docker run --detach \
--hostname gitlab.example.com \
--publish 443:443 --publish 80:80 --publish 23:23 \
--name gitlab \
--restart always \
--volume /srv/gitlab/config:/etc/gitlab \
--volume /srv/gitlab/logs:/var/log/gitlab \
--volume /srv/gitlab/data:/var/opt/gitlab \
gitlab/gitlab-ce:latest

dbae485d24492f656d2baf18526552353cd55aac662e32491046ed7fa033be3a

成功運行鏡像後,能夠打開瀏覽器,訪問Gitlab服務管理界面。

相關文章
相關標籤/搜索