Hack: uusi ohjelmointikieli HHVM:lle – Facebook Engineering

Onko kiire? Kokeile Hackia nyt: http://hacklang.org/

Vapautamme tänään Hackin, HHVM:lle kehittämämme ohjelmointikielen, joka toimii saumattomasti PHP:n kanssa. Hack sovittaa yhteen PHP:n nopean kehityssyklin ja staattisen tyypittelyn tarjoaman kurinalaisuuden ja lisää samalla monia ominaisuuksia, joita löytyy yleisesti muista nykyaikaisista ohjelmointikielistä.

Olemme ottaneet Hackin käyttöön Facebookissa, ja se on ollut suuri menestys. Viime vuoden aikana olemme siirtäneet lähes koko PHP-koodipohjamme Hackiin sekä orgaanisen hyväksynnän että useiden itse kehitettyjen refaktorointityökalujen ansiosta.

Olemme myös ylpeitä voidessamme julkaista Hackin avoimen lähdekoodin version yleisölle http://hacklang.org/ osana HHVM-runtime-alustamme, joka tukee nyt sekä Hackia että PHP:tä.

Motivaatio

Jokainen PHP-ohjelmoija tuntee jokapäiväiset tehtävät, jotka voivat olla hankalia tai hankalia. Yllä oleva koodi on hyvä esimerkki yleisestä virheestä, jossa metodia saatetaan kutsua yllättäen null-oliolle, mikä aiheuttaa virheen, joka huomataan vasta ajon aikana. Toinen esimerkki on monimutkainen sovellusrajapinta, jonka semantiikan kehittäjät saattavat ymmärtää hyvin, mutta silti käyttää aikaa arkipäiväisten metodien nimien etsimiseen dokumentaatiosta.

Facebookin mittakaavassa – kun tuhannet insinöörit toimittavat uutta koodia kahdesti päivässä – tällaiset hidastelut ovat vielä ongelmallisempia. Ennen Hackia meillä oli yksinkertainen kieli, jossa oli nopea palautesilmukka – mutta miten voisimme lieventää edellä kuvattuja ongelmia? Voisiko virheiden varhainen havaitseminen toimia rinnakkain nopean iteroinnin kanssa ja samalla säilyttää investointimme PHP:hen? Voisiko parannettu koodianalyysi ja introspektio auttaa tekemään kehittäjistä tuottavampia automaattisen täydennyksen kaltaisten työkalujen avulla?

Traditionaalisesti dynaamisesti tyypitetyt kielet mahdollistavat nopean kehityksen, mutta uhraavat kyvyn havaita virheet varhaisessa vaiheessa ja tutkia koodia nopeasti, erityisesti suuremmissa koodipohjissa. Sitä vastoin staattisesti tyypitetyt kielet tarjoavat enemmän turvaverkkoa, mutta usein nopean iteroinnin kustannuksella. Uskoimme, että oli pakko löytyä jokin kultainen piste.

Näin syntyi Hack. Uskomme, että se tarjoaa parhaat puolet sekä dynaamisesti että staattisesti tyypitetyistä kielistä ja että se on arvokas kaikenkokoisille projekteille.

Hack-kieli

Hackin juuret ovat syvällä PHP:ssä. Itse asiassa useimmat PHP-tiedostot ovat jo kelvollisia Hack-tiedostoja. Teimme tietoisen valinnan olla tukematta kourallista vanhentuneita funktioita ja ominaisuuksia, jotka eivät olleet yhteensopivia staattisen tyypityksen kanssa (esim. ”muuttujan muuttujat” ja extract()-funktio). Olemme myös lisänneet monia uusia ominaisuuksia, joiden uskomme tekevän kehittäjistä tuottavampia.

Tärkein lisäyksemme on staattinen tyypitys. Olemme kehittäneet järjestelmän, jonka avulla funktioiden allekirjoituksiin ja luokan jäseniin voidaan merkitä tyyppitietoja; tyypintarkastusalgoritmimme (”tyypintarkastaja”) päättelee loput. Tyyppitarkastus on inkrementaalinen, joten jopa yhden tiedoston sisällä osa koodista voidaan muuntaa Hack-koodiksi, kun taas loput koodista pysyy dynaamisesti tyypitettynä. Teknisesti ottaen Hack on ”asteittain tyypitetty*”* kieli: dynaamisesti tyypitetty koodi toimii saumattomasti yhteen staattisesti tyypitetyn koodin kanssa.

Hackin tyyppijärjestelmässä olemme ottaneet käyttöön useita ominaisuuksia, kuten geneeriset tyypit, nollattavat tyypit, tyypin aliasing ja tyyppiparametrien rajoitukset. Nämä uudet kielen ominaisuudet ovat huomaamattomia, joten Hackilla kirjoitettu koodi näyttää ja tuntuu edelleen dynaamiselta kieleltä, johon PHP-ohjelmoijat ovat tottuneet.

Hack lisää kuitenkin staattisen tyypintarkistuksen lisäksi muita ominaisuuksia, mukaan lukien kokoelmat, lambda-lausekkeet ja paluutyyppien ja parametrityyppien ajoaikainen pakottaminen.

Kokoelmat tarjoavat siistin, tyypin kannalta turvallisen vaihtoehdon PHP:n taulukoille. Suunnittelimme ne erityisesti toimimaan hyvin staattisen tyypityksen ja geneeristen ominaisuuksien kanssa. Collections API tarjoaa monia klassisia ylemmän asteen funktioita, kuten map() ja filter(), jotka helpottavat funktionaalisen ohjelmoinnin tyylejä.

Lambda-lausekkeet antavat tiiviin syntaksin sulkujen luomiseen. Vaikka PHP:ssä on sulkeumia, se vaatii ohjelmoijaa nimenomaan nimeämään muuttujat, joita hän tarvitsee käyttää sulkeutuvista alueista. Hackin lambda-lausekkeiden avulla päättelemme nämä käyttötavat automaattisesti, mikä säästää turhaa työtä. Lambda-lausekkeiden avulla on kätevämpää hyödyntää Collections API:ta täysimääräisesti.

Palauttamis- ja parametrityyppien (mukaan lukien skalaarityypit, kuten int ja string) ajoaikainen pakottaminen tarjoaa turvallisuutta, joka ylittää sen, mitä voidaan tarkastaa staattisesti, kun tyyppimerkintöjä lisätään vähitellen koodikantaan. Ajonaikainen pakottaminen auttaa ohjelmoijia havaitsemaan ja diagnosoimaan tietyntyyppisiä ongelmia helpommin, ja se auttaa HHVM:n JIT:tä tuottamaan tehokkaampaa koodia tekemällä siitä turvallista luottaa tyyppi-annotaatioihin optimointitarkoituksessa.

Tyyppien välitön tarkistus

Kehityksen aikana PHP-ohjelmoija tyypillisesti siirtyy nopeasti edestakaisin lähdekoodin ja selaimen välillä. Insinöörit voivat iteroida niin nopeasti kuin tarvitsevat, testata ja virittää käyttökokemusta, kunnes se on täydellinen.

Traditionaalisesti tyypintarkastaja häiritsisi tätä palautekierrosta, koska lähdekoodin analysointi vie aikaa. Emme halunneet hidastaa PHP:n työnkulkua, joten keksimme uuden lähestymistavan, jolla sovitamme yhteen välittömän palautteen ja tyyppiturvallisuuden.

Ratkaisumme oli arkkitehtuuriltaan tyyppitarkistaja paikalliseksi palvelimeksi, joka tarkkailee tiedostojärjestelmää. Palvelin pitää kaiken tiedon lähdekoodista muistissa ja päivittää itsensä automaattisesti, kun tiedosto muuttuu levyllä. Tämä lähestymistapa on tuottanut tulosta: tyypintarkastaja toimii tyypillisesti alle 200 millisekunnissa ja kestää harvoin yli sekunnin, joten se on helppo integroida kehitystyönkulkuun ilman havaittavaa viivettä.

Koodinsiirto

Hackin tyyppiturvallisuudesta ja refaktoroinnista koituvat hyödyt kasvavat sitä suuremmiksi, mitä enemmän sitä käytetään koodipohjassa. Ymmärtäen, että joidenkin koodien olisi vaikea siirtyä heti kokonaan Hackiin, meille oli tärkeää, että Hack kehitetään siten, että se voi olla suoraan rinnakkain muiden PHP-tiedostojen kanssa, kun se otetaan käyttöön asteittain.

Muutosprosessin loppuosa, kuten tyyppi-annotaatioiden lisääminen ja uusien kieliominaisuuksien käyttäminen, voidaan tehdä koodikantaan sopivalla tavalla. Esimerkiksi tyyppihuomautus voidaan lisätä yhteen funktioon, mutta jättää pois toisesta funktiosta, jopa samassa tiedostossa. Jos funktion parametrilla tai luokan jäsenellä ei ole eksplisiittistä tyyppi-annotaatiota, tyypintarkastaja pitää sen tyyppiä dynaamisena, eikä se tarkista kyseisen arvon tyyppiä.

Facebookissa huomasimme, että insinöörimme arvostivat Hackia niin paljon, että he alkoivat muuntaa vapaaehtoisesti suurimman osan omasta koodistaan. Koska puussamme on miljoonia rivejä koodia, halusimme myös jonkinlaista automaatiota, joten rakensimme ja käytämme useita koodinmuokkaustyökaluja prosessin avuksi (jotka julkaisemme osana Hackia).

Ei hätää, PHP:si on turvassa!

HHVM on edelleen PHP-ajoaika, ja aiomme pitää sen sellaisena. Itse asiassa työskentelemme kovasti saavuttaaksemme tasavertaisuuden PHP-5:n kanssa. Yksi HHVM:n tärkeimmistä prioriteeteista on ajaa muokkaamatonta PHP-5-lähdekoodia sekä yhteisön vuoksi että siksi, että luotamme sisäisesti kolmannen osapuolen PHP-kirjastoihin.

HHVM on nyt ajoaika, joka tukee *kumpikin* PHP:tä ja Hackia, joten voit alkaa hyödyntää Hackin uusia ominaisuuksia asteittain.

Hyvää hauskanpitoa Hackin kanssa!

Olemme iloisia voidessamme avata lähdekoodin sekä Hackille että työkaluille, joita voit käyttää automaattiseen muuntamiseen. Tämä on vasta ensimmäinen askel, ja olemme sitoutuneet jatkamaan tämän ohjelmiston kehittämistä, jotta kehitys olisi entistäkin helpompaa sekä omille insinööreillemme että laajemmalle yhteisölle. Hackin arvo *ei* rajoitu vain suuriin projekteihin: tyyppitietojen, hyvien virheilmoitusten ja nopean palautteen avulla myös pienet koodipohjat voivat hyötyä Hackin hyödyistä.

Ensi kuussa esittelemme kielen myös Hack Developer Day -tapahtumassa Facebookin kampuksella Menlo Parkissa, ja toivomme näkevämme teidät siellä joko henkilökohtaisesti tai netissä.

Haluaisimme mielellämme palautetta tähänastisesta työstämme ja toivotamme kaikki tervetulleiksi osallistumaan HHVM:n ja Hackin yhteisöihin.

Kiitokset

Hackin kehittämiseen ovat osallistuneet monet ihmiset.

Hackin ydintiimiin kuuluvat Julien Verlaguet, Joel Beales, Eugene Letuchy, Gabriel Levi, Joel Marcey, Erik Meijer, Alok Menghrajani, Bryan O’Sullivan, Drew Paroski, James Pearce, Joel Pobar ja Joshua Van Dyke Watzman.

Erikoiskiitos kuuluu yhteisön varhaisille omaksujille arvokkaasta palautteesta kielen parantamiseksi: James Miller, Simon Welsh, Nils Adermann, Fabien Potencier ja Alexander Mols.

Hack on kirjoitettu pääasiassa OCamlilla. Haluamme kiittää Gallium-tiimiä (INRIA) OCaml-kielen kehittämisestä ja Ocsigen-tiimiä (CNRS – University of Paris Diderot – INRIA) Ocsigenin js_of_ocaml-osan kehittämisestä.

Ja tietenkin kiitokset kaikille muillekin, jotka ovat auttaneet tekemään Hackista sen kielen, joka se on tänään. Lista on liian tyhjentävä blogikirjoitukseen, mutta tiedätte, keitä olette.

Vastaa

Sähköpostiosoitettasi ei julkaista.