- 31.07.15 07:07 •
- ph_piter •
- • # 263895
- • Habrahabr
- 6 •
- 14109
- cum ar fi Forbes, doar mai bine.
Buna ziua, cititorii noștri regulate și ocazionale.
Astăzi, dorim să vă oferim un articol interesant despre design API și capcanele asociate. Nu întrebați cum am ajuns peste ea, o căutare creativă - este foarte neliniar.
La proiectarea API, trebuie să ia în considerare mai mulți factori. Siguranța, consecvența, stilul de management de stat; se pare că lista este fără sfârșit. Cu toate acestea, un factor este adesea trecute cu vederea - este o chestiune de scară. În cazul în care proiectarea API încă de la început să ia în considerare amploarea sistemului, apoi mai târziu (când sistemul va crește) pe care le poate salva sute de ore de timp de lucru.
Uneori este dificil de formulat, ceea ce este interfața de programare a aplicațiilor (API). C punct de vedere tehnic la API-ul include orice funcție numită de codul unui alt programator. Discuții despre codul ce „trage“ pe API-ul, sunt în afara domeniului de aplicare a acestui articol, așa că vom presupune că API - aceasta este cea mai simplă funcție.
În acest articol, exemple simple, special selectate servesc numai pentru a ilustra tema principală. funcțiile utilizate în limbajul C #, dar principiile de bază stabilite aici sunt aplicabile în aproape toate limbile, cadre și sisteme. structură de date într-un articol modelat stilul relațional distribuit folosit în mai multe baze de date comerciale. Din nou, exemplele sunt scrise doar pentru motive ilustrative, nu le trateze ca recomandări.
Să presupunem că scrieți un sistem simplu de procesare a comenzilor pentru client, și au identificat deja trei clase majore (sau, dacă preferați, „structura de date“). Clasa client are o „cheie străină“ (în terminologia de bază de date) pentru clasa de adrese, iar în clasa comandă are chei străine pentru adresa de clase și Client. Sarcina ta este de a crea o bibliotecă care poate fi utilizată pentru procesarea comenzilor (Comenzi). Prima regulă de afaceri este cazul: starea HomeAddress clientului (Client) trebuie să fie aceeași cu starea în BillingAddress ordine (comanda). Nu întreba de ce, regulile de afaceri nu sunt, de obicei înțeleg mintea :)
Verificați dacă cele două câmpuri sunt la fel - în mod evident, o sarcină ușoară. Speri pentru a impresiona seful, asa ca nascocit o decizie în mai puțin de 10 minute. Funcția VerifyStatesMatch returnează o valoare boolean care apelantul poate determina ruleaza o regulă de afaceri sau nu. Vă conduce pe biblioteca în câteva teste simple și asigurați-vă că la executarea de cod a petrecut o medie de 50 ms, nici un stocuri nu este vizibil. Cap foarte mulțumit, da biblioteca altor dezvoltatori, astfel încât să-l folosească în aplicațiile lor.
A doua zi, vin la locul de muncă, și trebuie să monitorizeze etaleaza un autocolant: „Vino la mine urgent - Chef“ Puteți ghici că ieri a fost atât de succes cu biblioteca sa că astăzi șeful decis să vă taxeze o problemă și mai gravă. La scurt timp, cu toate acestea, se pare că codul are probleme serioase.
Nu este cel mai bun start a zilei, nu? Cred că cei mai mulți dezvoltatori au confruntat vreodată o situație similară. Te-ai gândit că ai scris biblioteca „ideal“, și a adus o întreagă grămadă de probleme. Dar, dacă înțelegi corect ce „unul“, „mulți“, „Zero“ și „Nimic“, vei învăța să se facă distincția între cazul în care API-ul dvs. nu îndeplinește așteptările colegilor.
Primul ghid de acțiune - pentru a înțelege ce „One“, și cum să-l folosească. Vreau să spun, API-ul ar trebui, în orice caz, să se ocupe de o porțiune de intrare de așteptat, fără erori. Astfel de erori sunt teoretic posibile, dar pentru a le raporta apelantului, nu trebuie să. „Nu este evident?“ - s-ar putea crede. Ei bine, să luăm un exemplu și să ia în considerare ce pot apărea erori atunci când procesarea comenzilor.
Acestea sunt doar exemple, așa că hai să stabilească codul nostru și trece mai departe.
Du-te înapoi la scenariul descris mai sus. Trebuie să vorbim cu Bob. Bob plâns de faptul că codul se execută lent, dar valoarea de 50 ms este în concordanță cu durata sistemului așteptat cu arhitectura. Dar se pare că Bob se ocupă de 100 de ordine de cel mai mare utilizator într-un singur pachet, astfel încât ciclul Bob pentru executarea metodei este irosit 5 secunde.
Tu. Bob, ai primit codul meu este prea lent? Acesta este cheltuit pe procesarea de ordinul a numai 50 ms.
Bob. Clientul nostru Acme Inc. Se impune ca ordinele lor au fost procesate sub formă de pachete la o rată maximă. Trebuie să servească 100 de ordine de 5 secunde, astfel încât - este prea lung.
Tu. Oh, nu am știut că trebuie să proceseze pachetul comanda.
Bob. Ei bine, e doar pentru Acme, ele au, de asemenea, cel mai mare client.
Tu. Eu nu spun nimic despre Acme, nici unul dintre ordinele de lot
Bob. Codul dvs. nu asigură prelucrarea eficientă a mai multe comenzi în același timp?
Tu. Ah ... da, desigur.
În mod clar, ceea ce sa întâmplat și de ce codul pare Bob este „prea lent.“ Nu ai spus nimic nici despre Acme, nici de prelucrare a lot. Ciclul Bob încarcă clasa regulate Client și sunt susceptibile de a încărca 100 de ori aceeași înregistrare adresă. Această problemă este ușor de rezolvat dacă luați o serie de comenzi, mai degrabă decât una, plus adăugând unele cache simplu. Params cuvinte cheie în C # există pentru astfel de situații.
Dacă vom modifica funcția, în acest fel, de prelucrare a lot, Bob brusc accelerat. Cele mai multe dintre aceste provocări vor dispărea, pentru că puteți găsi doar o înregistrare a acesteia într-un depozit temporar ID (dicționar).
Odată ce ați deschis API la „mulți“ - și imediat trebuie să se conecteze orice control la frontieră. Ce este, de exemplu, dacă cineva trimite un milion de comenzi în metoda ta? Se pare că există un număr mare de oportunități în afara acestei arhitecturi? Este în acest caz, este util ca o reprezentare a arhitecturii sistemului și a proceselor de afaceri. Dacă știți că, în practică, poate fi necesar pentru a trata mai mult de 10 000 de comenzi, puteți lua cu încredere controlul de 50 000. În acest fel vă asigura că nimeni nu va fi capabil de a pune sistemul o provocare uriașă inacceptabilă.
Desigur, lista de posibile optimizări nu este limitată, dar exemplul arată cum poți scăpa de muncă inutilă dacă de la început pentru a conta pe „set“ elemente.
Desigur, verificați toate referirile la nul - este o afacere de complicat, și uneori măsură excesivă. Cu toate acestea, în nici un caz nu ar trebui să se bazeze pe datele furnizate de o sursă care nu dețineți controlul. Prin urmare, trebuie să verificați nule parametrul «ordinele», precum și copii ale ordinului în cadrul acestuia la zero.
Verificați cu regularitate pentru nul, puteți evita enervant apeluri de la clienții care caută suport tehnic și întrebați ce „obiect instanță.“ Prefer întotdeauna perebdet; mai bine lasa funcția mea returnează implicit și autentificat mesajul (sau trimite un avertisment), care vor fi eliminate de eroare destul de inutil „nu indică o instanță a unui obiect.“ Desigur, această decizie depinde în întregime de tipul de sistem pe codul ruleaza pe client sau pe server, etc. Ideea este că zero poate fi ignorată, dar numai atâta timp cât nu se va intoarce impotriva.
EXPLICAȚIE: Pentru a fi sincer, eu nu spun că funcția este de a „inactiv“ în cazul în care va cădea de stat invalid. Dacă zero de opțiuni pentru sistemul dvs. sunt inacceptabile, arunca o excepție (ca ArgumentNull în .NET). Cu toate acestea, în unele situații împiedică complet o întoarcere tăcere semnificativă, și nu este necesar să se acorde excepții. De exemplu, metodele actuale de a reveni, de obicei, valoarea pe care a fost trimis la ei în cazul în care nu pot face nimic cu această valoare. Există prea mulți factori care nu permit să facă recomandări generale privind momentul în față cu zero.
Tu. John, ce treci în codul meu? Se pare ca o parte-comandă.
John. Oh, îmi pare rău. Me ceva nu este nevoie de metoda dvs., dar alte cereri de bibliotecă pe care am trece parametrii de comandă. Cred că acest lucru este biblioteca codul. Nu lucrez cu ordinele, dar folosește alte necesități de bibliotecă.
Tu. Biblioteca ar trebui să fie corectată: strâmbe ca proiectate!
John. Știi, că biblioteca a dezvoltat organic cu obiectivele de afaceri - se schimbă ceva. Matt a scris-o, și în această săptămână nu va mai fi; în general, nu știu cum să-l schimbe. Codul dvs. nu ar trebui să verifice dacă intrarea este validă?
Tu. Da ... într-adevăr.
Sper că am reușit să transmit cititorului ideea principală a acestui articol nu este cazul, astfel încât codul poate lua orice informație de intrare fără probleme. La punerea în aplicare orice funcție sau API este necesar să se ia în considerare modul de a utiliza acest API. În exemplul nostru, funcția inițială a crescut de la 12 la 50 de linii, chiar dacă n-am făcut nicio modificare drastice fac. Toate codul pe care am adăugat, trebuie să ne asigurăm scalabilitate, controlul frontierelor, precum și funcția de mânere în mod corect și eficient orice intrare.
Volumul de date stocate în ultimii ani a crescut exponențial, și, prin urmare, amploarea datelor de intrare va crește, în timp ce calitatea datelor pot cădea numai. Dacă de la dreapta începe să scrie API, acesta poate juca un rol vital în creșterea afacerilor, adaptarea la baza de clienți în creștere, și în viitor - pentru a salva pe suport tehnic (dureri de cap și vei avea mai puține) costurile.