不为有趣之事,何遣有涯之生
不失其所者久,死而不亡者寿

AMQ简明教程(2)

hzqiuxm阅读(182)评论(0)

JMS 概念简介

JMS是什么

JMS Java Message Service,Java消息服务,是Java EE中的一个技术。

JMS规范

JMS定义了Java 中访问消息中间件的接口,并没有给予实现,实现JMS 接口的消息中间件称为JMS Provider,例如ActiveMQ

JMS provider:实现JMS接口和规范的消息中间件
JMS message:JMS的消息,JMS消息由以下三部分组成:
1:消息头:每个消息头字段都有相应的getter和setter方法
2:消息属性:如果需要除消息头字段以外的值,那么可以使用消息属性
3:消息体:封装具体的消息数据

JMS producer:消息生产者,创建和发送JMS消息的客户端应用
JMS consumer:消息消费者,接收和处理JMS消息的客户端应用

消息的消费可以采用以下两种方法之一:
1:同步消费:通过调用消费者的receive方法从目的地中显式提取消息,receive 方法可以一直阻塞到消息到达。
2:异步消费:客户可以为消费者注册一个消息监听器,以定义在消息到达时所采取的动作

JMS domains:消息传递域

JMS规范中定义了两种消息传递域:
点对点(point-to-point,简写成PTP)消息传递域和发布/订阅消息传递域(publish/subscribe,简写成pub/sub)

1:点对点消息传递域的特点如下:
(1)每个消息只能有一个消费者
(2)消息的生产者和消费者之间没有时间上的相关性。无论消费者在生产者发送消息的时候是否处于运行状态,它都可以提取消息。

2:发布/订阅消息传递域的特点如下:
(1)每个消息可以有多个消费者
(2)生产者和消费者之间有时间上的相关性。订阅一个主题的消费者只能消费自它订阅之后发布的消息。

JMS 规范允许客户创建持久订阅,这在一定程度上放松了时间上的相关性要求。
持久订阅允许消费者消费它在未处于激活状态(离线)时发送的消息。

3:在点对点消息传递域中,目的地被称为队列(queue);在发布/订阅消息传递域中,目的地被称为主题(topic)

Connection factory:连接工厂,用来创建连接对象,以连接到JMS的provider
JMS Connection:封装了客户与JMS 提供者之间的一个虚拟的连接

JMS Session:是生产和消费消息的一个单线程上下文会话用于创建消息生产者(producer)、消息消费者(consumer)和消息(message)等。
会话提供了一个事务性的上下文,在这个上下文中,一组发送和接收被组合到了一个原子操作中。

Destination:消息发送到的目的地
Acknowledge:签收
Transaction:事务
JMS client:用来收发消息的Java应用

Non-JMS client:使用JMS provider本地API写的应用,用来替换JMS API实现收发消息的功能,通常会提供其他的一些特性
比如:CORBA、RMI等。

Administered objects:预定义的JMS对象,通常在provider规范中有定义,提供给JMS客户端来访问
比如: ConnectionFactory和Destination

AMQ简明教程(1)

hzqiuxm阅读(216)评论(0)

ActiveMQ简介

ActiveMQ是什么

ActiveMQ是Apache推出的,一款开源的,完全支持JMS1.1和J2EE 1.4规范的JMS
Provider实现的消息中间件(Message Oriented Middleware,MOM)

ActiveMQ能干什么

最主要的功能就是:实现JMS Provider,用来帮助实现高可用、高性能、可伸缩、
易用和安全的企业级面向消息服务的系统

ActiveMQ特点

  • 完全支持JMS1.1和J2EE 1.4规范(持久化,XA消息,事务)
  • 支持多种传送协议:in-VM,TCP,SSL,NIO,UDP,JGroups,JXTA
  • 可插拔的体系结构,可以灵活定制,如:消息存储方式、安全管理等
  • 很容易和Application Server集成使用
  • 多种语言和协议编写客户端。语言: Java,C,C++,C#,Ruby,Perl,Python,PHP
  • 从设计上保证了高性能的集群,客户端-服务器,点对点
  • 可以很容易的和Spring结合使用
  • 支持通过JDBC和journal提供高速的消息持久化
  • 支持与Axis的整合

消息中间件的主要应用场景

在多个系统间进行整合和通讯的时候,通常会要求:
1:可靠传输,数据不能丢失,有的时候,也会要求不能重复传输;
2:异步传输,否则各个系统同步发送接受数据,互相等待,造成系统瓶颈

目前比较知名的消息中间件:

IBM MQSeries
BEA WebLogic JMS Server
Oracle AQ
Tibco
SwiftMQ
AcitveMQ:是免费的java实现的消息中间件
与其他中间件的比较:
http://www.cnblogs.com/liping13599168/articles/1915245.html

下载地址:http://activemq.apache.org/activemq-5111-release.html

maven 依赖地址:

<!--ActiveMQ -->
<dependency>
    <groupId>org.apache.activemq</groupId>
    <artifactId>activemq-all</artifactId>
    <version>5.11.1</version>
</dependency>
<dependency>
    <groupId>org.apache.xbean</groupId>
    <artifactId>xbean-spring</artifactId>
    <version>4.0</version>
</dependency>

如果你采用的是springboot框架,你需要添加的依赖如下:

compile ('org.springframework.boot:spring-boot-starter-activemq')

这个依赖已经包含了如下几个依赖

<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-jms</artifactId>
</dependency>
<dependency>
   <groupId>org.apache.activemq</groupId>
   <artifactId>activemq-broker</artifactId>
</dependency>

下载并安装ActiveMQ服务器端

1:从http://activemq.apache.org/download.html(http://activemq.apache.org/activemq-5111-release.html)下载最新的ActiveMQ
2:直接解压,然后拷贝到你要安装的位置就好了
启动运行
1:普通启动:到ActiveMQ/bin下面,./activemq start
2:启动并指定日志文件./activemq start > /tmp/activemqlog
检查是否已经启动
ActiveMQ默认采用61616端口提供JMS服务,使用8161端口提供管理控制台服
务,执行以下命令以便检验是否已经成功启动ActiveMQ服务:
1:比如查看61616端口是否打开: netstat -an | grep 61616
2:也可以直接查看控制台输出或者日志文件
3:还可以直接访问ActiveMQ的管理页面:http://192.168.10.55:8161/admin/
默认的用户名和密码是admin/admin
关闭ActiveMQ,可以用./activemq stop
暴力点的可以用ps -ef | grep activemq 来得到进程号,然后kill掉

示例程序

创建一个小工程来测试下消息的发送与接收

此处创建一个maven工程,直接在POM文件中引入2个依赖包

创建2个类

package jmstest.queue;

import org.apache.activemq.ActiveMQConnectionFactory;

import javax.jms.*;

/**
 * Created by hzqiuxm on 2015/5/30.
 */
public class queueSend {

    public static void main(String[] args) throws Exception {
        ConnectionFactory connectionFactory = new ActiveMQConnectionFactory("tcp://192.168.1.55:61616");
        Connection connection = connectionFactory.createConnection();
        connection.start();

        //开启事务,消息确认方式为自动
        Session session = connection.createSession(Boolean.TRUE, Session.AUTO_ACKNOWLEDGE);
        //创建队列
        Destination destination = session.createQueue("my-queue");
        //生产者把消息传送到队列中
        MessageProducer producer = session.createProducer(destination);
        for(int i=0; i<3; i++) {
            TextMessage message = session.createTextMessage("message--"+i);
            Thread.sleep(1000);
            //通过消息生产者发出消息
            producer.send(message);
        }
        session.commit();
        session.close();
        connection.close();
    }
}
package jmstest.queue;

import org.apache.activemq.ActiveMQConnectionFactory;

import javax.jms.*;

/**
 * Created by hzqiuxm on 2015/5/30.
 */
public class queueReceive {

    public static void main(String[] args) throws Exception {
        ConnectionFactory cf = new ActiveMQConnectionFactory("tcp://192.168.1.55:61616");
        Connection connection = cf.createConnection();
        connection.start();
        //开启事务,

        final Session session = connection.createSession(Boolean.TRUE, Session.AUTO_ACKNOWLEDGE);
        Destination destination = session.createQueue("my-queue");
        MessageConsumer consumer = session.createConsumer(destination);
        int i=0;
        while(i<3) {
            i++;
            TextMessage message = (TextMessage) consumer.receive();
            session.commit();
            System.out.println("收到消息:" + message.getText());
        }
        session.close();
        connection.close();
    }
}

Docker简明教程(6)

hzqiuxm阅读(163)评论(0)

构建静态网站

网站结构

准备好文件

1 Dockerfile文件

FROM ubuntu:16.04
MAINTAINER James Turnbull "james@example.com"
ENV REFRESHED_AT 2014-06-01

RUN apt-get -qq update && apt-get -qq install nginx

RUN mkdir -p /var/www/html/website
ADD nginx/global.conf /etc/nginx/conf.d/
ADD nginx/nginx.conf /etc/nginx/

EXPOSE 80

2 创新nginx目录,新增2个配置文件

global.conf
server {
        listen          0.0.0.0:80;
        server_name     _;

        root            /var/www/html/website;
        index           index.html index.htm;

        access_log      /var/log/nginx/default_access.log;
        error_log       /var/log/nginx/default_error.log;
}
nginx.conf
user www-data;
worker_processes 4;
pid /run/nginx.pid;
daemon off;

events {  }

http {
  sendfile on;
  tcp_nopush on;
  tcp_nodelay on;
  keepalive_timeout 65;
  types_hash_max_size 2048;
  include /etc/nginx/mime.types;
  default_type application/octet-stream;
  access_log /var/log/nginx/access.log;
  error_log /var/log/nginx/error.log;
  gzip on;
  gzip_disable "msie6";
  include /etc/nginx/conf.d/*.conf;
}

开始构建

1 执行

docker build -t hzqiuxm/nginx

查看下构建历史

docker history hzqiuxm/nginx

可以对照镜像看到,history的命令从新构建的hzqiuxm/nginx镜像的最后一层开始,追溯到最开的ubuntu镜像

2 构建一个nginx容器

docker run -d -p 80 --name website -v $PWD/website:/var/www/html/website hzqiuxm/nginx nginx

可以看到启动的容器的80端口被映射到了宿主机的32768端口,我们可以输入IP:端口访问该网站

如果要修改的话,只要修改宿主机website下的index.html文件即可,修改后刷新页面即可看到效果

知识点扩展

  • 容器之间的连接有3种方法,一般只推荐Docker Networking (其他二种分别是内部网络和Docker链接)
  • Docker Network可以在不同宿主机容器间通讯(根据创建网络的方式不同来实现)

Docker简明教程(5)

hzqiuxm阅读(193)评论(0)

镜像构建

使用commit命令创建镜像(不推荐)

虽然不推荐,但还是要了解下

  • 登录到DockerHub
docker login

如果没有账号前往docker.com官网进行注册

  • 创建一个需要提交的容器
docker run -i -t ubuntu /bin/bash
apt-get -y update
apt-get -y install apache2
  • 退出创建的容器
exit
  • 提交定制了apache2的容器
docker commit b729d5a05235 hzqiuxm/apache2

用Dockerfile构建镜像 (推荐)

优点: 具备可重复性,透明性,幂等性
- 编写脚本Dockerfile
制定一个目录下创建一个文件Dockerfile

# Version: 0.0.1
FROM unbuntu:14.04
MAINTAINER James Turnbull "hzqiuxm@163.com"
RUN apt-get update && apt-get install -y nginx
RUN echo 'Hi I am in your contaniner' \
    >/usr/share/nginx/html/index.html
EXPOSE 80
  • 执行脚本
docker build -t="hzqiuxm/static_web" .
注意后面的. 表示当前目录

  • 推送镜像到自己的DockerHub
docker push hzqiuxm/static_web

构建关键点

  • Dockerfile构建缓存保证每次从失败的步骤继续
  • Dockerfile新指令

自动构建

除了上述二种方式,我们可以可以把GitHub或BitBucket中含有Dockerfile文件的仓库连接到DockerHub即可

删除镜像

docker rmi hzqiuxm/static_web

只会删除本地的镜像

运行自己的Docker Registry

  • 利用DockerHub提供的私有仓库(小项目推荐)
  • 在防火墙后面运行自己的Registry(大项目推荐)

Docker简明教程(4)

hzqiuxm阅读(180)评论(0)

Container简单操作

启动

  • 直接启动
docker run -t -i docker.io/ubuntu /bin/bash
  • 根据以前的Container的ID来启动
docker ps -a

docket start 11414221a8bc
docker ps -a

停止

  • 交互模式下直接
exit

或者

docker stop

暂停

旧版本中有,新版本中舍弃了,不建议使用,听过就好

清除

sudo docker rm containerID

创建镜像Image

  • 进入交互模式
docker run -t -i docker.io/ubuntu /bin/bash
  • 更新下安装源
apt-get update

  • 安装vim
apt-get install -y vim
  • 制作新镜像
docker commit 2653ad309080 dockerlearning/ubuntu_vim

  • 查看镜像
docker images

后台运行Container

docker run -t -i docker.io/ubuntu /bin/bash \

日志查看

docker logs -f container_name/id

列出容器进程

docker top container_name/id

查看端口绑定情况

docker port container_name port

参考链接

https://www.dockerbook.com/code/index.html

Docker简明教程(3)

hzqiuxm阅读(198)评论(0)

Docker介绍番外篇,Docker诞生

冷藏厂乱入

谈起Docker,禁不住想起小黑羊小时候在冷藏厂打工的经历.....
为什么冷藏厂会乱入?因为小黑羊说那简直是虚拟化和Docker活生生的例子。

先建个库房

要造冷藏厂,你得先造一个库房对吧?
下面这个库房敞亮不?

能造库房的包工头很多,比如华为、惠普、Dell、联想、曙光、浪潮之类的。
他们给了这些库房一个高大上的名字:物理服务器

库房变成冷藏厂

鱼呀、肉啊就可以存到库房了吗?当然不行!
你需要低温才可以保鲜!不然会发臭坏掉的......

所以我们需要购置制冷机,目前市场上主流的制冷机有两大系列Windows制冷机和Linux制冷机。

配备了制冷机的库房就摇生一变成了冷藏厂了,这样你就可以把你的鸡鸭鱼肉虾、蔬菜、水果都装进来保鲜了

那是不是就皆大欢喜了?NO!NO!NO!相信你也一定注意到了一个问题:各种库藏品都很矫情,放在一起很容易串味儿的,没人喜欢吃咸鱼味的鸡腿或者鸡腿榴莲味的虾吧?而且它们对温度要求也不一致,怎么办?

聪明的泥瓦匠

有个叫VMware的泥瓦匠想了个办法,他把库房隔成很多叫做“虚拟机”的小房间,“密封”起来,每个房间放一个制冷机,这就是冷库虚拟化。
这样就不怕串味儿,每个小房间的温度独立可控,鱼呀虾呀表示很Happy。

世界清净了,后来还有几个泥瓦匠也学会了库房分隔术,到处给人修冷库。
泥瓦匠Vmware用的砌墙工具叫ESXi,泥瓦匠Citrix用的砌墙工具叫Xen Server,泥瓦匠Microsoft用的砌墙工具叫Hyper-V,还有一些草根泥瓦匠用的工具叫KVM

这下总皆大欢喜了吧?然而并没有,这世界上矫情的人太多,如此完美的方案他们还是吹毛求疵瞎BB:

万恶的资本家老板最后问道:还能不能想点别的更好的办法?

Docker横空出世

于是——晴天霹雳一声响,新秀Docker来登场。

制冷机Linux是个喜欢动脑筋的好青年,它发明了一种叫“LXC”的“软隔离”技术,冷库分隔成叫做“容器”的小单间,但每个房间不需要单独安装制冷机,只要布些导冷管和温控阀门,这样看起来就达到目的了。

后来有人把“LXC”这种“软隔离”技术发扬光大,用一堆“GO”零件进行改装,可以大幅提高冷库的建设和改进速度,于是Docker横空出世了。
Docker被业内称为容器管理引擎,其实它就是一套给冷库快速建“单间”和铺“导冷管”的装置,源于LXC,但是更智能。

比如,有些“冷库”的使用者不知道储存“冷冻大虾”的单间该建成什么样,“导冷管”该怎么排布。Docker就建了一个“样板间”展览中心,小白们仿照“样板间”在自家冷库里可以原样造一个出来,这种“样板间”被称为“Docker镜像”,展览中心被称为“Docker Hub”。Docker Hub,你懂滴!


(来自对小黑羊微信公众号文章的整理与改编)

Docker简明教程(2)

hzqiuxm阅读(199)评论(0)

Docker概念理解

容器概念理解

容器是一种虚拟化的方案

特点

  • 它是操作系统级别的虚拟化
  • 只能运行相同或相似内核的系统中
  • 依赖linux内核NameSpace和Cgroups(Control Group)特性

相对于虚拟机的优点

  • 虚拟机是利用软件模拟硬件,需要安装操作系统,依赖库,应用;而容器把其中的大头操作系统给去掉了,所以非常轻量化,占用系统资源(硬盘,内存,CPU)会少很多
  • 安装方便,启动速度快

什么是Docker?

  • 将应用程序自动部署到容器的轻量级引擎技术

特点

  • Go语言编写,遵从Apache2.0开源协议
  • 目标是消除各环境差异,实现快速开发测试部署软件生命周期
  • 提倡面向服务的编程,每个容器最好只部署一个微服务

适用场景

  • 适用Docker容器进行开发、测试、部署
  • 创建隔离的环境,很适合个性化的SaaS服务
  • 搭建测试环境

四个核心概念理解

  • Image
    在Docker 中非常非常重要的概念,它是Docker 的核心,Docker 所创建运行的
    Container 完全基于Image 运行,并且它是只读的,我们在下一个册子会去解释,现在您
    只需要记住Image 在Docker 中非常的重要。

  • Repository
    存放Image 的地方,其中Docker Hub 下面就有非常多非常多的Repository,每个
    Repository 有很多很多的Image。

  • Registry
    Registry 其实很容易和Repository 混淆,Docker Hub 在我的理解是一个Registry,
    也就是说Registry 不直接存放Image,Image 是由Registry 下面的若干个Repository 去
    存放的,可能后文中我们会去搭建一个private Registry 存放image,你可以理解我们的
    Registry 下有一个默认的Repository 去存放。

  • Container
    Container 是一个可读写的空间,是由若干个Image 组成的,我们的应用以后都会运
    行在Container 中,同样在后文中我们会为大家介绍如何创建容器,如何启动运行容器。

三层概念

  • Docker Layer 是一个宏观的layer, 包括了若干个read-only 的Images 和一个writable 和readable 的Container layer.
  • Image Layer 是最下面的层(我指的不是Kernel)那些read-only 的Images.
  • Container Layer 是一个可读可写的Layer,我们不仅可以用yum/apt-get 安装软件,而且可以部署我们的服务,产生或者修改一些新的文件.

DockerC/S架构

Docker简明教程(1)

hzqiuxm阅读(193)评论(0)

Docker简单安装(CentOS)

依赖检查与源更新

  • Linux内核最好是3.10以上版本
uname -a

  • 更新yum源
yum update

安装方法一:命令安装

  • 输入命令
yum install -y docker-engine

可能遇到的问题

  • 如果提示没有响应的docker包,
    Docker 软件包已经包括在默认的 CentOS-Extras 软件源里,使yum的CentOS-Extras配置生效。
vim /etc/yum.repos.d/CentOS-Base.repo 
将文件CentOS-Base.repo中enabled的値从0变成1
再执行: yum install docker
启动服务:service docker start 或 systemctl start docker

如果无法启动,可能是内核无法支持SELinux,需要修改下配置

vi /etc/sysconfig/docker中配置 //设置为 selinux-enabled = false 再启动就可以了

安装方法二:脚本安装

执行安装脚本

curl -fsSL https://get.docker.com/ | sh

启动服务

service docker start 或者 systemctl start docker

检查安装结果

  • 查看安装信息
docker info

docker version

当然你也可以设置为开机启动:

systemctl enable docker

第一个Hello World

docker run hello-world

用ubuntu系统镜像来打印Hello World

  • 下载ubuntu最近镜像
docker pull ubuntu
  • 查看本地镜像
docker images

  • 创建并运行一个Container的sh环境输出一句话
docker run -t -i docker.io/ubuntu echo "Hello World"

  • 进入你container 中,运行交互式的sh

Nginx安装及SSL相关配置

hzqiuxm阅读(228)评论(0)

Nginx安装及SSL相关配置

环境准备

  • GCC编译器安装(编译源码需要使用)
    执行命令gcc -v 查看编译器是否已经安装,如果没有的话安装 执行yum install gcc
    在 linux 编译,需要 gcc,make,cmake,autoconf,libtool 等工具,建议把常用工具都一起安装了
yum -y install gcc make cmake autoconf libtool
  • PCRE库安装(正则表达式库,配置文件需要使用)
    查看是否有pcre包: rpm -qa |grep pcre 一般是系统都有的,
    安装命令 yum -y install pcre pcre-devel 或者:yum install pcre

nginx源码编译安装

  • 下载源码
    前往nginx的官网下载
    获得下载路径后,执行命令 wget http://nginx.org/download/nginx-1.10.3.tar.gz

  • 解压安装包
    执行命令: tar zxvf nginx-1.4.2.tar.gz

  • 编译安装
    进入解压路径cd nginx-1.6.0
    执行命令 ./configure --prefix=/usr/local/nginx 指定安装目录,可以自己决定
    最后执行make && make install

  • 启动或配置
    安装好后,可以在nginx的sbin目录下启动服务,可能出现的错误是默认的80端口被其他程序占用
    使用命令netstat -antp 命令查看
    需要更改nginx配置的话进入conf文件夹下的nginx.conf文件进行配置,详细配置信息请查看nginx配置章节

HTTPS支持

  • 安装OPENSSL(生成证书或秘钥时需要)
    yum -y install openssl-devel

  • 配置编译环境
    执行 ./configure --prefix=/home/java/nginx --with-http_ssl_module
    如要用到其他的模块功能也类似这样安装,下面是比较常用的一些模块
    --with-http_stub_status_module 监控运行状态
    --with-http_ssl_module HTTPS支持
    --with-http_gzip_static_module 静态文件压缩
    --with-http_realip_module 获取真实IP

  • 执行编译安装命令
    make && make install

HTTPS安全配置简单介绍

尽量不要用默认配置,因为版本不同默认配置就会改变
- ssl on 开启SSL
- ssl_certificate 证书,发送给客户端验证服务器身份用,比如www.example.com.crt;nginx只支持一个证书,有中间证书的话要自己合并成一个文件,保证服务器证书在最前面
- ssl_certificate_key 私钥 解密消息,密钥使用 日入:www.example.com.key;
- ssl_protocols 协议 加密握手协议,常见:TLSv1 TLSv1.1 TLSv1.2; 不要配置SSL协议
- ssl_ciphers 加密套件,请选择有前向安全性的加密套件 可以特别指定 如:AES128+EECDH:AES128+EDH ,一般也会指定高安全的并表明禁用的加密套件 HIGH:!aNULL:!MD5(使用高级别的安全套件,禁用MD5);

推荐的加密套件:ECDHE-ECDSA-AES128-GCM-SHA256 ECDHE-ECDSA-AES256-GCM-SHA384 ECDHE-ECDSA-AES128-SHA ECDHE-ECDSA-

AES256-SHAECDHE-ECDSA-AES128-SHA256 ECDHE-ECDSA-AES256-SHA384 ECDHE-RSA-AES128-GCM-SHA256 ...

!aNULL !eNULL !LOW !3DES !MD5 !EXP !PSK !SRP !DSS !MEDIUM

  • ssl_prefer_server_ciphers on; 开启服务器算法优先原则,由服务器来决定适配算法
  • ssl_password_file 将私钥的密码加入到配置文件中(1.7.3版本之后才有,之前都是没有密码的)

    当你有多个站点,使用通配符证书的时候,把证书和私钥放在nginx的http段配置比较好

ssl_certificate     common.crt;
ssl_certificate_key common.key;

server {
    listen          443 ssl;
    server_name     www.example.com;
    ...
}

server {
    listen          443 ssl;
    server_name     www.example.org;
    ...
}

HTTPS配置加强版

DH秘钥交换加强

  • nginx默认提供的DH秘钥交换算法是1024位的,安全性还不够强,可以配置临时的DH秘钥交换
    > 一定要保证客户端也支持哦,比如java8以前是不支持1024位以上的DH参数的
  • 用OpenSSL生成2048位参数文件 openssl dhparam -out dh-2048.pem 2048
  • 配置 ssl_dhparam dh-2048.pem

不推荐更强的DH参数了,因为再高会显著影响SSL的握手效率了

ECDH秘钥交换加强

  • 套件的ECDHE密钥默认是256EC位,使用secp256r1作为曲线模型,加密强度相当于3072位RSA秘钥,应该足够安全了
  • 当然你也可以自己调整 ssl_ecdh_curve secp384r1 相当于7680位RSA密钥
  • 如果是在OpenSSL中使用还是建议用默认的,secp256r1曲线模型在OpenSSL中是做过优化的,运行的更快

HTTPS中TLS会话管理

独立会话缓存配置

  • ssl_session_cache shared:ssl_session_cache:1M 独立会话缓存 例如:shared:SSL:10M;

    分配1M的共享内存缓存,1M大概可以存放4000个会话

  • ssl_session_timeout 会话超时时间 例如:1140m,默认的只有5分钟,建议配置成24小时,能够减少TSL握手时间,提升效率

独立会话票证

  • 默认情况会话票证是由OpenSSL处理的
  • 会话票证使用的是128位的AES加密,web服务器启动初始化时会自动生成一个一次性的,根据服务器配置不同,可能会有多个票证密钥同时使用的情况
  • 服务器重启会生成新的票证密钥,这会导致所有已经接入的客户端需要重新进行TLS会话
  • 出于安全性考虑,每一站点分配一个独立的会话票证是最安全的
    配置 ssl_session_ticket_key ticket.key
  • 当你使用服务器集群且不希望部署共享票证密钥时,可以禁用 ssl_session_tickets off

客户端身份认证

  • 想配置启用客户端身份验证,Nginx需要提供一个完整证书链的所有CA证书,以及一份相关的证书吊销列表
  • 开启客户端验证身份验证配置 ssl_verify_client on;
  • 指定客户端证书到根证书的最大证书路径长度 ssl_verify_depth 2;
  • 指定允许签发客户端证书的CA证书 ssl_client_certificate sub-ca.crt 将发送给用户用于客户端证书选取
  • 完整证书链中需要包含的其他CA证书 ssl_trusted_certificate root-ca.crt
  • 证书吊销列表,文件有更新时Nginx需要重新加载 ssl_revoked-certificates.crl

在Nginx中SSL/TSL协议问题

这个话题其实对Nginx用户来说是个好消息,为什么呢?因为SSL/TSL协议上的问题发现后,在Nginx上都得到了快速的解决,甚至在问题公开之前就修复了

  • 不安全的重新协商

    Nginx直接不支持客户端,也不支持服务器发起重新协商

  • BEAST

    这种攻击需要攻击者控制受害者发送的数据,只有浏览器会受到攻击

  • CRIME

    利用TLS协议启动压缩时信息泄露,Nginx已经对所有OpenSLL版本都支持禁用压缩了

漫谈缓存(1)

hzqiuxm阅读(169)评论(0)

1 漫谈缓存 - 缓存概述

前言

在股市动荡,投资乏力时你可能听过现金为王;在传统媒体互联化的潮流中,你可能听过流量为王;在网络知识内容越来越同质的时代,你可能听过内容为王。那么在你系统性能表现不佳,客户抱怨响应时间过长等问题中,我想告诉你的是缓存为王。如果你是个爱吃小龙虾的,那么很多事情没有什么是一顿小龙虾搞不定的,如果搞不定,那就两顿。同理,不管什么系统,位于系统的哪一层,没有什么是缓存解决不了的,如果解决不了那就加一层。

什么是缓存

言归正传,我们来正式谈一谈缓存。我们不要以为经常听到,看到,用到的东西,就一定对其了解。要知道万有引力发现也是从苹果为什么从树上掉下来这么司空见惯的现象中来的。

缓存和缓冲

缓存和缓冲有什么区别?相信很多人其实对这两个词解释不清楚,甚至混用。从英文的角度去看缓存是cache,缓冲是buffer,它们是完全不同的两个单词。

我曾看到有的人是这么解释缓存的:位于速度相差较大的两种硬件/软件之间的,用于协调两者数据传输速度差异的结构。
我觉得这个概念其实更适合缓冲。为什么呢?缓存和缓冲从中文的角度看,仅一字之差,关键性区别就在这一个字。

缓存的侧重点是存,作用是提供一种便利性。比如:我们去超市里买东西,为了增加我们购物的便利性,超市会在购物入口提供一个寄存箱,用来存放我们随身携带的一些大件物品;还有我们经常使用的丰巣快递柜,无论收寄快递,我们只要前往我们住所或上班地点较近的丰巣快递柜进行相应的操作的就行了,丰巣的快递柜为我们寄取物品提供了很好的便利性。
image_1bniasmetrn71nb9fge1endtql1t.png-264.7kB

缓冲的侧重点是冲,它的目的是让对象冲的慢点,作用是提供一种保护性。比如:在公路上,在转弯下坡和小区路口的路段,都会建造一个减速带,用来强行对车子减速,免得车子速度过快产生危险;其实我们平时用的很多东西都有缓冲装置:自行车座位下面的减震垫、一些篮球鞋的鞋垫、运动员跳高竿下面垫子等等物品提供的都是缓冲功能,都是对我们身体部位的保护。

image_1bniar58814ta1si48251vicmvl1g.png-294.4kB

我们再回头看之前的那个解释,大家是不是觉得这个解释更适合缓冲了?所以我更喜欢这么去理解这两个词的概念。

缓存cache:为了提供便利性,建立的数据交换区。
缓冲buffer:为了提供保护性,建立的数据交换区。

计算机缓存

就拿我们熟悉的计算机CPU来举例,看看缓存的作用。

CPU由两大部件组成:控制器和运算器,控制器用来处理指令;运算器用来进行实际运算。

一般我们的数据都会从硬盘上加载到内存中,再由cpu去内存当中去取数据。但是我们看看cpu的频率和内存频率有多大区别。

我们通常衡量一个CPU好坏的指标是其频率,比如4.0GHz,表示一秒钟内这个CPU可以进行4亿次运算,每次运算时间为0.25纳秒。
那么我们去访问内存数据的时间大约是上百纳秒,二者相差百倍。

为了充分利用CPU的高效性,我们引入了多级缓存机制,来增加CPU取数据的便利性。所以一般CPU中会包含一级缓存、二级缓存,甚至有的还有三级缓存。每种缓存的材料都有不同,越是靠近CPU的材料越接近CPU,频率相差越少。

所以通过CPU多级缓存,我们在取数上从二方面增加了便利性,一方面是距离上便利性,本来CPU和内存物理距离上本来就远,而多级缓存更近(类似之前丰巣快递柜);另一方面是时间便利性,由于缓存本身频率更快,取数据的时间更短了。

大多数CPU计算的时候有80-90%的数据是从缓存中直接取得的,使得我们的计算机运行效率大大得到提升。

下图是一个CPU多级缓存的简易示意图:
image_1bnkcol0c1sda1kc7d3ueu91d6e9.png-29.3kB

软件设计Buffer困惑

写过JAVA的人都知道,在JAVA传统的BIO操作里,有很多的流操作,这些输入输出流都是基于抽象基类InputStream/OutputStream。其中有一个缓冲流BufferedxxxStream,相信很多人都用过。但是我碰到过的很多开发人员却把这个流理解成了缓存,因为用了这个流,文件I/O操作的效率比不用之前提升了不少。但是我们可以清楚的看到官方的把它叫做缓冲流,名字也是Buffer打头的。好像也没提供啥保护性,好像你讲的不对哦,这个缓冲提供的明显是便利性,真的是这样吗?

我们想想看,为什么BufferedxxxStream叫缓冲?如果不用它的话,我们是不是要频繁的和硬盘进行I/O操作,有了缓冲流,相当于减少了和I/O的频繁操作次数,就像本来每秒要交互1000次,现在减少到了1次。是不是对硬盘或系统起到了保护性作用?缓冲流正是起到了I/O慢点冲的作用。至于效率上的提升,真是因为次数上的减少,原来的999次对硬盘的操作,变成了对内存的操作。要知道磁盘搜索时间是毫秒级别的,和内存相比,效率相差十万百万倍,所以这才是缓冲流效率提升的真相。

从整体角度看缓存

其实缓存思想在我们计算机或者软件设计上随处可见应用十分广泛。接下来我们看看缓存的分类。

缓存分类

其实目前业界并没有严格的缓存分类,都是根据其实际的应用场景进行分类。

如果按照硬件和软件来分,就可以分成:硬件缓存和软件缓存。

如果按照一个对象类型上可以分为:客户端缓存、服务端缓存、第三方缓存。

如果按照缓存资源类型可以分为:静态缓存和动态缓存。

如果按照缓存的位置可以分为:本地缓存、分布式缓存。

如果按照系统架构上可以分为:web端缓存、应用端缓存、数据库缓存等。

本文不可能穷尽所有的分类方式,也不能面面俱到介绍锁列出的各种缓存类别。作为一个软件开发人员或者架构师,那最常见的方式还是从系统架构作为第一划分维度去了解和掌握缓存,是最直接最有效的。在第一维度的划分下,我们还可以根据第二和第三维度进一步细化。

接下来我们就从系统架构角度来看一看缓存。

系统架构角度看缓存

架构从粗的大方向可以分为三层:WEB层,应用层,持久层。

现代软件设计发展较快,层次也越分越细,但是只是根据功能职责进一步对这三层进行了更细粒度的划分,比如:界面层,控制层,业务层,服务层,代理层,数据层。就是把之前的每层根据功能职责都划分出了二层,就拿原本的应用层来说,划分成了业务层和服务层。业务层可能会对业务的热点数据进行缓存,服务层主要是把一些公共的功能集中起来以SOA或者微服务的方式封装好,以API方式提供,不需要缓存,增大了整个系统的可扩展性。

根据这三层作为第一维度的划分,整理除了下面的表格:
image_1bnkv58kgoq918coo8d1d3o1f5gm.png-30.2kB

缓存对象是指该层主要缓存的是哪些数据,缓存方式是指一般我们会采用什么手段去缓存这些缓存对象,常用技术工具就是各种缓存方式目前比较流行的一些技术与工具了。

缓存的重要指标

我们现在知道,缓存的主要目的是提供便利性。如果你家小区明明有丰巣快递柜,但是要收很高的费用,快递员每次要你到小区门口来拿快递,那这个快递柜(缓存)的意义就没有了。那么软件设计上的缓存也一样,我们要考查这个缓存是不是真的提供了便利性。那怎么衡量呢?我们是通过缓存的命中率来衡量的,说白了就是你去缓存里拿你要的东西能不能拿到。

缓存的问题

这里主要是想和大家说一下,再好的东西,也要我们合理的去利用。一个好的系统缓存需要我们精心去设计,一般的缓存设计会存在这么二个问题:缓存穿透和缓存雪崩。

缓存穿透:是指缓存命中率不高,缓存数据有问题,并没有起到很大的便利性。就像快递员每次收到大物件无法放进快递柜时,会在快递柜给你留了张纸条:请到XXX地领取你的快递。你肯定会说:这又不是寻宝游戏,直接通知我去XXX地不就行了!

缓存雪崩:就是你缓存数据的地方突然奔溃了,这下子本来在缓存处就要返回的请求,必须请求到后端并等待响应了。就像丰巣快递柜自动取件失灵了,每次都要快递员来送取快递了,快递员可能会忙不过来。

至于怎么解决,我们先按下不表,以后会跟大家说清楚,这里主要记得有这么二个概念就行。

小结

本章是对缓存概念的一个整体介绍,让你对缓存有个全方面的了解,你需要掌握的知识点如下:

1 缓存和缓冲的区别是什么?
2 理解计算机CPU多级缓存和缓冲类设计原理
3 从架构角度作为第一维度如何划分缓存类别,每层的缓存对象、缓存方式,常用技术工具有哪些?
4 衡量缓存的重要指标是什么?
5 不好的缓存设计可能会有什么问题?

后面我会对每一层缓存方式和缓存技术工具做详细的介绍,希望本节对你有所帮助。

欢迎加入紫牛小筑

进入小筑关于作者