ET框架---LocationComponent学习笔记

LocationComponent

请大家关注我的微博:@NormanLin_BadPixel坏像素


作为程序员,我们对数据,对逻辑是敏感的。看到一段代码,我们很快就能看懂里面的逻辑,数据是怎么变化的。但是,这段代码在整个工作环境中起到了什么作用,我们不能一眼看出来。

就像这个组件,里面的数据变化很容易看懂,但是我们不知道这些数据代表了什么。作者也没有注释,我们只能猜测,之后再来验证。

我们看变量名,locations,储存地址的一个字典。我们顺藤摸瓜,找到在哪里储存了这个地址。我们在ActorComponent的扩展方法里找到了

public static async Task AddLocation(this ActorComponent self)
{
    await Game.Scene.GetComponent<LocationProxyComponent>().Add(self.actorId);
}

LocationProxyComponent里面

public async Task Add(long key)
{
    Session session = Game.Scene.GetComponent<NetInnerComponent>().Get(this.LocationAddress);
    await session.Call(new ObjectAddRequest() { Key = key, AppId = this.AppId });
}

从而我们得知,locations字典里面,键是ActorComponentactorId,值则是LocationProxyComponentAppId。而我们知道,这个AppId是启动服务时候从启动设置里面获取的。也就是说,这里登记的地址,是添加了ActorComponent组件的实体对象所在服务器的地址。为什么要这么做呢?

我们知道,ET是分布式的服务器架构,不同的服务会存在在不同的服务器上。那不同服务器之间实体对象的互相访问就要获取对方所在的服务器,才能精准的访问。

举一个例子。我们的游戏有两张地图,地图的数据由两个不同的服务器Map1、Map2管理。

我们有两个玩家Player1、Player2分别在Map1、Map2上。

在进入地图的时候,会记录Player1所在服务器的地址是Map1,Player2所在服务器的地址是Map2。这些数据会存在另外一个服务器location服务器上。

这个时候,如果Player1要给Player2发送消息,则要经过一下的步骤。

  1. 获取Player2的Id。(不管你用什么方法获取)
  2. 根据Id向location服务器发送内部请求,获取Player2所在服务器的地址Map2。
  3. 根据Map2的地址(AppId)从配置信息里面获取到Map2服务器的IP地址。
  4. 有了这两个信息,Player2的ID跟Map2的IP地址。我们就可以创建跟Map2的会话Session,并且发送针对Player2的消息了。

有的同学可能会问,我们既然在第一步能获取到Player2的Id,为什么不能获取到它所在服务器的地址,而要从location获取?

这里我的理解是,Player的Id,也就是实体对象的Id在其生命周期内是固定不变且唯一的。所以我们在传输保存Player的信息的时候,可以保存Id来标识它。如果我们保存服务器地址的话会出现什么情况呢?

假如Player1跟其他1000万个人是好友,那它每次更换服务器的时候,它都得通知那1000万个人更换地址,这是极其愚蠢的。这也体现了location服务器的作用,每个实体对象更换服务器的时候,只要通知location服务器更新地址,其他对象就可以获得正确的地址了。

我们看到,这个组件里除了添加和获取的方法外,还有LockUnLock方法。顾名思义,是锁住地址的意思。为什么要锁住地址呢?我的理解是,有得实体对象可能会转换服务器,比如玩家进入另一张地图。而这个转换过程是有时间的,在这个时间内如果想对玩家发送消息,则容易出错,我们可以想象成玩家既不在地图1也不在地图2上。这个时候,我们就锁住玩家的地址,所有获取地址的请求全部都搁置,等待玩家转换完成后再处理。这样,获取的地址才是正确的。而搁置的请求,则会以LocationTask储存在taskQueues字典里。

private readonly Dictionary<long, Queue<LocationTask>> taskQueues = new Dictionary<long, Queue<LocationTask>>();
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值