![]() |
![]() |
![]()
Post
#1
|
|
Grupa: Zarejestrowani Postów: 338 Pomógł: 2 Dołączył: 4.03.2006 Skąd: Łódź Ostrzeżenie: (0%) ![]() ![]() |
Dawno mnie tu nie było (IMG:style_emoticons/default/smile.gif)
Forumowicze, problem z kolejką w PHP. System, który tworzę przetwarza dane co minutę (z CRONa). Niestety uruchomienie pojedynczego procesu np, przetwarzaj.php nie kończy się w 1 minucie, ponieważ przetwarzanie danych może trwać np. 2 mninuty dla pojedynczego rekordu bazy danych, a rekordów jest np. 20. Teoretycznie szeregowe uruchomienie przetwarzania zajmie więc 40 min. Każdy przetwarzaj.pho bierze z bazy zatem 1 rekord i tylko taki mieli. Moje pytanie: w jaki sposób napisać kolejkę, która poprawnie przetworzy takie dane? Wywołać z crona 20x ten sam przetwarzaj.php? Zanim proces zacznie wykonywać swoją pracę, ustawia na rekordzie bazy, że jest on przetwarzany, więc inny proces weźmie kolejne dane. Spotkaliście się z podobnym problemem, macie pomysły? |
|
|
![]() |
![]()
Post
#2
|
|
Grupa: Zarejestrowani Postów: 6 476 Pomógł: 1306 Dołączył: 6.08.2006 Skąd: Kraków Ostrzeżenie: (0%) ![]() ![]() |
To może inaczej, co jest powodem tak długiego przetwarzania pojedynczego rekordu? Bo jeżeli są to jakieś ciężkie operacje wykorzystujące procesor albo dysk, wykonanie równoległych przetwarzań wcale nie musi przyspieszyć ich ogólnego czasu wykonywania. Zaś jeżeli jest to spowodowane przykładowo oczekiwaniem na pobranie danych z sieci to już jak najbardziej miałoby to sens.
1. Zamiast odpalać co minutę zadanie w Cronie, utwórz sobie daemona(y) (System_Daemon). 2. Generalnie utworzenie w bazie danych kolumny status (awaiting, processing, processed) będzie niewystarczające. Dwa (lub nawet więcej) procesy mogłyby pobrać ten sam wiersz nim którykolwiek z nich zdąży zmienić jego status z awaiting na processing. Tutaj trzeba by było albo zablokować na chwilę tabelę dla odczytu:
3. Jeżeli masz możliwość nie pisz tego w PHP, tylko w czymś co wspiera współbieżność (ot, chociażby Java) - znacznie uprości Ci to życie. EDIT: Ewentualnie zamiast ręcznego bawienia się w blokowanie tabeli skorzystaj z transakcji, i tak zawsze trzeba, na odpowiednim poziomie izolacji - tutaj potrzebny byłby chyba aż poziom serializable. Ten post edytował Crozin 23.05.2012, 07:38:35 |
|
|
![]() ![]() |
![]() |
Aktualny czas: 4.10.2025 - 00:45 |