什么是分布式?
将一个大的系统划分为多个业务模块,业务模块分别部署到不同的机器上,各个业务模块之间通过接口进行数据交互。区别分布式的方式是根据不同机器不同业务。
微服务的设计是为了不因为某个模块的升级和BUG影响现有的系统业务。
微服务与分布式的细微差别是,微服务的应用不一定是分散在多个服务器上,可以是同一个服务器。
分布式和微服的架构很相似,只是部署的方式不一样而已,分布式属于微服务。
1、Maven:
1、maven的三种打包方式及区别?
maven package:打包到本项目,一般是在项目target目录下。如果a项目依赖于b项目,打包b项目时,只会打包到b项目下target下,
编译a项目时就会报错。
maven install:打包到本地仓库,如果没有设置过maven本地仓库,一般在用户/.m2目录下。如果a项目依赖于b项目,那么install b时,
会在本地仓库同时生成pom文件和jar文件,可以看install b
maven deploy:打包上传到远程仓库,如:私服nexus等,需要配置pom文件
9、Redis:
1、Redis的使用?
使用方法:在service模块的pom中引入jedis依赖,常见JedisClient接口,定义set、get、hget、expire、ttl等方法,创建JedisClientCluster类实现接口,
并重写里面的方法,创建JedisClientPool类,实现接口,并重写里面的方法。
Key命令:
Expire:设置过期时间、TTL:查看key的过期时间、Persist:清除key的过期时间。
Redis持久化方案:
Rdb:保存到磁盘中;AOF:把数据库操作命令保存到文件中,数据库恢复时把命令重新执行一遍。
Redis集群:
集群没有入口,连接任意一个即可。
集群的容错机制:发送ping命令,超过半数就认为挂掉。
redis集群中至少需要三台服务器来保证高可用,三个备用服务器,至少需要6台服务器,需要使用ruby脚本搭建集群。
注意:单机版和集群版不能共存,使用单机版时注释集群版的配置。使用集群版,把单机版注释。
2、redis分布式锁
业务场景是要求同一个用户针对同一类借款,只可以存在一笔待还借款。
第三方平台每次都会在同一时间发送多次相同的借款请求。
使用redis锁控制用户借款串行执行。
3、redis存储的数据类型有哪些?
String、List、Set、Hash、SortedSet。
4、Redis的使用场景?
1、活动倒计时方案
1、活动开始的时间是固定的。
2、使用SELECT NOW();取出当前时间并作为基准时间
3、拿活动开始时间-基准时间可以计算出一个秒为单位的数值,并作为活动过期时间。
4、在redis中设置一个key(活动开始标识)。使用expire命令将第三步计算出来的时间设置为key的过期时间。
5、使用redis中的Ttl命令取出key的剩余生存时间,在前台展示活动剩余的时间。
2、秒杀方案
1、把商品的数量放到redis中。
2、秒杀时使用redis中的decr命令对商品数量减一。如果不是负数说明抢到。
3、一旦返回数值变为0说明商品已售完。
10、Kafka :
1、Kafka的简单概述
Kafka是一个分布式发布-订阅消息传递系统。
producer:消息生产者,发布消息到kafka集群的终端或服务。
consumer:从 kafka 集群中消费消息的终端或服务。
topic:每条发布到 kafka 集群的消息都属于topic类别,即 kafka 是面向 topic 的。
生产者将输入写入到主题topic,而消费者则从主题topic中读取写入的数据。因为卡夫卡是一个分布式系统,所以topic主题会实现跨多个节点
分区和复制。
Activemq:
在service层的pom中导入activemq-all的jar包,在商品添加完成后把商品的id发送一个mq消息。
11、Dubbo :
实现不同系统之间的调用。(要实现商品列表查询需要两个系统之间进行通信)
缺点:只能是java与java项目之间调用
Provider、Consumer、Registry、Monitor、Container
使用方法:在service层的pom中引入dubbo、zookeeper和zkclient依赖,同时要排除netty的依赖,避免jar包冲突,在spring配置文件中配置约束、
注册中心端口号、地址,并在20880端口上暴露服务,然后发布dubbo服务。
在web层的pom中引入相同的依赖,在spring配置文件中引入约束、注册中心端口号、地址,并引用dubbo服务。
在spring配置文件中配置注册中心的地址、需要暴露服务端口号,
默认20880,发布服务。
服务Provider启动时首先初始化一个Spring容器,然后向注册中心
发送注册服务,消费者从注册中心拿去提供者的服务,监控中心监控
提供者和消费者的关系。
注册中心就如同房产中介,使用Zookeeper作为注册中心,也可以使用redis,
,可执行文件前面都带x,由于要快照存储,需要修改zoo.cfg配置文件,
./+文件名 start启动Zookeeper,status/stop查看启动模式。
在service模块中发布服务,在接口模块中调用服务,引入dubbo依赖时,spring和netty的依赖会产生冲突
要在pom中添加exclusions排除标签。
32位的虚拟机要装32位的软件。
在pom文件中添加模块的依赖就可以引用模块里面的接口了。
解压:tar zxxf + 文件名
包扫描器扫描到包时会创建一个bean,bean的id是类名首字母小写。
16、Nginx
nginx:是一个http(web)服务器;就是只能运行html、css、js
tomcat:http服务器+servlet服务器;可以运行html、css、js、java
tomcat虽然能提供http服务,但性能达不到高并发要求。并发请求超过1000相应速度就会下降
nginx+多个tomcat实现高并发的性能
Nginx反向代理配置:
Nginx是一款高性能的http服务器/反向代理服务器及电子邮件代理服务器。
应用场景:
1、http服务器,可以做网页静态服务器。
2、虚拟主机,一台服务器虚拟多个网站,启动多个网站,配置多个server。
3、反向代理,负载均衡,反向代理搭建多台服务器集群。
通过域名去访问指定的IP地址,使用SwitchHost修改配置信息和Nginx配置文件。
通过后面的域名去访问前面的ip地址。
在nginx.conf进行配置:
server { listen 81; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { root html81; index index.html index.htm; } } server { listen 80; server_name www.souhu.com; #charset koi8-r; #access_log logs/host.access.log main; location / { root html-souhu; index index.html index.htm; } } server { listen 80; server_name www.163.com; #charset koi8-r; #access_log logs/host.access.log main; location / { root html-163; index index.html index.htm; } }
通过http://192.168.25.128:81/访问html81下的index文件
C:\Windows\System32\drivers\etc\hosts
vim html-souhu/index.html
sbin/nginx -s reload
复制文件夹:cp -r html/ html81
192.168.25.128 www.souhu.com
192.168.25.128 www.163.com
17、SSO系统:
SSO是在多个应用系统中,用户只需要登录一次就可以访问所有相互信任的应用系统,注册和登录都是一个单独的系统。
传统登陆模式:
判断用户是否登录:判断session中是否有用户信息,通常使用拦截器来处理。
集群:多台服务器提供相同服务;
建立集群:Session复制,
集群中的节点最多不能超过5个,并发量多了要采用分布式;
Session服务器:Session的统一管理
单点登录主要解决了Session共享的问题;
认证:检查数据是否可用
传递参数(用户名,手机号,邮箱唯一),类型(1/2/3)
如果数据库中存在该数据,该注册数据不可用,不存在的话该数据可以使用。
/{param}/{type}:URL传参,后台接收要用@PathVariable注解。
注册:先验证用户名、手机号和邮箱是否为空,然后认证用户信息是否重复,之后对密码进行Bcrypt加密,之后插入数据。
登录:先校验用户名是否存在,再校验密码是否正确,然后使用UUID生成token,把密码清空,将token作为key,用户信息作为value放入到redis中并
设置Sessio的有效时间,然后将token放入到cookie中。
再次登录:先从Cookie中取token,调用接口通过token去redis中查询是否存在用户信息,查不到说明用户登录已经过期返回登录页面,存在重新设置
过期时间,返回用户已经登录然后进入到首页。
安全退出:通过token去删除redis中的用户信息,并把过期时间设置为0.
解决js的跨域问题可以使用jsonp。
JsonUtils.objectToJson():对象转JSON
JsonUtils.jsonToPojo():JSON转对象
18、Freemarker:静态模板页面:
使用方法:引入freemarker依赖,然后将模板和Java对象整合到一个html页面。
获取Configuration对象,设置版本号、模板文件路径、编码格式,然后将对象写入到一个静态页面,设置存放路径。
语法 :${key}:取值、</#list>:遍历、</#if>:判断、<#include “”>:包含,类似于JSTL中的语法。
redis中存放的value值是json数据,需要转化为对象之后才能使用。
在页面点击商品图片或标题展示商品详情页面:通过商品id去查询商品信息和商品详情信息。
通过商品id去redis中查询数据,查询不到再去数据库中查询数据,然后放入redis中,设置过期时间为一天。
生成静态页面的时机:商品添加后,生成静态页面。可以使用Activemq,订阅topic(商品添加)
网页访问:使用nginx访问网页。在此方案下tomcat只有一个作用就是生成静态页面。
为了提高redis的高可用,使用定时任务把不常访问的商品从redis缓存中清除。
Freemaker生成静态页面的时机:添加商品后使用activemq广播消息,freemaker监听到消息去数据库查询商品生成静态页面
传统项目是一个工程部署到一个Tomcat上,300-400并发访问量后性能就会降低,当并发量达到1000时要考虑解决问题的方法,可以使用Nginx提供负载均衡,
把请求分配给Tomcat集群,当用户登录后把信息写入Session中,Tomcat中的广播机制可以实现Session共享问题,当并发量达到10000时,由于Tomcat要去进行
Session复制,所以没有时间再去解决用户的请求,需要按照功能点把系统拆分,拆分成独立的功能。然后根据每个模块的并发量大小再去进行集群的配置。
前台需要查询数据库,订单系统需要查询服务,这是可以把查询整理为一个服务,所以SOA架构被引入了,代码复用性提高了。
SOA架构:把项目分为表现层和服务层,表现层只用于展示页面,服务层只用于提供服务。
<dubbo:registry protocol=“zookeeper” address=“192.168.25.128:2181” /> tracker_server=192.168.25.133:22122 E:\图片\测试图片\500.jpg <dubbo:registry protocol=“zookeeper” address=“192.168.25.128:2181” /> <dubbo:protocol name=“dubbo” port=“20881” />
什么地方用到了页面静态化?
https://blog.csdn.net/yang_guang3/article/details/84309631
商品详情页面展示的时候;
语法:
</#list>:遍历数据,<#include>:引入其他页面,d a t e ? d a t e : 格 式 化 日 期 , {date?date}:格式化日期,date?date:格式化日期,{person} :获取数据,<#if > <#else>:判断语句;
如果要取一个不存在的值时,不能直接取,要取非${aaa! },利用if语句转入到else语句中。
用法:
1、引入freemarker相关依赖;2、编写xml配置文件(模板标签和模板文件存放路径);3、利用FreeMarkerConfigurer,Template生成模板文件。
Quartz的使用
商城中促销功能的实现
1.每天凌晨24点从mysql中查找明天过生日的用户的手机号码存入到redis中
2.每天早上7点从redis中读取手机号发促销短信