Upgrade to Pro — share decks privately, control downloads, hide ads and more …

factory_boy: testing like a pro. DjangoCon EU 2022

Camila Maia
September 22, 2022

factory_boy: testing like a pro. DjangoCon EU 2022

Camila Maia

September 22, 2022
Tweet

More Decks by Camila Maia

Other Decks in Technology

Transcript

  1. @cmaiacd
    factory_boy
    DjangoCon EU 2022 - Porto 󰐨
    Camila Maia
    testing like a pro

    View Slide

  2. @cmaiacd
    You can find this presentation at:
    speakerdeck.com/cmaiacd

    View Slide

  3. @cmaiacd
    Who am I?

    View Slide

  4. @cmaiacd
    Backend Developer @

    View Slide

  5. @cmaiacd
    Brazilian 󰎙

    View Slide

  6. @cmaiacd
    Living in Berlin 󰎲

    View Slide

  7. @cmaiacd
    Queer 󰝲

    View Slide

  8. @cmaiacd
    󰘊 󰘋 🐶

    View Slide

  9. @cmaiacd
    Coding since 2010
    👵

    View Slide

  10. @cmaiacd
    Python 🐍 and Ruby
    💎

    View Slide

  11. @cmaiacd
    Community ❤

    View Slide

  12. @cmaiacd
    Conferences

    View Slide

  13. @cmaiacd
    Open Source ❤

    View Slide

  14. @cmaiacd
    Creator of ScanAPI

    View Slide

  15. @cmaiacd
    +1.5k
    + 1.2k ⭐

    View Slide

  16. @cmaiacd
    Workshop
    Tomorrow 4:55 PM
    󰠁󰳕

    View Slide

  17. @cmaiacd

    View Slide

  18. @cmaiacd
    factory_boy: what is it?

    View Slide

  19. @cmaiacd
    It is a fixtures replacement

    View Slide

  20. @cmaiacd
    Based on factory_bot (Thoughtbot)

    View Slide

  21. @cmaiacd
    First version: Django only
    Nowadays: framework-independent
    Unittest, Pytest...

    View Slide

  22. @cmaiacd
    For complex objects:
    ❌ Fixtures: static, hard to maintain
    ✅ Factories: easy-to-use

    View Slide

  23. @cmaiacd

    View Slide

  24. @cmaiacd
    🧰 🛠 🔧 ⚙
    Sequence
    Faker
    Fuzzy attributes
    LazyFunction
    LazyAttribute
    Inheritance
    Inheritance
    Params
    Traits
    Strategies
    RelatedFactory / SubFactory

    View Slide

  25. @cmaiacd
    My Experience

    View Slide

  26. @cmaiacd
    +3 years
    Django Monolith
    🐘

    View Slide

  27. @cmaiacd
    +230 tables
    +2200 relevant files
    +75k relevant lines

    View Slide

  28. @cmaiacd

    View Slide

  29. @cmaiacd
    A poorly designed
    factory might affect
    many tests

    View Slide

  30. @cmaiacd
    Implicit errors

    View Slide

  31. @cmaiacd
    The tests are created in a way to
    fit the factory
    factory-oriented testing

    View Slide

  32. @cmaiacd
    Factories can get too
    tied

    View Slide

  33. @cmaiacd
    Developers bump into
    the same issue again
    and again

    View Slide

  34. @cmaiacd
    Patterns 👀
    Best practices? 🤔

    View Slide

  35. @cmaiacd
    Demo App

    View Slide

  36. @cmaiacd
    Polls

    View Slide

  37. @cmaiacd
    Poll

    View Slide

  38. @cmaiacd
    Results

    View Slide

  39. @cmaiacd
    s

    View Slide

  40. @cmaiacd
    Model - Poll
    Poll
    Question
    Choice
    n:1
    pub_date : DateTimeField
    premium : BooleanField
    author : CharField
    question_text : CharField
    language : CharField
    choice_text : CharField
    votes : IntegerField
    1:1

    View Slide

  41. @cmaiacd
    Model - Poll

    View Slide

  42. @cmaiacd
    Model - Poll

    View Slide

  43. @cmaiacd
    Model - Question

    View Slide

  44. @cmaiacd
    Model - Choice

    View Slide

  45. @cmaiacd
    Best Practices

    View Slide

  46. @cmaiacd
    1. FACTORIES SHOULD
    REPRESENT THEIR MODELS

    View Slide

  47. @cmaiacd
    Avoid implicit errors

    View Slide

  48. @cmaiacd
    BAD ❌

    View Slide

  49. @cmaiacd
    GOOD ✅

    View Slide

  50. @cmaiacd
    2. DO NOT RELY ON DEFAULTS
    FROM FACTORIES

    View Slide

  51. @cmaiacd
    ● If a default value is changed, all tests that
    depend on it will break
    ● The setup of a test should contain all the logic
    to ensure it will always pass
    ● Explicit better than implicit

    View Slide

  52. @cmaiacd
    BAD ❌

    View Slide

  53. @cmaiacd
    GOOD ✅

    View Slide

  54. @cmaiacd
    3. FACTORIES SHOULD
    CONTAIN ONLY THE REQUIRED
    DATA

    View Slide

  55. @cmaiacd
    If the field is nullable (null=True) the
    attribute should be under a trait and not as a
    default value

    View Slide

  56. @cmaiacd
    BAD ❌

    View Slide

  57. @cmaiacd
    GOOD ✅

    View Slide

  58. @cmaiacd
    If we want to have an author, we can use
    PollFactory(with_author=True) now
    When are we going to remember to test the case
    PollFactory(author=None)?
    We should not assume there is an author when DB
    actually allows to not have it.

    View Slide

  59. @cmaiacd
    4. BUILD OVER CREATE

    View Slide

  60. @cmaiacd
    MyFactory.build()
    creates a local object (memory)
    MyFactory.create()
    creates a local object + stores it in the DB

    View Slide

  61. @cmaiacd
    BAD ❌

    View Slide

  62. @cmaiacd
    GOOD ✅

    View Slide

  63. @cmaiacd
    BUILD STRATEGY
    ========== 14 passed in 1.76 seconds ==========
    CREATE STRATEGY
    ========== 14 passed in 3.26 seconds ==========

    View Slide

  64. @cmaiacd
    5.
    IF FK IS IN THE TABLE:
    SUBFACTOR
    IF FK IS IN THE OTHER TABLE:
    RELATEDFACTORY + TRAIT

    View Slide

  65. @cmaiacd
    SubFactory: builds/creates the SubFactory during
    the process of creation of the main factory
    RelatedFactory: builds/creates the RelatedFactory
    after creating the main factory

    View Slide

  66. @cmaiacd
    Good ✅

    View Slide

  67. @cmaiacd
    6. USE FIXTURES TO WRAP
    FACTORIES TO AVOID
    DUPLICATION

    View Slide

  68. @cmaiacd
    BAD ❌

    View Slide

  69. @cmaiacd
    GOOD ✅

    View Slide

  70. @cmaiacd
    7. AVOID SHARING
    FACTORIES OR FIXTURES
    AMONG DIFFERENT FILES

    View Slide

  71. @cmaiacd
    Many tests depending
    on the same
    factory/fixture

    View Slide

  72. @cmaiacd
    Tends to inflate the
    factory/fixture

    View Slide

  73. @cmaiacd
    Hard to maintain

    View Slide

  74. @cmaiacd
    Change a
    factory/fixture…
    tons of tests breaking

    View Slide

  75. @cmaiacd
    Fixture / Factory
    oriented testing

    View Slide

  76. @cmaiacd
    Ok, ok, I got it! 😌
    Now I know the best
    practices 💪

    View Slide

  77. @cmaiacd
    So let’s try to fix one
    first factory…
    🤓

    View Slide

  78. @cmaiacd

    View Slide

  79. @cmaiacd
    Baby steps 🐣

    View Slide

  80. @cmaiacd
    Código

    View Slide

  81. @cmaiacd
    Official doc 📄
    factoryboy.readthedocs.io

    View Slide

  82. @cmaiacd
    Common recipes 󰠉
    factoryboy.readthedocs.io/
    en/stable/recipes.html

    View Slide

  83. @cmaiacd
    Code
    github.com/FactoryBoy/
    factory_boy

    View Slide

  84. @cmaiacd
    THANK YOU!
    MUITO OBRIGADA!
    @cmaiacd camilamaia
    󰠁
    cmaiacd.com

    View Slide