Diskuze: API pro databázi - dotazy zvenčí
V předchozím kvízu, Online test znalostí PHP, jsme si ověřili nabyté zkušenosti z kurzu.

Tvůrce

Zobrazeno 39 zpráv z 39.
//= Settings::TRACKING_CODE_B ?> //= Settings::TRACKING_CODE ?>
V předchozím kvízu, Online test znalostí PHP, jsme si ověřili nabyté zkušenosti z kurzu.
Podle popisu to vypadá OK. Záleží na realizaci. Budete chtít použít relační databázi nebo jinou?
Normálně relační. Na webu bude spíše info o aplikaci, resp. uživatel si bude moct prohlídnou svůj profil, editovat ale více bude muset dělat na klientech na mobilu... a klienti budou potřebovat dostávat a updatovat data v DB
Zatím víc neprozradím, popravdě, není úplně jasný ani celá realizace
projektu . Ale co je 100%
jisté tak je to, že se pokusíme skloubit virtuální hraní s realitou. Tedy
tak, že realita jako taková bude nesmírně důležitá pro virtuální pokrok
Pokud mluvíme o RESTful API tak to má svoje specifika a best practise, které je dobré dodržovat (ne dogmaticky, ale rozumně). REST API rozdělil Leonard Richardson do 3 resp. 4 úrovní:
Nultá úroveň - samotný přenos dat. REST se totiž neváže na HTTP, takže je teoreticky možné použít jinou možnost přenosu. HTTP je ale dnes tak moc rozšířené, že snad ani nemá cenu mluvit o jiných možnostech.
První úroveň - Zdroje (Resources): Místo toho, abys posílal požadavky na jeden centrální bod, použiješ jich víc. Každý zdroj má pak právě jeden koncový bod, kde ho můžeš dosáhnout. GET /articles - vrátí seznam článků, GET /articles/1/comments vrátí seznam komentářů k jednomu danému článku apod. Je důležité zvolit si nějaké standard pojmenovávání zdrojů (např. používat buď jen množné číslo - GET /articles, GET /comments, nebo jen jednotné GET /article, /comment)
Druhá úroveň - HTTP verbs: neomezuj se jen na GET a POST. HTTP nabízí i další metody jako jsou PUT, PATCH, DELETE, OPTIONS. Názvy zdrojů nesmí obsahovat slovesa, jen podstatná jména (i když v některých případech je lepší to porušit, jako třeba u vyhledávání - GET /search)
Best practise v používání HTTP verbs je: GET - získání dat, POST - vytvoření, PUT - úpravy, DELETE - smazání, PATCH - částečné úpravy (PATCH vlastně není v základní specifikaci HTTP ale v RESTfull API se dost používá)
V HTTP jsou taky stavové kódy a je jich zdaleka víc, než jen 200 OK. Pravděpodobně znáš ještě minimálně 404 Not Found. Já používám v REST API nejčastěji asi: 200 OK, 201 Created (při POST, pokud byl vytvořen obsah), 204 No Content (když požadavek na server pokud proběhne v pořádku, ale server nic nevrátí), 304 No Modified (pro cache), 400 Bad Request (Požadavek na server je nějakým způsoben nečitelný - třeba špatný JSON apod.), 401 Unauthorized (když klient není ověřen), 403 Forbidden (když klient nemá přístup k danému obsahu), 404 Nod Found (zdroj není nalezen), 405 Method Not Allowed (zdroj není dostupný pro tuto metodu - příklad je možné použít GET /articles a POST /articles, ale už třeba nemůžeš článek smazat, takže nelze DELETE /articles - je vhodné vývojářům v tomto momentu poskytnout seznam podporovaných metod pro danou URL), 410 Gone (zdroj není už na téhle adrese dostupný - to se používá při verzování), 415 Unsupported Media Type (klient v požadavku na server uvedl Content-Type, který server nepodporuje), 422 Unprocessable Entity (chyba validace dat - třeba formuláře apod.), 429 Too-Many requests (kdybys chtěl zpřístupnit API veřejnosti, ale chceš kontrolovat maximální počet požadavků pro každého klienta - třeba za den)
Velmi důležité je udržet REST API bezstavové. Např. autentikace uživatele by neměla záviset na session nebo cookies. Každý požadavek by měl obsahovat ověřovací údaje, podle kterých REST API pozná, kdo se připojil. Možností je víc, nejrozšířenějším standardem je OAuth (to doporučuji - počítá i s případy, kdy nelze u klienta jako je Android nebo JavaScript uchránit citlivé údaje).
Třetí úroveň - Hypermedia Controls: konečně třetí úroveň s poněkud divným akronymem: HATEOAS (Hypermedia as the Engine of Application State). Pro mě velmi zajímavé téma, ale zatím se moc nepoužívá. Velice zjednodušeně jde to, že máš jeden základní endpoint, který ti vrátí odkaz na další zdroje, ty zase odkazují na další atd. Každý zdroj tak klientovi dává možnosti, jakou akci provést nebo kam jít dál. Představit se to dá jako HTML dokument s odkazy na další stránky. Výhody jsou celkem jasné - klient není závislý na URL adresách (jen na té první) - ty se mohou klidně změnit. Také lze v průběhu přidávat nebo měnit další funkčnost, aniž by se u klienta něco upravilo.
Nakonec bych ještě přidal pár doporučení, které se mi osvědčila při návrhu RESTful API v mé aplikaci:
GZIP komprese - v PHP je to triviální věc a prohlížeče
s GZIP umí pracovat
JSON jako hlavní formát - hodně rozšířený formát, se kterým umí pracovat dobře spousta jazyků. Kdyby ses ale rozhodl podporovat i jiný formát, použij hlavičku Content-Type pro detekci (když klient pošle request s Content-Type: application/json vrať mu JSON, když Content-Type: application/xml, vrat XML - když něco jiného, vrat klientovi error 415 Unsupported Media Type). Detekci typu můžeš dát i do URL (GET /articles.xml, GET /articles.json), ale v tom případě nepoužívej Content-Type - je to pak matoucí.
Cache - HTTP má vestavěnou podporu pro nesdílený cache pomocí hlaviček ETag nebo Last-Modified
Relace - Osvědčilo se mi používat /<zdroj>/<id>/<relace>/<id relace>/<další relaci> atd. Uvedu pár příkladů, abys to líp pochopil:
GET /articles/1/comments - vrátí komentáře k článku s ID 1
GET /articles/1/comments/5 - vrátí komentář s ID 5 k článku s ID 1
DELETE /articles/1/comments/5 - smaže komentář s ID 5 u článku s ID 1
Stránkování - neni nic jednoduššího než klientovi poskytnout URL na další, předchozí příp. poslední stránku. Používá se na to hlavička "Link". Je taky vhodné klientovi vrátit přesný počet všech položek v hlavičce X-Total-Count
Verze přímo v URL - (např. /v1/articles/5) můžeš tak snadno rozdělit verze API (pro podporu starších aplikací). Nikdy ale nevkládej do URL minoritní verzi (jako např. v1.1 apod.) - to totiž značí, že se veřejné rozhraní často mění, což by nemělo. (Poskytování verze přímo v URL je mimochodem v rozporu s pravidlem v první úrovni REST API, ale vyplatí se verzi v URL uvádět)
snake_case, camelCase, PascalCase - používej všude jen jeden typ (nebo ještě lépe nabídni klientům možnost zvolit si, který z nich chtějí použít). snake_case je mnohem líp čitelný než camelCase, ale s camelCase se zase přirozeněji pracuje v JS.
Tak to bylo ode mě vše
Mohl bych toho říct mnohem víc, ale už Tě tím nebudu zatěžovat. Raději
tě odkážu na pár zdrojů, kde se dočteš víc:
http://www.vinaysahni.com/…-restful-api¨
http://apigee.com/…st-practices
http://martinfowler.com/…tyModel.html
EDIT: sám jsem napsal knihovnu pro REST API v PHP, ale nebudu ji tady
raději veřejně zmiňovat, protože by to mohlo vyvolat nechtěné reakce Kdybys měl zájem, mohu ti poslat
odkaz.
Wow, schválně jsem se koukal a ten komentář má skoro 7.000 znaků,
nechceš to publikovat?
Chtěl jsem o REST API něco napsat Pokusím se to někdy trochu upravit, aby to bylo vhodné publikovat
jako článek.
Zajímavý článek jsem našel i tady:
http://www.zdrojak.cz/…-webove-api/
Je to o konkrétním API Twitteru. Bohužel ho asi Twitter mezitím změnil a
proto ty ukázky nefungují. To však není problém, pro inspiraci to
stačí.
Článek jsem četl a je zajímavý. I když Twitter je zrovna API, od kterého bych se moc neinspiroval. Např. POST statuses/destroy/:id, GET statuses/show/:id je IMHO prostě špatně. Proč to dělat složitě? Stačí přece DELETE statuses/:id, GET statuses/:id Když mám zařízení, ze kterého nemůžu nijak vyvolat metodu DELETE, použiji třeba POST a nastavím speciální hlavičku X-HTTP-Method-Override nebo speciální parametr v Query string v URL. Rozhodně bych to ale nedával přímo do názvu zdroje. To samé s Direct messages: mají tam třeba GET direct_messages a POST direct_messages/new Proč? Taky mi vadí, že mají minoritní verzi přímo v URL.
Wow Díky za odpověď,
půlku věcí ani prakticky neznám
:[ ... možná by odkaz pomohl
V diskuzním fóru pod článkem je to vysvětleno. Tvé argumenty považuji za správné.
Ještě jsem našel jedno zajímavé REST API.
https://www.parse.com/docs/rest
Asi už nějaké API zvládnu. Vlastně je to jen rozšířením toho, co už
znám a je tomu dán nějaký řád.
Tohle vypadá mnohem líp
Já můžu ještě doporučit GutHub API http://developer.github.com/ nebo některá API od Google,
třeba Google Drive - https://developers.google.com/…2/reference/
Petr Nymsa: Jaký odkaz myslíš? Na tu knihovnu, nebo na některé
ty věci v PHP?
Koukám, že Google také v klidu používá v URL slovesa. Když si někdo napíše vlastního klienta, tak může používat všechny typy požadavků, ale pokud se mám spoléhat na kvalitu prohlížečů, tak kromě GET a POST se toho moc použít nedá. Ještě přes AJAX by mělo fungovat PUT a DELETE.
Někdy je lepší tam ta slovesa dát (třeba u toho vyhledávání), ale jen výjimečně. Tady to mají jako zkratku k dané operaci, která se často používá (POST /files/fileId/touch -> PATCH /files/fileId { "updateDate": "datum" })
V JavaScriptu přes AJAX nemám problém s GET, POST, DELETE, PATCH ani UPDATE, ale kdyby to prostě někdy nešlo, je vhodné dát klientovi tu možnost "přepsat" metodu. Pokud možno ale nedovolit přepisování metod u GET, jen u POST požadavků.
Zkusil jsem si teď požadavky u lokálního PHP serveru. Kromě UPDATE zvládá všechny ostatní zmíněné.
PUT funguje také. Problémy tedy nebudou v serverech, ale jen v klientech.
Zkusil jsem ještě server moxo.cz, ten sežere i ABCDEF a je mu to úplně fuk.
No já nevím .. asi napíšu
ještě jednou co potřebujeme aby klient dělal s DB nebo nějakým způsobem
toho dosáhl
Na co se mám zaměřit nejdřív ? Nikdy jsem ještě právě nějakou API pro přístup k DB nedělal a tak nevím od čeho se přesně odpíchnout
API je jednoduché, nemusíš to dělat přes REST, vystačíš si s POST a GET. Funguje to většinou tak, že posíláš JSONy nebo XML mezi serverem a aplikací.
Takhle jsem to původně zamýšlel Díky, mrknu na to
Výpis informací (SELECT) -> metoda GET
Modifikace dat (INSERT, UPDATE, DELETE) -> metoda POST
Zkoušel jsem víc prohlížečů. Z formuláře kromě POST všechno převáděly na GET. Ostatní metody jsou zřejmě dostupné pouze přes AJAX.
REST API je prostředník mezi aplikací a daty. Ze všeho nejdřív se zaměř na veřejné rozhraní (strukturu tabulek pokud používáš relační databázi), pak si definuj, které operace nad těmi daty mohou klienti (aplikace) dělat a podle toho k datům udělej REST API. Samotná implementace už není tak složitá. Cíl je udělat něco takového (nevím, co chceš přesně udělat, takže to neber jako nějaký hotový návrh):
GET /users/<ID> - vrátí informace o uživateli
PUT /users/<ID> - upraví data o uživateli
GET /users/<ID>/score - vrátí záznamy o výsledku všech her
uživatele
POST /users/<ID>/score - vloží záznam o výsledku jedné hry
GET /users/<ID>/score/<ID> - vrátí výsledek z jedné
konkrétní hry
DELETE /users/<ID>/score/<ID> - smaže výsledek z jedné hry
POST /games - vytvoří novou hru
GET /games - vrátí seznam všech her
GET /games/<ID> - vrátí informace o jedné konkrétní hře
...
S tím, že tohle bude fungovat pouze přes AJAX nebo vlastního klienta.
U běžného prohlížeče lze počítat pouze s metodami GET a POST.
To snad nevadí, ne? Klient bude většinou Android, iOS, Windos phone aplikace nebo JavaScript. Případně to může být PHP, Ruby, Python a další serverové jazyky, kde to není žádný problém.
Tím jsem chtěl upozornit na to, že jako klienta REST není možné použít internetový prohlížeč. Pouze přes AJAX.
Ještě jedna zajímavost: Databáze CouchDB používá REST API. Není tedy nutné to rozhraní programovat.
Ještě jsem zjistil, že PHP 5.4 jako server zvládá i WebDAV. Apache by ho měl zvládnout také.
Možná by stálo za to použít přímo rozhraní WebDAV.
Napsal jsem si takový jednoduchý router pro REST v PHP:
http://www.itnetwork.cz/dev-lighter/176
A ještě jsem našel, jak je to s metodami PUT a DELETE
http://stackoverflow.com/…sed-in-forms
Zjednodušeně: PUT a DELETE jsou podporovány v HTTP, ale nejsou podporovány v HTML. To znamená, že není možné je použít ve webových formulářích. AJAX však pracuje přímo s HTTP a proto v něm je možné používat i tyto metody.
A ještě způsob, jak to obchází některé frameworky.
<form method="POST" ...>
<input type="hidden" name="_method" value="PUT" />
Určitě se to však nesnaž tunelovat přes GET.
Našel jsem dva klienty jako pluginy do Firefoxu (RESTClient) a Chrome (Dev
HTTP Client) které zvládají REST API. Sice neumí víc než Curl, ale vypadá
to hezčí
Ty jsou hodně užitečné. Já používám do Chrome Postman https://chrome.google.com/…oooidkmcomcm
Také hezké, ale asi zůstanu u osvědčeného Curl. Umožňuje mi dělat automatické testy.
Díky za odpovědi ! (Kit, Drahomír Hanák)
Vytvořit API není mojí hlavní úlohou v projektu, sice budu se podílet na její tvorbě ale hlavní vývoj má na starost Neaktivní uživatel , má jistou představu jak ji realizovat, možná by se mohl zde podělit s nápadem abychom schytali názory a kritiku
Správně definované API je polovinou úspěchu. Nepodceňoval bych to.
Já to nepodceňuju. Stejěn první měsíc vývoje bude cílem vytvořit to
API + web. Ale hlavní hlava tohoto je FunebrakCZ . Já jsem hlavně realizátor
celého projektu, vývoj klientů
Ten router průběžně vylepšuji. Ten v dev-lighteru má sice trochu zpoždění za tím lokálním, ale třeba se ti také bude hodit.
Zobrazeno 39 zpráv z 39.