在服务层接口的开发中,有些接口可能调用频繁,负载过重。这时候需要引入负载均衡,降级。
目前若依把下面这些调用频繁的接口用@FeignClient封装,feign本身里面就包含有了ribbon负载均衡。
@GetMapping("dept/get/{deptId}")
public SysDept selectSysDeptByDeptId(@PathVariable("deptId") long deptId);
@PostMapping("operLog/save")
public void insertOperlog(@RequestBody SysOperLog operLog);
@PostMapping("logininfor/save")
public void insertLoginlog(@RequestBody SysLogininfor logininfor);
@GetMapping("menu/perms/{userId}")
public Set<String> selectPermsByUserId(@PathVariable("userId") Long userId);
@GetMapping("role/get/{roleId}")
public SysRole selectSysRoleByRoleId(@PathVariable("roleId") long roleId);
@GetMapping("user/get/{userId}")
public SysUser selectSysUserByUserId(@PathVariable("userId") long userId);
@GetMapping("user/find/{username}")
public SysUser selectSysUserByUsername(@PathVariable("username") String username);
@PostMapping("user/update/login")
public R updateUserLoginRecord(@RequestBody SysUser user);
/**
* 查询拥有当前角色的所有用户
* @param auditor
* @return
* @author zmr
*/
@GetMapping("user/hasRoles")
public Set<Long> selectUserIdsHasRoles(@RequestParam("roleIds") String roleIds);
/**
* 查询所有当前部门中的用户
*
* @param deptId
* @return
* @author zmr
*/
@GetMapping("user/inDepts")
public Set<Long> selectUserIdsInDepts(@RequestParam("deptIds") String deptIds);
服务熔断:一般是某个服务异常引起的,相当于“保险丝”,当某个异常条件被触发,直接熔断整个服务,不是等到此服务超时
服务降级:降级一般是从整体负荷考虑,当某个服务熔断之后,服务器将不再被调用,客户端可自己准备一个本地的fallback回调,返回一个缺省值,虽然服务水平下降,当能用,比直接挂掉要强
Hystrix会在以下四种情况下触发fallback函数:
1.非HystrixBadRequestException异常:当抛出HystrixBadRequestException时,调用程序可以捕获异常,此时不会触发fallback,而其他异常则会触发fallback,调用程序将获得fallback逻辑的返回结果。
2.run()/construct()运行超时:执行命令的方法超时,将会触发fallback。
3.熔断器开启:当熔断器处于开启的状态,将会触发fallback。
4.线程池拒绝:线程池拒绝指的是 HystrixCommand 所使用的线程池没有足够的线程执行本次调用。Hystrix 使用的线程池的队列大小默认为 -1,线程数量为10。此时,队列类型为 SynchronousQueue。当线程数不足时,任务会就被拒绝。这种情况也算是一种执行失败,所以也会出发 Fallback。
降级后的解决方法:
适当调大Hystrix线程队列参数
动态水平扩容服务
优化下游服务,减少服务响应时间
降级例子
public class RemoteDeptFallbackFactory implements FallbackFactory<RemoteDeptService>
{/* (non-Javadoc)
* @see feign.hystrix.FallbackFactory#create(java.lang.Throwable)
*/
@Override
public RemoteDeptService create(Throwable throwable)
{
log.error(throwable.getMessage());
return new RemoteDeptService()
{
@Override
public SysDept selectSysDeptByDeptId(long deptId)
{
return null;
}
};
}
}
二次开发,添加新页面
1.添加菜单
菜单管理添加菜单,并且让用户获取到菜单,如userList做menu_key
2.新增 vue 文件
在 src/views 下新建页面的vue文件,如果相关页面有多个,可以新建一个文件夹来放置相关文件。
3.将文件加入菜单和路由
这一步可能是在菜单配置里操作,那么在后台或者数据库操作也行,如果不想放在数据库,可以按下面的步骤
后端添加好菜单并确保能获取到你新加的路由,在src\utils\routerUtil.js中动态引入页面组件,如:
userList: () => import('@/views/system/UserList')
加好后,访问 http://localhost:8000/system/userList 就可以看到新增的页面了。
system是上级模块名称userList是当前模块名称,也就是数据库中的menu_key(唯一),根据children关系获得
4.新增 model (非必须)
布局及路由都配置好之后,回到之前新建的 newPage.vue,可以开始写业务代码了!如果需要用到 vuex 中的数据流,还需要在 src/store/model 中建立相应的 model。
5.书写业务接口
在已有微服务中添加接口或新建一个微服务(gateway中配置好映射),添加完成可以用postman(推荐)测试接口是否正常,在src/api中添加对应请求方法,参考system.js,在vue文件中导入