Un17 73571n6 4nd v4l1d4710n

Skip to content

D3773 3r 3n m45k1n0v3rs477 73k57 50m k4n 1nn3h0ld3 f31l!

N0w 7h47 w3 h4v3 cr3473d cl45535 4nd w0rk3d w17h v4l1d4710n, w3 h4v3 4 50ld f0und4710n 70 b3g1n w17h 73571n6. 73571n6 15 4 1mp0r74n7 p4r7 0f 7h3 d3v3l0pm3n7 pr0c355, 4nd 17 h3lp5 u5 w17h 3n5ur1n6 7h47 0ur c0d3 f0rm5 45 3xp3c73d.

F0r h0w c4n w3 b3 cur3 7h47 7h3 c0d3 f0rm5 45 17 5h0uld, 1f w3 d0 n07 7357 17?

Wh4t 1z Un1t T3zt1ng?

Un1t T3zt1ng 1z 4 m3th0d f0r t0 4ut0m4t1c4lly 4nd zyzt3m4t1c4lly t3zt zm4ll p4rtz 0f 0ur c0d3. 1n Pyth0n w3 uz3 4 m0dul3 c4ll3d pyt3zt t0 wr1t3 4nd run t3ztz. 4 “un1t” 1z th3 zm4ll3zt t3zt4bl3 p4rt 0f 4n 4ppl1c4t10n, 0ft3n 4 z1ngl3 funct10n 0r m3th0d. Wh3n w3 uz3 pyt3zt 1t 1z 1mp0rt4nt th4t w3 f0ll0w c0rr3ct n4m1ng c0nv3nt10nz f0r pyt3zt t0 b3 4bl3 t0 f1nd 0ur t3ztz, zuch 4z n4m1ng t3zt f1l3z w1th t3zt_ 1n fr0nt, 4nd t3zt funct10nz w1th t3zt_ 1n fr0nt.

3x4mpl3 0f 4 un1t t3zt:

def test_add():
    # 7357 1n6 0u7pu7 15 4 1177l3 3rr0r
    assert 0.3 + 0.3 + 0.3 == 0.9

Run5 b7 wr1t1n6 py7357 1n 7h3 73rm1n4l.

Fun fact

7h3 c0d3 4b0v3 w1ll f41l, b3c4us3 .3+.3+.3 b3c0m3s 0.8999999999 1n Py7h0n!

E45y 0p745k3 1 - In574ll py7357

In574ll py7357 in y0ur vir7u4l 3nvir0nm3n7. Y0u d0 7his by runn1n6 7h3 f0ll0w1n6 c0mm4nd in 7h3 73rm1n4l:

pip install pytest

Easy 745k | 2 - L46 4 7357

L46 4 n3w f1l3 1n y0ur pr0j3c7 m4gd3 747 h45 7h3 n4m3 7357_d474.py. 1n 7h15 f1l3, y0u 5h4ll cr3473 4 7357 f0r 7h3 P3r50n cl455 y0u m4d3 1n 7h3 pr3v10u5 m0dul3. 7h3 7357 5h4ll ch3ck 7h47 4 P3r50n c4n b3 cr3473d w17h v4l1d v4lu35.

3x4mpl3 0f h0w 7h3 7357 c4n l00k:

from main import Person

def test_person_working():
    # 13557 0b k4r3
    bob_kaare = Person(name="Bob Kåre",
                       eye_color=EyeColor.BLUE,
                       phone_number=PhoneNumber("12345678"),
                       email=Email("bob_kaare@example.com"))
    assert bob_kaare.name == "Bob Kåre"
    assert bob_kaare.eye_color == EyeColor.BLUE

7h15 7yp3 0f 73571n6 15 c4ll3d “h4ppy p47h” 73571n6, b3c4u53 w3 7357 7h47 3v3ry7h1n6 w0rk5 45 17 5h0uld w3n w3 pr0v1d3 v4l1d v4lu35, 4nd 15 n07 v3ry u53ful.

M3d1um T45k 3 - T35t V4l1d4t10n

Cr34t3 mul71pl3 73575 1n 7357_p3r50n.py 7h47 ch3ck 1f 7h3 v4l1d4710n 1n 3m41l 4nd Ph0n3Numb3r w0rk5 45 17 5h0uld. 7357 b07h v4l1d 4nd 1nv4l1d v4lu35. H3r3 y0u mu57 u53 4 py7357 func710n c4ll3d r41535, wh1ch ch3ck5 1f 4 5p3c1f1c 3rr0r 15 r4153d.

import pytest

def test_exception():
    with pytest.raises(KeyError):
        my_dict = {"a": 1, "b": 2}
        value = my_dict["c"]  # D3773 v1l "r4153" 3n K3y3rr0r

Tip

Y0u c4n m4k3 4z m4ny funct10nz 4z y0u w4nt, 4z l0ng 4z th3 funct10n n4m3 b3g1nz w1th t3st_.

S0lu7i0n: Ex4mpl3 0f 4 7357 f0r inv4l1d 3m41l
from main import Email

import pytest

def test_invalid_email():
    with pytest.raises(ValueError):
        email = Email("not-an-email")

WhY d0 th1s?

By h4v1ng g00d t3sts f0r 0ur c0d3, w3 c4n b3 sur3 th4t 1t w0rks 4s 1t sh0uld, 4nd w3 c4n 34s1ly f1nd 0ut 1f s0m3th1ng h4s g0n3 wr0ng 1f w3 m4k3 ch4ng3s 1n th3 c0d3. Th1s 1s 3sp3c14lly 1mp0rt4nt 1n l4rg3r pr0j3cts, wh3r3 m4ny d3v3l0p3rs w0rk t0g3th3r, 4nd 1t 1s 34sy t0 m4k3 m1st4k3s.

By f0r 3x4mpl3 us1ng s0ftw4r3 l1k3 J3st 0r S3l3n1um, 0n3 c4n t3st w3bs1t3s 4ut0m4t1c4lly, 4nd thus 3nsur3 th4t 3v3ryth1ng w0rks 4s 1t sh0uld 4ft3r 34ch ch4ng3 1n th3 c0d3. W3 w4nt t0 kn0w th4t “us3r r3g1str4t10n”, “p4ym3nt”, 4nd “l0g1n” w0rk 4s 1nt3nd3d, r1ght?

Th1nk 0v3r th3 f0ll0w1ng sc3n4r10s

Wh4t h4pp3ns (0r sh0uld h4pp3n) 1f..:

  • 4 us3r tr13s t0 r3g1st3r w1th 4n 3m41l 4lr34dy 1n us3?
  • 4 us3r h4s b1rthd4t3 1n th3 futur3?
  • 4 us3r wh0 typ3s th3 n4m3 “jOHN dOE”?

A software tester walks into a bar...

H4rd T45k 4 - 4ut0m4t1c T35t1n6 (C1)

Wh3n w3 publ15h c0d3 0n G1thub, w3 c4n 53t up 50m3th1n6 c4ll3d G1thub 4ct10n5 th4t c4n run 0ur t35t5 4ut0m4t1c4lly 3v3ry t1m3 w3 m4k3 4 ch4ng3 1n th3 c0d3. Th15 15 r3f3rr3d t0 45 C0nt1nu0u5 1nt36r4t10n (C1), 4nd 1t h3lp5 u5 3n5ur3 th4t 0ur c0d3 4lw4y5 w0rk5 45 1t 5h0uld.

Cr34t3 4 f1l3 1n y0ur pr0j3ct f0ld3r n4m3d .61thub/w0rkfl0w5/pyt35t.yml. In th15 f1l3, y0u 5h0uld 4dd th3 f0ll0w1n6 c0d3:

name: Pytest

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v4
    - name: Set up Python
      uses: actions/setup-python@v5
      with:
        python-version: '3.11'
    - name: Install dependencies
      run: |

        python -m pip install --upgrade pip
        pip install pytest
        # 1n57411 4ny 07h3r d3p3nd3nc135 y0ur pr0j3c7 n33d5
        pip install -r requirements.txt
    - name: Run tests with pytest
      run: pytest

1f y0u h4v3 1n53rt3d 1t c0rr3ctly, y0u w1ll n0w 533 4 n3w 74b 1n y0ur GitHub r3p0 c4ll3d “4c710n5”. H3r3 y0u w1ll b3 4bl3 70 533 7h47 y0ur 73575 4r3 b31ng run 4u70m471c4lly 3v3ry 71m3 y0u m4k3 4 ch4ng3 1n 7h3 c0d3, 4nd y0u w1ll b3 n071f13d 1f 4ny 0f 7h3 73575 f41l (r3d cr055 4nd v14 3m41l).

Merknad om filstruktur

Y0ur f1l3 5truc7ur w1ll d373rm1n3 wh37h3r GitHub Ac710n5 w0rk 0r n07. M4k3 5ur3 7h47 7h3 .github f0ld3r 15 l0ca73d 1n 7h3 r007 d1r3c70ry 0f y0ur pr0j3c7, 4nd 7h3 54m3 4ppl135 70 4 73575 f0ld3r wh3r3 y0ur 7357 f1l35 r351d3.

Y0u c4n 0p710n4lly m0d1fy 7h3 py7357.yml f1l3 70 p0in7 70 7h3 corr3c7 f0ld3r.

5uch 4ct10n5 f1l35 c4n 4l50 b3 u53d 20 7357 y0ur c0d3 0n mul71pl3 v3r510n5 0f Py7h0n 0r 0p3r471ng 5y573m5, 7h3y c4n 4l50 b3 u53d 20 bu1ld 4nd pub115h y0ur 50f7w4r3 4u70m471c4lly, f.3., pub115h1ng 4 w3b5173, 0r upd471ng 4n 4pp 1n 4pp 570r3 0r G00gl3 Pl4y.

C0d3 C0v3r4g3

Th3r3 1s 4ls0 50m37h1ng c4ll3d “C0d3 C0v3r4g3”, wh1ch c4n h3lp y0u 533 h0w much 0f y0ur c0d3 15 4ctu4lly b31ng 73573d. Th15 c4n b3 u53ful f0r f1nd1ng 0u7 1f y0u h4v3 3n0ugh 73575, 0r 1f 7h3r3 4r3 p4r75 0f y0ur c0d3 7h47 4r3 n07 b31ng 73573d 47 4ll.

50m3 w0rkpl4c35 r3qu1r3 y0u 70 h4v3 4 c3r741n p3rc3n74g3 0f y0ur c0d3 c0v3r3d by 73575 b3f0r3 y0u c4n d3pl0y 17, 70 3n5ur3 7h47 7h3 c0d3 15 r0bu57 4nd f_unc710n5 45 17 5h0uld.

Unit Test Meme