ЁЯФм рдзрдбрд╛ 05 тАФ API рдмрд╛рдВрдзрд╛: ~235 рдкреНрд░рд╛рдорд╛рдгрд┐рдХ рдУрд│реАрдВрддрд▓реЗ рдХрд╛рдЙрдВрдЯрд░
ЁЯУН рддреБрдореНрд╣реА рдЗрдереЗ рдЖрд╣рд╛рдд: 12 рдкреИрдХреА рдзрдбрд╛ 05 ┬╖ рдорд╛рдЧреЗ: lesson-04-json-and-schemas ┬╖ рдкреБрдвреЗ: lesson-06-auth
ЁЯУж рдпрд╛ рдмреНрд░рдБрдЪрдордзреНрдпреЗ рдХрд╛рдп рдЖрд╣реЗ
рдзрдбреЗ 01тАУ04, рдЖрдгрд┐ рддреНрдпрд╛рд╕реЛрдмрдд рдЦрд▒реНрдпрд╛ counter рдЪреЗ рдорд╛рд░реНрдЧрджрд░реНрд╢рд┐рдд рд╡рд╛рдЪрди тАФ api/school_api.py тАФ рдЖрдгрд┐ рддреНрдпрд╛рдд рддреБрдордЪреА рдкрд╣рд┐рд▓реА рднрд░.
ЁЯзТ 5 рд╡рд░реНрд╖рд╛рдВрдЪреНрдпрд╛ рдореБрд▓рд╛рд▓рд╛ рд╕рдордЬрд╛рд╡рд▓реНрдпрд╛рд╕рд╛рд░рдЦреЗ
Counter рдмрд╛рдВрдзрдгреЗ рд╣реЗ framework рдЪреЗ рдХрд╛рдо рд╡рд╛рдЯрддреЗ, рдЬреЛрдкрд░реНрдпрдВрдд рддреБрдореНрд╣реА рдПрдХ рдЙрдШрдбреВрди рдкрд╛рд╣рдд рдирд╛рд╣реА. рдЖрдордЪреНрдпрд╛ counter рдЪреЗ рдиреЗрдордХреЗ рдЪрд╛рд░ рднрд╛рдЧ рдЖрд╣реЗрдд, file рдордзреНрдпреЗ рд╡рд░реВрди рдЦрд╛рд▓реА:
- рдЯреЗрдмрд▓рд╛рдВрдЪрд╛ рдирдХрд╛рд╢рд╛ ЁЯзн тАФ routes:
route()/v1/students/2рдЪреЗ['students', '2']рдХрд░рддреЗ, рдЖрдгрд┐do_GET/do_POST/do_PUT/do_DELETEslip рдХреЛрдгрддреНрдпрд╛ drawer рдмрджреНрджрд▓ рдЖрд╣реЗ рддреЗ рдард░рд╡рддрд╛рдд. - рддрдкрд╛рд╕рдгреНрдпрд╛ тЬЕ тАФ
validate_student()(form, рдзрдбрд╛ 04) рдЖрдгрд┐authorized()(pass, рдзрдбрд╛ 06). рдХреЛрдгрддреЗрд╣реА рдХрд╛рдо рдХрд░рдгреНрдпрд╛рдЪреНрдпрд╛ рдЖрдзреА рдирдореНрд░рдкрдгреЗ рдирдХрд╛рд░ рджреНрдпрд╛. - Archive ЁЯЧДя╕П тАФ
STUDENTS, рдПрдХ dict. рдЖрдЬ рддреЗ memory рдордзреНрдпреЗ рдЖрд╣реЗ; Database school рддреЗ рдЯрд┐рдХрд╛рдК рдмрдирд╡рддреЗ. Counter рд▓рд╛ рддреНрдпрд╛рдЪреА рдкрд░реНрд╡рд╛ рдирд╕рддреЗ. - Plumbing ЁЯФз тАФ
send()рдкреНрд░рддреНрдпреЗрдХ рд╢рд┐рдХреНрдХрд╛ рддреНрдпрд╛рдЪ headers рд╕рд╣ рд▓рд┐рд╣рд┐рддреЗ (X-API-Version,X-Request-Id,Content-Type);error()рдкреНрд░рддреНрдпреЗрдХ рдирдХрд╛рд░ рдПрдХрд╛рдЪ рдЖрдХрд╛рд░рд╛рдд рд▓рд┐рд╣рд┐рддреЗ;log_line()рдкреНрд░рддреНрдпреЗрдХ slip рд╕рд╛рдареА рдПрдХ рдУрд│ рдЫрд╛рдкрддреЗ;rate_limited()рдореНрд╣рдгрдЬреЗ рд░рд╛рдВрдЧ (рдзрдбрд╛ 10).
рд╣рд╛рдЪ server рдЖрд╣реЗ. Frameworks рддреБрдореНрд╣рд╛рд▓рд╛ decorators, typed models, docs generators рдЖрдгрд┐ async рджреЗрддрд╛рдд тАФ рдЦрд▒реНрдпрд╛ рдХрд╛рдорд╛рд╕рд╛рдареА рддреЗ рд╡рд╛рдкрд░рд╛ тАФ рдкрдг рддреЗ рд╣реЗрдЪ рдЪрд╛рд░ рднрд╛рдЧ automate рдХрд░рдд рдЕрд╕рддрд╛рдд, рдЖрдгрд┐ рдЖрддрд╛ рддреБрдореНрд╣реА рддреЗ рднрд╛рдЧ рдкрд╛рд╣рд┐рд▓реЗ рдЖрд╣реЗрдд.
ЁЯЧ║я╕П рдЖрдХреГрддреА
flowchart TB
subgraph file["api/school_api.py тАФ the four parts"]
r["1 ЁЯзн routes: route() + do_GET/POST/PUT/DELETE"]
c["2 тЬЕ checks: validate_student() ┬╖ authorized()"]
s["3 ЁЯЧДя╕П archive: STUDENTS (a dict тАФ for now)"]
p["4 ЁЯФз plumbing: send() ┬╖ error() ┬╖ log_line() ┬╖ rate_limited()"]
end
client["ЁЯзС any HTTP client"]
client <-->|"HTTP"| p
p --> r --> c --> s
ЁЯУЦ рдпрд╛ рдУрд│реА рд╡рд╛рдЪрд╛ (рдореНрд╣рдгрдЬреЗ рддреБрдореНрд╣реА рд╣рд░рд╡рдгрд╛рд░ рдирд╛рд╣реА)
validate_studentтАФ рднрд╛рдЧ 2, formclass HandlerтЖТsend,error,log_lineтАФ рднрд╛рдЧ 4, рд╢рд┐рдХреНрдХреЗrate_limited,authorized,read_jsonтАФ рднрд╛рдЧ 2/4, рджреНрд╡рд╛рд░рдкрд╛рд▓routeрдЖрдгрд┐ рдЪрд╛рд░do_*methods тАФ рднрд╛рдЧ 1, рдЯреЗрдмрд▓рд╛рдВрдЪрд╛ рдирдХрд╛рд╢рд╛list_studentsтАФ рдзрдбрд╛ 08 рдЗрдереЗ рд░рд╛рд╣рддреЛnotifyтАФ рдзрдбрд╛ 11 рдЪрд╛ callback
тЭУ рдХрд╛рдп (рдЪреЛрд░рдгреНрдпрд╛рд╕рд╛рд░рдЦреЗ рддрдкрд╢реАрд▓)
- рд▓рд╡рдХрд░, рдХреНрд░рдорд╛рдиреЗ рдирдХрд╛рд░ рджреНрдпрд╛: rate limit тЖТ path тЖТ auth тЖТ media type тЖТ JSON тЖТ validation тЖТ рдХрд╛рдо. рдкреНрд░рддреНрдпреЗрдХ рддрдкрд╛рд╕рдгреА рд╕реНрд╡рд╕реНрдд рдЖрд╣реЗ рдЖрдгрд┐ рдкреНрд░рддреНрдпреЗрдХреАрдЪрд╛ рд╕реНрд╡рддрдГрдЪрд╛ status code рдЖрд╣реЗ.
- рдПрдХрдЪ
send()рдореНрд╣рдгрдЬреЗ рдкреНрд░рддреНрдпреЗрдХ response рд╡рд░ рддреЗрдЪ headers тАФ рдлрдХреНрдд request id рд╕реБрджреНрдзрд╛ рддреБрдордЪреЗ рддрд╛рд╕рдиреНрддрд╛рд╕ рд╡рд╛рдЪрд╡реЗрд▓ (рдзрдбрд╛ 12). ThreadingHTTPServerslips рдПрдХрд╛рдЪ рд╡реЗрд│реА рд╣рд╛рддрд╛рд│рддреЛ; рдзрдбреНрдпрд╛рд╕рд╛рдареА dict рдкреБрд░реЗрд╕рд╛ рд╕реБрд░рдХреНрд╖рд┐рдд рдЖрд╣реЗ, рдЖрдгрд┐ рдЦрд░рд╛ database рдиреЗрдордХрд╛ рдпрд╛рдЪреАрдЪ рдЬрд╛рдЧрд╛ рдШреЗрддреЛ.- Status codes рдореНрд╣рдгрдЬреЗ рдирд┐рд░реНрдгрдп: create рд╡рд░
201+Location, delete рд╡рд░204, рди рдмрджрд▓рд▓реЗрд▓реНрдпрд╛ ETag рд╡рд░304тАФ рдкреНрд░рддреНрдпреЗрдХ рдПрдХ рдЕрд╢реА рдУрд│ рдЖрд╣реЗ рдЬрд┐рдЪреНрдпрд╛рдХрдбреЗ рддреБрдореНрд╣реА рдмреЛрдЯ рджрд╛рдЦрд╡реВ рд╢рдХрддрд╛. - Secrets environment рдордзреВрди рдпреЗрддрд╛рдд (
SCHOOL_API_KEY), code рдордзреВрди рдХрд┐рдВрд╡рд╛ URL рдордзреВрди рдХрдзреАрдЪ рдирд╛рд╣реА.
ЁЯдФ рдХрд╛
рдХрд╛рд░рдг "рдЖрдореНрд╣рд╛рд▓рд╛ X рд╕рд╛рдареА API рд╣рд╡реЗ" рд╣реЗ рдкреНрд░рддреНрдпреЗрдХ team рдордзрд▓реЗ sprint ticket рдЕрд╕рддреЗ, рдЖрдгрд┐ рдЖрддрд╛ рддреБрдореНрд╣реА рддреНрдпрд╛рдЪрд╛ рдкреНрд░рд╛рдорд╛рдгрд┐рдХ рдЕрдВрджрд╛рдЬ рд▓рд╛рд╡реВ рд╢рдХрддрд╛: plumbing рдПрдХрд╛ рджрд┐рд╡рд╕рд╛рдЪреЗ рдХрд╛рдо (framework рдиреЗ рддреЛ рдПрдХ рддрд╛рд╕ рд╣реЛрддреЛ); рдЦрд░реЗ рдХрд╛рдо рдореНрд╣рдгрдЬреЗ contract тАФ рдирд╛рдореЗ, forms, error рдЪрд╛ рдЖрдХрд╛рд░, auth model. рдЬреНрдпрд╛ teams рд╣реЗ рдмрд░реЛрдмрд░ рдХрд░рддрд╛рдд рддреНрдпрд╛ рдЕрд╕реЗ counters ship рдХрд░рддрд╛рдд рдЬреНрдпрд╛рдВрдирд╛ call рдХрд░рд╛рдпрд▓рд╛ рдЗрддрд░ teams рдирд╛ рдЖрд╡рдбрддреЗ.
ЁЯФз рдХрд╕реЗ + ЁЯзк рдХрд░реВрди рдкрд╛рд╣рд╛ тАФ рдкреНрд░рддреНрдпрдХреНрд╖ рд╡рд╛рдврд╡рд╛
# 1) prove the baseline:
python3 api/school_api.py & sleep 1; bash api/smoke_test.sh | head -20
# 2) YOUR first endpoint тАФ the homework cabinet. In school_api.py:
# HOMEWORK = [] (part 3, next to STUDENTS)
# in do_GET: if p == ["homework"]: return self.send(200, {"items": HOMEWORK})
# in do_POST: if p == ["homework"]: (authorized? read_json? require "title") тЖТ HOMEWORK.append(...); 201
# 3) restart and call it:
curl -s http://127.0.0.1:8080/v1/homework
curl -s -X POST http://127.0.0.1:8080/v1/homework -H 'X-API-Key: hall-pass-123' -H 'Content-Type: application/json' -d '{"title":"read lesson 06"}'
# 4) add the two operations to api/openapi.yaml тАФ the catalogue must not lie
тЬЕ рддрдкрд╛рд╕рд╛ тАФ рддреБрдореНрд╣рд╛рд▓рд╛ рдХрд╛рдп рджрд┐рд╕рд╛рдпрд▓рд╛ рд╣рд╡реЗ
GET /v1/homework {"items": []} рдкрд░рдд рджреЗрддреЗ, POST рддреБрдордЪреНрдпрд╛ item рд╕рд╣ 201 рджреЗрддреЗ, рдЖрдгрд┐ рджреБрд╕рд░рд╛ GET рддреНрдпрд╛рдЪреА рдпрд╛рджреА рджрд╛рдЦрд╡рддреЛ. Key рд╢рд┐рд╡рд╛рдпрдЪрд╛ POST 401 рдкрд░рдд рджреЗрддреЛ тАФ рдХрд╛рд░рдг рддреБрдореНрд╣реА authorized() рдкреБрдиреНрд╣рд╛ рд╡рд╛рдкрд░рд▓реЗ. Smoke test рдЕрдЬреВрдирд╣реА pass рд╣реЛрддреЛ: рддреБрдореНрд╣реА рдмрд╛рдХреАрдЪреНрдпрд╛рдВрдирд╛ рд╣рд╛рдд рди рд▓рд╛рд╡рддрд╛ рдПрдХ рдХрдкрд╛рдЯ рдЬреЛрдбрд▓реЗ.
ЁЯПБ рддреБрдореНрд╣реА рдЖрддреНрддрд╛рдЪ рдХрд╛рдп рд╕рд┐рджреНрдз рдХреЗрд▓реЗ
рддреБрдореНрд╣реА рдЦрд░реЗ API рдЪрд╛рд░рд╣реА рднрд╛рдЧрд╛рдВрддреВрди рд╡рд╛рдврд╡рд▓реЗ тАФ route, check, store, plumbing тАФ рдЖрдгрд┐ рдЖрдзреАрдЪреЗ contract рдЪрд╛рд▓реВрдЪ рд░рд╛рд╣рд┐рд▓реЗ.
тЪая╕П рдиреЗрд╣рдореАрдЪреНрдпрд╛ рдЪреБрдХрд╛
- рддрдкрд╛рд╕рдгреНрдпрд╛рдВрдЪреНрдпрд╛ рдЖрдзреА рдХрд╛рдо рдХрд░рдгреЗ (рдЖрдзреА dict рдордзреНрдпреЗ рд▓рд┐рд╣рд┐рдгреЗ, рдордЧ validation)
- рд╕реНрд╡рддрдГрдЪрд╛ рд╡реЗрдЧрд│рд╛ error format рдЕрд╕рд▓реЗрд▓рд╛ рдирд╡реАрди endpoint тАФ рдиреЗрд╣рдореА
self.error(...) - рд╣рд╛рддрд╛рдиреЗ рд▓рд┐рд╣рд┐рд▓реЗрд▓реНрдпрд╛ responses рдордзреНрдпреЗ
Content-Length/Content-Typeрд╡рд┐рд╕рд░рдгреЗ тАФ рддреБрдореНрд╣реА рдХрдзреАрдЪ рд╡рд┐рд╕рд░реВ рдирдпреЗ рдореНрд╣рдгреВрдирдЪsend()рдЖрд╣реЗ - API key source file рдордзреНрдпреЗ рдареЗрд╡рдгреЗ
ЁЯПн рдкреНрд░рддреНрдпрдХреНрд╖ рд╡рд╛рдкрд░рд╛рдд рд╣реЗ рдХрд╛ рдорд╣рддреНрддреНрд╡рд╛рдЪреЗ: frameworks рд╣реЗ рднрд╛рдЧ decorators рдорд╛рдЧреЗ рд▓рдкрд╡рддрд╛рдд, рдЬреЗ рдкрд╣рд╛рдЯреЗ 3 рд╡рд╛рдЬрддрд╛ рдХрд╛рд╣реАрддрд░реА рдмрд┐рдШрдбреЗрдкрд░реНрдпрдВрдд рдЫрд╛рди рдЕрд╕рддреЗ. рдЪрд╛рд░ рднрд╛рдЧ рдорд╛рд╣реАрдд рдЕрд╕рд▓реЗрд▓реЗ engineers framework рдЪреЗ stack traces рдирдХрд╛рд╢рд╛рд╕рд╛рд░рдЦреЗ рд╡рд╛рдЪрддрд╛рдд; рдмрд╛рдХреАрдЪреНрдпрд╛рдВрдирд╛ рддреЗ рдлрдХреНрдд рдЧреЛрдВрдЧрд╛рдЯ рд╡рд╛рдЯрддреЛ.
тПня╕П рдкреБрдвреЗ
рдХреЛрдгрддреНрдпрд╛ slips рдХреЛрдг рджреЗрдК рд╢рдХрддреЛ? Auth тАФ keys, tokens, OAuth, рдЖрдгрд┐ writes рд╕рд╛рдареА рд╣реЙрд▓ рдкрд╛рд╕.
git checkout lesson-06-auth