Apollo源码解析——创建App



一、概述

创建app流程

在这里插入图片描述

二、创建流程

1.页面操作

示例如下:

在这里插入图片描述

在这里插入图片描述

2.后台代码:

  1. AppController#apps方法

在接到请求后,首先将app对象转成model对象,然后写库,发布app创建的事件出去。

    public App create(@Valid @RequestBody AppModel appModel) {
        //将AppModel转成App对象
        App app = transformToApp(appModel);
        //保存App对象到数据库
        App createdApp = appService.createAppInLocal(app);
        //发布AppCreationEvent创建事件
        publisher.publishEvent(new AppCreationEvent(createdApp));
        //授予 App 管理员的角色
        Set<String> admins = appModel.getAdmins();
        if (!CollectionUtils.isEmpty(admins)) {
            rolePermissionService.assignRoleToUsers(RoleUtils.buildAppMasterRoleName(createdApp.getAppId()),
                            admins, userInfoHolder.getUser().getUserId());
        }
       //返回app对象
        return createdApp;
    }
  1. CreationListener#onAppCreationEvent

在上面创建完成后会广播出来一个事件,事件的消费者如下,这里就会发送http请求到Admin Server,对应adminservice服务中AppController#create

  @EventListener
  public void onAppCreationEvent(AppCreationEvent event) {
    // 将 APP 转成 AppDTO 对象
    AppDTO appDTO = BeanUtils.transform(AppDTO.class, event.getApp());
    // 获取有效的 Env 数组
    List<Env> envs = portalSettings.getActiveEnvs();
    //循环 Env 数组,调用对应的Admin Service 的 API , 创建App 对象
    for (Env env : envs) {
      try {
        appAPI.createApp(env, appDTO);
      } catch (Throwable e) {
        logger.error("Create app failed. appId = {}, env = {})", appDTO.getAppId(), env, e);
        Tracer.logError(String.format("Create app failed. appId = %s, env = %s", appDTO.getAppId(), env), e);
      }
    }
  }
  1. AppController#create
  @PostMapping("/apps")
  public AppDTO create(@Valid @RequestBody AppDTO dto) {
    App entity = BeanUtils.transform(App.class, dto);
    //如果appId已经存在,那重复了就抛出异常
    App managedEntity = appService.findOne(entity.getAppId());
    if (managedEntity != null) {
      throw new BadRequestException("app already exist.");
    }
   //保存 App 对象到数据
    entity = adminService.createNewApp(entity);
   //将保存的 App 对象,转换成 AppDTO 返回
    return BeanUtils.transform(AppDTO.class, entity);
  }
  1. AdminService#createNewApp

这里会创建默认的namespacecluster

  // 保存 App 对象到数据库
    String createBy = app.getDataChangeCreatedBy();
    App createdApp = appService.save(app);

    String appId = createdApp.getAppId();

    //创建 App 的默认命名空间 "application"
    appNamespaceService.createDefaultAppNamespace(appId, createBy);

    //创建 App 的默认集群 "default"
    clusterService.createDefaultCluster(appId, createBy);

    //创建 Cluster 的默认命名空间
    namespaceService.instanceOfAppNamespaces(appId, ConfigConsts.CLUSTER_NAME_DEFAULT, createBy);
  1. 在上面发现保存app的时候会涉及到跨系统的交互,因为要写到两个不同的DB,Patrol在同步App到Admin Server的时候,可能会存在app存在于patrol,不存在于admin service中,Apollo是怎么解决的?

这里参考这个:官方解答

会在页面上会出现『补缺环境』和『补缺namespace』按钮,可以手动进行事后补偿。


总结

这里创建的时候设计到不同系统的同步,这种补偿策略可以参考,可以根据不同的场景来选择。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值