GVKun编程网logo

使用 Docker 和 Nginx 打造高性能二维码服务(二)(docker nginx 502)

8

在这篇文章中,我们将为您详细介绍使用Docker和Nginx打造高性能二维码服务的内容,并且讨论关于二的相关问题。此外,我们还会涉及一些关于167dockerdocker构建nginx容器系列问题do

在这篇文章中,我们将为您详细介绍使用 Docker 和 Nginx 打造高性能二维码服务的内容,并且讨论关于的相关问题。此外,我们还会涉及一些关于167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo、C# ZXing.Net生成二维码、识别二维码、生成带Logo的二维码(二)、Centos7安装nginx(二)之docker中安装nginx、docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 Docker 构建 Nginx + ffmpeg + OBS 直播服务器的知识,以帮助您更全面地了解这个主题。

本文目录一览:

使用 Docker 和 Nginx 打造高性能二维码服务(二)(docker nginx 502)

使用 Docker 和 Nginx 打造高性能二维码服务(二)(docker nginx 502)

使用 Docker 和 Nginx 打造高性能二维码服务(二)
三年前我曾写过一篇《使用 Docker 和 Nginx 打造高性能的二维码服务》,时过境迁,容器软件、基础系统、Nginx、QRCode 依赖库都经历了版本升级,为了构建可维护,性能更好的 QRCode 生成服务,就有了本篇折腾内容。

希望本篇内容的出现可以帮到同样需要减少各种语言、框架中二维码生成实现代码的你。

写在前面
TLDR,如果你是曾经的读者,可以直接访问下面的链接,然后搭建属于你的高性能二维码服务,镜像非常小巧,DockerHub 上显示只有 13.47MB,如果你下载解压到本地,也仅有 32.9MB,相比 Nginx 官方相同版本最小的镜像只大了 10MB。

  • 代码:https://github.com/soulteary/nginx-qrcode-server
  • 镜像:https://hub.docker.com/repository/docker/soulteary/nginx-qrcode-server
    如果你希望了解这个服务是怎么构建的,可以接着阅读下面的章节。如果你想了解该如何使用,可以直接翻阅至使用部分。

准备源代码
这里需要准备三份代码:Nginx、libqrencode、ngx_http_qrcode_module。

Nginx 的代码版本选择和基础镜像版本一致就好;libqrencode 在 alpine 软件仓库中的版本太过陈旧,我们这里使用最新的发布版本 4.1.1;ngx_http_qrcode_module 作者没有准备版本,所以这里我将代码 fork 了一份,做了一些细节修改,并打上了一个名为 2020.01.06 的版本。

这样做还有一个好处,如果软件代码没有版本,我们只能通过 Git 或者 Zipball 方式下载,这两种方式我们都还需要在镜像中多安装一款对应的软件进行代码下载或者解压缩,而使用 “release” 后的版本代码,则可以直接使用系统镜像自带的 tar 来处理压缩包,进一步控制镜像大小:


NGINX_VERSION=1.19.6
LIBQR_VERSION=4.1.1
NGX_LIBQR_VERSION=20210106

curl -L https://github.com/fukuchi/libqrencode/archive/v${LIBQR_VERSION}.tar.gz -o "v${LIBQR_VERSION}.tar.gz" 
curl -L "http://nginx.org/download/nginx-${NGINX_VERSION}.tar.gz" -o nginx.tar.gz
curl -L "https://github.com/soulteary/ngx_http_qrcode_module/archive/${NGX_LIBQR_VERSION}.tar.gz" -o ${NGX_LIBQR_VERSION}.tar.gz

构建服务镜像
之前构建服务的时候,采用的是使用通用基础镜像编译 Nginx 和它的 “小伙伴”(模块),在三年后的今天,我们不妨直接使用 Nginx 基础镜像,所谓 “原汤化原食”,最大限度复用官方提供的环境、配置参数、入口脚本… 毕竟,偷懒是工程师的美德。


FROM nginx:1.19.6-alpine

准备 Nginx 构建环境
虽然我们使用 Nginx 官方镜像作为基础镜像,但是因为要再次构建 Nginx,所以基础构建工具必不可少。从官方镜像源文件中,我们可以找到必备的工具的安装命令:


apk add --no-cache --virtual .build-deps gcc libc-dev make openssl-dev pcre-dev zlib-dev linux-headers libxslt-dev gd-dev geoip-dev perl-dev libedit-dev mercurial bash alpine-sdk findutils

这里在安装软件的时候声明安全列表名称为 .build-deps,方便用完后一键清理,节约镜像容量。

准备 QRCode 构建环境
根据官方文档,在 alpine 中找到各种依赖包的名称,和处理 Nginx 构建环境时一样,将依赖安装列表声明为 .build-qrcode:

apk add --no-cache --virtual .build-qrcode openssl-dev pcre-dev zlib-dev build-base autoconf automake libtool libpng-dev libgd pcre pcre-dev pkgconfig gd-dev

编译 QREncode 依赖库
编译 QREncode 非常简单,先使用 autogen 脚本生成配置文件,接着就是 “C 语言编译安装” 一键三连常规操作:


tar -zxC /usr/src -f v${LIBQR_VERSION}.tar.gz
cd /usr/src/libqrencode-${LIBQR_VERSION} && \
   ./autogen.sh && LDFLAGS=-lgd ./configure && \
   make && make install

编译 Nginx 执行文件
前文提到我们为什么要使用 Nginx 官方镜像来进行编译构建,因为能 “偷懒”,原汁原味复用官方构建配置和运行环境:


tar -zxC /usr/src -f nginx.tar.gz && \
cd /usr/src/nginx-$NGINX_VERSION && \

CONFARGS=$(nginx -V 2>&1 | sed -n -e ''s/^.*arguments: //p'') \
CONFARGS=${CONFARGS/-Os -fomit-frame-pointer/-Os} && \
echo $CONFARGS && \

./configure --with-compat $CONFARGS --add-module=../ngx_http_qrcode_module/ && \
make && make install && \

使用 sed 将 nginx -V 输出参数进行截断,然后使用字符串替换方式去掉我们不需要的参数,在 Nginx 配置过程中,使用 --with-compat 参数将 “官方” 参数拼合到命令中即可节约我们大量精力去折腾基础配置。

如果你决定使用 ubuntu 或者 debian 版本的镜像(比如官方不带 alpine)的镜像,进行构建,这里获取参数需要使用临时 shell 文件进行中转,因为不同的 shell 对于引号的处理模式有些不同,例如下面这样:

CONFARGS=$(nginx -V 2>&1 | sed -n -e ''s/^.*arguments: //p'') \
echo "./configure --with-compat $CONFARGS --add-module=../ngx_http_qrcode_module/">tmpconf.sh && chmod 755 tmpconf.sh 
    && ./tmpconf.sh && rm tmpconf.sh

如果使用非 alpine 镜像,除了上面的内容外,还需要补全一些基础依赖,比如 pcre 等。

完成的配置文件
将上面的配置进行整合,稍作调整,就能够得到完成的 Docker 镜像配置文件了。


FROM nginx:1.19.6-alpine

ARG NGINX_VERSION=1.19.6
ARG LIBQR_VERSION=4.1.1
ARG NGX_LIBQR_VERSION=20210106

RUN apk add --no-cache --virtual .build-deps gcc libc-dev make openssl-dev pcre-dev zlib-dev linux-headers libxslt-dev gd-dev geoip-dev perl-dev libedit-dev mercurial bash alpine-sdk findutils && \
    apk add --no-cache --virtual .build-qrcode openssl-dev pcre-dev zlib-dev build-base autoconf automake libtool libpng-dev libgd pcre pcre-dev pkgconfig gd-dev && \
    mkdir -p /usr/src && cd /usr/src && \
    curl -L https://github.com/fukuchi/libqrencode/archive/v${LIBQR_VERSION}.tar.gz -o "v${LIBQR_VERSION}.tar.gz" && \
    tar -zxC /usr/src -f v${LIBQR_VERSION}.tar.gz && \
    cd /usr/src/libqrencode-${LIBQR_VERSION} && ./autogen.sh && LDFLAGS=-lgd ./configure && make && make install && cd /usr/src && \
    curl -L "http://nginx.org/download/nginx-${NGINX_VERSION}.tar.gz" -o nginx.tar.gz && \
    curl -L "https://github.com/soulteary/ngx_http_qrcode_module/archive/${NGX_LIBQR_VERSION}.tar.gz" -o ${NGX_LIBQR_VERSION}.tar.gz && \
    tar zxvf ${NGX_LIBQR_VERSION}.tar.gz && mv ngx_http_qrcode_module-${NGX_LIBQR_VERSION} ngx_http_qrcode_module && \
    tar -zxC /usr/src -f nginx.tar.gz && \
    cd /usr/src/nginx-$NGINX_VERSION && \
    CONFARGS=$(nginx -V 2>&1 | sed -n -e ''s/^.*arguments: //p'') \
    CONFARGS=${CONFARGS/-Os -fomit-frame-pointer/-Os} && \
    echo $CONFARGS && \
    ./configure --with-compat $CONFARGS --add-module=../ngx_http_qrcode_module/ && \
    make && make install && \
    apk del .build-deps .build-qrcode && \
    rm -rf /tmp/* && rm -rf /var/cache/apk/* && rm -rf /usr/src/ && \
    curl -L https://raw.githubusercontent.com/soulteary/ngx_http_qrcode_module/master/conf/nginx.conf -o /etc/nginx/nginx.conf

如果你在国内构建,希望构建速度变快,可以在镜像执行软件安全前添加一句命令,对软件源进行修改,再进行构建操作:


RUN cat /etc/apk/repositories | sed -e "s/dl-cdn.alpinelinux.org/mirrors.aliyun.com/" | tee /etc/apk/repositories

基础使用
前文提到,我已经将代码和镜像提到了官方仓库,所以如果你只是想了解如何做,和想使用,使用下面的命令可以一键获取已经构建好的镜像文件。


docker pull soulteary/nginx-qrcode-server:release-2021.01.06

如果你希望直接查看效果,可以使用 docker 基础命令将服务启动在本机的某个端口:


docker run --rm -it -p 8080:80 soulteary/nginx-qrcode-server:release-2021.01.06

然后打开浏览器,访问 http://localhost:8080,即可看到服务正常运行(展示一个默认二维码)。

和三年前一样,你可以访问类似 http://localhost:8080/?size=150&margin=20&txt=https%3A%2F%2Fsoulteary.com 来尝试通过调整 URL 参数获得更加适合你的使用场景的生成结果。

默认配置
如果你想进行一些细节调整,可以参考默认配置,将其修改为更符合你使用场景的配置。


worker_processes  1;

events {
    worker_connections  1024;
}

http {
    include       mime.types;
    default_type  application/octet-stream;

    sendfile        on;

    keepalive_timeout  65;

    server {
        listen       80;
        server_name  localhost;

  location / {

      set $fg_color 000000;
      set $bg_color FFFFFF;
      set $level 0;
      set $hint 2;
      set $size 300;
      set $margin 80;
      set $version 2;
      set $case 0;
      set $txt "https://soulteary.com";

      if ( $arg_fg_color ){
                set $fg_color $arg_fg_color;
      }
      if ( $arg_bg_color ){
                set $bg_color $arg_bg_color;
      }
      if ( $arg_level ){
                set $level $arg_level;
      }
      if ( $arg_hint ){
                set $hint $arg_hint;
            }
            if ( $arg_size ){
                set $size $arg_size;
            }
            if ( $arg_margin ){
                set $margin $arg_margin;
            }
            if ( $arg_ver ){
                set $version $arg_ver;
            }
            if ( $arg_case ){
                set $case $arg_case;
            }
            if ( $arg_txt ){
                set $txt $arg_txt;
            }

   qrcode_fg_color $fg_color;
   qrcode_bg_color $bg_color;

   qrcode_level    $level;
   qrcode_hint     $hint;
   qrcode_size     $size;
   qrcode_margin   $margin;
   qrcode_version  $version;
   qrcode_casesensitive $case;
   qrcode_urlencode_txt $txt;

   qrcode_gen;
  }

    }
}

简单性能测试
这个模式下,默认足够应对一些基础场景,我们先以笔记本为环境,使用 ab 进行简单进行性能测试:


ab -n 1000 -c 10 -r http://localhost:8080/

This is ApacheBench, Version 2.3 <$Revision: 1879490 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/
Licensed to The Apache Software Foundation, http://www.apache.org/

Benchmarking localhost (be patient)
Completed 100 requests
Completed 200 requests
Completed 300 requests
Completed 400 requests
Completed 500 requests
Completed 600 requests
Completed 700 requests
Completed 800 requests
Completed 900 requests
Completed 1000 requests
Finished 1000 requests

Server Software:        nginx/1.19.6
Server Hostname:        localhost
Server Port:            8080

Document Path:          /
Document Length:        579 bytes

Concurrency Level:      10
Time taken for tests:   2.711 seconds
Complete requests:      1000
Failed requests:        0
Total transferred:      722000 bytes
HTML transferred:       579000 bytes
Requests per second:    368.91 [#/sec] (mean)
Time per request:       27.107 [ms] (mean)
Time per request:       2.711 [ms] (mean, across all concurrent requests)
Transfer rate:          260.11 [Kbytes/sec] received

Connection Times (ms)
              min  mean[+/-sd] median   max
Connect:        0    0   0.1      0       1
Processing:     5   27   2.6     26      39
Waiting:        5   27   2.7     26      39
Total:          6   27   2.7     26      39

Percentage of the requests served within a certain time (ms)
  50%     26
  66%     27
  75%     28
  80%     28
  90%     30
  95%     31
  98%     34
  99%     38
 100%     39 (longest request)

可以看到本地单机在使用默认配置,不进行优化的情况下,默认 QPS 是 368,计算响应时间在 3 毫秒内。足够一般的业务或小规模场景使用,毕竟你不会真的只使用一台和笔记本性能差不多的机器作为生产服务器。

如果换上一台小规格的(4C4G)的云服务器,并使用另外一台机器进行访问性能测试,可以看到单机器单实例,性能并不会有太多波动,依旧是每个请求大概消耗 3 毫秒。


Server Software:        nginx/1.19.6
Server Hostname:        192.168.93.25
Server Port:            8080

Document Path:          /?txt=123
Document Length:        557 bytes

Concurrency Level:      10
Time taken for tests:   2.960 seconds
Complete requests:      1000
Failed requests:        0
Total transferred:      700000 bytes
HTML transferred:       557000 bytes
Requests per second:    337.79 [#/sec] (mean)
Time per request:       29.604 [ms] (mean)
Time per request:       2.960 [ms] (mean, across all concurrent requests)
Transfer rate:          230.91 [Kbytes/sec] received

Connection Times (ms)
              min  mean[+/-sd] median   max
Connect:        0    0   0.1      0       3
Processing:     4   29   1.5     29      32
Waiting:        4   29   1.5     29      32
Total:          4   29   1.4     30      32

如果你的请求密集程度不高,单是这样的配置的机器和运行方式,假设请求分布均匀,足够满足每分钟 1.8 万次的请求。但是现实中请求一定存在高峰和低谷,所以接下来,我们再来进行一些基础优化,加强应对高并发场景的能力。

搭配内存缓存实现高性能展示
因为本方案中挑战高性能二维码生成,本质是依赖高性能的生成工具,以及 Nginx 异步非阻塞 IO ,依赖 CPU 密集计算实现。所以为了进一步提升服务能力,可以下手的点除了继续优化代码之外,最简单的方案便是堆无状态的可水平扩展实例数量和增加缓存,减少不必要的重复计算,把 CPU 让给更有计算需要的 “请求”。

同时我们看到响应时间已经在个位数毫秒级别,为了进一步提升性能,这里务必要避免资源落盘,最优解是 Nginx 本身应用内存,次优解是各种能够保持长链接的内存缓存应用。

Nginx 本身并不开放自身的内存,但是为了满足这类需求,从大概十年前就提供了外部内存模块(ngx_http_memcached_module),可以在不改动代码的情况下使用这个模块来完成计算内容的持久化,以及请求不落磁盘。

水平扩展实例,通过重复启动容器可以轻松做到,搭配 SLB、HAProxy 、甚至是 Nginx 都可以,这里依旧选择 Traefik 作为前端,只需要一条启动命令,服务注册、负载均衡就都完事了。

先给出 docker-compose.yml 完整配置,使用 K8S 的同学可以参考修改。

version: "3.6"

services:

  qrcode:
    image: soulteary/nginx-qrcode-server:release-2021.01.06
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf:ro
    networks:
      - traefik
    labels:
      - traefik.enable=true
      - traefik.docker.network=traefik
      - traefik.http.routers.qrcode-www.rule=Host(`qrcode.lab.io`)
      - traefik.http.routers.qrcode-www.entrypoints=http
      - traefik.http.routers.qrcode-ssl.rule=Host(`qrcode.lab.io`)
      - traefik.http.routers.qrcode-ssl.entrypoints=https
      - traefik.http.routers.qrcode-ssl.tls=true
      - traefik.http.services.qrcode-backend.loadbalancer.server.scheme=http
      - traefik.http.services.qrcode-backend.loadbalancer.server.port=80
    expose:
      - 80
    restart: always
    depends_on: 
      - memcached
    environment:
      - TZ=Asia/Shanghai
    logging:
        driver: "json-file"
        options:
            max-size: "10m"

  memcached:
    image: memcached:1.6.9-alpine
    expose:
      - 11211
    networks:
      - traefik
    restart: always
    logging:
        driver: "json-file"
        options:
            max-size: "10m"

networks:
  traefik:
    external: true

因为要和 memcached “梦幻联动”,所以我们还需要修改默认的 Nginx 配置文件:

worker_processes 1;

events {
    worker_connections 1024;
}

http {
    include mime.types;
    default_type application/octet-stream;

    sendfile on;
    keepalive_timeout 65;

    upstream memcache_server {
        server memcached:11211;
        keepalive 512;
    }

    server {
        listen 80;
        server_name localhost;

        location = /favicon.ico {
            access_log off; empty_gif;
        }

        memcached_buffer_size 4k;
        memcached_connect_timeout 100ms;
        memcached_read_timeout 100ms;
        memcached_send_timeout 100ms;
        memcached_socket_keepalive on;

        location / {
            set $memcached_key "$uri?$args";
            #or set $memcached_key $query_string;
            memcached_pass memcache_server;
            error_page 404 502 504 = @private;
        }

        location @private {
            # internal;
            add_header X-Cache-Key $memcached_key;

            set $fg_color 000000;
            set $bg_color FFFFFF;
            set $level 0;
            set $hint 2;
            set $size 300;
            set $margin 80;
            set $version 2;
            set $case 0;
            set $txt "https://soulteary.com";

            if ( $arg_fg_color ) {
                set $fg_color $arg_fg_color;
            }
            if ( $arg_bg_color ) {
                set $bg_color $arg_bg_color;
            }
            if ( $arg_level ) {
                set $level $arg_level;
            }
            if ( $arg_hint ) {
                set $hint $arg_hint;
            }
            if ( $arg_size ) {
                set $size $arg_size;
            }
            if ( $arg_margin ) {
                set $margin $arg_margin;
            }
            if ( $arg_ver ) {
                set $version $arg_ver;
            }
            if ( $arg_case ) {
                set $case $arg_case;
            }
            if ( $arg_txt ) {
                set $txt $arg_txt;
            }

            qrcode_fg_color $fg_color;
            qrcode_bg_color $bg_color;

            qrcode_level $level;
            qrcode_hint $hint;
            qrcode_size $size;
            qrcode_margin $margin;
            qrcode_version $version;
            qrcode_casesensitive $case;
            qrcode_urlencode_txt $txt;

            qrcode_gen;
        }

    }
}

使用 docker-compose up --sacale qrcode=4 -d 一键启动四个相同的 QRCode 实例。

接着使用 ab 再次在另外一台机器上对这台机器进行网络请求测试,并适当增大测试请求数量,多次测试可以看到 4C4G 的云服务器的 QPS 提升到了 600+,而单个请求的响应时间缩短到了 1.6 毫秒左右,差不多是单机每分钟可承受 3.6 万次请求的服务能力。

实际生产场景,我们会使用核心数更多的机器、以及增加机器节点数量,可以带来更大的服务响应能力,在应对突发流量时,可通过云服务弹性部署,进一步提升响应能力。

这里吐槽一下,我的笔记本单机单实例的情况,居然 QPS 到达了 2700,云虚拟机上的性能测试真的是看脸。

ab -n 10000 -c 10 http://qrcode.lab.io/?txt=123
This is ApacheBench, Version 2.3 <$Revision: 1807734 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/
Licensed to The Apache Software Foundation, http://www.apache.org/

Benchmarking qrcode.lab.io (be patient)
Completed 1000 requests
Completed 2000 requests
Completed 3000 requests
Completed 4000 requests
Completed 5000 requests
Completed 6000 requests
Completed 7000 requests
Completed 8000 requests
Completed 9000 requests
Completed 10000 requests
Finished 10000 requests

Server Software:        nginx/1.19.6
Server Hostname:        qrcode.lab.io
Server Port:            80

Document Path:          /?txt=123
Document Length:        557 bytes

Concurrency Level:      10
Time taken for tests:   16.185 seconds
Complete requests:      10000
Failed requests:        0
Total transferred:      7050000 bytes
HTML transferred:       5570000 bytes
Requests per second:    617.86 [#/sec] (mean)
Time per request:       16.185 [ms] (mean)
Time per request:       1.618 [ms] (mean, across all concurrent requests)
Transfer rate:          425.38 [Kbytes/sec] received

Connection Times (ms)
              min  mean[+/-sd] median   max
Connect:        0    0   0.1      0       5
Processing:     4   16   7.7     14      67
Waiting:        4   16   7.7     14      67
Total:          4   16   7.7     14      67

Percentage of the requests served within a certain time (ms)
  50%     14
  66%     18
  75%     20
  80%     22
  90%     27
  95%     32
  98%     36
  99%     40
 100%     67 (longest request)

此外,观察服务器 CPU 使用情况,发现可以轻松将 CPU 打满,丝毫不会浪费你的每一分钱。

线上使用,根据自己需求水平扩展相同规格的几台虚拟机,并水平扩展实例个数,即可实现满足自己业务需求的高性能 QRCode 服务啦,当然,如果你的二维码生成需求是确定的,可以减少 Nginx 配置中动态的部分,让一些配置 “常量化”,进一步减少计算量,以及避免一些恶意的请求浪费计算资源。

因为我们使用了 Nginx,这里如果想设置服务能力上限,避免资源被滥用,也可以通过 Nginx 常规方式快捷的实现一些功能需求:设置 LimitReq 来限制和避免一些外部恶意请求,以及结合日志进分析来获取二维码生成和访问统计计数等需求。

最后
原本想使用二阶段构建,将 Ngx_QRCode 模块构建为动态模块,构建出一套更小的镜像。但是因为调用 GD 库编译存在一些问题,暂时作罢,有时间再搞吧。

相比三年前的镜像,这次构建结果小了一半之多,还是挺欣慰的。

--EOF

167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo

167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo

docker构建nginx容器系列问题


background : 最近为小伙伴们筹划docker系列的技术分享,研究了一会docker相关技术, 在此记录一下构建nginx容器时候的坑

1.nginx服务器根目录问题

docker 官方镜像提供的nginx基于debian/jessie平台,其文件结构和ubuntu中的nginx中并不相同

eg:

run一个niginx容器

<span>//80端口被占用,so...</span>
$ sudo docker run <span>-it</span><span>-p</span><span>800</span>:<span>800</span> nginx
$ sudo docker ps 

CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                                   NAMES
<span>1801</span>a32aab54        nginx               <span>"nginx -g ''daemon off"</span><span>2</span> minutes ago       Up <span>2</span> minutes        <span>80</span>/tcp, <span>443</span>/tcp, <span>0.0</span><span>.0</span><span>.0</span>:<span>800</span><span>-&gt;</span><span>800</span>/tcp   berserk_kare
登录后复制

进入容器内部

<span>$ </span>sudo docker exec -it <span>1801</span>a32aab54 /bin/bash
root<span>@1801a32aab54</span><span>:/</span><span># </span>
登录后复制

查看nginx目录

<span># cd /etc/nginx/</span>
conf<span>.d</span>/         koi-utf         mime<span>.types</span>      nginx<span>.conf</span>      uwsgi_params    
fastcgi_params  koi-win         modules/        scgi_params     win-utf  
登录后复制

可以看到不仅没有熟悉的 /sites-available,也没有 /sites-enabled

继续查看nginx配置

<span># cat /conf.d/default.conf</span><span>server</span> {
    listen       <span>80</span>;
    server_name  localhost;

    <span>#charset koi8-r;</span><span>#access_log  /var/log/nginx/log/host.access.log  main;</span>    location / {
        root   /usr/share/nginx/html;
        <span>index</span><span>index</span>.html <span>index</span>.htm;
    }

    <span>#error_page  404              /404.html;</span><span># redirect server error pages to the static page /50x.html</span><span>#</span>
    error_page   <span>500</span><span>502</span><span>503</span><span>504</span>  /<span>50</span>x.html;
    location = /<span>50</span>x.html {
        root   /usr/share/nginx/html;
    }
    <span>#...省略php-fpm配置,好长..</span>
}
登录后复制

根目录配置: root /usr/share/nginx/html;

测试

<span># cd /usr/share/nginx/html</span><span># touch index.html</span><span># echo "test nginx in docker" &gt;index.html</span>
登录后复制

php-fpm配置相关

'').addClass(''pre-numbering'').hide(); $(this).addClass(''has-numbering'').parent().append($numbering); for (i = 1; i '').text(i)); }; $numbering.fadeIn(1700); }); });

以上就介绍了167 docker docker构建nginx容器系列问题,包括了docker,nginx方面的内容,希望对PHP教程有兴趣的朋友有所帮助。

C# ZXing.Net生成二维码、识别二维码、生成带Logo的二维码(二)

C# ZXing.Net生成二维码、识别二维码、生成带Logo的二维码(二)

1.使用ZXint.Net生成带logo的二维码

/// <summary>
/// 生成带Logo的二维码
/// </summary>
/// <param name="text"></param>
static void Generate3(string text)
{
//Logo 图片
Bitmap logo = new Bitmap(@"H:\桌面\截图\102.jpg");
//构造二维码写码器
MultiFormatWriter writer = new MultiFormatWriter();
Dictionary<EncodeHintType, object> hint = new Dictionary<EncodeHintType, object>();
hint.Add(EncodeHintType.CHARACTER_SET,"UTF-8");
hint.Add(EncodeHintType.ERROR_CORRECTION,ErrorCorrectionLevel.H);

//生成二维码
BitMatrix bm = writer.encode(text,BarcodeFormat.QR_CODE,300,300,hint);
BarcodeWriter barcodeWriter = new BarcodeWriter();
Bitmap map = barcodeWriter.Write(bm);


//获取二维码实际尺寸(去掉二维码两边空白后的实际尺寸)
int[] rectangle = bm.getEnclosingRectangle();

//计算插入图片的大小和位置
int middleW = Math.Min((int)(rectangle[2] / 3.5), logo.Width);
int middleH = Math.Min((int)(rectangle[3]/3.5),logo.Height);
int middleL = (map.Width - middleW) / 2;
int middleT = (map.Height - middleH) / 2;

//将img转换成bmp格式,否则后面无法创建Graphics对象
Bitmap bmpimg = new Bitmap(map.Width,map.Height,PixelFormat.Format32bppArgb);
using (Graphics g=Graphics.FromImage(bmpimg))
{
g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
g.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
g.DrawImage(map,0,0);
}
//将二维码插入图片
Graphics myGraphic = Graphics.FromImage(bmpimg);
//白底
myGraphic.FillRectangle(Brushes.White,middleL,middleT,middleW,middleH);
myGraphic.DrawImage(logo,middleL,middleT,middleW,middleH);

//保存成图片
bmpimg.Save(@"H:\桌面\截图\generate3.png",ImageFormat.Png);
}

 

调用:

//生成带图片的二维码
Generate3("https://www.baidu.com/");
Generate3("ionic是一个强大的混合式/hybrid HTML5移动开发框架,特点是使用标准的HTML、CSS和JavaScript,开发跨平台的应用 ,只需要几步就可以快速创建您的Ionic应用,创建应用从这里开始");

Centos7安装nginx(二)之docker中安装nginx

Centos7安装nginx(二)之docker中安装nginx

一、简介

本人最近对k8s+docker容器云、微服务进行一些调研,尝试着在docker中安装Nginx。先来安利docker一波,真是神器,但是对于docker的有点本人将在docker的相关文章中介绍。

  • 需求:做自动化运维的同学可能需要测试自己写完的shell脚本,docker是一个比虚拟机快照更方便的选择。只需要启动一个docker容器,将写好的脚本以挂载文件的方式,在docker容器中运行即可(copy进去再执行也可以)。
  • 环境: 虚拟机+docker
  • 优点:当shell脚本有问题的时候,直接kill掉docker容器,修改完shell后重启一个容器再运行即可。
  • 目的:为了练习Nginx的安装配置。由于docker使用Linux内核namespace\cgroup等隔离技术,近似等同于虚拟机(有些隔离做的不彻底,不能完全等同于),在docker中练习安装Nginx比跟在虚拟机上安装相差无异,但开销更少。如果仅仅是为了在docker中使用Nginx,只需要直接拉取Nginx镜像再开启容器即可。

二、安裝过程

在docker中安装Nginx的步骤跟上一篇文章Centos7安装nginx(一)大致相同。需要注意的是在docker中使用systemctl必须以特殊的方式启动容器,否则会报错Docker: Failed to get D-Bus connection: Operation not permitted

docker中使用systemctl报错

安装过程主要分为二部分:

  • 启动容器
  • 安装Nginx
    安装部分参考文章Centos7安装nginx(一),本文重点讲解如何启动docker容器,避免在配置systemctl来管理Nginx时出现报错信息。

1. 启动容器

  • 容器的正确启动姿势
  1. docker pull centos:7(拉取镜像)

    拉取镜像

  2. docker images(查看镜像具体信息)

    镜像信息


    步骤3中的镜像版本要与拉去下来的版本信息对应
  3. docker run -d --name Nginx --privileged=true docker.io/centos:7 /usr/sbin/init(以后台运行的方式启动容器)

    以后台的方式启动容器

  4. docker exec -it Nginx /bin/bash(进入容器)

    以交互的方式进入容器

  • docker容器中使用systemctl报错总结
  1. Docker: Failed to get D-Bus connection: Operation not permitted

    • 原因
      1. 这个的原因是因为dbus-daemon没能启动。启动容器时,带上参数--privileged=true、将你的CMD或者entrypoint设置为/usr/sbin/init即可(两者缺一不可)。会自动将dbus等服务启动起来。
    • 解决办法:
      • 在启动容器时添加参数
        • docker run -d --name centos7 --privileged=true centos:7 /usr/sbin/init
        • docker exec -it centos7 /bin/bash

          docker容器中成功使用systemctl

2. 安装Nginx

参考文章Centos7安装nginx(一)

三、总结

本文主要记录了docker中使用systemctl的报错问题,为下一篇文章Centos7安装nginx(三)之shell脚本自动化安装nginx,通过shell自动化安装Nginx做准备。文章可能在编辑过程中,由于个人疏忽、不同版本markdown解析器不兼容等原因导致字符书写错误,导致安装失败。本文属于原创,若有引用请注明出处。若有疑问或错误,欢迎各位指出,可以评论或者跟本人联系。

docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 Docker 构建 Nginx + ffmpeg + OBS 直播服务器

docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 Docker 构建 Nginx + ffmpeg + OBS 直播服务器

docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 介绍

docker Nginx rtmp

一个Dockerfile从源代码安装Nginx,Nginx-rtmp-module和FFmpeg HLS实时流媒体的默认设置。 建立在Alpine
Linux上。

  • Nginx 1.15.3 (从源代码编译)

  • Nginx-rtmp-module 1.2.1 (从源代码编译)

  • ffmpeg 4.0.2 (从源代码编译)

  • 默认HLS设置(见: nginx.conf)

用法:

服务端

  • 拉取docker镜像并运行:

    docker pull jun3/rtmp
    docker run –name rtmp -p 1935:1935 -p 8080:80 -d -it jun3/rtmp

或者

  • 构建docker镜像并运行:

    docker build -t jun3/rtmp .
    docker run –name rtmp -p 1935:1935 -p 8080:80 -d -it jun3/rtmp

  • 将实时内容串流到服务端:

    rtmp://:1935/stream/$STREAM_NAME

OBS配置

  • 流类型: 自定义流媒体服务器

  • 流地址: rtmp://localhost:1935/stream

  • 流密钥: hello

观看流

  • 在Safari,VLC或任何HLS播放器中,打开:

    http://:8080/live/$STREAM_NAME.m3u8

  • 例如: http://localhost:8080/live/hello.m3u8

FFMPEG构建

ffmpeg version 3.4.2 copyright (c) 2000-2018 the FFmpeg developers
  built with gcc 5.3.0 (Alpine 5.3.0)
  configuration: --enable-version3 --enable-gpl --enable-nonfree --enable-small --enable-libmp3lame --enable-libx264 --enable-libx265 --enable-libvpx --enable-libtheora --enable-libvorbis --enable-libopus --enable-libfdk-aac --enable-libass --enable-libwebp --enable-librtmp --enable-postproc --enable-avresample --enable-libfreetype --enable-openssl --disable-debug
  libavutil      55. 78.100 / 55. 78.100
  libavcodec     57.107.100 / 57.107.100
  libavformat    57. 83.100 / 57. 83.100
  libavdevice    57. 10.100 / 57. 10.100
  libavfilter     6.107.100 /  6.107.100
  libavresample   3.  7.  0 /  3.  7.  0
  libswscale      4.  8.100 /  4.  8.100
  libswresample   2.  9.100 /  2.  9.100
  libpostproc    54.  7.100 / 54.  7.100

  configuration:
    --enable-version3
    --enable-gpl
    --enable-nonfree
    --enable-small
    --enable-libmp3lame
    --enable-libx264
    --enable-libx265
    --enable-libvpx
    --enable-libtheora
    --enable-libvorbis
    --enable-libopus
    --enable-libfdk-aac
    --enable-libass
    --enable-libwebp
    --enable-librtmp
    --enable-postproc
    --enable-avresample
    --enable-libfreetype
    --enable-openssl
    --disable-debug

docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 官网

https://github.com/jun3372/rtmp

关于使用 Docker 和 Nginx 打造高性能二维码服务的介绍现已完结,谢谢您的耐心阅读,如果想了解更多关于167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo、C# ZXing.Net生成二维码、识别二维码、生成带Logo的二维码(二)、Centos7安装nginx(二)之docker中安装nginx、docker nginx rtmp 服务端OBS配置观看流FFMPEG构建 Docker 构建 Nginx + ffmpeg + OBS 直播服务器的相关知识,请在本站寻找。

本文标签: