谷粒商城-nginx搭建域名访问环境性能压测

news2024/11/25 3:27:34

nginx搭建域名访问环境

正向代理与反向代理

正向代理:客户端向代理服务器发请求并指定目标服务器,代理向目标服务器转交请求并将获得的内容返回给客户端。
反向代理:用户直接访问反向代理服务器就可以获得目标服务器的资源。反向代理服务器统一了访问入口。反向代理是对外界屏蔽了很多内部的信息

需求

访问“gulimall.com”,Nginx反向代理到网关地址“http://localhost:88/#”,展示商品页面

大致流程

在这里插入图片描述

配置反向代理-使得访问gulimall时访问nginx

windows域名解析会先找C:\Windows\System32\drivers\etc下的hosts文件,然后才找dns服务器
当我们在浏览器输入gulimall.com的时候,就会去找我们的虚拟机,此时虚拟机中的nginx是运行的话,就可以访问到nginx,因为nginx监听的是80端口

192.168.56.10	gulimall.com
方法一 直接使用nginx反向代理 使所有gulimall.com都转到首页

配置nginx.conf的主要内容
在这里插入图片描述
配置/etc/nginx/conf.d/gulimall.conf
监听gulimall.com域名 将其定位到首页
在这里插入图片描述

使用nginx将请求反向代理到网关

配置nginx.conf
在http中配置上由服务器 实现nginx负载均衡

upstream gulimall{        #配置上游服务器,起名为gulimall
      server 192.168.56.1:88;    #配置上游服务器为网关地址
    }
 
include /etc/nginx/conf.d/*.conf;    #该路径下的配置文件会全部合并到这里

修改/etc/nginx/conf.d/gulimall.conf

location / {    #配置请求的路由
       proxy_pass http://gulimall;    #因为主配置文件配置了上游服务器为网关地址,所以可以请求路由到=
    }

网关配置

- id: gulimall_host_route
          uri: lb://gulimall-product
          predicates:
            - Host=**.gulimall.com

踩坑:
nginx正确处理转发api请求到网关 但是主页访问失败
原因:nginx转发请求给网关时会丢失掉请求的host信息
解决方法:配置请求头

proxy_set_header Host $host;

压力测试

压力测试考察当前软硬件环境下系统所能承受的最大负荷并帮助找出系统瓶颈所在。使用压力测试, 我们有希望找到很多种用其他测试方法更难发现的错误。 有两种错误类型是:内存泄漏, 并发与同步问题。
内存泄漏:内存泄漏(Memory Leak)是指程序中已动态分配的堆内存由于某种原因程序未释放或无法释放,造成系统内存的浪费,导致程序运行速度减慢甚至系统崩溃等严重后果。
并发与同步:有效的压力测试系统将应用以下这些关键条件:重复, 并发, 量级, 随机变化

压力测试的性能指标

响应时间:响应时间指用户从客户端发起一个请求开始,到客户端接收到从服务器端返回的响应结束,整个过程所耗费的时间。响应时间越少越好。
HPS(Hits Per Second):每秒点击次数,单位是次/秒。
TPS(Transaction per Second):系统每秒处理交易数,单位是笔/秒。
Qps(Query per Second):系统每秒处理查询次数,单位是次/秒。
一般情况下用 TPS来衡量整个业务流程,用QPS来衡量接口查询次数,用HPS来表示对服务器单击请求。
无论TPS、QPS、HPS,此指标是衡量系统处理能力非常重要的指标,越大越好,根据经验,一般情况下:
金融行业:1000TPS~5000OTPS,不包括互联网化的活动
保险行业:100TPS~10000OTPS,不包括互联网化的活动
制造行业:10TPS~5000TPS
互联网电子商务:1000OTPS~1000000TPS
互联网中型网站:1000TPS~50000TPS
互联网小型网站:500TPS~10000TPS
最大响应时间(MaxResponse Time)指用户发出请求或者指令到系统做出反应(响应)的最大时间。
最少响应时间(Mininum ResponseTime)指用户发出请求或者指令到系统做出反应(响应)的最少时间。
90%响应时间(90%Response Time)是指所有用户的响应时间进行排序,第90%的响应时间

JMeter 压测示例

添加线程组 :右键“test plan” 添加

线程组参数详解:
线程数: 虚拟用户数。 一个虚拟用户占用一个进程或线程。 设置多少虚拟用户数在这里也就是设置多少个线程数。
Ramp-Up时间: 200个线程需要多少秒内全部启动完成。 如果线程数为 10, 准备时长为 2, 那么需要 2 秒钟启动 10 个线程, 也就是每秒钟启动 5 个线程。
循环次数: 每个线程发送请求的次数。勾选“永远”会一直压力测试下去。 如果线程数为 10, 循环次数为 100, 那么每个线程发送 100 次请求。 总请求数为 10*100=1000 。 如果勾选了“永远”, 那么所有线程会一直发送请求, 一到选择停止运行脚本。
Delay Thread creation until needed: 直到需要时延迟线程的创建。
调度器: 设置线程组启动的开始时间和结束时间(配置调度器时, 需要勾选循环次数为永远)
持续时间(秒) : 测试持续时间, 会覆盖结束时间
启动延迟(秒) : 测试延迟启动时间, 会覆盖启动时间
启动时间: 测试启动时间, 启动延迟会覆盖它。 当启动时间已过, 手动只需测试时当前时间也会覆盖它。
结束时间: 测试结束时间, 持续时间会覆盖它。
在结果树和汇总报告中查看请求结果

添加 HTTP 请求

在这里插入图片描述

本机压测错误解决JMeter Address Already in use

出现原因
windows 本身提供的端口访问机制的问题。
Windows 提供给 TCP/IP 链接的端口为 1024-5000, 并且要四分钟来循环回收他们。 就导致我们在短时间内跑大量的请求时将端口占满了。
解决思路
扩大提供给 TCP/IP 链接的端口
缩短循环回收时间
通过修改windows配置文件解决

性能监控

概念讲解

影响性能考虑点包括:数据库、 应用程序、 中间件(tomact、 Nginx) 、 网络和操作系统等方面
首先考虑自己的应用属于 CPU 密集型(以空间换时间 大量计算数据)还是 IO 密集型(以时间换空间 大量读取数据)
JVM内存模型
在这里插入图片描述
程序计数器 Program Counter Register:
记录的是正在执行的虚拟机字节码指令的地址,
此内存区域是唯一一个在JAVA虚拟机规范中没有规定任何OutOfMemoryError的区域
虚拟机栈: VM Stack
描述的是 JAVA 方法执行的内存模型, 每个方法在执行的时候都会创建一个栈帧,用于存储局部变量表, 操作数栈, 动态链接, 方法接口等信息
 局部变量表存储了编译期可知的各种基本数据类型、 对象引用
 线程请求的栈深度不够会报 StackOverflowError 异常
 栈动态扩展的容量不够会报 OutOfMemoryError 异常
 虚拟机栈是线程隔离的, 即每个线程都有自己独立的虚拟机栈
本地方法: Native Stack
本地方法栈类似于虚拟机栈, 只不过本地方法栈使用的是本地方法
堆: Heap
几乎所有的对象实例都在堆上分配内存
Java源文件编译成.class字节码文件 ,.class字节码文件被JVM的类装载器装载到JVM里,所有数据都在“运行时数据区”。性能优化主要是优化“运行时数据区”中的“堆”。
在这里插入图片描述
Java垃圾清理主要在堆区,元数据区直接操控物理内存

所有的对象实例以及数组都在堆上分配。 堆是垃圾收集器管理的主要区域, 也被称为“GC堆” ,也是我们优化最多考虑的地方。
新生代
Eden 空间
From Survivor 空间
To Survivor 空间
老年代
永久代/元空间
Java8 以前永久代, 受 jvm 管理, java8 以后元空间, 直接使用物理内存。 因此,默认情况下, 元空间的大小仅受本地内存限制。
创建对象放到堆内存的流程:
1.首先,任何新对象都分配到 eden 空间。两个幸存者空间开始时都是空的。
2.当 eden 空间填满时,将触发一个Minor GC(年轻代的垃圾回收),删除所有未引用的对象,大对象(需要大量连续内存空间的Java对象,如那种很长的字符串)直接进入老年代。
3.所有被引用的对象作为存活对象,将移动到第一个幸存者空间S0,并标记年龄为1,即经历过一次Minor GC。之后每经过一次Minor GC,年龄+1。
4.当 eden 空间再次被填满时,会执行第二次Minor GC,将Eden和S0区中所有垃圾对象清除,并将存活对象复制到S1并年龄加1,此时S0变为空。
5.如此反复在S0和S1之间切换几次之后,还存活的年龄等于15的对象在下一次Minor GC时将放到老年代中。
6.当老年代满了时会触发FullGC(全GC),Full GC 清理整个堆 – 包括年轻代和老年代。
7.Major GC是老年代的垃圾回收,经常会伴随至少一次Minor GC,比Minor GC慢10倍以上

Minor GC:清理年轻代空间(包括 Eden 和 Survivor 区域),释放在Eden中所有不活跃的对象,释放后若Eden空间仍然不足以放入新对象,则试图将部分Eden中活跃对象放入Survivor区。
Survivor区:Survivor区被用来作为Eden及老年代的中间交换区域,当老年代空间足够时,Survivor区的对象会被移到老年代,否则会被保留在Survivor区。
Major GC:清理老年代空间,当老年代空间不够时,JVM会在老年代进行major gc。
Full GC:清理整个堆空间,包括年轻代和老年代空间。Full GC比Minor GC慢十倍,应该尽量避免。
在这里插入图片描述
详细流程图
在这里插入图片描述

使用 jvisualvm监控本地和远程应用

Jdk 的两个小工具 jconsole、 jvisualvm(升级版的 jconsole) ;通过命令行启动, 可监控本地和远程应用。 远程应用需要配置
这里使用jvisualvm
1)监控线程状态
在这里插入图片描述
线程状态:
运行: 正在运行的
休眠: sleep
等待: wait
驻留: 线程池里面的空闲线程
监视: 阻塞的线程, 正在等待锁
2)安装Visual GC插件监控GC状态
在这里插入图片描述

监控指标

GC

在这里插入图片描述
当前正在运行的线程数不能超过设定的最大值。 一般情况下系统性能较好的情况下, 线程数最小值设置 50 和最大值设置 200 比较合适。
当前运行的 JDBC 连接数不能超过设定的最大值。 一般情况下系统性能较好的情况下,JDBC 最小值设置 50 和最大值设置 200 比较合适。
GC频率不能频繁, 特别是 FULL GC 更不能频繁, 一般情况下系统性能较好的情况下,JVM 最小堆大小和最大堆大小分别设置 1024M 比较合适。

数据库

在这里插入图片描述

SQL 耗时越小越好, 一般情况下微秒级别。
命中率越高越好, 一般情况下不能低于 95%。
锁等待次数越低越好, 等待时间越短越好

压测与优化

压测

压测nginx

docker stats查看nginx的运行状况,比如CPU、内存占有率、IO情况等
JMeter 压力测试:
设置虚拟机地址以及nginx端口监控nginx
在这里插入图片描述
得出结论nginx比较浪费CPU

压测网关

JMeter添加请求后运行:
在这里插入图片描述
这里是服务器本机地址和端口88
查看jvisualvm 发现网关对CPU的占用率同样比较高

简单服务
@ResponseBody
    @GetMapping("/hello")
    public String hello() {
        return "hello";
    }

检测结果

压测内容压测线程数吞吐量/s90%响应时间99%响应时间
Nginx50233511944
Gateway5010367831
简单服务5011341817
Gateway+简单服务

两者结合之后吞吐量下降
检测结果

压测内容压测线程数吞吐量/s90%响应时间99%响应时间
Gateway+简单服务50312430125
中间件越多,性能损失越大,大多损失在网络交互
全链路(nginx+GateWay+简单服务)
压测内容压测线程数吞吐量/s90%响应时间99%响应时间
Gateway+简单服务50312430125
全链路5080088310
压测首页一级菜单
压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页一级菜单渲染50270(慢的原因:db,thymeleaf)267365

分析得出慢的原因可能是数据库和thymeleaf渲染

压测三级分类
压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页一级菜单渲染50270(慢的原因:db,thymeleaf)267365
三级分类数据获取502(db)

慢的原因是数据库

压测全量网页(包括静态资源)
压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页一级菜单渲染50270(慢的原因:db,thymeleaf)267365
三级分类数据获取502(db)
首页全量数据获取507(静态资源)

慢的原因是静态资源

优化方向

1.数据库
2.thymeleaf渲染
3.静态资源

首页一级菜单优化

1)开启thymeleaf缓存

压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页一级菜单渲染50270(慢的原因:db,thymeleaf)267365
首页渲染(开缓存)50290251365

性能有一定提升
2)优化数据库
①一级分类根据parent_id查询 维奇加上索引

压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页一级菜单渲染50270(慢的原因:db,thymeleaf)267365
首页渲染(开缓存)50290251365
首页渲染(开缓存、 优化数据库)50700105183
全量数据获取优化
Nginx动静分离

在这里插入图片描述
为什么要动静分离
未分离的项目静态资源放在后端,无论是动态请求还是静态请求都会来到后台,这极大的损耗了后台Tomcat性能(大部分性能都用来处理静态请求)
动静分离后,后台只会处理动态请求,而静态资源直接由nginx返回。
具体步骤
在这里插入图片描述
1.静态资源存到Nginx里
1)在nginx的html目录下新建一个static目录用来存放静态资源
2)将gulimall-product的静态资源复制到该目录,并将本地静态资源删除
3)templates里文件静态资源路径前“static”
4)在nginx配置静态资源的路径映射
进入配置文件

vim /mydata/nginx/conf/conf.d/gulimall.conf 

#监听gulimall.com:80/static
location /static {
    root  /usr/share/nginx/html;       #资源在这个文件夹下匹配
}

优化结果

压测内容压测线程数吞吐量/s90%响应时间99%响应时间
首页全量数据获取507(静态资源)
首页全量数据获取5011

发现老年代GC问题
解决方法
调大堆内存
-Xmx1024m -Xms1024m -Xmn512m
-Xms :初始堆大小
-Xmx :最大堆大小
-Xmn :堆中新生代初始及最大大小

三级分类数据获取优化

每次遍历一级分类列表里的元素,都要查一次数据库
解决方法1:将数据库的多次查询变为一次
将查询的分类结果放入list,以后每次在list中获取即可

private List<CategoryEntity> getParent_cid(List<CategoryEntity> selectList,Long parentCid) {
        List<CategoryEntity> categoryEntities = selectList.stream().filter(item -> item.getParentCid().equals(parentCid)).collect(Collectors.toList());
        return categoryEntities;
    }
压测内容压测线程数吞吐量/s90%响应时间99%响应时间
三级分类数据获取502(db)
三级分类数据获取50111571896

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1465412.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

基于EasyCVR视频汇聚系统的公安网视频联网共享视频云平台建设思路分析(二)

一、需求分析 随着科技的飞速发展&#xff0c;视频监控联网技术在公安工作中发挥着越来越重要的作用。为了提高公安部门对各类事件的响应速度和处理能力&#xff0c;建设一个高效、稳定的公安视频联网共享云平台显得尤为重要。通过建设开放的视频联网共享云平台&#xff0c;实…

Android相机调用-libusbCamera【外接摄像头】【USB摄像头】 【多摄像头预览】

有的自定义系统&#xff0c;对于自己外接的USB摄像头&#xff0c;android原生的camera和camera2都无法打开&#xff0c;CameraX也用不了。这时候就要用libusbCamera&#xff0c;这个库可以打开摄像头&#xff0c;还可以多摄像头同时预览。本文主要是同时打开3个USB摄像头的项目…

C语言第二十九弹---浮点数在内存中的存储

✨个人主页&#xff1a; 熬夜学编程的小林 &#x1f497;系列专栏&#xff1a; 【C语言详解】 【数据结构详解】 目录 1、浮点数在内存中的存储 1.1、练习 1.2、浮点数怎么转化为二进制 1.3、浮点数的存储 1.3.1、浮点数存的过程 1.3.2、浮点数取的过程 1.3、题目解析…

配置开机自启

进入任务计划程序 点击创建基本任务&#xff0c;按照向导一步一步进行下去

【数据结构】排序(1)

目录 一、概念&#xff1a; 二、直接插入排序&#xff1a; 三、希尔排序&#xff1a; 四、直接选择排序&#xff1a; 五、堆排序&#xff1a; 六、冒泡排序&#xff1a; 一、概念&#xff1a; 排序的概念&#xff1a; 使一串记录&#xff0c;按照其中的某个或某些关键字…

阿里巴巴店铺宝藏全揭秘:一键获取所有商品信息,电商业务效率飙升

阿里巴巴店铺所有商品API接口技术全解析 一、引言 在阿里巴巴这个全球领先的电商平台上&#xff0c;店铺所有商品API接口&#xff08;item_search_shop&#xff09;为开发者提供了一个便捷的途径&#xff0c;能够获取店铺的所有商品信息。通过这一接口&#xff0c;无论是数据…

PostgreSQL教程(十一):SQL语言(四)之数据类型

一、数值类型 数值类型由 2 字节、4 字节或 8 字节的整数以及 4 字节或 8 字节的浮点数和可选精度的十进制数组成。 下表列出了所有可用类型。 数值类型 名字存储长度描述范围smallint2 字节小范围整数-32768 到 32767integer4 字节常用的整数-2147483648 到 2147483647bigi…

【无标题】旋转链表与力扣报错:member access within null pointer of type ‘struct ListNode‘

项目场景&#xff1a; 做单链表反转题目&#xff0c;报错&#xff1a;member access within null pointer of type ‘struct ListNode’ 题目链接:LINK 问题描述 我明明在初始化指针时候&#xff0c;已经处理了n2->next情况却依然报错 这个报错提示含义是&#xff1a;大概就…

HTTPS(超文本传输安全协议)被恶意请求该如何处理。

HTTPS&#xff08;超文本传输安全协议&#xff09;端口攻击通常是指SSL握手中的一些攻击方式&#xff0c;比如SSL握手协商过程中的暴力破解、中间人攻击和SSL剥离攻击等。 攻击原理 攻击者控制受害者发送大量请求&#xff0c;利用压缩算法的机制猜测请求中的关键信息&#xf…

每天一个知识点 - 如何快速熟悉后端项目

入职一家新公司的时候&#xff0c;不可避免的就是接触到新公司的项目&#xff0c;有些项目一启动就是好几年&#xff0c;业务功能极其复杂&#xff0c;下面我总结几个方法让大家快速熟悉后端项目&#xff08;图文结合&#xff09; 用例图简析 用例是系统中的一个功能单元&…

顶级性能更有AI助力 RTX AI轻薄本竟强大如斯?华硕无畏Pro15 2024体验

不知觉&#xff0c;2024龙年腾飞之年俨然到来。回望这过去的一年里&#xff0c;我们的生活发生了很多变化&#x1f3ee; 有对身体健康的焦虑&#xff0c;也有对事业发展的迷茫&#xff0c;也时常回过头来反思自己在过去的一年里都有哪些不足、希冀在新的一年里努力改进自己&am…

Windows环境下查看磁盘层级占用空间的解决方案

大家好,我是爱编程的喵喵。双985硕士毕业,现担任全栈工程师一职,热衷于将数据思维应用到工作与生活中。从事机器学习以及相关的前后端开发工作。曾在阿里云、科大讯飞、CCF等比赛获得多次Top名次。现为CSDN博客专家、人工智能领域优质创作者。喜欢通过博客创作的方式对所学的…

Unity之ShaderGraph如何实现水面波浪

前言 这几天通过一个水的波浪数学公式,实现了一个波浪效果,感觉成就感满满,下面给大家分享一下 首先先给大家看一下公式; 把公式转为ShaderGraph 第一行公式:waveType = z*-1*Mathf.Cos(wave.WaveAngle/360*2*Mathf.PI)+x*Mathf.Sin(WaveAngle/360*-2*Mathf.PI) 转换…

基于JAVA的公司货物订单管理系统 开源项目

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、功能模块2.1 客户管理模块2.2 商品维护模块2.3 供应商管理模块2.4 订单管理模块 三、系统展示四、核心代码4.1 查询供应商信息4.2 新增商品信息4.3 查询客户信息4.4 新增订单信息4.5 添加跟进子订单 五、免责说明 一、摘要 1.1 项目…

端口占用:Web server failed to start. Port XXX was already in use.原因分析-解决方案

一、windows 1.Web server failed to start. Port XXX was already in use出错原因分析 端口被占用了&#xff0c;我们只需要换一个端口就可以了&#xff0c;如果就想要用特定的端口&#xff0c;我们需要使用下面的命令&#xff0c;先找到对应端口号的进程号&#xff0c;然后结…

【QT-lineEidte动画效果

QT-lineEidte动画效果 一、演示效果二、核心代码三、下载链接 一、演示效果 二、核心代码 #ifndef DynamicUnderlineLineEdit_H #define DynamicUnderlineLineEdit_H#include <QWidget> #include <QLineEdit> #include <QPainter> #include <QPaintEvent…

产品渲染3D效果图一张多少钱,哪个平台更有性价比?

产品渲染3D效果图的价格受到多方面因素的影响&#xff0c;包括但不限于产品类型、渲染难度以及输出尺寸等。如果效果图需要后期处理&#xff0c;还有可能增加其他费用。接下来&#xff0c;我们来了解一下产品渲染效果图的费用情况。 1.产品渲染3D效果图一张多少钱&#xff1f; …

最长的回文串

开始想的简单了&#xff0c;确实没想到奇数字母删去一个后也能用 解法&#xff1a; 桶排序 #include<iostream> #include<vector> #include<algorithm> using namespace std; #define endl \n #define int long long signed main() {int t;cin >> t…

【C++11】lambda表达式 | 函数包装器

文章目录 一、lambda表达式1. 为什么需要lambda表达式2. lambda的定义3. lambda的语法捕捉列表 4. 函数对象和lambda表达式的底层原理 二、函数包装器1. function包装器2. bind包装器用bind包装器绑定固定参数用bind包装器调整传参顺序无意义的绑定 3. bind包装器的意义 一、la…

【Spring】Spring MVC

目 录 一.什么是 Spring MVC&#xff1f;1.MVC 定义2.MVC 和 Spring MVC 的关系 二.为什么要学 Spring MVC&#xff1f;三.怎么学 Spring MVC&#xff1f;1.Spring MVC 创建和连接综上连接方式&#xff1a; 2.获取参数1.传递单个参数2.获取多个参数3.获取对象4.获取表单参数5.接…