Tag: Muriel Silveira

带有TDD的手工iOS应用程序中的身份验证规则

让我们从身份验证过程开始,但并非全部开始,目前,我们仅对注册部分感兴趣。 这部分具有一些验证和重要行为。 此实现将使我们能够与一些BASS内容进行交互,这代表了应用程序难题的重要组成部分。 在这篇文章中,我们将介绍: 测试驱动开发 输入数据验证 准备与外部服务的一些集成 您可以在此处检查相关的github问题。 用户注册用例 该项目将使用自下而上的流程进行开发。 因此,我们将从编写测试和规则开始,而不是进行注册或登录屏幕。 第一个测试即将尝试使用空电子邮件值注册用户。 经过绿色测试之后,该重构用例类了。 第一个奇怪的是寄存器功能处的mutating关键字。 需要使用此关键字是因为该函数试图更改默认情况下不可变的结构值。 此应用程序将使用称为Clean Architecture的体系结构,该体系结构将软件分层。 这些层对于隔离按行为分开的组件和职责至关重要。 清洁体系结构和SOLID原则值得一提,我将在稍后单独讨论。 通过将软件划分为多个层,并遵循“依赖关系规则”,您将创建一个具有内在可测试性的系统,并具有其所隐含的所有优势。 马丁,罗伯特。 “清洁建筑” 2012 同样,此用例正在保存应该在表示层中的状态。 不在“应用程序业务规则”层中。 为了解决这个问题,我们可以创建一个演示者。 …我们也不希望该层受到数据库,UI或任何常用框架等外部性变化的影响。 该层与此类问题无关。 马丁,罗伯特。 “清洁建筑” 2012 上面的协议将成为演示者。 而且它的实现与用例无关紧要。 用例只需要具有故障方法的东西。 在我们的测试环境中,我们将使用演示者的测试双精度表示形式,该表示形式为存根双精度类型。 出于测试目的,我们可以用等效的“特技替身”: Test Double来代替真实的DOC(而不是SUT!)。 迈扎罗斯(Meszaros),杰拉德(Gerard)。 2009年“ Test Double” 存根提供对测试过程中进行的呼叫的固定答复,通常通常根本不响应为测试编程的内容。 存根还可以记录有关呼叫的信息,例如,电子邮件网关存根可以记住“已发送”的消息,或者仅记住“已发送”的消息数量。 福勒,马丁。 “不打Mo”,2007年 用例已更改为通过依赖关系使用演示者。 演示者将用作用例的依赖项,这样做将符合SOLID原则,更具体地讲是Dependency Inversion一个。 原则指出: 答:高级模块不应依赖于低级模块。 两者都应依赖抽象。 B.抽象不应依赖细节。 细节应取决于抽象。 马丁,罗伯特。 […]

用户注册用例中的第一个重构

我们可以“第一时间正确”获得系统是一个神话。 这篇文章是基于另外两个帖子。 首先检查它们以获得更广泛的了解: 使用TDD https://medium.com/cocoaacademymag/authentication-rules-in-a-handcrafted-ios-application-with-tdd-8db5396ebac6的手工iOS应用程序中的身份验证规则 使用集成测试在iOS上进行Firebase用户注册https://medium.com/cocoaacademymag/firebase-user-registration-at-ios-with-integration-tests-fa450e4ec8bb 这篇文章将为您提供有关我在项目中所做的更改的更新。 这些更改在此提交中。 我还将谈论: 单一责任原则 实体 测试驱动开发和单元测试 问题 在写这个项目的最后一篇文章时,我意识到我的用户注册用例不止一个责任。 这打破了第一个SOLID原则,即单一责任原则。 用例具有验证数据和跨其他层传递数据的复杂性。 现在我已经知道责任在哪里,是时候提取代码并对其进行测试了。 负责进行格式验证的代码将提取到小类中,这些小类将负责单个目的。 这些类称为实体。 实体封装了企业范围的业务规则。 实体可以是带有方法的对象,也可以是一组数据结构和函数… …它们封装了最通用和最高级的规则。 当某些外部变化时,它们变化的可能性最小。 马丁,罗伯特。 “清洁建筑” 2012 我只显示ValidateEmailEntity 。 因为其他实体遵循相同的过程。 所以我从 实体测试。 第一种情况非常简单,只是空电子邮件的断言,应该是无效的。 并使此测试成功运行。 下面的代码已经足够了。 在这个简单的场景之后,我开始增加测试的复杂性。 通过电子邮件使用无效字符,没有提供者,不完整和特殊字符来进行断言。 幸运的是,一个简单的正则表达式(可在Stack Overflow上找到)使所有方案都通过了。 下面的代码显示ValidateEmailEntity是如何获得的。 为每个数据格式验证创建一个实体后,我将回到用例并利用这些实体。 以下是具有多个职责的旧用例: 旧用例 重构(添加13个和删除24个)后, 用例更加简洁易懂: 如您所见,我还创建了一个具有isValid属性的协议,以促进错误验证。 另一个得到相应的错误。 可能要注意的是,我还创建了一个协议来保留某种模式,这对于仅过滤无效输入很有用,并且我还创建了一个error属性。 并且由于我正在测试与用例分开的验证,因此不再需要在用例级别上测试所有数据变体。 因此,我运行了测试,所有测试都是绿色的,重构成功完成。