Model konsolidace výpočtových prostředků

Umožňuje konsolidaci několika úloh nebo operací do jedné výpočetní jednotky. Může zvýšit využití výpočtových prostředků a snížit náklady a režii na správu, které jsou spojené s prováděním zpracování výpočtů v aplikacích hostovaných v cloudu.

Kontext a problém

Cloudová aplikace často implementuje řadu operací. V některých řešeních má smysl řídit se principem, který návrh napřed rozdělí na funkční části. Tyto operace se pak rozdělí na samostatné výpočetní jednotky, které se hostují a nasazují samostatně (například jako samostatné webové aplikace služby App Service, samostatná služba Virtual Machines nebo samostatné role cloudové služby). Tato strategie sice může zjednodušit logický návrh řešení, ale nasazení velkého počtu výpočetních jednotek v rámci stejné aplikace může zvýšit náklady hostování modulu runtime a způsobit, že správa systému bude složitější.

Příklad na obrázku znázorňuje zjednodušenou strukturu řešení hostovaného v cloudu, jehož implementace využívá více než jednu výpočetní jednotku. Každá výpočetní jednotka se spouští ve svém vlastním virtuálním prostředí. Jednotlivé funkce jsou implementované jako samostatné úlohy (označené jako Úloha A až Úloha E), které se spouští ve své vlastní výpočetní jednotce.

Spouštění úloh v cloudovém prostředí se sadou vyhrazených výpočetních jednotek

Každá výpočetní jednotka, i když je nečinná nebo málo používaná, využívá prostředky, za které se platí poplatky. Toto řešení proto není vždy nákladově nejvýhodnější.

V Azure to platí pro role v cloudové službě, službu App Services a službu Virtual Machines. Tyto položky se spouští ve svém vlastním virtuálním prostředí. Spouštění kolekce samostatných rolí, webů nebo virtuálních počítačů, které jsou určené k provádění sady dobře definovaných operací, ale které potřebují komunikovat a spolupracovat v rámci jednoho řešení, může představovat neefektivní využívání prostředků.

Řešení

Konsolidace více úloh nebo operací do jedné výpočetní jednotky pomáhá snižovat náklady, zvyšovat využití, zvyšovat rychlost komunikace a omezovat potřebu správy.

Úlohy lze seskupovat podle kritérií založených na funkcích poskytovaných prostředím a nákladech spojených s těmito funkcemi. Běžným přístupem je vyhledání úloh, které mají podobný profil z hlediska své škálovatelnosti, životnosti a požadavků na zpracování. Seskupením takových úloh se umožní, aby se daly škálovat jako jednotka. Elasticita, kterou poskytuje řada cloudových prostředí, umožňuje spouštění a zastavování dalších instancí výpočetní jednotky podle zatížení. Například Azure nabízí automatické škálování, které lze použít pro role v cloudové službě, službu App Services a službu Virtual Machines. Další informace najdete v pokynech k automatickému škálování.

Jako ukázkový příklad, který znázorňuje, jak lze pomocí škálovatelnosti určit, které operace by se neměly seskupovat, slouží následující dvě úlohy:

  • Úloha 1 zjišťuje málo časté a časově nezávislé zprávy, které se odesílají do fronty.
  • Úloha 2 zpracovává shluky s velkými objemy síťových přenosů.

Druhá úloha vyžaduje elasticitu, která může zahrnovat spouštění a zastavování velkého počtu instancí výpočetní jednotky. Použití stejného škálování u první úlohy by vedlo jen k dalším úlohám zjišťujícím výskyt málo častých zpráv ve stejné frontě a šlo by o plýtvání prostředky.

V řadě cloudových prostředí lze prostředky dostupné pro výpočetní jednotku určit pomocí údajů, jako jsou počet jader procesoru, velikost paměti, velikost místa na disku a podobně. Obecně platí, že čím více prostředků se určí, tím vyšší budou náklady. Pro úsporu finančních prostředků je důležité, abyste nákladnou výpočetní jednotku co nejvíce využívali a nenechávali ji delší dobu v nečinnosti.

Pokud některé úlohy vyžadují velký výkon procesoru jen v krátkých špičkách, zvažte jejich konsolidaci do jedné výpočetní jednotky nabízející potřebný výkon. Při této potřebě udržování nákladných prostředků v činnosti je ale důležité brát v úvahu možnost kolizí, ke kterým může docházet při jejich přetížení. Například dlouho běžící úlohy, které jsou náročné na výpočetní výkon, by neměly sdílet stejnou výpočetní jednotku.

Problémy a důležité informace

Při implementaci tohoto modelu zvažte následující informace:

Škálovatelnost a pružnost. V řadě cloudových řešení se implementuje škálovatelnost a elasticita na úrovni výpočetní jednotky tak, že se instance jednotky spouští a zastavují. Vyhněte se seskupování úloh, které mají konfliktní požadavky na škálovatelnost ve stejné výpočetní jednotce.

Doba života. Cloudová infrastruktura pravidelně recykluje virtuální prostředí, které je hostitelem výpočetní jednotky. Pokud výpočetní jednotka obsahuje mnoho dlouho běžících úloh, může být nutné nakonfigurovat tuto jednotku tak, aby neumožňovala recyklaci, dokud se tyto úlohy nedokončí. Případně můžete úlohy navrhovat pomocí bodového přístupu, při kterém je možné je snadno zastavit a po restartování výpočetní jednotky v nich pokračovat od bodu přerušení.

Četnost změn: Pokud se implementace nebo konfigurační úlohy často mění, může být potřeba zastavit výpočetní jednotku, která hostuje aktualizovaný kód, překonfigurovat tuto jednotku a znovu ji nasadit a pak ji restartovat. Tento proces bude také vyžadovat, aby se všechny ostatní úlohy ve stejné výpočetní jednotce zastavily, znovu nasadily a restartovaly.

Zabezpečení. Úlohy ve stejné výpočetní jednotce můžou sdílet stejný kontext zabezpečení a můžou mít přístup ke stejným prostředkům. Mezi úlohami musí existovat vysoký stupeň důvěryhodnosti, že některá úloha nepoškodí nebo jinak negativně neovlivní jiné úlohy. Zvýšení počtu úloh spouštěných ve výpočetní jednotce zvětšuje prostor pro útoky na jednotku. Každá úloha má jen takové zabezpečení jako úloha s nejvyšším ohrožením zabezpečení.

Tolerance poruch. Pokud u některé úlohy ve výpočetní jednotce dojde k chybě nebo k neobvyklému chování, může to ovlivnit ostatní úlohy, které se spouští ve stejné výpočetní jednotce. Pokud se například některou úlohu nepodaří správně spustit, může to způsobit selhání celé spouštěcí logiky výpočetní jednotky a zabránit spuštění dalších úloh ve stejné jednotce.

Kolize: Vyhýbejte se kolizím mezi úlohami, které soutěží o prostředky ve stejné výpočetní jednotce. V ideálním případě by měly úlohy, které sdílejí stejnou výpočetní jednotku, vykazovat různé charakteristiky využití prostředků. Ve stejné výpočetní jednotce by se tedy neměly nacházet třeba dvě úlohy, které jsou náročné na výpočetní výkon, nebo dvě úlohy, které využívají velké množství paměti. Kombinování úlohy náročné na výpočetní výkon s úlohou, která vyžaduje velké množství paměti, je však funkční kombinací.

Poznámka

Zvažte konsolidaci výpočetních prostředků pouze pro systém, který je v produkčním prostředí, aby operátoři a vývojáři mohli monitorovat systém a vytvořit Heat mapu , která určuje, jak jednotlivé úlohy používají různé prostředky. Pomocí této mapy se dají určit úlohy, které jsou vhodnými kandidáty pro sdílení výpočtových prostředků.

Složitost: Sloučení více úloh do jedné výpočetní jednotky zvyšuje složitost kódu v dané jednotce a následkem toho její testování, ladění a údržba můžou být obtížnější.

Stabilní logická architektura: Navrhujte a implementujte kód v jednotlivých úlohách tak, aby ho nebylo potřeba měnit, a to ani v případě, že se změní fyzické prostředí, ve kterém se příslušná úloha spouští.

Jiné strategie: Konsolidace výpočtových prostředků je jen jedním ze způsobů, jak snižovat náklady související se souběžným spouštěním více úloh. Zajištění efektivity tohoto přístupu vyžaduje pečlivé naplánování a monitorování. Jiné strategie můžou být vhodnější v závislosti na povaze úloh a na umístění uživatelů, kteří tyto úlohy spouštějí. Lepším řešením může být například funkční dekompozice zatížení (podle popisu v tématu Návod k dělení výpočtů).

Kdy se má tento model použít

Tento model se používá pro úlohy, které nejsou nákladově efektivní, když se spouštějí ve svých vlastních výpočetních jednotkách. Pokud je úloha po většinu času nečinná, může být spouštění této úlohy ve vyhrazené jednotce nákladné.

Tento model nemusí být vhodný pro úlohy provádějící kritické operace s odolností proti chybám nebo pro úlohy, které zpracovávají hodně citlivá nebo soukromá data a vyžadují svůj vlastní kontext zabezpečení. Tyto úlohy by se měly spouštět ve vlastním izolovaném prostředí v samostatné výpočetní jednotce.

Příklad

Při vytváření cloudové služby v Azure je možné konsolidovat zpracování, které provádí více úloh, do jediné role. Obvykle se jedná o roli pracovního procesu, která provádí úlohy na pozadí nebo úlohy asynchronního zpracování.

V některých případech je možné zahrnout úlohy na pozadí nebo úlohy asynchronního zpracování do webové role. Tento přístup umožňuje snížit náklady a zjednodušit nasazení, ale může mít dopad na škálovatelnost a odezvu veřejného rozhraní, které příslušná webová role nabízí.

Daná role je zodpovědná za spouštění a zastavování úloh. Když kontroler prostředků infrastruktury Azure načte roli, vyvolá pro tuto roli událost Start. Metodu OnStart třídy WebRole nebo WorkerRole pro zpracování této události je možné přepsat, třeba tak, aby inicializovala data a jiné prostředky, na kterých úlohy v této metodě závisí.

Po OnStart dokončení metody může role začít reagovat na požadavky. Další informace a pokyny k používání metod OnStart a Run v roli najdete v části Spouštěcí procesy aplikací v průvodci modely a postupy Přesouvání aplikací do cloudu.

Kód v metodě OnStart udržujte co nejstručnější. Azure neurčuje pro dokončení této metody žádný časový limit, ale daná role nebude moct začít reagovat na síťové požadavky, které se jí posílají, dokud se tato metoda nedokončí.

Po dokončení metody OnStart daná role spustí metodu Run. V tomto okamžiku může kontroler prostředků infrastruktury zahájit odesílání požadavků této roli.

Vložte kód, který ve skutečnosti vytváří úlohy v metodě Run. Upozorňujeme, že metoda Run definuje životnost dané instance role. Po dokončení této metody kontroler prostředků infrastruktury způsobí vypnutí této role.

Když se role vypne nebo recykluje, kontroler prostředků infrastruktury zabrání v příjmu všech dalších příchozích požadavků z nástroje pro vyrovnávání zatížení a vyvolá událost Stop. Tuto událost můžete zachytit tak, že přepíšete metodu OnStop dané role, a před ukončením této role provedete veškerý požadovaný úklid.

Všechny akce prováděné v metodě OnStop se musí dokončit během pěti minut (nebo během 30 sekund, pokud používáte emulátor Azure na místním počítači). Jinak kontroler prostředků infrastruktury Azure předpokládá, že se daná role pozdržela, a vynutí její zastavení.

Úlohy se spouští pomocí metody Run, která čeká na jejich dokončení. Úlohy implementují obchodní logiku cloudové služby a můžou reagovat na zprávy odeslané dané roli pomocí nástroje pro vyrovnávání zatížení Azure. Obrázek znázorňuje životní cyklus úloh a prostředků v roli v cloudové službě Azure.

Životní cyklus úloh a prostředků v roli v cloudové službě Azure

Soubor WorkerRole.cs v projektu ComputeResourceConsolidation.Worker ukazuje příklad, jak je možné tento model implementovat v cloudové službě Azure.

Projekt ComputeResourceConsolidation.Worker je součástí řešení ComputeResourceConsolidation, které si lze stáhnout z GitHubu.

Metody úloh MyWorkerTask1 a MyWorkerTask2 ukazují, jak lze provádět různé úlohy ve stejné roli pracovního procesu. Následující kód ukazuje úlohu MyWorkerTask1. Jedná se o jednoduchou úlohu, která po prodlevě 30 sekund vytvoří jako výstup trasovací zprávu. Tento proces se opakuje, dokud se tato úloha nezruší. Kód v úloze MyWorkerTask2 je podobný.

// A sample worker role task.
private static async Task MyWorkerTask1(CancellationToken ct)
{
  // Fixed interval to wake up and check for work and/or do work.
  var interval = TimeSpan.FromSeconds(30);

  try
  {
    while (!ct.IsCancellationRequested)
    {
      // Wake up and do some background processing if not canceled.
      // TASK PROCESSING CODE HERE
      Trace.TraceInformation("Doing Worker Task 1 Work");

      // Go back to sleep for a period of time unless asked to cancel.
      // Task.Delay will throw an OperationCanceledException when canceled.
      await Task.Delay(interval, ct);
    }
  }
  catch (OperationCanceledException)
  {
    // Expect this exception to be thrown in normal circumstances or check
    // the cancellation token. If the role instances are shutting down, a
    // cancellation request will be signaled.
    Trace.TraceInformation("Stopping service, cancellation requested");

    // Rethrow the exception.
    throw;
  }
}

Kód příkladu ukazuje běžnou implementaci procesu na pozadí. V reálné aplikaci můžete použít stejnou strukturu s tím rozdílem, že do těla smyčky, která čeká na požadavek na zrušení, umístíte vlastní logiku zpracování.

Když role pracovního procesu inicializuje prostředky, které používá, metoda Run spustí obě úlohy souběžně, jak se ukazuje tady.

/// <summary>
/// The cancellation token source use to cooperatively cancel running tasks
/// </summary>
private readonly CancellationTokenSource cts = new CancellationTokenSource();

/// <summary>
/// List of running tasks on the role instance
/// </summary>
private readonly List<Task> tasks = new List<Task>();

// RoleEntry Run() is called after OnStart().
// Returning from Run() will cause a role instance to recycle.
public override void Run()
{
  // Start worker tasks and add to the task list
  tasks.Add(MyWorkerTask1(cts.Token));
  tasks.Add(MyWorkerTask2(cts.Token));

  foreach (var worker in this.workerTasks)
  {
      this.tasks.Add(worker);
  }

  Trace.TraceInformation("Worker host tasks started");
  // The assumption is that all tasks should remain running and not return,
  // similar to role entry Run() behavior.
  try
  {
    Task.WaitAll(tasks.ToArray());
  }
  catch (AggregateException ex)
  {
    Trace.TraceError(ex.Message);

    // If any of the inner exceptions in the aggregate exception
    // are not cancellation exceptions then re-throw the exception.
    ex.Handle(innerEx => (innerEx is OperationCanceledException));
  }

  // If there wasn't a cancellation request, stop all tasks and return from Run()
  // An alternative to canceling and returning when a task exits would be to
  // restart the task.
  if (!cts.IsCancellationRequested)
  {
    Trace.TraceInformation("Task returned without cancellation request");
    Stop(TimeSpan.FromMinutes(5));
  }
}
...

V tomto příkladu metoda Run čeká na dokončení úloh. Pokud dojde ke zrušení úlohy, metoda Run předpokládá, že daná role se vypíná a před dokončením čeká na zrušení zbývajících úloh (čeká maximálně pět minut, než se ukončí). Pokud dojde k selhání úlohy z důvodu očekávané výjimky, metoda Run zruší danou úlohu.

Do metody Run je možné implementovat komplexní strategie monitorování a zpracování výjimek, třeba restartování úloh, které selhaly, nebo zahrnutí kódu, který dané roli umožní spouštět a zastavovat jednotlivé úlohy.

Metoda Stop v následujícím kódu se vyvolá, když kontroler prostředků infrastruktury vypne danou instanci role (vyvolá se z metody OnStop). Kód elegantně zastaví každou úlohu tak, že ji zruší. Pokud dokončení některé úlohy trvá více než pět minut, proces zrušení v metodě Stop přestane čekat a daná role se ukončí.

// Stop running tasks and wait for tasks to complete before returning
// unless the timeout expires.
private void Stop(TimeSpan timeout)
{
  Trace.TraceInformation("Stop called. Canceling tasks.");
  // Cancel running tasks.
  cts.Cancel();

  Trace.TraceInformation("Waiting for canceled tasks to finish and return");

  // Wait for all the tasks to complete before returning. Note that the
  // emulator currently allows 30 seconds and Azure allows five
  // minutes for processing to complete.
  try
  {
    Task.WaitAll(tasks.ToArray(), timeout);
  }
  catch (AggregateException ex)
  {
    Trace.TraceError(ex.Message);

    // If any of the inner exceptions in the aggregate exception
    // are not cancellation exceptions then rethrow the exception.
    ex.Handle(innerEx => (innerEx is OperationCanceledException));
  }
}

Při implementaci tohoto modelu můžou být relevantní také následující modely a pokyny:

  • Pokyny pro automatické škálování. Automatické škálování se používá ke spouštění a zastavování instancí služby, která hostuje výpočtové prostředky, v závislosti na očekávané poptávce po zpracování.

  • Pokyny k dělení výpočetních prostředků. Popisuje, jak přidělovat služby a komponenty v cloudové službě způsobem, který pomůže minimalizovat provozní náklady při zachování škálovatelnosti, výkonu, dostupnosti a zabezpečení služby.

  • Součástí tohoto modelu je ukázková aplikace ke stažení.