前文链接

  1. 高可用系列文章之一 - 概述 - 东风微鸣技术博客 (ewhisper.cn)
  2. 高可用系列文章之二 - 传统分层架构技术方案 - 东风微鸣技术博客 (ewhisper.cn)

四 NGINX 高可用实施方案

高可用的实施, 主要步骤概述如下:

  1. NGINX 的安装及基础配置
  2. 负载均衡层高可用: NGINX + Keepalived配置
  3. 应用服务层高可用: NGINX -> 应用服务层 转发配置

系统软 硬件详细配置清单

根据制造业高可用架构设计, 以及业务需求, 部署模型建议配置如下:

  • 负载均衡服务器(即 NGINX + Keepalived): 2台, 操作系统 Linux. 配置建议如下:
名称 规格 备注
CPU 2 core
内存 4 GB
硬盘 50 GB
操作系统 SUSE12 64位及补丁
网卡 至少1块网卡, 支持VRRP 技术
  • 软件运行配置环境:
软件 规格
NGINX 1.16.1
Keepalived 2.0.10

4.1 NGINX 安装及配置

4.1.1 分区及目录

建议至少分为以下3个区:

分区及目录 大小 备注
主分区( /) 默认 nginx程序及配置文件位于该分区(/etc/nginx)
日志分区(/var/log/nginx) 10G-20G
程序目录分区(/usr/share/nginx/html) 10G 可选, nginx用作web server时需要用到此目录.

4.1.2 程序及依赖版本

程序组件 安装包名 版本 md5
nginx nginx-1.16.1-1.sles12.ngx.x86_64.rpm 1.16.1 396A359F26DD0100CD59545BAFFAFE85

4.1.3 NGINX程序规范

  • nginx程序目录: /etc/nginx
  • 执行程序路径: /usr/sbin/nginx
  • 主配置文件路径:/etc/nginx/conf/nginx.conf
  • 各个应用系统转发配置文件目录:/etc/nginx/conf.d/
  • 日志目录:/var/log/nginx
  • 各个应用系统静态文件目录:/usr/share/nginx/html

4.1.4 系统级别配置优化

注意:

需要 root 用户执行.

  1. 安装组件: logrotate
  2. 修改连接数:
vi /etc/security/limits.conf
# vi编辑
* soft nofile 65535
* hard nofile 65535
  1. 修改系统内核配置:
vi /etc/sysctl.conf
# vi编辑 # NGINX Tuning Performance
fs.file-max = 65535 vm.zone_reclaim_mode = 0 net.core.somaxconn = 2048 net.ipv4.tcp_tw_recycle = 0
net.ipv4.tcp_timestamps = 1
net.ipv4.tcp_slow_start_after_idle = 0
net.ipv4.tcp_mtu_probing = 1 # 生效
sysctl -p

4.1.5 配置NGINX repo

注意:

本节命令可以根据具体情况, 在公司内部 repo 仓库机器上进行操作.

其他机器只需要配置内部 repo 地址即可.

键入以下 zypper 命令以添加 SLES 的 zypper 存储库

$ sudo zypper addrepo -G -t yum -c 'http://nginx.org/packages/sles/12' nginx

接下来,您必须验证数字签名以保持下载包的完整性和来源。使用wget命令获取nginx签名密钥:

$ wget http://nginx.org/keys/nginx_signing.key

示例输出:

--2020-01-09 23:48:48--  http://nginx.org/keys/nginx_signing.key
Resolving nginx.org (nginx.org)... 206.251.255.63, 95.211.80.227, 2001:1af8:4060:a004:21::e3, ...
Connecting to nginx.org (nginx.org)|206.251.255.63|:80... connected.
HTTP request sent, awaiting response... 200 OK
Length: 1561 (1.5K) [text/plain]
Saving to: ‘nginx_signing.key’ 100%[==================================================>] 1,561 --.-K/s in 0s 2020-01-09 23:48:49 (117 MB/s) - ‘nginx_signing.key’ saved [1561/1561]

使用rpm命令将密钥导入rpm:

$ sudo rpm --import nginx_signing.key

4.1.6 SUSE 上安装NGINX

键入以下 zypper 命令:

$ sudo zypper install nginx=1.16.1

4.1.7 可选: 配置防火墙

注意:

如果机房流量入口有其他专用防火墙, 则可以关闭 nginx 服务器上的防火墙, 且不需要执行此步骤.

首先创建Nginx特定服务的配置文件,使用vi命令等文本编辑器打开端口80:

$ sudo vi /etc/sysconfig/SuSEfirewall2.d/services/nginx

添加以下配置:

## Name: Nginx web server
## Description: Open ports for Nginx Server # space separated list of allowed TCP ports
TCP="http"

(如果不需要 HTTPS 支持,则只需要允许 TCP 端口号 80 上的通信。)保存并退出 VI/VIM 文本编辑器。现在,只需运行以下命令打开端口80:

$ sudo yast firewall

必须使用 TAB 和箭头键在 YaST 中跳转。在 YaST 中,跳转到允许的服务,然后按 Enter 键:

使用 TAB 跳转到“Allowed Services”,然后按向下箭头键选择 Nginx web server,然后按回车键。必须按 Alt-A 来将Nginx服务器添加到防火墙:

Alt-NAlt-F 保存并完成 SLES 上的防火墙设置。返回 shell 提示符后,列出 sle 上的所有 iptables 规则:

$ sudo iptables -S

示例输出:

-A input_ext -p tcp -m limit --limit 3/min -m tcp --dport 80 --tcp-flags FIN,SYN,RST,ACK SYN -j LOG --log-prefix "SFW2-INext-ACC-TCP " --log-tcp-options --log-ip-options
-A input_ext -p tcp -m tcp --dport 80 -j ACCEPT

使用 sudo 命令和 grep 命令的组合来确定端口 80 是否打开:

sudo sh -c 'iptables -L -n -v | grep :80'

4.1.8 启动 NGINX Server

键入以下 systemctl 命令以在系统启动时启用 Nginx: (开机自启)

$ sudo systemctl enable nginx

启动 Nginx web 服务器:

$ sudo systemctl start nginx

验证:

$ systemctl status nginx

要判断 80 端口是否监听, 运行以下 netstat 命令或 ss 命令:

$ sudo netstat -tulpn | grep :80
$ sudo ss -tulpn | grep :80

4.1.9 NGINX 基础操作

停止:

$ sudo systemctl stop nginx

启动:

$ sudo systemctl start nginx

重新启动服务:

$ sudo systemctl restart nginx

更改配置后重新加载 Ngnix:

$ sudo systemctl reload nginx

️ 建议:

配置更新后使用 reload 来重新加载nginx.

访问 nginx 页面:

假设 NGINX IP为: 192.168.0.1. 使用浏览器或 curl 访问:

http://serve_IP
http://your-domain
http://192.168.0.1

$ curl -I 192.168.122.43

示例输出:

HTTP/1.1 200 OK
Server: nginx/1.16.1
Date: Sat, 03 Feb 2020 19:18:53 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 17 Oct 2019 13:30:50 GMT
Connection: keep-alive
ETag: "59e6060a-264"
Accept-Ranges: bytes

4.1.10 查找有关 SLES 上 Nginx 配置文件的信息

现在 Nginx 已经启动并运行了。接下来可以定制配置。

SLES 的服务器配置文件:

  • /etc/nginx/: nginx 默认配置目录
  • /etc/nginx/nginx.conf: nginx 主配置文件
  • /etc/nginx/conf.d/default.conf: 默认 virtual host 的配置

修改主配置:

$ sudo vi /etc/nginx/nginx.conf

4.1.11 NGINX 日志

  • /var/log/nginx/access.log: 访问日志
  • /var/log/nginx/error.log: 错误日志

4.1.12 nginx.conf

主配置文件详细说明如下:

#### 全局块 开始 #####
# 配置允许运行Nginx服务器的用户和用户组
#user nginx nginx;
# 配置允许Nginx进程生成的worker process数
worker_processes 4;
#worker_cpu_affinity 0001 0010 0100 1000; # 配置Nginx服务器运行时的错误日志文件存放路径和名称
#error_log logs/error.log;
error_log logs/error.log info; # 配置Nginx服务器运行时的pid文件存放路径和名称
pid logs/nginx.pid;
#### 全局块 结束 ##### #### events块 开始 ####
events {
# 配置事件驱动模型
use epoll;
accept_mutex off;
multi_accept off;
worker_connections 65535;
}
#### events块 结束 #### #### http块 开始 ####
http {
# 定义MIME-Type
include mime.types;
default_type application/octet-stream; # 配置请求处理日志的格式
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent $request_time $upstream_response_time "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for" "$host"'; access_log logs/access.log main; # 配置允许使用sendfile方式传输
sendfile on;
#tcp_nopush on; # 配置连接超时时间
#keepalive_timeout 0;
keepalive_timeout 65; # nginx允许的客户端请求头部的缓冲区大小
client_header_buffer_size 4k; # gzip conf
gzip on;
gzip_min_length 1024;
gzip_buffers 32 4k;
gzip_http_version 1.1;
gzip_comp_level 6;
gzip_types text/plain application/xml image/x-icon image/svg+xml image/png text/css image/jpeg image/gif application/x-javascript application/javascript application/json;
gzip_vary on;
gzip_disable "MSIE [1-6]\."; # security
port_in_redirect off;
server_tokens off; # proxy buffer
proxy_buffers 8 4k;
proxy_buffer_size 4k;
proxy_temp_file_write_size 4k;
proxy_temp_path proxy_temp; # proxy cache
# proxy_cache_path cache/ keys_zone=cache_all:10m; #### server块 开始 ####
## 配置虚拟主机localhost
server {
listen 80 reuseport;
server_name localhost; #charset koi8-r; access_log logs/host.access.log main; location / {
root html;
index index.html index.htm;
} error_page 404 /404.html; # redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
} }
#### server 块 结束 #### # HTTPS server
#
#server {
# listen 443 ssl;
# server_name localhost; # ssl_certificate cert.pem;
# ssl_certificate_key cert.key; # ssl_session_cache shared:SSL:1m;
# ssl_session_timeout 5m; # ssl_ciphers HIGH:!aNULL:!MD5;
# ssl_prefer_server_ciphers on; # location / {
# root html;
# index index.html index.htm;
# }
#} # virtual hosts
include conf.d/default.conf; }
#### http块 结束 ####

️ 建议:

为了保证主配置文件的干净. 建议通过 include conf.d/default.conf; 类似这样的方式来引入其他virtual hosts配置.

4.1.13 日志转储

  1. sudo vi /etc/logrotate.d/nginx

  2. 编辑内容:

    /var/log/nginx/*.log {
    daily
    rotate 90 # 保留90天, 按需调整
    create
    dateext
    #compress # 是否启用压缩, 按需调整
    #minsize 1M
    #create 0644 nginx nginx # nginx日志所属用户和组, 按需调整
    # copytruncate 用于还在打开中的日志文件,把当前日志备份并截断;是先拷贝再清空的方式,拷贝和清空之间有一个时间差,可能会丢失部分日志数据。
    # delaycompress 和compress 一起使用时,转储的日志文件到下一次转储时才压缩
    missingok
    ifempty # default
    nomail
    #noolddir # default
    sharedscripts # 运行postrotate脚本,作用是在所有日志都轮转后统一执行一次脚本。如果没有配置这个,那么每个日志轮转后都会执行一次脚本
    postrotate # 在logrotate转储之后需要执行的指令,例如重新启动 (kill -HUP) 某个服务!必须独立成行
    if [ -f /var/log/nginx/nginx.pid ]; then
    kill -USR1 `cat /var/log/nginx/nginx.pid`
    fi
    endscript
    }
  3. 强制运行一次来测试:logrotate -f -v /etc/logrotate.d/nginx(对应目录只能 user 有w权限, 否则会报错)

  4. 配置好即可, logrotate 会自动读取/etc/logrotate.d的配置并自动执行.

备注:

cron.daily 会在 3:22+(5,45) 这个时间段执行

4.2 NGINX + Keepalived配置

️ 假定:

假设相关IP如下:

  1. VIP: 192.168.0.100
  2. NGINX - 主IP: 192.168.0.1
  3. NGINX - 从IP: 192.168.0.2
  4. NGINX - 主从的IP对应的网卡为 eth0

4.2.1 Keepalived 安装配置

$ sudo zypper install keepalived=2.0.10

4.2.2 Keepalived 配置

Keepalived启动默认读取配置文件路径 /etc/keepalived/keepalived.conf ,添加配置文件:

sudo vi /etc/keepalived/keepalived.conf

NGINX - 主 机器配置如下:

vrrp_script chk_nginx {
script "/etc/keepalived/nginx_pid.sh" # 检测nginx状态的脚本路径
interval 2
weight -20
fall 3
}
vrrp_instance VI_1 {
state MASTER # 从机为 BACKUP
interface eth0 # 具体的网卡接口看情况进行填写
virtual_router_id 51
priority 110 # 备机权值为100
advert_int 1
authentication {
auth_type PASS
auth_pass 123456
}
track_script {
chk_nginx
}
virtual_ipaddress {
192.168.0.100/24 brd 192.168.0.255 dev eth0 label eth0:vip # 根据实际情况进行修改
}
}

配置说明如下:

  1. weight -20: keepalived 配置里 priority 110 是初始权重;主的初始设置了 110,备的设置了 100;如果检测失败,权重 -20. 主从切换.

  2. virtual_router_id 51 自己定义的虚拟路由的id。vrrp_instance VI_1 块中 virtual_router_id 指令的值 51 是一个示例值;根据需要改变它,使其在您的环境中独一无二。

  3. 添加

NGINX - 从 机器配置如下:

vrrp_script chk_nginx {
script "/etc/keepalived/nginx_pid.sh" # 检测nginx状态的脚本路径
interval 2
weight -20
}
vrrp_instance VI_1 {
state BACKUP # 辅机为 BACKUP
interface eth0 # 具体的网卡接口看情况进行填写
virtual_router_id 51
priority 100 # 备机权值为100
advert_int 1
authentication {
auth_type PASS
auth_pass 123456
}
track_script {
chk_nginx
}
virtual_ipaddress {
192.168.0.100/24 brd 192.168.0.255 dev eth0 label eth0:vip # 根据实际情况进行修改
}
}

4.2.3 配置检测脚本

备注:

使用 root 用户

配置检测脚本: /etc/keepalived/nginx_pid.sh

#!/bin/bash
A=`ps -C nginx --no-header|wc -l`
if [ $A -eq 0 ]
then
systemctl start nginx
exit 1
else
exit 0
fi

赋予执行权限: chmod 750 /etc/keepalived/nginx_pid.sh

4.2.4 启动 Keepalived

键入以下 systemctl 命令以在系统启动时启用 keepalived: (开机自启)

$ sudo systemctl enable keepalived

启动 Nginx web 服务器:

$ sudo systemctl start keepalived

验证:

$ systemctl status keepalived

4.2.4 显示节点状态

要查看当前哪个节点是给定 VIP 的主节点,请在定义 VRRP 实例的接口上运行命令 ip addr show(在以下命令中,eth0节点suse12-1和上的接口suse12-2):

suse12-1 # ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state
UP qlen 1000
link/ether 52:54:00:33:a5:a5 brd ff:ff:ff:ff:ff:ff
inet 192.168.0.1/24 brd 192.168.0.255 scope global dynamic eth0
valid_lft 3071sec preferred_lft 3071sec
inet 192.168.0.100/32 scope global eth0
valid_lft forever preferred_lft forever suse12-2 # ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state
UP qlen 1000
link/ether 52:54:00:33:a5:87 brd ff:ff:ff:ff:ff:ff
inet 192.168.0.2/24 brd 192.168.0.255 scope global eth0
valid_lft forever preferred_lft forever

在此输出中,第二行 inet 表示 suse12-1 是主节点, 已为其分配了已定义的 VIP(192.168.0.100)。inet 输出中的其他行显示主节点的实际IP地址(192.168.0.1)和备用(或 从)节点的IP地址(192.168.0.2)。

至此, nginx + keepalived 的负载均衡层高可用已经配置完成.

4.3 NGINX -> 应用服务层 转发配置

️ 假定:

假设应用系统的相关信息如下:

  1. 请求及业务协议为HTTP协议;
  2. 应用系统节点1 IP为: 172.30.0.1
  3. 应用系统节点2 IP为: 172.30.0.2
  4. 业务系统监听端口为: 8080

4.3.1 修改配置文件

以 mes 系统高可用配置为例(协议为 HTTP 协议), 新增 /etc/nginx/conf.d/mes.conf:

# mes access

upstream mes{
# ip_hash; # 源地址会话保持, 按需开启
server 172.30.0.1:8080;
server 172.30.0.2:8080;
} server {
listen 80;
#server_name mes.example.com 192.168.0.100; # server_name为对应的访问域名, 按需开启 #set max uploading file size to 20m
client_max_body_size 20m; #charset koi8-r; # keepalive
# 设置代理的HTTP协议版本(默认是1.0版本)
proxy_http_version 1.1; # 按需调整
# 允许重新定义或追加字段到传递给代理服务器的请求头信息(默认是close)
proxy_set_header Connection ""; proxy_set_header HOST $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; access_log logs/mes_access.log main buffer=16k flush=5m;
error_log logs/mes_error.log;
location / {
#root html;
#index index.html index.htm;
proxy_pass http://mes;
#proxy_redirect off;
# proxy_cache cache_all;
} #error_page 404 /404.html; # redirect server error pages to the static page /50x.html
#
#error_page 500 502 503 504 /50x.html;
#location = /50x.html {
# root html;
#}
}

4.3.2 主配置文件 include

在 http 块新增如下内容

include conf.d/mes.conf;

4.3.2 重新加载 nginx

更改配置后重新加载Ngnix使配置生效:

sudo systemctl reload nginx

4.3.3 验证

通过 VIP 进行访问, 查看对应应用系统日志, 观察是否 2 个节点都接收到请求.

五 变更控制流程

严格遵循 制造业本公司的变更控制规范. 进行相关的变更控制和审批流程.

一个新的应用需要上线或者变更,通常涉及以下步骤:

可以随时实施的变更:

  1. 系统项目组需至少提供端口、路径、后端地址(域名可选);
  2. /etc/nginx/conf.d 中增加一个配置文件;
  3. /etc/nginx/nginx.conf 中增加一个 include,指向新增的配置文件;

需要在变更窗口进行的变更:

  1. 重新载入(sudo systemctl reload nginx)配置.
  2. 通知用户, 访问的 Server IP 由: 原应用服务器 IP 调整为 NGINX 的 VIP.
  3. 修改客户端和浏览器配置, 访问的 Server IP 由: 原应用服务器 IP 调整为 NGINX 的 VIP.
  4. 验证变更是否成功.

5.1 回退步骤

回退较为简单, 步骤如下:

  1. 通知用户, 访问的 Server IP 调整为: 原应用服务器 IP.
  2. 修改客户端和浏览器配置, 访问的 Server IP 调整为: 原应用服务器 IP.
  3. 回退完成
  4. 验证回退是否成功.

参考文件

参考文件
High Availability Support for NGINX

三人行, 必有我师; 知识共享, 天下为公. 本文由东风微鸣技术博客 EWhisper.cn 编写.

高可用系列文章之三 - NGINX 高可用实施方案的更多相关文章

  1. 一步步实现windows版ijkplayer系列文章之三——Ijkplayer播放器源码分析之音视频输出——音频篇

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  2. 一步步实现windows版ijkplayer系列文章之二——Ijkplayer播放器源码分析之音视频输出——视频篇

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  3. 一步步实现windows版ijkplayer系列文章之七——终结篇(附源码)

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  4. 一步步实现windows版ijkplayer系列文章之六——SDL2源码分析之OpenGL ES在windows上的渲染过程

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  5. 一步步实现windows版ijkplayer系列文章之五——使用automake生成makefile

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  6. 一步步实现windows版ijkplayer系列文章之四——windows下编译ijkplyer版ffmpeg

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  7. 一步步实现windows版ijkplayer系列文章之一——Windows10平台编译ffmpeg 4.0.2,生成ffplay

    一步步实现windows版ijkplayer系列文章之一--Windows10平台编译ffmpeg 4.0.2,生成ffplay 一步步实现windows版ijkplayer系列文章之二--Ijkpl ...

  8. 高可用系列之Nginx

    1.1Keepalived高可用软件 Keepalived起初是专为LVS设计的,专门用来监控LVS集群系统中各个服务节点的状态,后来又加入了VRRP的功能,因此除了配合LVS服务外,也可以作为其他服 ...

  9. keepalived对nginx高可用演练脚本

    keepalived对nginx高可用演练脚本 参考文章:http://deidara.blog.51cto.com/400447/302402/ .安装nginx.keepalived.epel-r ...

  10. (5.8)mysql高可用系列——MySQL中的GTID复制(实践篇)

    一.基于GTID的异步复制(一主一从)无数据/少数据搭建 二.基于GTID的无损半同步复制(一主一从)(mysql5.7)基于大数据量的初始化 正文: [0]概念 [0.5]GTID 复制(mysql ...

随机推荐

  1. Kafka Eagle 3.0.1功能预览

    1.概述 最近有同学留言,关于Kafka Eagle的一些使用问题.今天笔者就为大家来详细介绍Kafka Eagle 3.0.1的功能以及使用方法. 2.内容 在3.0.1版本中,EFAK优化了分布式 ...

  2. mapboxgl加载tiff

    缘起 近期在项目中遇到这么一个需求,需要在地图上展示一组格网数据,格网大小为2m*2m,地图api用的mapboxgl.起初拿到这个需要感觉很easy,在地图上添加一个fill图层就好啦.把格网面数据 ...

  3. Bing 广告平台迁移到 .net6

    原文链接 https://devblogs.microsoft.com/dotnet/bing-ads-campaign-platform-journey-to-dotnet-6/ 广告组件平台对于微 ...

  4. SpringMVC访问静态资源的问题。

    在项目中引用css和js文件一直出错,反复修改文件路径始终访问不到.究其原因原来是应该在web.xml 文件中添加访问静态资源的默认servlet. 如下. <servlet-mapping&g ...

  5. Selenium+Python系列(二) - 元素定位那些事

    一.写在前面 今天一实习生小孩问我,说哥你自动化学了多久才会的,咋学的? 自学三个月吧,真的是硬磕呀,当时没人给讲! 其实,学什么都一样,真的就是你想改变的决心有多强罢了. 二.元素定位 这部分内容可 ...

  6. Magnet: Push-based Shuffle Service for Large-scale Data Processing

    本文是阅读 LinkedIn 公司2020年发表的论文 Magnet: Push-based Shuffle Service for Large-scale Data Processing 一点笔记. ...

  7. go-zero docker-compose 搭建课件服务(八):集成jaeger链路追踪

    0.转载 go-zero docker-compose 搭建课件服务(八):集成jaeger链路追踪 0.1源码地址 https://github.com/liuyuede123/go-zero-co ...

  8. ROS2时间同步(python)

    最近1周一直研究ROS2的时间同步,翻越很多博客,很少有人使用ROS2进行时间同步的代码,无奈不断尝试与源码阅读,终于将其搞定, 为此,本博客将介绍基于python的ROS2的时间同步方法. 本博客内 ...

  9. Python基础之模块:2、包的使用和软件开发目录规范及常用内置模块

    目录 一.包的使用 1.什么是包 2.包的具体使用 1.常规导入 2.直接导入包名 二.编程思想转变 1.面条阶段 2.函数阶段 3.模块阶段 三.软件目录开发规范 1.bin 2.conf 3.co ...

  10. k8s 中的 ingress 使用细节

    k8s中的ingress 什么是ingress Ingress 如何使用 ingress 使用细节 参考 k8s中的ingress 什么是ingress k8s 中使用 Service 为相同业务的 ...