Na dobre lub na złe przeprowadziliśmy migrację całej naszej aplikacji internetowej LAMP z dedykowanych maszyn do chmury (maszyny Amazon EC2). Jak dotąd idzie świetnie, ale sposób, w jaki robimy crony, jest nieoptymalny. Mam pytanie dotyczące Amazona, jak najlepiej zarządzać zadaniami cron w chmurze przy użyciu „sposobu Amazon”.
Problem : mamy wiele serwerów internetowych i musimy uruchamiać crony do zadań wsadowych, takich jak tworzenie kanałów RSS, wyzwalanie wiadomości e-mail, a właściwie wiele różnych rzeczy. ALE zadania crona muszą być uruchamiane tylko na jednym komputerze, ponieważ często zapisują w bazie danych, więc zduplikowałyby wyniki, gdyby były uruchamiane na wielu komputerach.
Do tej pory wyznaczyliśmy jeden z serwerów WWW jako „główny serwer WWW” i ma on kilka „specjalnych” zadań, których nie mają inne serwery sieciowe. Kompromisem za przetwarzanie w chmurze jest niezawodność - nie chcemy „głównego serwera internetowego”, ponieważ jest to pojedynczy punkt awarii. Chcemy, aby wszystkie były identyczne i aby można było przeskalować w górę lub w dół bez pamiętania, aby nie usuwać głównego serwera internetowego z klastra.
Jak możemy przeprojektować naszą aplikację, aby konwertować zadania Linux cron na przejściowe elementy pracy, które nie mają ani jednego punktu awarii?
Moje dotychczasowe pomysły:
- Miej maszynę przeznaczoną tylko do uruchamiania cronów. Byłoby to trochę łatwiejsze w zarządzaniu, ale nadal stanowiłoby pojedynczy punkt awarii i zmarnowałoby trochę pieniędzy na posiadanie dodatkowej instancji.
- Niektóre zadania można by przenieść z cronów Linuksa do MySQL Events, jednak nie jestem wielkim fanem tego pomysłu, ponieważ nie chcę umieszczać logiki aplikacji w warstwie bazy danych.
- Być może możemy uruchomić wszystkie crony na wszystkich maszynach, ale zmienić nasze skrypty cron, aby wszystkie zaczęły się od odrobiny logiki, która implementuje mechanizm blokujący, więc tylko jeden serwer faktycznie podejmuje działanie, a inne po prostu pomijają. Nie jestem fanem tego pomysłu, ponieważ brzmi to potencjalnie błędnie i wolałbym skorzystać z najlepszych praktyk Amazon, zamiast tworzyć własne.
- Wyobrażam sobie sytuację, w której zadania są gdzieś zaplanowane, dodane do kolejki, a następnie każdy z serwerów WWW może być pracownikiem, który może powiedzieć „hej, wezmę to”. Amazon Simple Workflow Service brzmi dokładnie w ten sposób, ale obecnie niewiele o nim wiem, więc wszelkie szczegóły byłyby pomocne. Wydaje się, że coś tak prostego jak cron wydaje się ciężkie? Czy jest to właściwa usługa, czy może istnieje bardziej odpowiednia usługa Amazon?
Aktualizacja: Od czasu zadania pytania obejrzałem webinarium Amazon Simple Workflow Service na YouTube i zauważyłem o 34:40 ( http://www.youtube.com/watch?v=lBUQiek8Jqk#t=34m40s ). slajd wspominający o zadaniach cron jako przykładowej aplikacji. Na swojej stronie dokumentacji „ AWS Flow Framework samples for Amazon SWF ” Amazon podaje, że ma przykładowy kod dla cronów:
... > Zadania Cron W tym przykładzie długotrwały przepływ pracy okresowo wykonuje działanie. Pokazana jest możliwość kontynuowania wykonywania jako nowych egzekucji, tak aby wykonanie mogło działać przez bardzo długi czas. ...
Ściągnąłem AWS SDK dla Java ( http://aws.amazon.com/sdkforjava/ ) i na pewno zakopany w śmiesznych warstwach folderów jest kod java ( aws-java-sdk-1.3.6/samples/AwsFlowFramework/src/com/amazonaws/services/simpleworkflow/flow/examples/periodicworkflow
).
Problem polega na tym, że jeśli mam być szczery, to nie pomaga, ponieważ nie jest to coś, co mogę łatwo strawić dzięki moim umiejętnościom. Brakuje tej samej próbki w PHP SDK i nie wydaje się, aby istniał samouczek, który omawia ten proces. Zasadniczo więc wciąż szukam porad lub wskazówek.
Odpowiedzi:
Zapisałem się do wsparcia Amazon Gold, aby zadać im to pytanie, to była ich odpowiedź:
źródło
Myślę, że ten film odpowiada dokładnie na twoje pytanie - cronjobs the aws way (skalowalny i odporny na błędy):
Korzystanie z Cron w chmurze z Amazon Simple Workflow
Film opisuje usługę SWF przy użyciu konkretnego przypadku użycia implementacji cronjobs.
Względna złożoność rozwiązania może być trudna do przełknięcia, jeśli pochodzisz bezpośrednio z pliku crontab. Na końcu znajduje się studium przypadku, które pomogło mi zrozumieć, co daje ta dodatkowa złożoność. Sugerowałbym obejrzenie tego studium przypadku i rozważenie wymagań dotyczących skalowalności i odporności na błędy, aby zdecydować, czy należy migrować z istniejącego rozwiązania crontab.
źródło
Zachowaj ostrożność przy używaniu SQS do cronjobów, ponieważ nie gwarantują one, że tylko „jedno zadanie będzie widoczne tylko dla jednej maszyny”. Gwarantują, że „przynajmniej jeden” otrzyma wiadomość.
Od: http://aws.amazon.com/sqs/faqs/#How_many_times_will_I_receive_each_message
Na razie mogę pomyśleć o rozwiązaniu, w którym masz jedną instancję z zainstalowaną instancją Gearman Job Server: http://gearman.org/ . Na tym samym komputerze konfigurujesz zadania cron, które generują polecenie wykonania zadania cronjob w tle. Wtedy jeden z twoich serwerów WWW (pracowników) zacznie wykonywać to zadanie, co gwarantuje, że tylko jeden go podejmie. Nie ma znaczenia, ilu masz pracowników (zwłaszcza gdy używasz automatycznego skalowania).
Problemy z tym rozwiązaniem to:
źródło
Amazon właśnie udostępnił nowe funkcje dla Elastic Beanstalk. Z dokumentów :
Możesz teraz utworzyć środowisko zawierające
cron.yaml
plik konfigurujący zadania planowania:Wyobrażałbym sobie, że ubezpieczenie uruchomienia go tylko raz w środowisku autoskalowanym jest wykorzystywane przez kolejkę komunikatów (SQS). Kiedy demon Cron wyzwala zdarzenie, umieszcza to wywołanie w kolejce SQS, a wiadomość w kolejce jest oceniana tylko raz. Dokumentacja mówi, że wykonanie może zostać opóźnione, jeśli SQS ma wiele komunikatów do przetworzenia.
źródło
Natknąłem się na to pytanie po raz trzeci i pomyślałem, że się wtrącę. Od jakiegoś czasu mamy ten dylemat. Wciąż naprawdę poczuć AWS brakuje funkcji tutaj.
W naszym przypadku, po przyjrzeniu się możliwym rozwiązaniom, zdecydowaliśmy, że mamy dwie możliwości:
cloud-init
skryptów, aby uruchomić cronjobs. Oczywiście wiąże się to z przestojami, co prowadzi do pominięcia cronjobów (podczas wykonywania niektórych zadań co minutę, tak jak my).rcron
używa. Oczywiście magia nie jest tak naprawdęrcron
sama w sobie, jest w logice, której używasz do wykrywania uszkodzonego węzła (używamykeepalived
tutaj) i „ulepszania” innego węzła do nadrzędnego.Zdecydowaliśmy się na drugą opcję, po prostu dlatego, że jest niesamowicie szybka i mieliśmy już doświadczenie z serwerami internetowymi obsługującymi te cronjobs (w naszej erze przed AWS).
Oczywiście to rozwiązanie ma na celu zastąpienie tradycyjnego podejścia cronjob z jednym węzłem, w którym decydującym czynnikiem jest czas (np. „Chcę, aby zadanie A było uruchamiane raz dziennie o 5 rano” lub jak w naszym przypadku „Chcę zadanie B uruchomić raz na minutę ” ). Jeśli używasz cronjobs do wyzwalania logiki przetwarzania wsadowego, naprawdę powinieneś się przyjrzeć
SQS
. Nie ma dylematu aktywny-pasywny, co oznacza, że możesz użyć jednego serwera lub całej siły roboczej do przetwarzania swojej kolejki. Sugerowałbym również rozważenieSWF
możliwości skalowania siły roboczej (chociażauto scaling
w większości przypadków może to również zadziałać).Chcieliśmy uniknąć uzależnienia od innej osoby trzeciej.
źródło
W dniach 12/16 lutego Amazon opublikował na blogu temat planowania zadań SSH przy użyciu AWS Lambda . Myślę, że to odpowiada na pytanie.
źródło
Jeśli masz już aktywną usługę Redis, to wygląda na dobre rozwiązanie:
https://github.com/kvz/cronlock
Czytaj więcej: http://kvz.io/blog/2012/12/31/lock-your-cronjobs/
źródło
Dystrybucja polega na dystrybucji „Amazon”, co oznacza, że nieporęczne pliki cron należy podzielić na wiele mniejszych zadań i przekazać odpowiednim maszynom.
Używając kolejki SQS z typem ustawionym na FIFO, sklej ją razem, aby upewnić się, że każde zadanie jest wykonywane tylko przez jedną maszynę. Toleruje również awarie, ponieważ kolejki będą buforować, dopóki maszyna nie zacznie się obracać.
Zastanów się również, czy naprawdę potrzebujesz grupować te operacje. Co się stanie, jeśli aktualizacje z jednej nocy będą znacznie większe niż oczekiwano? Nawet przy dynamicznym pozyskiwaniu zasobów przetwarzanie może zostać opóźnione w oczekiwaniu na uruchomienie wystarczającej liczby maszyn. Zamiast tego przechowuj dane w SDB, powiadamiaj maszyny o aktualizacjach za pośrednictwem SQS i twórz swój kanał RSS w locie (z buforowaniem).
Zadania wsadowe pochodzą z czasów, gdy zasoby przetwarzania były ograniczone, a usługi „na żywo” miały pierwszeństwo. W chmurze tak nie jest.
źródło
Dlaczego miałbyś budować własne? Dlaczego nie użyć czegoś takiego jak Quartz (z planowaniem klastrowym). Zobacz dokumentację.
http://quartz-scheduler.org/documentation/quartz-2.x/configuration/ConfigJDBCJobStoreClustering
źródło
To, co robimy, to jeden konkretny serwer, który jest częścią naszego klastra aplikacji internetowych za ELB, który również ma przypisaną określoną nazwę DNS, abyśmy mogli uruchamiać zadania na tym konkretnym serwerze. Ma to również tę zaletę, że jeśli to zadanie spowoduje spowolnienie serwera, ELB usunie go z klastra, a następnie zwróci go po zakończeniu zadania i ponownie stanie się zdrowy.
Działa jak mistrz.
źródło
Jedną z metod sprawdzenia, czy wyrażenie cron działa w sposób Amazon, jest uruchomienie go za pomocą polecenia events. Na przykład:
aws events put-rule --name "DailyLambdaFunction" --schedule-expression "<your_schedule_expression>
Jeśli wyrażenie harmonogramu jest nieprawidłowe, to się nie powiedzie.
Więcej zasobów: https://docs.aws.amazon.com/cli/latest/reference/events/put-rule.html
źródło
Jeśli chcesz skorzystać z usługi innej niż AWS, możesz sprawdzić Microsoft Azure . Platforma Azure oferuje świetny program do planowania zadań .
źródło
Ponieważ nikt nie wspomniał o wydarzeniu CloudWatch , powiedziałbym, że jest to sposób AWS na wykonywanie zadań cron. Może uruchamiać wiele akcji, np. Funkcję Lambda, zadanie ECS.
źródło