Mitä jaettava ja tuotantokelpoinen analyysikoodi on? Mitä pitäisi ottaa huomioon, kun sellaista ollaan tekemässä? Tässä blogissa kerron neljä tärkeintä kohtaa, mitä kunkin Data Scientistin pitäisi pitää mielessä koodia tehdessä.
Usein katselmoin eri Data Scientistien kirjoittamaa analyysiskriptiä, joka on toteutettu joko R:llä tai Pythonilla. Näissä analyysien laadullinen puoli on erittäin hyvin ja analyyttisesti tehty. Dataa on käsitelty outlierien karsimisella ja puuttuvien arvojen poistamisella tai imputoinnilla. Mallin ja mallinnuksessa käytettyjen muuttujien valinta on tehty huolella ja tulokset on testattu ja todettu, jotta ratkaisu vastaa siihen ongelmaan, mitä ollaan lähdetty ratkomaan.
Harmillisen usein skriptit on kuitenkin kirjoitettu vain yhden pistemäisen ongelman ratkaisemiseen ja vain ainoastaan tekijänsä omiin tarpeisiin.
Ei muille jaettavaksi saati hyödynnettäväksi myöhemmin samantyyppisen ongelman ratkaisemisessa. Lopputulos on myös erittäin kaukana siitä, että skripti voitaisiin laittaa automaattisesti tuotantoon siten, että tekijä voi nukkua yöunensa rauhassa. Alla mielestäni neljä tärkeintä kohtaa, jotka kunkin Data Scientistin pitäisi pitää mielessä koodia tehdessä.
#1 Ympäristöjen hallinta, CI/CD ja versionhallinta
Ratkaisua ei pitäisi toteuttaa vain ja ainoastaan tuotantoon – kuten valitettavan usein näen tapahtuvan – vaan kehitystä tulisi tehdä siihen tarkoitetussa kehitysympäristössä. Tehdyt ratkaisut on hyvä testata tuotannon kaltaisessa testiympäristössä ja kun ollaan varmoja toimivuudesta, viedään sitten vasta tuotantoon. Näin vältytään yllättäviltä ongelmilta tuotannossa ja pystytään tekemään jatkokehitystä pudottamatta jo toimivaa ratkaisua pois päältä.
Näkisin, että continuous integration/deployment -työkalut pitäisi olla osa jokapäiväistä Data Scientistin työtä.
Koodit tulisi pitää versionhallinnassa eikä Data Scientistin omalla läppärillä. Tämä perinteinen “it works on my machine” -ajattelu on harmittavan tyypillistä Data Science -piireissä, koska nopeita testailuja on näin kiva toteuttaa. Tämä tekee kuitenkin hallaa lopputulokselle, sillä ilman asiallista versionhallinnan käyttöä ratkaisun muutoshistoria jää vain kehittäjän omaan päähän, jos sinnekään. Tällöin ratkaisun jakaminen muille kehittäjille vaikeutuu ja mahdollinen sairasloma saattaa katkaista pitkäksi aikaa koko ratkaisun kehittämisen.
#2 Logitus, monitorointi ja hälytykset
Usein ratkaisut ovat vailla minkäänlaista logitusta saati monitorointia ja hälytyksiä. Logituksen tarkoitus on nostaa toteutuksen ongelmakohdat esille. Lisäksi kehittäjän kannalta kiinnostavaa on myös logituksen tuoma mahdollisuus analysoida sitä, miten ratkaisua käytetään. Sitä kautta toteutuksen jatkojalostaminen voidaan toteuttaa Data Science -hengessä analyyttisesti, eikä parhaiden arvausten perusteella.
Monitorointi ja automaattiset hälytykset yhdessä logituksen kanssa puolestaan mahdollistavat ongelmien ja virheiden automaattisen havainnoinnin.
Valitettavan usein virheet huomataan vasta loppukäyttäjien toimesta, ei ennakoitujen hälytysten kautta. Jos ratkaisuja kehitetään nykyaikaisesti pilvipalveluiden päällä, on siellä varsin helppoa ottaa käyttöön logitus-, monitorointi- ja hälytystoiminnallisuudet. Esimerkiksi AWS:n CloudWatch on yksi hyvä palvelu, jolla nämä voidaan toteuttaa.
#3 Salasanojen hallinta ja parametrisointi
Ohjelmistokehittäjille varsin tutut asiat ovat valitettavan usein unohtuneet tekoälyskripteistä. Usein salasanat, kymmenriviset SQL-lausekkeet ja tietokanta-urlit ovat samassa läjässä muun koodin kanssa. Tietoturvan, luettavuuden ja koodin muualla hyödynnettävyyden kannalta nämä ovat ensiarvoisen tärkeitä ottaa huomioon.
Parametrisointiin ja salasanojen hallintaan voi käyttää vaikkapa ohjelmien provisiointien ja konfiguraation hallinnan automatisointiin tarkoitettuja välineitä.
Tällaisia ovat esimerkiksi ansible tai vaikkapa pilvipalveluiden tarjoamat salasananhallintapalvelut.
#4 Testaa. Testaa. Testaa.
Testauksen merkitystä ei voi koskaan korostaa liikaa. Kone ei tee virhettä, mutta kehittäjä ja käyttäjä tekevät. Data Scientist yleensä panostaa isosti datan ja mallin testaamiseen, mutta kokonaisratkaisun laadulliset testaukset jäävät lähes poikkeuksetta vajaiksi. Lopputuloksen jalkautuksen kannalta kuitenkin tärkein osa on loppukäyttäjän kokemus ratkaisun toimivuudesta.
Mitä toimivampi kokonaisratkaisu, sitä helpompi sitä on myydä eteenpäin. Tähän auttaa testaus.
Laadullinen testaus pitäisi ottaa heti alusta alkaen automatisoidusti käyttöön. Lisäksi aina koodia kirjoittaessa pitäisi olla mielessä, miten testaan tämän toiminnallisuuden. Testaaminen on myös osa laadukasta ohjelmointitapaa.
Jos edellä mainitsemani kolme pääkohtaa on otettu ratkaisua kehittäessä huomioon, on todella paljon helpompaa rakentaa laadukkaat ja kattavat, automatisoidut, testit. Lue lisää esimerkiksi dev.solita.fi-blogista What is elegant code actually?.