Vela → smart cache foar tiidsearjes en mear

Yn fintech moatte wy faaks frij massive folumes fan gegevens oer falutakoersferwurking ferwurkje. Wy krije gegevens út ferskate boarnen, en elk fan har hat in eigen idee fan hoe't jo wikselkoersen kinne ekstrapolearje foar moarn, oermorgen, folgjende moanne en sels de kommende trije jier. As mar ien koe foarsizze tariven rjocht, It soe tiid wêze om it bedriuw te sluten en gewoan dom jild hinne en wer te feroarjen. Guon boarnen binne betrouber, guon leverje folsleine jiskefet, mei seldsume ynklúzjes fan hast krekte wearden, mar foar eksoatyske pearen. Us taak is om dizze tsientûzenen wearden per sekonde troch te siften en te bepalen wat krekt te sjen is oan klanten. Wy moatte de iene juste wearde filterje út tonnen smoargens en slib, krekt lykas flamingo's by it middeis dwaan.

Vela → smart cache foar tiidsearjes en mear

In bysûnder ûnderskiedend skaaimerk fan flamingo's is har massive nei ûnderen bûgde bek, wêrmei't se iten filterje út wetter of modder.
 - Wiki

Sa is de biblioteek berne Vela, dy't in steat-cache opslacht foar meardere wearden op bepaalde tiidintervallen. Under de motorkap filtert it minne en ferâldere gegevens op 'e flecht, en jout ek tagong ta de lêste N falidearre wearden foar elke kaai (faluta-pearen, yn ús gefal).

Litte wy sizze dat wy tariven sammelje foar trije faluta-pearen. Ienfâldichste definysje Vela om de hjoeddeistige steat op te slaan sil it der sa útsjen:

defmodule Pairs do
  use Vela,
    eurusd: [sorter: &Kernel.<=/2],
    eurgbp: [limit: 3, errors: 1],
    eurcad: [validator: Pairs]

  @behaviour Vela.Validator

  @impl Vela.Validator
  def valid?(:eurcad, rate), do: rate > 0
end

It bywurkjen fan wearden

Vela.put/3 De funksje sil it folgjende dwaan yn folchoarder:

  • sil feroarsaakje validator oer de wearde, as ien is definiearre (sjoch haadstik Validaasje ûnder);
  • sil de wearde tafoegje oan 'e rige goede wearden as de falidaasje suksesfol wie, of oan' e tsjinstrige :__errors__ oars;
  • sil feroarsaakje sortearjen as sorter definieare foar in opjûne kaai, of sil de wearde gewoan oan 'e kop fan' e list sette (LIFO, sjoch haadstik Sortearje ûnder);
  • sil trim de rige neffens de parameter :limit trochjûn op skepping;
  • sil de bywurke struktuer weromjaan Vela.

iex|1 > pairs = %Pairs{}
iex|2 > Vela.put(pairs, :eurcad, 1.0)
#⇒ %Pairs{..., eurcad: [1.0], ...}
iex|3 > Vela.put(pairs, :eurcad, -1.0)
#⇒ %Pairs{__errors__: [eurcad: -1.0], ...}
iex|4 > pairs |> Vela.put(:eurusd, 2.0) |> Vela.put(:eurusd, 1.0)
#⇒ %Pairs{... eurusd: [1.0, 2.0]}

Ek Vela ympleminten Access, sadat jo ien fan 'e standertfunksjes kinne brûke foar djippe bywurking fan struktueren út it arsenal om wearden te aktualisearjen Kernel: Kernel.get_in/2, Kernel.put_in/3, Kernel.update_in/3, Kernel.pop_in/2, en Kernel.get_and_update_in/3.

Validaasje

In validator kin wurde definiearre as:

  • eksterne funksje mei ien argumint (&MyMod.my_fun/1), it sil allinich de wearde krije foar falidaasje;
  • eksterne funksje mei twa arguminten, &MyMod.my_fun/2, se sil in pear krije serie, value foar falidaasje;
  • module ymplemintaasje Vela.Validator;
  • konfiguraasje parameter threshold, en - opsjoneel - compare_by, sjoch haadstik Fergeliking ûnder.

As falidaasje suksesfol is, wurdt de wearde tafoege oan 'e list ûnder de oerienkommende kaai; oars, de tuple {serie, value} giet nei :__errors_.

Fergeliking

De wearden opslein yn dizze rigen kinne alles wêze. Les jaan Vela om se te fergelykjen, is it nedich om oer te dragen compare_by parameter yn 'e searjedefinysje (útsein as de wearden net kinne wurde fergelike mei de standert Kernel.</2); dizze parameter moat fan type wêze (Vela.value() -> number()). Standert is it ienfâldich & &1.

Ek kinne jo in parameter trochjaan oan de rige definysje comparator om delta-wearden te berekkenjen (min/max); bygelyks, troch transmitting Date.diff/2 as komparator kinne jo de juste delta's krije foar datums.

In oare handige manier om te wurkjen is om in parameter troch te jaan threshold, dy't definiearret de maksimale tastiene ferhâlding fan de nije wearde oan {min, max} tuskenskoft. Sûnt it wurdt oantsjutte as in persintaazje, wurdt de kontrôle net brûkt comparatormar noch brûkt compare_by. Om bygelyks in drompelwearde foar datumtiden op te jaan, moatte jo opjaan compare_by: &DateTime.to_unix/1 (om in hiele getal wearde te krijen) en threshold: 1, wêrtroch't nije wearden allinich tastien wurde as se yn binne ±band ynterval fan de hjoeddeiske wearden.

Uteinlik kinne jo gebrûk meitsje Vela.equal?/2 om twa caches te fergelykjen. As de wearden in funksje definiearje equal?/2 of compare/2, dan sille dizze funksjes brûkt wurde foar ferliking, oars brûke wy dom ==/2.

It krijen fan wearden

It ferwurkjen fan de aktuele tastân begjint normaal mei oproppen Vela.purge/1, dy't ferâldere wearden ferwideret (as validator ferbûn oan timestamps). Jo kinne dan belje Vela.slice/1dy't weromkomme sil keyword mei rige nammen as kaaien en de earste, werklike wearden.

Jo kinne ek brûke get_in/2/pop_in/2 foar tagong op leech nivo ta de wearden yn elke rige.

Applikaasje

Vela kin ekstreem nuttich wêze as in tiidrige-cache yn in prosessteat lykas GenServer/Agent. Wy wolle nea gebrûk meitsje fan muffe kursuswearden, en om dit te dwaan hâlde wy gewoan it proses mei steat ferwurke Vela, mei de hjirûnder werjûn validator.

@impl Vela.Validator
def valid?(_key, %Rate{} = rate),
  do: Rate.age(rate) < @death_age

и Vela.purge/1 ferwideret rêstich alle muffe wearden elke kear as wy de gegevens nedich binne. Om tagong te krijen ta de werklike wearden skilje wy gewoan Vela.slice/1, en as in lytse skiednis fan 'e kursus fereaske is (de heule searje), jouwe wy it gewoan werom - al sortearre - mei falidearre wearden.

Lokkige tiidrige caching!

Boarne: www.habr.com

Add a comment