婚恋app源码开发,如何实现接口隔离原则?"/>
婚恋app源码开发,如何实现接口隔离原则?
如何理解接口隔离原则
Robert Martin 在 SOLID 原则中是这样定义它的:“Clients should not be forced to depend upon interfaces that they do not use。” 直译成中文的话就是:客户端不应该被强迫依赖它不需要的接口。其中的 “客户端”,可以理解为接口的调用者或者使用者。
理解婚恋app源码的接口隔离原则,重点在于怎么理解"接口",可以从以下方面出发:
- 一组 API 接口集合
- 单个 API 接口或函数
作为“接口”的一组 API 接口集合
现在我们有一组跟账号相关的接口提供给婚恋app源码后台查询账户系统调用,包括:获取账号id、获取账号名、获取账号的金额。具体可以看看下面的例子:
public interface AccountService {String getAccountId();String getAccountName();long getMoney();
}public class AccountServiceImpl implements AccountService {public String getAccountId() {...}public String getAccountName() {...}public long getMoney() {...}
}
此时,婚恋app源码后台管理账户系统需要实现账号金额的增减操作,希望账号系统提供相应接口。
这时,我们需要怎么做呢?你可能会直接在 AccountService 新增 addMoney(long) 和 deductMoney(long) 方法。功能是实现解决了,但是这里会给不细心的小伙伴挖坑的。
这里为什么会有坑呢?婚恋app源码账户的金额增减是很重要的操作,我们的预期是金额增减操作只提供给到后台管理账户系统,其他系统不能调用,否则哪一天,小伙伴手一抖,坑就大了。从婚恋app源码服务架构的角度出发,可以通过接口鉴权来限制接口调用,防止误操作账号金额。
较佳的实现方案,按照接口隔离原则 ISP ,婚恋app源码客户端不应该被强迫依赖它不需要的接口,需要把增减账号金额的接口单独放到另外的接口 LimitedAccountService 类中,接口只限于提供给后台管理账户系统调用,其他系统只提供 AccountService 接口,具体实现:
public interface LimitedAccountService {void addMoney(long money);void deductMoney(long money);
}
public class LimitedAccountServiceImpl implements LimitedAccountService {public void addMoney(long money) {...}public void deductMoney(long money) {...}
}
在设计微服务或者类库接口的时候,如果部分接口只被部分调用者使用,那我们就需要将这部分接口隔离出来,单独给对应的调用者使用,而不是强迫其他调用者也依赖这部分不会被用到的接口。
作为“接口”的单个 API 接口或函数
我们用另外一种角度去理解"接口",理解为单个 API 接口或函数(方便后续描述,简称为"函数")。对于函数,对于接口的理解为:函数的设计要功能单一,不要将多个不同的功能逻辑在一个函数中实现。。接下来,我们去看一个例子:
// 玩家信息统计 BO 类
public class UserStatistics {private int maxLevel;private int minLevel;private int averageScore;// getter and setter
}public UserStatistics calculate(List<User> users) {UserStatistics userStatistics = new UserStatistics();// 统计玩家信息...return userStatistics;
}
方法 calculate 包含了最高等级、最小等级、平均积分的计算,职责不够单一。当然,判断函数是否职责单一,这也有主观的因素,也存在场景的因素。试想一下,现在婚恋app源码有一些情况是只需要用到最高等级maxLevel 、最低等级 minLevel,另外的一些情况下则只用到平均积分averageScore。如果我们每次都调用函数 calculate 来计算,会把所有信息都计算一遍,会造成很多无用功,浪费了CPU资源,倘若我们的数据量很大,这会导致系统很大的性能压力。
在此场景下,函数 calculate 的设计就不合理了,我们换一种实现方式:
public int calculateMaxLevel(List<User> users) {...}public int calculateMinLevel(List<User> users) {...}public int calculateAverageScore(List<User> users) {...}
在第二种实现方式中,我们将函数 calculate 拆分成多个接口实现,按需调用,解决了上面提到的问题。
在这里,或许会有疑问,接口隔离原则和单一职责怎么那么相似的?其实俩个原则侧重的点不一样,单一职责侧重的是婚恋app源码模块、类、接口的设计;而接口隔离原则侧重婚恋app源码接口的设计,调用者只使用部分接口或者接口的部分功能,我们都可以认为接口的设计不够职责单一。
更多推荐
婚恋app源码开发,如何实现接口隔离原则?
发布评论