Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff

Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff
A partire dallo scorso anno, la nostra azienda ha iniziato a organizzare hackathon. Il primo di questi concorsi ha avuto molto successo, ne abbiamo scritto in Articolo. Il secondo hackathon si è svolto a febbraio 2019 e non ha avuto meno successo. Riguardo agli obiettivi di tenere quest'ultimo non molto tempo fa ho scritto organizzatore.

Ai partecipanti è stato affidato un compito piuttosto interessante con completa libertà nella scelta dello stack tecnologico per la sua implementazione. Era necessario implementare una piattaforma decisionale per un'implementazione conveniente delle funzioni di punteggio dei clienti che potesse funzionare con un flusso rapido di applicazioni, resistere a carichi pesanti e il sistema stesso fosse facilmente scalabile.

Il compito non è banale e può essere risolto in molti modi, come eravamo convinti durante la dimostrazione delle presentazioni finali dei progetti dei partecipanti. All'hackathon c'erano 6 team di 5 persone, tutti i partecipanti avevano buoni progetti, ma la nostra piattaforma si è rivelata la più competitiva. Abbiamo un progetto molto interessante, di cui vorrei parlare in questo articolo.

La nostra soluzione è una piattaforma basata sull'architettura Serverless all'interno di Kubernetes, che riduce il tempo necessario per portare nuove funzionalità in produzione. Consente agli analisti di scrivere codice in un ambiente a loro conveniente e di distribuirlo in produzione senza la partecipazione di ingegneri e sviluppatori.

Cos'è il punteggio

Tinkoff.ru, come molte aziende moderne, ha un punteggio cliente. Lo scoring è un sistema di valutazione del cliente basato su metodi statistici di analisi dei dati.

Ad esempio, un cliente si rivolge a noi chiedendogli di concedergli un prestito o di aprire con noi un conto imprenditore individuale. Se intendiamo concedergli un prestito, dobbiamo valutare la sua solvibilità e, se il conto è di un imprenditore individuale, dobbiamo essere sicuri che il cliente non effettuerà transazioni fraudolente.

La base per prendere tali decisioni sono modelli matematici che analizzano sia i dati dell'applicazione stessa che i dati della nostra memoria. Oltre allo scoring, metodi statistici simili possono essere utilizzati anche per generare raccomandazioni individuali per nuovi prodotti per i nostri clienti.

Il metodo di tale valutazione può accettare una varietà di dati di input. E ad un certo punto possiamo aggiungere un nuovo parametro all'input che, in base ai risultati dell'analisi sui dati storici, aumenterà il tasso di conversione dell'utilizzo del servizio.

Disponiamo di una grande quantità di dati sulle relazioni con i clienti e il volume di queste informazioni è in costante crescita. Affinché il punteggio funzioni, l’elaborazione dei dati richiede anche regole (o modelli matematici) che permettano di decidere rapidamente chi approvare una richiesta, chi rifiutare e chi offrire un paio di prodotti in più, valutandone il potenziale interesse.

Per questo compito utilizziamo già un sistema decisionale specializzato IBM WebSphere ILOG JRules BRMS, che, sulla base delle regole stabilite da analisti, tecnologi e sviluppatori, decide se approvare o rifiutare un particolare prodotto bancario al cliente.

Esistono molte soluzioni già pronte sul mercato, sia modelli di punteggio che sistemi decisionali stessi. Utilizziamo uno di questi sistemi nella nostra azienda. Ma l'attività cresce, si diversifica, aumenta sia il numero di clienti che il numero di prodotti offerti e, allo stesso tempo, emergono idee su come migliorare il processo decisionale esistente. Sicuramente le persone che lavorano con il sistema esistente hanno molte idee su come renderlo più semplice, migliore e più conveniente, ma a volte le idee esterne sono utili. Il New Hackathon è stato organizzato con l'obiettivo di raccogliere idee valide.

Compito

L'hackathon si è tenuto il 23 febbraio. Ai partecipanti è stato offerto un compito di combattimento: sviluppare un sistema decisionale che dovesse soddisfare una serie di condizioni.

Ci è stato detto come funziona il sistema esistente e quali difficoltà sorgono durante il suo funzionamento, nonché quali obiettivi aziendali dovrebbe perseguire la piattaforma sviluppata. Il sistema deve avere un rapido time-to-market per lo sviluppo delle regole in modo che il codice di lavoro degli analisti entri in produzione il più rapidamente possibile. E per quanto riguarda il flusso delle domande in entrata, il tempo decisionale dovrebbe tendere al minimo. Inoltre, il sistema in fase di sviluppo deve avere funzionalità di cross-sell per dare al cliente l'opportunità di acquistare altri prodotti aziendali se approvati da noi e se presentano potenziale interesse da parte del cliente.

È chiaro che è impossibile scrivere dall'oggi al domani un progetto pronto per il rilascio che andrà sicuramente in produzione, ed è abbastanza difficile coprire l'intero sistema, quindi ci è stato chiesto di implementarne almeno una parte. Sono stati stabiliti una serie di requisiti che il prototipo deve soddisfare. È stato possibile provare sia a coprire tutti i requisiti nella loro interezza, sia a lavorare nel dettaglio sulle singole sezioni della piattaforma in fase di sviluppo.

Per quanto riguarda la tecnologia, a tutti i partecipanti è stata data completa libertà di scelta. È stato possibile utilizzare qualsiasi concetto e tecnologia: streaming di dati, apprendimento automatico, sourcing di eventi, big data e altri.

La nostra soluzione

Dopo un breve brainstorming, abbiamo deciso che una soluzione FaaS sarebbe stata l'ideale per completare l'attività.

Per questa soluzione è stato necessario trovare un framework Serverless idoneo a implementare le regole del sistema decisionale in fase di sviluppo. Poiché Tinkoff utilizza attivamente Kubernetes per la gestione dell'infrastruttura, abbiamo esaminato diverse soluzioni già pronte basate su di esso, di cui vi parlerò più avanti.

Per trovare la soluzione più efficace, abbiamo esaminato il prodotto in fase di sviluppo attraverso gli occhi dei suoi utenti. Gli utenti principali del nostro sistema sono gli analisti coinvolti nello sviluppo delle regole. Le regole devono essere distribuite sul server o, come nel nostro caso, distribuite nel cloud, per il successivo processo decisionale. Dal punto di vista di un analista, il flusso di lavoro è simile al seguente:

  1. L'analista scrive uno script, una regola o un modello ML basato sui dati del warehouse. Nell'ambito dell'hackathon, abbiamo deciso di utilizzare Mongodb, ma qui la scelta del sistema di archiviazione dei dati non è importante.
  2. Dopo aver testato le regole sviluppate sui dati storici, l'analista carica il suo codice nel pannello di amministrazione.
  3. Per garantire il controllo delle versioni, tutto il codice andrà ai repository Git.
  4. Attraverso il pannello di amministrazione sarà possibile distribuire il codice nel cloud come modulo Serverless funzionale separato.

I dati iniziali dei clienti devono passare attraverso un servizio di arricchimento specializzato progettato per arricchire la richiesta iniziale con i dati del magazzino. Era importante implementare questo servizio in modo tale che funzionasse con un unico repository (da cui l'analista prende i dati durante lo sviluppo delle regole) per mantenere una struttura dati unificata.

Anche prima dell'hackathon, abbiamo deciso quale framework Serverless avremmo utilizzato. Oggi ci sono molte tecnologie sul mercato che implementano questo approccio. Le soluzioni più popolari all'interno dell'architettura Kubernetes sono Fission, Open FaaS e Kubeless. Ci sono anche buon articolo con la loro descrizione e analisi comparativa.

Dopo aver valutato tutti i pro e i contro, abbiamo scelto scissione. Questo framework Serverless è abbastanza facile da gestire e soddisfa i requisiti dell'attività.

Per lavorare con Fission, è necessario comprendere due concetti di base: funzione e ambiente. Una funzione è un pezzo di codice scritto in uno dei linguaggi per i quali esiste un ambiente Fission. Elenco degli ambienti implementati in questo framework include Python, JS, Go, JVM e molti altri linguaggi e tecnologie popolari.

Fission è anche in grado di eseguire funzioni suddivise in più file, preconfezionati in un archivio. Il funzionamento di Fission in un cluster Kubernetes è assicurato da pod specializzati, gestiti dal framework stesso. Per interagire con i pod del cluster, a ciascuna funzione deve essere assegnata la propria route e alla quale è possibile passare parametri GET o corpo della richiesta nel caso di una richiesta POST.

Di conseguenza, abbiamo pianificato di ottenere una soluzione che consentisse agli analisti di implementare script di regole sviluppati senza la partecipazione di ingegneri e sviluppatori. L'approccio descritto elimina inoltre la necessità per gli sviluppatori di riscrivere il codice dell'analista in un altro linguaggio. Ad esempio, per l’attuale sistema decisionale che utilizziamo, dobbiamo scrivere regole in tecnologie e linguaggi altamente specializzati, la cui portata è estremamente limitata, e c’è anche una forte dipendenza dal server applicativo, poiché tutti i progetti di regole bancarie vengono distribuiti in un unico ambiente. Di conseguenza, per implementare nuove regole è necessario rilasciare l’intero sistema.

Nella soluzione da noi proposta non è necessario rilasciare regole; il codice può essere facilmente implementato con un clic di un pulsante. Inoltre, la gestione dell'infrastruttura in Kubernetes ti consente di non pensare al carico e al ridimensionamento; tali problemi sono risolti immediatamente. Inoltre, l’utilizzo di un unico data warehouse elimina la necessità di confrontare i dati in tempo reale con quelli storici, semplificando il lavoro dell’analista.

Quello che abbiamo ottenuto

Dato che siamo arrivati ​​all'hackathon con una soluzione già pronta (nelle nostre fantasie), tutto quello che dovevamo fare era convertire tutti i nostri pensieri in righe di codice.

La chiave del successo in qualsiasi hackathon è la preparazione e un piano ben scritto. Pertanto, la prima cosa che abbiamo fatto è stata decidere in quali moduli sarebbe stata composta la nostra architettura di sistema e quali tecnologie avremmo utilizzato.

L’architettura del nostro progetto è stata la seguente:

Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff
Questo diagramma mostra due punti di ingresso, l'analista (l'utente principale del nostro sistema) e il cliente.

Il processo di lavoro è strutturato in questo modo. L'analista sviluppa una funzione di regola e una funzione di arricchimento dei dati per il suo modello, archivia il suo codice in un repository Git e distribuisce il suo modello nel cloud tramite l'applicazione dell'amministratore. Consideriamo come verrà chiamata la funzione distribuita e prendiamo decisioni sulle richieste in arrivo dai client:

  1. Il cliente compila un modulo sul sito web e invia la sua richiesta al responsabile del trattamento. Una domanda sulla quale occorre prendere una decisione arriva all'input del sistema e viene registrata nel database nella sua forma originale.
  2. Successivamente, la richiesta grezza viene inviata per l'arricchimento, se necessario. È possibile integrare la richiesta iniziale con dati sia provenienti da servizi esterni che dallo storage. Anche la query arricchita risultante viene archiviata nel database.
  3. Viene avviata la funzione analista, che accetta una query arricchita come input e produce una soluzione, che viene anche scritta nello storage.

Abbiamo deciso di utilizzare MongoDB come archivio nel nostro sistema grazie all'archiviazione dei dati orientata ai documenti sotto forma di documenti JSON, poiché i servizi di arricchimento, inclusa la richiesta originale, aggregavano tutti i dati tramite controller REST.

Quindi, avevamo XNUMX ore per implementare la piattaforma. Abbiamo distribuito i ruoli con successo; ogni membro del team aveva la propria area di responsabilità nel nostro progetto:

  1. Pannelli di amministrazione front-end per il lavoro dell'analista, attraverso i quali può scaricare regole dal sistema di controllo della versione degli script scritti, selezionare opzioni per arricchire i dati di input e modificare gli script delle regole online.
  2. Amministrazione backend, inclusa API REST per il front e integrazione con VCS.
  3. Configurazione dell'infrastruttura in Google Cloud e sviluppo di un servizio per l'arricchimento dei dati di origine.
  4. Un modulo per l'integrazione dell'applicazione di amministrazione con il framework Serverless per la successiva implementazione delle regole.
  5. Script di regole per testare le prestazioni dell'intero sistema e aggregazione di analisi sulle applicazioni in arrivo (decisioni prese) per la dimostrazione finale.

Cominciamo in ordine.

Il nostro frontend è stato scritto in Angular 7 utilizzando il kit UI bancario. La versione finale del pannello di amministrazione era simile a questa:

Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff
Dato che c'era poco tempo, abbiamo cercato di implementare solo le funzionalità chiave. Per implementare una funzione nel cluster Kubernetes è stato necessario selezionare un evento (un servizio per il quale è necessario implementare una regola nel cloud) e il codice della funzione che implementa la logica decisionale. Per ogni distribuzione di una regola per il servizio selezionato, abbiamo scritto un registro di questo evento. Nel pannello di amministrazione puoi vedere i registri di tutti gli eventi.

Tutto il codice funzione era archiviato in un repository Git remoto, che doveva essere impostato anche nel pannello di amministrazione. Per controllare la versione del codice, tutte le funzioni sono state archiviate in diversi rami del repository. Il pannello di amministrazione offre anche la possibilità di apportare modifiche agli script scritti, in modo che prima di distribuire una funzione in produzione, sia possibile non solo controllare il codice scritto, ma anche apportare le modifiche necessarie.

Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff
Oltre alle funzioni di regole, abbiamo implementato anche la possibilità di arricchire gradualmente i dati di origine utilizzando le funzioni di Enrichment, il cui codice era anche uno script in cui era possibile andare nel data warehouse, chiamare servizi di terze parti ed eseguire calcoli preliminari . Per dimostrare la nostra soluzione, abbiamo calcolato il segno zodiacale del cliente che ha lasciato la richiesta e determinato il suo operatore di telefonia mobile utilizzando un servizio REST di terze parti.

Il backend della piattaforma è stato scritto in Java e implementato come applicazione Spring Boot. Inizialmente avevamo pianificato di utilizzare Postgres per archiviare i dati amministrativi, ma, come parte dell'hackathon, abbiamo deciso di limitarci a un semplice H2 per risparmiare tempo. Sul backend, è stata implementata l'integrazione con Bitbucket per controllare la versione delle funzioni di arricchimento delle query e degli script delle regole. Per l'integrazione con repository Git remoti, abbiamo utilizzato Libreria JGit, che è una sorta di wrapper sui comandi CLI, che consente di eseguire qualsiasi istruzione git utilizzando una comoda interfaccia software. Quindi avevamo due repository separati per le funzioni e le regole di arricchimento e tutti gli script erano divisi in directory. Attraverso la UI era possibile selezionare l'ultimo commit di uno script di un ramo arbitrario del repository. Quando si apportavano modifiche al codice tramite il pannello di amministrazione, i commit del codice modificato venivano creati in repository remoti.

Per realizzare la nostra idea avevamo bisogno di infrastrutture adeguate. Abbiamo deciso di implementare il nostro cluster Kubernetes nel cloud. La nostra scelta è ricaduta su Google Cloud Platform. Il framework serverless Fission è stato installato su un cluster Kubernetes, che abbiamo distribuito in Gcloud. Inizialmente, il servizio di arricchimento dei dati di origine è stato implementato come un'applicazione Java separata racchiusa in un Pod all'interno del cluster k8s. Ma dopo una dimostrazione preliminare del nostro progetto nel bel mezzo dell'hackathon, ci è stato consigliato di rendere il servizio di arricchimento più flessibile per offrire l'opportunità di scegliere come arricchire i dati grezzi delle applicazioni in arrivo. E non abbiamo avuto altra scelta se non quella di rendere anche il servizio di arricchimento Serverless.

Per lavorare con Fission, abbiamo utilizzato la CLI Fission, che deve essere installata sopra la CLI Kubernetes. La distribuzione delle funzioni in un cluster k8s è abbastanza semplice; è sufficiente assegnare un percorso interno e un ingresso alla funzione per consentire il traffico in entrata se è necessario l'accesso all'esterno del cluster. La distribuzione di una funzione in genere non richiede più di 10 secondi.

Presentazione finale del progetto e sintesi

Per dimostrare come funziona il nostro sistema, abbiamo inserito un semplice modulo su un server remoto dove è possibile inviare una richiesta per uno dei prodotti della banca. Per richiederlo bisognava inserire le proprie iniziali, data di nascita e numero di telefono.

I dati dal modulo cliente sono andati al responsabile del trattamento, che ha inviato contemporaneamente richieste per tutte le regole disponibili, dopo aver precedentemente arricchito i dati secondo le condizioni specificate, e li ha salvati in un archivio comune. In totale, abbiamo implementato tre funzioni che prendono decisioni sulle applicazioni in arrivo e 4 servizi di arricchimento dei dati. Dopo aver inviato la domanda, il cliente ha ricevuto la nostra decisione:

Come abbiamo realizzato il cloud FaaS all'interno di Kubernetes e come abbiamo vinto l'hackathon di Tinkoff
Oltre al rifiuto o all'approvazione, il cliente ha ricevuto anche un elenco di altri prodotti, le cui richieste abbiamo inviato parallelamente. È così che abbiamo dimostrato la possibilità della vendita incrociata nella nostra piattaforma.

Erano disponibili in totale 3 prodotti bancari fittizi:

  • Credito.
  • Giocattolo
  • Mutuo.

Durante la dimostrazione, abbiamo implementato funzioni preparate e script di arricchimento per ciascun servizio.

Ciascuna regola richiedeva il proprio set di dati di input. Quindi, per approvare un mutuo, abbiamo calcolato il segno zodiacale del cliente e lo abbiamo collegato alla logica del calendario lunare. Per approvare il giocattolo, abbiamo verificato che il cliente avesse raggiunto la maggiore età e, per emettere un prestito, abbiamo inviato una richiesta a un servizio aperto esterno per determinare l'operatore cellulare e su di esso è stata presa una decisione.

Abbiamo cercato di rendere la nostra dimostrazione interessante e interattiva, tutti i presenti potevano accedere al nostro modulo e verificare la disponibilità dei nostri servizi fittizi. E alla fine della presentazione, abbiamo dimostrato l'analisi delle domande ricevute, che mostrava quante persone hanno utilizzato il nostro servizio, il numero di approvazioni e rifiuti.

Per raccogliere analisi online, abbiamo inoltre implementato uno strumento BI open source metabase e l'abbiamo avvitato al nostro magazzino. Metabase permette di costruire schermate con analisi sui dati che ci interessano; basta registrare una connessione al database, selezionare le tabelle (nel nostro caso raccolte dati, visto che abbiamo utilizzato MongoDB), e specificare i campi di nostro interesse .

Di conseguenza, abbiamo ottenuto un buon prototipo di piattaforma decisionale e durante la dimostrazione ogni ascoltatore ha potuto verificarne personalmente le prestazioni. Una soluzione interessante, un prototipo finito e una dimostrazione di successo ci hanno permesso di vincere, nonostante la forte concorrenza di altri team. Sono sicuro che si possa scrivere un articolo interessante anche sul progetto di ogni team.

Fonte: habr.com

Aggiungi un commento