首页
关于
Search
1
意外通知
29 阅读
2
欢迎来到我的个人博客
14 阅读
3
Mysql 二进制安装脚本
14 阅读
4
脚本练习合集
10 阅读
5
CI/CD理念与流程
9 阅读
默认分类
登录
Search
无冕の神
累计撰写
19
篇文章
累计收到
4
条评论
首页
栏目
默认分类
页面
关于
搜索到
19
篇与
的结果
2026-02-03
mysql事务案例
准备表-- 商品表:存储商品信息CREATE TABLE products (product_id INT PRIMARY KEY AUTO_INCREMENT, product_name VARCHAR(100) NOT NULL, price DECIMAL(10, 2) NOT NULL, stock INT NOT NULL DEFAULT 0, created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, CHECK (price >= 0), CHECK (stock >= 0))CHARSET=UTF8;-- 订单表:存储订单基本信息CREATE TABLE orders (order_id INT PRIMARY KEY AUTO_INCREMENT, user_id INT NOT NULL, total_amount DECIMAL(10, 2) NOT NULL, status ENUM('pending', 'paid', 'shipped', 'delivered', 'cancelled') NOT NULL DEFAULT 'pending', created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, CHECK (total_amount >= 0))CHARSET=UTF8;-- 支付表:存储支付详情CREATE TABLE payments (payment_id INT PRIMARY KEY AUTO_INCREMENT, order_id INT NOT NULL, amount DECIMAL(10, 2) NOT NULL, payment_method ENUM('credit_card', 'alipay', 'wechat', 'cash') NOT NULL, payment_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP, FOREIGN KEY (order_id) REFERENCES orders(order_id) ON DELETE CASCADE, CHECK (amount >= 0))CHARSET=UTF8;-- 用户积分表:用于案例中的积分更新操作CREATE TABLE user_points (user_id INT PRIMARY KEY, points INT NOT NULL DEFAULT 0, updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, CHECK (points >= 0))CHARSET=UTF8;-- 向商品表插入初始数据(案例中操作了product_id=101的商品)INSERT INTO products (product_id, product_name, price, stock)VALUES (101, '无线蓝牙耳机', 149.99, 50), -- 案例中会扣减该商品库存(102, '智能手表', 299.99, 30),(103, '便携式充电宝', 59.99, 100);-- 向用户积分表插入数据(案例中操作了user_id=501的用户)INSERT INTO user_points (user_id, points)VALUES (501, 1000), -- 案例中会为该用户增加积分(502, 500),(503, 2000);-- 初始订单表和支付表可以为空-- 因为案例中会创建新的订单和支付记录-- 这里插入一条历史订单作为示例(不会影响案例操作)INSERT INTO orders (order_id, user_id, total_amount, status)VALUES (1000, 502, 89.99, 'delivered');INSERT INTO payments (payment_id, order_id, amount, payment_method)VALUES (2000, 1000, 89.99, 'wechat');-- 1. 关闭自动提交模式SHOW VARIABLES LIKE 'autocommit';SET AUTOCOMMIT = 0;-- 2. 开始新事务START TRANSACTION;-- 模拟订单处理流程-- 步骤1: 扣减商品库存UPDATE products SET stock = stock - 2 WHERE product_id = 101;开始案例-- 设置第一个保存点SAVEPOINT after_stock_update;-- 步骤2: 创建订单记录INSERT INTO orders (order_id, user_id, total_amount, status)VALUES (1001, 501, 299.98, 'pending');-- 设置第二个保存点SAVEPOINT after_order_create;-- 步骤3: 记录支付信息INSERT INTO payments (payment_id, order_id, amount, payment_method)VALUES (2001, 1001, 299.98, 'credit_card');-- 假设这里发现支付方式错误,需要回滚到创建订单之后ROLLBACK TO SAVEPOINT after_order_create;-- 修正后重新记录支付信息INSERT INTO payments (payment_id, order_id, amount, payment_method)VALUES (2001, 1001, 299.98, 'alipay');-- 释放不再需要的保存点RELEASE SAVEPOINT after_stock_update;-- 步骤4: 更新用户积分UPDATE user_points SET points = points + 299 WHERE user_id = 501;-- 设置第三个保存点SAVEPOINT after_points_update;-- 检查所有操作无误后提交事务COMMIT;-- 假设发现积分计算错误,需要回滚所有操作-- ROLLBACK;-- 恢复自动提交模式SET AUTOCOMMIT = 1;REDO 的工作过程当事务对数据进行修改时(如 INSERT、UPDATE),数据库会先将修改操作记录到REDO 日志缓冲区(内存区域),同时在内存中的数据页(Buffer Pool)中执行实际修改。事务提交前,数据库会先将 REDO 日志从缓冲区强制刷写到磁盘上的 REDO 日志文件目的:即使事务修改的数据还未从内存刷到磁盘(如数据文件),只要日志已持久化,崩溃后仍可通过日志恢复。当数据库重启时,会启动恢复进程,扫描 REDO 日志文件:对于所有已提交但数据未刷盘的事务,根据日志内容重新执行修改操作(即 “重做”),将数据更新到磁盘; UNDO 的工作过程当事务对数据进行修改时(如 UPDATE、DELETE),数据库会先将修改前的旧值记录到 UNDO 日志中(通常存储在内存缓冲区),再执行实际的修改操作(更新内存数据页)主动回滚:当用户执行ROLLBACK命令时,数据库会根据当前事务的 UNDO 日志,反向执行操作,直至事务所有修改被撤销。崩溃恢复:数据库重启时,对于未提交的事务(包括崩溃时正在执行的事务),恢复进程会扫描 UNDO 日志,撤销其所有修改,确保这些未完成的事务不会对数据库留下 “脏数据”。 排他锁(简称 X 锁):事务 A 对数据加 X 锁后,其他事务既不能加 X 锁(无法修改),也不能加共享锁保证数据修改操作的独占性,防止多个事务同时修改同一资源。共享锁(简称 S 锁):事务 A 对数据加 S 锁后,其他事务可加 S 锁(共同读取),但不能加 X 锁(需等待 S 锁释放)。允许多个事务同时读取同一资源,避免读操作被写操作阻塞
2026年02月03日
3 阅读
0 评论
0 点赞
2026-02-03
Nginx后端服务器(即 upstream 模块中配置的服务器)有多种状态
weight(权重,默认值 1)upstream backend { server 192.168.1.101 weight=3; # 权重 3,被分配概率更高 server 192.168.1.102 weight=1; # 权重 1}max_fails(最大失败次数,默认值 1)若失败次数达到 max_fails,Nginx 会在 fail_timeout 时间内将该服务器标记为 “不可用”,不再分配请求。upstream backend { server 192.168.1.101 max_fails=3; # 3 次失败后标记为不可用}fail_timeout(失败超时时间,默认值 10 秒)配合 max_fails 使用,定义 “失败次数统计的时间窗口” 和 “服务器被标记为不可用后的隔离时间”。若 max_fails=3 且 fail_timeout=20s,表示 20 秒内失败 3 次,服务器会被隔离 20 秒。隔离时间结束后,Nginx 会重新尝试将请求分配给该服务器,若成功则恢复可用状态。upstream backend { server 192.168.1.101 max_fails=3 fail_timeout=20s;}down(手动标记为不可用)手动将服务器标记为 “永久不可用”,Nginx 不会向其分配任何请求。upstream backend { server 192.168.1.101 down; # 该服务器不参与负载均衡 server 192.168.1.102;}backup(备份服务器)标记为备份服务器,仅当所有非备份服务器(正常或临时不可用)都无法处理请求时,才会接收请求。upstream backend { server 192.168.1.101; server 192.168.1.102; server 192.168.1.103 backup; # 主服务器都故障时启用}max_conns(最大连接数)限制后端服务器同时处理的最大连接数,超过则不再分配新请求。upstream backend { server 192.168.1.101 max_conns=1000; # 最多同时处理 1000 个连接}这些状态可组合使用upstream backend {server 192.168.1.101 weight=2 max_fails=3 fail_timeout=15s; server 192.168.1.102 weight=1 max_conns=500; server 192.168.1.103 backup; server 192.168.1.104 down;}
2026年02月03日
3 阅读
0 评论
0 点赞
2026-02-03
Nginx负载均衡算法
一、内置基础算法 这些算法无需额外模块,默认集成在 Nginx 中,通过 upstream 模块配置即可使用。 1. 轮询(Round Robin)rr 原理:默认调度算法,将请求按顺序轮流分配到不同的后端服务器(逐个分发,循环往复)。 特点: 简单直观,无需额外配置。 假设所有后端服务器性能相同,适合服务器硬件配置一致的场景。 不考虑服务器负载、响应时间等实时状态。 适用场景:后端服务器性能均衡、无特殊会话需求的普通 Web 服务(如静态资源服务、API 接口等)。 配置示例: nginx upstream backend { server 192.168.1.101; # 后端服务器1 server 192.168.1.102; # 后端服务器2 server 192.168.1.103; # 后端服务器3 } 调度效果:请求顺序为 101 → 102 → 103 → 101 → 102 → 103 → ...。 注意:若某台服务器故障(如超时、返回错误码),Nginx 会自动将其暂时排除,故障恢复后重新加入轮询。 2. 加权轮询(Weighted Round Robin) 原理:在轮询基础上,为后端服务器分配权重(weight 参数),权重越高的服务器接收的请求越多(权重比 = 请求数量比)。 特点: 可根据服务器性能差异调整权重(性能强的服务器权重高,承担更多请求)。 权重默认值为 1,权重为 0 的服务器不参与分配。 适用场景:后端服务器硬件配置不一致(如部分服务器 CPU / 内存更强),需按性能分配负载。 配置示例: nginx upstream backend { server 192.168.1.101 weight=3; # 权重3,接收3/6的请求 server 192.168.1.102 weight=2; # 权重2,接收2/6的请求 server 192.168.1.103 weight=1; # 权重1,接收1/6的请求 } 调度效果:请求分配比例为 101:102:103 = 3:2:1(如顺序为 101→101→101→102→102→103,循环重复)。 3. IP 哈希(IP Hash) 原理:根据客户端的 IP 地址计算哈希值,将同一客户端的请求始终分配到同一台后端服务器(哈希值固定, 映射的服务器固定)。 特点: 实现会话保持(Session Sticky):适合需要保存客户端状态的场景(如用户登录状态、购物车数据等)。 哈希计算基于客户端 IP(IPv4 的前 3 段或完整 IPv6 地址),避免因客户端 IP 微小变化(如动态 IP) 导致映射变化。 适用场景:需要保持会话一致性的服务(如电商网站、后台管理系统)。 配置示例: nginx upstream backend { ip_hash; # 启用IP哈希算法 server 192.168.1.101; server 192.168.1.102; } 注意: 若后端服务器故障,需手动下线(down 标记),否则哈希映射会重新计算,导致会话丢失。 不适合客户端 IP 集中的场景(如同一局域网内的大量用户,可能导致某台服务器负载过高)。 4. 最少连接(Least Connections) 原理:优先将请求分配给当前连接数最少的后端服务器(实时监控服务器连接数,动态调整分配)。 特点: 考虑服务器的实时负载(连接数越少,说明越空闲),避免某台服务器因连接堆积过载。 适合请求处理时间差异较大的场景(如部分请求耗时久,导致服务器连接数偏高)。 适用场景:请求处理时间不稳定的服务(如复杂查询、文件上传下载)。 配置示例: nginx upstream backend { least_conn; # 启用最少连接算法 server 192.168.1.101; server 192.168.1.102; } 扩展:可结合权重使用(weight),此时计算 “加权最少连接”(连接数 / 权重的值越小,优先级越高),兼顾性能差异。二、扩展算法(需第三方模块) 部分高级算法需要通过额外模块(如 ngx_http_upstream_fair_module、nginx-upstream-consistent-hash 等)实现,需手动编译模块到 Nginx 中。 1. fair 算法 原理:根据后端服务器的响应时间(处理请求的快慢)分配请求,响应时间越短的服务器优先接收请求。 特点: 基于服务器实时响应速度动态调度,更贴合 “负载均衡” 的本质(响应快的服务器处理更多请求)。 需安装第三方模块 ngx_http_upstream_fair_module(Nginx 官方不自带)。 配置示例: nginx upstream backend { fair; # 启用fair算法 server 192.168.1.101; server 192.168.1.102; } 2. 一致性哈希(Consistent Hash) 原理:通过哈希算法将客户端请求和后端服务器映射到同一个哈希环上,请求根据哈希值顺时针映射到最近的服务器。 特点: 当后端服务器新增或下线时,只有少量请求会被重新分配(哈希环扰动小),适合缓存服务(如 Redis 集群)的负载均衡。 可结合权重调整服务器在哈希环上的 “节点数量”(权重越高,节点越多,分配的请求越多)。 适用场景:分布式缓存、分布式存储等需要减少服务器变动影响的场景。 配置示例(需安装 nginx-upstream-consistent-hash 模块): nginx upstream backend { consistent_hash $request_uri; # 基于请求URI计算哈希 server 192.168.1.101 weight=3; server 192.168.1.102 weight=2; }哈希键可自定义(如 $request_uri 基于请求路径,$remote_addr 基于客户端 IP)。 三、算法选择建议 场景需求 推荐算法 理由 服务器性能一致,无特殊需求 轮询(默认) 简单高效,分发均匀。 服务器性能差异大 加权轮询 按权重分配请求,性能强的服务器承担更多负载。 需要会话保持(如登录状态) IP 哈希 同一客户端请求固定到一台服务器,避免会话丢失。 请求处理时间差异大 最少连接 动态分配请求到空闲服务器,避免某台服务器过载。 缓存服务(如 Redis 集群) 一致性哈希 服务器上下线时,减少缓存失效范围,降低服务波动。 关注响应速度优化 fair 算法 优先分配给响应快的服务器,提升整体用户体验(需额外模块支持)。四、总结 Nginx 负载均衡算法覆盖了从简单到复杂的场景,核心是通过 upstream 模块配置,结合 server 指令的 weight等参数调整行为。实际使用中,需根据后端服务器特性、业务对会话性能的要求,选择最合适的算法,必要时可通过第三方模块扩展功能。
2026年02月03日
3 阅读
0 评论
0 点赞
2026-02-03
LinuxI/O 多路复用
select、poll、epoll 是 Linux 系统中用于实现 I/O 多路复用的机制,它们的主要区别如下:数据结构与最大连接数select使用固定长度的位掩码(bitmap)表示文件描述符(FD)集合,默认最大支持 1024 个 FD(由 FD_SETSIZE 限制)。 缺点:FD 数量受限,需手动管理位掩码,效率低。poll使用 pollfd 数组存储 FD 信息,理论上无最大连接数限制(仅受系统资源限制)。 优点:突破了 select 的 FD 数量限制。epoll使用内核事件表(红黑树)管理 FD,最大连接数取决于系统内存(如百万级)。 优点:数据结构更高效,适合处理大量连接。事件通知机制select/poll采用轮询方式:每次调用需遍历所有 FD,检查是否有事件发生。 时间复杂度:O (n),连接数越多性能越差。epoll采用事件驱动机制:内核直接通知哪些 FD 就绪,无需轮询。 时间复杂度:O (1),性能不随 FD 数量增加而下降。内存拷贝与内核开销select/poll每次调用需将 FD 集合从用户空间拷贝到内核空间,开销较大。epoll使用 epoll_ctl() 注册 FD 到内核事件表,仅需一次拷贝。后续只需在用户空间和内核空间之间传递 就绪事件列表,效率更高。应用场景select适合连接数少且固定的场景(如早期 UNIX 系统)。poll适合中等数量连接的场景(突破了 select 的限制)。epoll适合大量连接且活跃连接较少的场景(如高性能服务器、Nginx、Redis 等)。 accept_mutex on:是 Nginx 配置中的一个关键指令,用于控制多个 worker 进程如何处理新连接的负载均衡。负载均衡:当多个 Nginx worker 进程监听同一个端口时,accept_mutex 会使这些进程竞争一个全局锁(互斥锁) 每次仅允许一个 worker 进程接受新连接。 避免 “惊群效应”:若没有这个锁,当新连接到达时,所有 worker 进程都会被唤醒(即 “惊群”),但只有一个 进程能成功处理连接,其他进程会空转,浪费 CPU 资源。multi_accept on:是 Nginx 配置中的一个指令,用于控制 worker 进程如何处理新连接。批量接受连接:当一个 worker 进程通过 accept() 系统调用获取到新连接时,若 multi_accept on启用, 该进程会一次性接受所有已就绪的连接,而不是只接受一个。 减少上下文切换:默认情况下(multi_accept off),Nginx 每个事件周期仅接受一个连接,可能导致频繁的 上下文切换。启用后可减少这种开销。 ab -c 1000 -n 10000 http://127.0.0.1/-c 1000:并发数(Concurrency),即同时发起 1000 个请求。-n 10000:总请求数(Number),即总共发送 10000 个请求。worker_rlimit_nofile:用于调整 worker 进程的最大文件描述符数量。在高并发场景下,合理设置该参数 可避免 “Too many open files” 错误,提升系统稳定性。 Linux 系统默认每个进程最多可打开 1024 个文件描述符(包括网络连接、文件等),高并发时可能不足。 通过 worker_rlimit_nofile 可直接为 Nginx worker 进程设置更高的限制,无需修改系统全局配置 (如 /etc/security/limits.conf)。 server_tokens off;取消在客户端显示具体的nginx版本号(作用在server空间内)
2026年02月03日
2 阅读
0 评论
0 点赞
2026-02-03
软链接文件和硬链接文件的区别
1.当原文件发生修改时,软链接文件和硬链接文件内容都会发生修改 2.当软连接文件和硬链接文件发生修改时,原文件也会发生修改 3.当软链接文件和硬链接文件被删除时,原文件不受影响 4.当原文件删除时,软链接失效,硬链接文件正常使用 5.软链接文件可以跨分区跨文件系统创建,硬链接文件不可以 6.硬链接文件不会分配独立的inode,软链接文件会分配独立的inode验证跨分区文件系统创建软链接文件和硬链接文件[root@localhost mnt]# df -ThFilesystem Type Size Used Avail Use% Mounted on/dev/nvme0n2p1 ext4 974M 587M 321M 65% /mnt/mountpoint/dev/nvme0n2p2 ext4 974M 24K 907M 1% /mnt/mountpoint2[root@localhost mnt]# touch /mnt/mountpoint/testfile[root@localhost mnt]# ln -s /mnt/mountpoint/testfile /mnt/mountpoint2/softfile[root@localhost mnt]# ln /mnt/mountpoint/testfile /mnt/mountpoint2/hardfileln: failed to create hard link '/mnt/mountpoint2/hardfile' => '/mnt/mountpoint/testfile': Invalid cross-device link
2026年02月03日
1 阅读
0 评论
0 点赞
1
2
3
4