依赖注入vs单例,初始化



我现在正在做一个大项目,这个应用程序正在利用许多不同的服务,如:评论、点赞、发帖、购买等等…

每个服务都有一个类。

现在,我想要限制注册用户的某些操作,如发布、评论等。

到目前为止,每个类都只使用类方法,如下所示:

 @interface UpdateOrderServies : NSObject
+(void)deleteOrder: (STOrder *)order
         andReturn: (void(^)(NSError *error))errorBlock;
+(void)updateOrder: (STOrder *)order
         andReturn: (void(^)(NSError *error))errorBlock;

但是现在,我想先检查用户是否注册,如果没有,不返回值。所以我想出的最好方法是将类更改为单色,并在每次调用类时询问用户是否像这样注册:

+(id) getInstance {
    static UpdateOrderServies *__sharedDataModel = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        __sharedDataModel = [[UpdateOrderServies alloc]init];
    });
    if (![__sharedDataModel userIsRegisterd]) {
        return nil;
    }
    return __sharedDataModel;
}

它工作,但是,嗯,这不是一个很好的答案,正如你所看到的…我想要更普通的。我正在考虑使用台风依赖注入,但是如果用户注册了,我就没有地方可以检查每个调用……有什么更好的办法来处理这个问题吗?更有活力…

根据你上面的问题,我认为你不是在寻找依赖注入,而是面向方面编程。

面向方面编程(AOP)被设计用来解决你上面描述的问题——那些跨越系统中许多模块的问题。例子:
  • 每次用户与服务交互时,都应该检查安全性。
  • 所有交易应该有审计跟踪
  • 每个商店交互应该产生一个天才推荐

如果我们使用普通的面向对象编程来满足这些横切需求,我们就打破了单一职责原则,一个本应该只涉及一个主题的类现在承担了更多的角色,这变得令人困惑、重复和混乱。

AOP将这些横切关注点模块化,然后使用方法拦截确定所有应该应用这些关注点的地方。(在AOP中我们称之为切点表达式)。

在Objective-c中,你可以使用isa - swizling,消息转发或使用NSProxy来手工AOP——这些都是在运行时实现方法拦截的方法。或者,你可以使用一个库,一个由Pete Steinberger和他的团队开发的名为"Aspects"的库。这个库目前还没有切入点表达式语言,但肯定比直接使用ObjC运行时来拦截方法要简单得多。

授权方面如何工作的摘要:

  • 在登录时,我们使用用户名/密码挑战,oauth令牌或类似的方式验证用户。对用户进行身份验证后,我们现在可以对服务调用进行授权。
  • 确定需要授权的每个服务和所需的权限(您可以选择您喜欢的角色、功能等方案)。
  • 好的面向对象原则说每个类应该有一个单一的职责。因此,您的服务客户机应该完全用于调用远程服务。我们可以编辑服务客户机来评估登录用户的权限并决定是否继续。但这将是混乱和重复的。相反,我们将使用步骤2中的信息(每个服务所需的权限),并将该信息的评估委托给授权模块。
  • 现在是AOP步骤:对于每个服务调用,我们将告诉AOP库拦截服务客户机方法并首先调用授权模块。
这样您的横切需求(授权客户端调用)就不会重复。现在,为了简单起见,您可能会决定是否让每个服务调用调用一个授权模块,但它仍然有助于了解AOP和横切关注点背后的理论。依赖注入/Typhoon

依赖注入与你的问题没有直接关系,尽管它确实可以帮助你避免单例客户端的陷阱:

  • 在你的类之间创建一个清晰的契约——增加代码内聚。
  • 确定应用程序中的关键"参与者",并描述它们组装成一个整体的方式。可以用一个演员换另一个演员来履行同样的合同。
  • 使用模拟和存根简化单元测试。
  • 简化了集成测试——能够将一个参与者交换为另一个参与者,从而使系统进入所需的状态。例如,只修补一个授权模块。

最新更新