zoukankan      html  css  js  c++  java
  • 容器基础(七): 使用docker compose部署程序

    配置

    上一节的基础上,  增加如下的docker-compose.yml文件, 然后用docker-compose up命令启动容器进行部署: 

     1 version: "3"
     2 services:
     3   server:
     4     image: update/server:v0.1
     5     labels:
     6       description: "tcp server test script"
     7     restart: always
     8     command: -p 3000
     9 
    10   worker:
    11     image: update/worker:v0.1
    12     labels:
    13       description: "tcp client test script"
    14     restart: always
    15     links:
    16       - server:server
    17     command: -d server -p 3000

    启动信息:

     1 linux:/app # docker-compose  up
     2 Creating network "app_default" with the default driver
     3 Creating app_server_1_17e8cbeb1e01 ... done
     4 Creating app_worker_1_bd97b9199c60 ... done
     5 Attaching to app_server_1_74e7ece79785, app_worker_1_bb9dcc04daf9
     6 
     7 
     8 linux:/app/original/server # docker ps
     9 CONTAINER ID        IMAGE                COMMAND                  CREATED              STATUS              PORTS               NAMES
    10 81211aa6383c        update/worker:v0.1   "python worker.py ..."   About a minute ago   Up About a minute                       app_worker_1_bb9dcc04daf9
    11 76c322567db7        update/server:v0.1   "python server.py ..."   About a minute ago   Up About a minute                       app_server_1_74e7ece79785
    12 linux:/app/original/server # docker exec ^C
    13 linux:/app/original/server # docker exec 81211aa6383c ss -a | grep 3000
    14 tcp    ESTAB      0      0           172.18.0.3:52448        172.18.0.2:3000
    15 linux:/app/original/server # docker exec 76c322567db7 ss -a | grep 3000
    16 tcp    LISTEN     0      5                    *:3000                  *:*
    17 tcp    ESTAB      0      0           172.18.0.2:3000         172.18.0.3:52448
    18 linux:/app/original/server # docker exec 76c322567db7 tail -f /update/server/log/server.log
    19 2018-11-19 09:35:59 [INFO]  Waiting for connection...
    20 2018-11-19 09:36:00 [INFO]  ('172.18.0.3', 52448) connected
    21 tail: unrecognized file system type 0x794c7630 for '/update/server/log/server.log'. please report this to bug-coreutils@gnu.org. reverting to polling
    22 ^C
    23 linux:/app/original/server # docker exec 81211aa6383c tail -f /update/worker/log/worker.log
    24 tail: unrecognized file system type 0x794c7630 for '/update/worker/log/worker.log'. please report this to bug-coreutils@gnu.org. reverting to polling
    25 2018-11-19 09:38:30 [INFO]  [recv] hello, docker!
    26 2018-11-19 09:38:35 [INFO]  [recv] hello, docker!
    27 2018-11-19 09:38:40 [INFO]  [recv] hello, docker!
    28 ^C
    29 linux:/app/original/server # 
    30 linux:/app #  docker-compose -f docker-compose.yml down
    31 Stopping app_worker_1_bd97b9199c60 ... done
    32 Stopping app_server_1_17e8cbeb1e01 ... done
    33 Removing app_worker_1_bd97b9199c60 ... done
    34 Removing app_server_1_17e8cbeb1e01 ... done
    35 Removing network app_default
    36 linux:/app #

    支持环境变量传参 

    在上面的基础上,把命令行传参的方式改为通过环境变量传参:

     1 FROM jason/debian-python27:v1.0
     2 
     3 MAINTAINER jason<djsxut@163.com>
     4 
     5 RUN mkdir -p /env/server
     6 
     7 COPY . /env/server
     8 
     9 WORKDIR /env/server
    10 
    11 ENV PATH $PATH:/env/server
    12 
    13 ENTRYPOINT ["python", "server.py"]
    /app/env/server/Dockerfile
     1 #!/usr/bin/python
     2 # -*- coding: utf-8 -*-
     3 
     4 import os
     5 import sys
     6 import time
     7 import socket
     8 import select
     9 import signal
    10 import threading
    11 
    12 log_file = "log/server.log"
    13 
    14 def log(msg):
    15   if not os.path.exists("log"):
    16     os.mkdir("log")
    17   with open(log_file, "a") as wf:
    18     wf.writelines(
    19         time.strftime("%Y-%m-%d %H:%M:%S", time.localtime(time.time())) +
    20         " [INFO]  " + msg + "
    ")
    21 
    22 def do_listen(port):
    23   server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    24   server_socket.bind(('', port))
    25   server_socket.listen(5)
    26   print 'Waiting for connection...'
    27   log('Waiting for connection...')
    28   server_socket.setblocking(0)
    29 
    30   rfd = [server_socket, ]
    31 
    32   while True:
    33     rlist, wlist, xlist = select.select(rfd, [], [])
    34     for sock in rlist:
    35       if sock == server_socket:
    36         newsock, addr = server_socket.accept()
    37         print '[+] %s connected' % str(addr)
    38         log('%s connected' % str(addr))
    39         rfd.append(newsock)
    40       else:
    41         data = sock.recv(1024)
    42         if data:
    43           sock.send(data)
    44         else:
    45           print '[-] %s closed' % str(sock.getpeername())
    46           log('%s closed' % str(sock.getpeername()))
    47           rfd.remove(sock)
    48           sock.close()
    49 
    50 def signal_handler(signum, frame):
    51   print '
    [-] signal(%d) received, exit!' % signum
    52   log('signal(%d) received, exit!' % signum)
    53   sys.exit(-1)
    54 
    55 if __name__ == '__main__':
    56   try:
    57     port = int(os.environ['APP_PORT'])
    58   except:
    59     print '[-] environment APP_PORT should be set'
    60     log('environment APP_PORT should be set')
    61     sys.exit(-1)
    62 
    63   signal.signal(signal.SIGINT, signal_handler)  
    64 
    65   try:
    66     do_listen(port)
    67   except Exception, e:
    68     print e
    69     print '
    Exit'
    /app/env/server/server.py
     1 FROM jason/debian-python27:v1.0
     2 
     3 MAINTAINER jason<djsxut@163.com>
     4 
     5 RUN mkdir -p /env/worker
     6 
     7 COPY . /env/worker
     8 
     9 WORKDIR /env/worker
    10 
    11 ENV PATH $PATH:/env/worker
    12 
    13 ENTRYPOINT ["python", "worker.py"]
    /app/env/worker/Dockerfile
     1 #!/usr/bin/python
     2 # -*- coding: utf-8 -*-
     3 
     4 import os
     5 import sys
     6 import time
     7 import socket
     8 import signal
     9 import getopt
    10 import threading
    11 
    12 log_file = "log/worker.log"
    13 
    14 def log(msg):
    15   if not os.path.exists("log"):
    16     os.mkdir("log")
    17   with open(log_file, "a") as wf:
    18     wf.writelines(
    19         time.strftime("%Y-%m-%d %H:%M:%S", time.localtime(time.time())) +
    20         " [INFO]  " + msg + "
    ")
    21 
    22 class Handler:
    23   def __init__(self, domain, port):
    24     self.domain = domain
    25     self.port   = port
    26     self.sock   = None
    27 
    28   def get_socket(self):
    29     for res in socket.getaddrinfo(self.domain, self.port,
    30                                   socket.AF_INET, socket.SOCK_STREAM):
    31       family, socktype, proto, canonname, sa = res
    32       try:
    33         self.sock = socket.socket(family, socktype, proto)
    34         #self.sock.setblocking(0)
    35         #sock.settimeout(0.5)
    36         self.sock.connect(sa)
    37       except socket.error, msg:
    38         if self.sock != None:
    39           self.sock.close()
    40         self.sock = None
    41       else:
    42         return True
    43 
    44     return False
    45 
    46   def do_handler(self):
    47     while self.sock == None and self.get_socket() == False:
    48       print '[-] connect failed...'
    49       log('connect failed...')
    50       time.sleep(5)
    51 
    52     print '[+] %s connected' % str(self.sock.getpeername())
    53     log('[+] %s connected' % str(self.sock.getpeername()))
    54     while True:
    55       # do something
    56       self.sock.send('hello, docker!')
    57       data = self.sock.recv(1024)
    58       if data:
    59         print '[+][recv] %s' % data
    60         log('[recv] %s' % data)
    61         time.sleep(5)
    62       else:
    63         print '[-] server closed, exit'
    64         log('server closed, exit')
    65         self.sock.close()
    66         self.sock = None
    67         break
    68 
    69 def signal_handler(signum, frame):
    70   print '
    [-] signal(%d) received, exit!' % signum
    71   log('signal(%d) received, exit!' % signum)
    72   sys.exit(-1)
    73 
    74 if __name__ == '__main__':
    75   signal.signal(signal.SIGINT, signal_handler)  
    76 
    77   try:
    78     domain = os.environ['APP_DOMAIN']
    79     port = int(os.environ['APP_PORT'])
    80   except:
    81     print '[-] environment APP_PORT/APP_DOMAIN should be set'
    82     log('environment APP_PORT/APP_DOMAIN should be set')
    83     sys.exit(-1)
    84 
    85   try:
    86     handler = Handler(domain, port)
    87     handler.do_handler()
    88   except Exception, e:
    89     print e
    90     print '
    Exit'
    /app/env/worker/worker.py

    简单修改下docker-compose.yml文件:

     1 version: "3"
     2 services:
     3   server:
     4     image: env/server:v0.1 
     5     build:
     6       context: /app/env/server
     7       dockerfile: Dockerfile
     8     labels:
     9       description: "tcp server test script"
    10     restart: always
    11     environment:
    12       - APP_PORT=${APP_PORT-3000}
    13     volumes:
    14       - /app/env/server/log:/env/server/log
    15   
    16   worker:
    17     image: env/worker:v0.1
    18     build: /app/env/worker
    19     labels:
    20       description: "tcp client test script"
    21     restart: always
    22     links:
    23       - server
    24     environment:
    25       - APP_PORT=${APP_PORT-3000}
    26       - APP_DOMAIN=server
    27     volumes:
    28       - /app/env/worker/log:/env/worker/log
    29     deploy:
    30       replicas: 3

     执行结果如下所示:

     1 linux:/app/env/server # APP_PORT=5000 docker-compose up -d
     2 WARNING: Some services (worker) use the 'deploy' key, which will be ignored. Compose does not support 'deploy' configuration - use `docker stack deploy` to deploy to a swarm.
     3 Creating network "env_default" with the default driver
     4 Building server
     5 Step 1/7 : FROM jason/debian-python27:v1.0
     6  ---> cd0b2f7d8d04
     7 Step 2/7 : MAINTAINER jason<djsxut@163.com>
     8  ---> Using cache
     9  ---> d239a9d50575
    10 Step 3/7 : RUN mkdir -p /env/server
    11  ---> Running in f1802bbbf5f8
    12  ---> b196dec5ece6
    13 Removing intermediate container f1802bbbf5f8
    14 Step 4/7 : COPY . /env/server
    15  ---> 789a69dde7bc
    16 Removing intermediate container 53d720f6e28d
    17 Step 5/7 : WORKDIR /env/server
    18  ---> 8bc3b957a769
    19 Removing intermediate container dfd8c4cecd45
    20 Step 6/7 : ENV PATH $PATH:/env/server
    21  ---> Running in 0935ca701a19
    22  ---> d6fdd5814444
    23 Removing intermediate container 0935ca701a19
    24 Step 7/7 : ENTRYPOINT python server.py
    25  ---> Running in 9209e05da1a9
    26  ---> c34b7a72cb0b
    27 Removing intermediate container 9209e05da1a9
    28 Successfully built c34b7a72cb0b
    29 WARNING: Image for service server was built because it did not already exist. To rebuild this image you must use `docker-compose build` or `docker-compose up --build`.
    30 Building worker
    31 Step 1/7 : FROM jason/debian-python27:v1.0
    32  ---> cd0b2f7d8d04
    33 Step 2/7 : MAINTAINER jason<djsxut@163.com>
    34  ---> Using cache
    35  ---> d239a9d50575
    36 Step 3/7 : RUN mkdir -p /env/worker
    37  ---> Running in de82f380b738
    38  ---> 480f67b5dc6a
    39 Removing intermediate container de82f380b738
    40 Step 4/7 : COPY . /env/worker
    41  ---> c7b98717c8c8
    42 Removing intermediate container 1d0857c192e6
    43 Step 5/7 : WORKDIR /env/worker
    44  ---> a6cedc9734a0
    45 Removing intermediate container cd648d954ada
    46 Step 6/7 : ENV PATH $PATH:/env/worker
    47  ---> Running in 977e0045899e
    48  ---> 5d20c078708d
    49 Removing intermediate container 977e0045899e
    50 Step 7/7 : ENTRYPOINT python worker.py
    51  ---> Running in 3f92d15c16f0
    52  ---> bd3579c73bd3
    53 Removing intermediate container 3f92d15c16f0
    54 Successfully built bd3579c73bd3
    55 WARNING: Image for service worker was built because it did not already exist. To rebuild this image you must use `docker-compose build` or `docker-compose up --build`.
    56 Creating env_server_1_be9373e6fe83 ... done
    57 Creating env_worker_1_e4e9c2ece128 ... done
    58 linux:/app/env/server #
    59 linux:/app/env/server #
    60 linux:/app/env/server # docker images | grep env
    61 env/worker              v0.1                bd3579c73bd3        19 seconds ago      207MB
    62 env/server              v0.1                c34b7a72cb0b        22 seconds ago      207MB
    63 linux:/app/env/server # docker ps
    64 CONTAINER ID        IMAGE               COMMAND              CREATED             STATUS              PORTS               NAMES
    65 93c7d5f760e8        env/worker:v0.1     "python worker.py"   20 seconds ago      Up 19 seconds                           env_worker_1_57f3186eefba
    66 0712a2615e12        env/server:v0.1     "python server.py"   21 seconds ago      Up 20 seconds                           env_server_1_1615d4c9ff54
    67 linux:/app/env/server # cat log/server.log
    68 2018-11-20 02:41:32 [INFO]  Waiting for connection...
    69 2018-11-20 02:41:33 [INFO]  ('172.18.0.3', 38708) connected
    70 linux:/app/env/server # cat ../worker/log/worker.log
    71 2018-11-20 02:41:33 [INFO]  [+] ('172.18.0.2', 5000) connected
    72 2018-11-20 02:41:33 [INFO]  [recv] hello, docker!
    73 linux:/app/env/server # docker-compose down
    74 WARNING: Some services (worker) use the 'deploy' key, which will be ignored. Compose does not support 'deploy' configuration - use `docker stack deploy` to deploy to a swarm.
    75 Stopping env_worker_1_57f3186eefba ... done
    76 Stopping env_server_1_1615d4c9ff54 ... done
    77 Removing env_worker_1_57f3186eefba ... done
    78 Removing env_server_1_1615d4c9ff54 ... done
    79 Removing network env_default
    80 linux:/app/env/server #
    result

    Excellence, is not an act, but a habit.
    作者:子厚.
    出处:http://www.cnblogs.com/aios/
    本文版权归作者和博客园共有,欢迎转载、交流、点赞、评论,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接。

  • 相关阅读:
    【Android数据存储】内部存储
    【Android数据存储】SharedPreferences
    【JAVA】Java开发使用技巧_获取当前项目中某个文件路径
    【Android Studio】Android Studio 常用快捷键
    跨域问题:解决跨域的三种方案
    maven问题:如何启动maven项目
    maven问题:如何不继承父工程的依赖
    itmacy_我的博客
    springboot定时器
    管理者最高境界:看不见,听不见,做不了
  • 原文地址:https://www.cnblogs.com/aios/p/9987724.html
Copyright © 2011-2022 走看看