Docker的安装和命令可以参考 https://www.cnblogs.com/milton/p/9866963.html .

资源规划

这一步要区分传统资源和Docker资源, 为后面的细节定好基础. 因为Docker的特性, 适合于占CPU和MEM资源, 但是对HDD资源要求不高的应用. 不适合用于对数据有持久化要求以及安全性要求较高的应用, 例如MySQL和日志系统.

在开发和测试环境, 你可以随手启动一个MySQL来配合开发, 但是在生产环境目前还是不太现实的, 需要整套运维工具跟进对Docker的配合后才能实现足够的安全性.

生产环境涉及的资源如下:

  • 堡垒机, VPN, 网关, 用于生产环境的底层访问控制, >= 1
  • 存档备份, 低性能大容量带冗余的存储, >=1
  • CI工具, Jenkins, 用于在生产环境进行自动部署, =1
  • RMDB 数据库, MySQL等, >=2
  • NoSQL 数据库, MongoDB, Redis 等, >=2
  • 缓存服务, Ehcache, Redis等, >=1
  • 文件服务, FastDF等, >=1
  • 配置和服务注册服务, Zookeeper, EurekaServer等, >=3
  • 日志服务, Kafka等, >=1
  • 搜索服务, Elasticsearch等, >=1
  • JVM节点, 这是用于运行jar项目的节点, =N
  • WEB服务, Nginx等, >=2

其中与业务开发关系最大, 适合用Docker进行部署的就是JVM节点部分, 还有缓存服务, WEB服务, 日志服务, 配置和注册服务, 也是适合通过Docker管理的. 这边假定仅仅使用Docker配置JVM节点.

网络划分

三类网络的私有地址范围

10.0.0.0       - 10.255.255.255
172.16.0.0   - 172.31.255.255
192.168.0.0 - 192.168.255.255

与环境现有子网综合考虑. 需要达到的目标是

  • 每个容器有独立的 IP,运维就可以像连接虚机一样通过ssh连接容器
  • 需要跨宿主机之间的容器通信
  • 访问控制, 安全性和隔离性
  • 性能损失尽量小

如果是在IDC自建机房的规划, 网络的实现方案可以参考这一篇 http://www.cnblogs.com/sammyliu/p/5926343.html ,

方案一: 基于bridge

将默认的docker bridge网桥替换为 linuxbridge, 把 linuxbridge 网段的 ip 加入到容器里, 实现容器与传统环境应用的互通.

首先在宿主机上添加一个linux bridge, 把宿主机网卡(可以是物理机的, 也可以是虚拟机的), 把这个网卡加入bridge里面, bridge配上网卡原本的管理IP. 
然后创建一个新的docker bridge网络, 指定bridge子网, 并将该网络的网桥绑定到上一步创建的网桥上.

docker network create --gateway 10.199.45.200 --subnet 10.199.45.0/24 -o com.docker.network.bridge.name=br-oak --aux-address "DefaultGatewayIPv4=10.199.45.1" oak-net

容器启动时候指定网络为第二步中创建的bridge网络, 同时为容器指定一个该网络子网内的IP. 容器启动后网络IP默认即可与外界互通.

这是最容易实现的方式, 如果要实现Docker在网络内跨宿主机迁移, 需要宿主机位于同一VLAN, 并且为了避免IP冲突, 要实现整个VLAN的IP的统一管理.

方案二: 基于Calico, 这个还没有仔细研究, 不介绍了.

安全组配置

如果是在公共云服务例如阿里云上, 并且docker数量也比较小的情况下, 就直接用宿主机端口映射就好了. 可以创建子网, 可以配置阿里云的安全组进行访问控制. 根据 对不同目标(外网, 安全组)的访问许可, 设置不同的安全组. 安全组的设置原则是, 1) 全局禁止安全组之间互访, 2) 设置资源组 + 此资源的授权组. 例如

全局组: 全部虚机
可访问全局组的: 堡垒机, VPN

外网: 默认
可访问外网的: 如公共接口模块, CI工具, 可分为一组

DB组: 只允许从特定组访问的, 分为一组
可访问DB组的: 如公共接口模块, 备份计划模块等, 可分为一组

COMMON组:
可访问COMMON组的: 下游边界业务模块等

部署Spring Cloud Jar

编写Dockerfile. 因为java:8默认不带vi, nano, ifconfig这些命令, 建议基于java:8制作一个自己的image, 把nano和net-tools装上, 这样方便运维查看容器环境信息.

FROM java:8
ADD target/scot-eureka.jar scot-eureka.jar
ENTRYPOINT ["java", "-jar", "/scot-eureka.jar"]

一个更完整的Dockerfile例子

FROM openjdk:8-jre-alpine
VOLUME ./mysql:/var/lib/mysql
ADD /build/libs/application.jar app.jar
ENTRYPOINT exec java $JAVA_OPTS -Djava.security.egd=file:/dev/./urandom -jar /app.jar

or

FROM openjdk:8-jre
RUN echo "Europe/Berlin" > /etc/timezone && dpkg-reconfigure -f noninteractive tzdata
RUN mkdir /data
WORKDIR /data
ADD myapp.jar /data/myapp.jar ENV springprofiles="" \
MAXRAMIFNOLIMIT=4096 ENTRYPOINT MAXRAM=$(expr `cat /sys/fs/cgroup/memory/memory.limit_in_bytes` / 1024 / 1024) && \
MAXRAM=$(($MAXRAM>$MAXRAMIFNOLIMIT?$MAXRAMIFNOLIMIT:$MAXRAM))m && \
echo "MaxRam: $MAXRAM" && \
java -XX:MaxRAM=$MAXRAM -Djava.security.egd=file:/dev/./urandom -jar -Dspring.profiles.active="$springprofiles" myapp.jar #when "-XX:+UseCGroupMemoryLimitForHeap" isn't experimental anymore, you can use the following
#ENTRYPOINT java -XX:+UseCGroupMemoryLimitForHeap -Djava.security.egd=file:/dev/./urandom -jar -Dspring.profiles.active="$springprofiles" myapp.jar EXPOSE 8080

制作Docker Image

docker build -t scot-eureka .

启动Docker container

docker run -d --name eureka -p : scot-eureka
# or
docker run -m 1024MB -d --name container-name -p 9100:9100 -e JAVA_OPTS="-Xmx512M -Xms512M -XX:MaxRAM=1024M" imagename:tag

其中8761是jar本身打开的端口, 8762是从外部(容器IP或者本机IP)去访问的端口, 可以通过 docker ps 或者 docker port [docker-name | container-id] 查看映射关系

$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
2ea7392a8b51 scot-eureka "java -jar /scot-eur…" minutes ago Up minutes 0.0.0.0:->/tcp eureka

这时候就可以通过容器或本机的 IP:8762 端口去访问eureka.jar启动的服务了.

在实际环境中, 需要事先配置好IP信息, package时写入jar, 给docker创建自定义的network, 在run的时候--net 指定network, --ip指定IP. 或者使用zookeeper提供的配置服务, 在启动时实时获取IP配置.

对JVM内存参数的要求

在docker容器中可以查看默认的heap size, 这个和docker run -m 指定的内存大小是无关的, 只和宿主机内存容量有关, 一般为这个容量的1/4 (参考  https://blog.csanchez.org/2017/05/31/running-a-jvm-in-a-container-without-getting-killed/ )

$ java -XshowSettings:vm -version
VM settings:
Max. Heap Size (Estimated): 1.67G
Ergonomics Machine Class: server
Using VM: Java HotSpot(TM) 64-Bit Server VM java version "1.8.0_152"
Java(TM) SE Runtime Environment (build 1.8.0_152-b16)
Java HotSpot(TM) 64-Bit Server VM (build 25.152-b16, mixed mode)

在容器中

$ docker run -m 100MB openjdk:8u121 java -XshowSettings:vm -version
VM settings:
Max. Heap Size (Estimated): 444.50M
Ergonomics Machine Class: server
Using VM: OpenJDK 64-Bit Server VM

在Java8之前, Max memory = [-Xmx] + [-XX:MaxPermSize] + number_of_threads * [-Xss]   在Java8之后用Metaspace代替了PermGen, 而Metaspace仅受主机实际内存限制. 仅仅使用-Xmx限制内存大小是不够的, 需要用-XX:MaxRAM限制实际使用的内存大小, 才能避免被Docker Daemon关闭. 在8u131+之后, 可以用 UseCGroupMemoryLimitForHeap 参数进行检测

$ docker run -m 2G -ti --rm openjdk:8-jdk java -XshowSettings:vm -XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap -XX:MaxRAMFraction=1 -version
Max. Heap Size (Estimated): 1.74G

It turns out that Java VisualVM doesn't know anything about OffHeap, and, as a result, it can be very tricky to investigate your Java application's memory consumption using this tool. Also, it's crucial to understand the JVM options you use. As for me, it was the discovery that specifying -Xmx=512m tells the JVM to allocate a 512mb heap. It’s not telling the JVM to limit its entire memory usage to 512mb. There are code caches and all sorts of other off heap data.

For specifying total memory, you should use the -XX:MaxRAM parameter. Be aware that with MaxRam=512m your heap will be approximately 250mb. Be careful and pay attention to your app JVM options.

Spring Cloud开发实践 - 04 - Docker部署的更多相关文章

  1. Spring Cloud开发实践 - 01 - 简介和根模块

    简介 使用Spring Boot的提升主要在于jar的打包形式给运维带来了很大的便利, 而Spring Cloud本身的优点不是那么明显, 相对于Dubbo而言, 可能体现在跨语言的交互性上(例如可以 ...

  2. Spring Cloud开发实践 - 03 - 接口实现和下游调用

    接口实现 Scot Commons Impl 接口实现模块 scot-commons-impl, 一方面实现了 scot-commons-api 的接口, 一方面将自己暴露为 REST 服务. 有4个 ...

  3. Spring Cloud开发实践 - 02 - Eureka服务和接口定义

    服务注册 EurekaServer Eureka服务模块只有三个文件, 分别是pom.xml, application.yml 和 EurekaServerApplication.java, 内容如下 ...

  4. Spring Cloud Alibaba | Nacos集群部署

    目录 Spring Cloud Alibaba | Nacos集群部署 1. Nacos支持三种部署模式 2. 集群模式下部署Nacos 2.1 架构图 2.2 下载源码或者安装包 2.3 配置集群配 ...

  5. Spring Cloud开发人员如何解决服务冲突和实例乱窜?(IP实现方案)

    一.背景 在我上一篇文章<Spring Cloud开发人员如何解决服务冲突和实例乱窜?>中提到使用服务的元数据来实现隔离和路由,有朋友问到能不能直接通过IP来实现?本文就和大家一起来讨论一 ...

  6. Spring cloud项目实践(一)

    链接地址:http://sail-y.github.io/2016/03/21/Spring-cloud%E9%A1%B9%E7%9B%AE%E5%AE%9E%E8%B7%B5/ 什么是Spring ...

  7. spring/spring boot/spring cloud开发总结

    背景        针对RPC远程调用,都在使用dubbo.dubbox等,我们也是如此.由于社区暂停维护.应对未来发展,我们准备尝试新技术(或许这时候也不算什么新技术了吧),选择使用了spring ...

  8. Spring Cloud开发人员如何解决服务冲突和实例乱窜?

    一.背景 在我们开发微服务架构系统时,虽然说每个微服务都是孤立的可以单独开发,但实际上并非如此,要调试和测试你的服务不仅需要您的微服务启动和运行,还需要它的上下文服务.依赖的基础服务等都要运行:但如果 ...

  9. 微服务电商项目发布重大更新,打造Spring Cloud最佳实践!

    Spring Cloud实战电商项目mall-swarm地址:转发+关注 私信我获取地址 系统架构图   系统架构图 项目组织结构 mall├── mall-common-- 工具类及通用代码模块├─ ...

随机推荐

  1. git如何上传所有的新文件 gitlab如何上传所有的新文件 git本地覆盖服务器 强制本地覆盖服务器

    原文地址:  https://blog.csdn.net/qq_28093585/article/details/78749153 目的描述:新建的git项目,项目中有许多要从本地上传到git仓库的新 ...

  2. Java NIO ServerSocketChannel

    A Java NIO ServerSocketChannel is a channel that can listen for incoming TCP connections, just like ...

  3. 浅谈 Boost.Asio 的多线程模型

    Boost.Asio 有两种支持多线程的方式,第一种方式比较简单:在多线程的场景下,每个线程都持有一个io_service,并且每个线程都调用各自的io_service的run()方法. 另一种支持多 ...

  4. Python json模块dumps loads

    python中json数据的使用. dumps和loads也是需要成对使用的,就像c++ new/delete malloc/free一样需要成对使用. 看着像json的字符串,也不一定是json字符 ...

  5. 我眼中的SCRUM

    回顾一下我所认识的scrum,算是对自己知识的一个梳理. scrum到底是什么,书中都说,它不是方法学,不是过程,而是一个框架.我并没有太理解这句话,所以先把scrum中都有些什么来说一下(可跟前一篇 ...

  6. require.js 最佳实践【转】

    https://www.cnblogs.com/digdeep/p/4607131.html require.js是一个js库,相关的基础知识,前面转载了两篇博文:Javascript模块化编程(re ...

  7. 原生javascript实现异步的7种方式

    1.$(document).ready 点评: 需要引用jquery :兼容所有浏览器. 2.标签的async=”async”属性 async的定义和用法(是HTML5的属性) async 属性规定一 ...

  8. 【ElasticSearch】ElasticSearch-索引优化-自定义索引

    ElasticSearch-索引优化-自定义索引 es 指定 索引 字段_百度搜索 [es]创建索引和映射 - 匡子语 - 博客园 reindex,增加字段,并新增数据 - Elastic中文社区 e ...

  9. C指针原理(14)

    tcc源码分析 本博客所有内容是原创,如果转载请注明来源 http://blog.csdn.net/myhaspl/ tcctok.h定义了C语言的词法分析的基本元素,主要定义了关键字. /* key ...

  10. DOM对象操作html元素1

    <!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <m ...