Dinamik For-Each
İş akışı oluşturulurken dal sayısı bilinmiyorsa ->for_each() kullanın. Queuety, iş akışı durumundan bir dizi okur, her öğe için bir dal işi dağıtır ve yalnızca yapılandırılmış tamamlanma koşulu sağlandığında ilerler.
->for_each() yöntemi
use Queuety\Contracts\ForEachHandler;
use Queuety\Contracts\ForEachReducer;
use Queuety\Enums\ForEachMode;
use Queuety\Queuety;
Queuety::workflow( 'index_site' )
->then( PlanPagesStep::class )
->for_each(
items_key: 'pages',
handler_class: IndexPageStep::class,
result_key: 'page_results',
mode: ForEachMode::Quorum,
quorum: 2,
reducer_class: IndexSummaryReducer::class,
name: 'index_pages',
)
->then( PublishIndexStep::class )
->dispatch( [ 'site_id' => 42 ] );
Planlayıcı adımı, pages değerini iş akışı durumuna yazar. For-each adımı bu diziyi okur ve her öğe için bir dal işi dağıtır.
Dal işleyicileri
For-each dal işleyicileri Contracts\ForEachHandler uygular:
use Queuety\Contracts\ForEachHandler;
final class IndexPageStep implements ForEachHandler {
public function handle_item( array $state, mixed $item, int $index ): array {
$page = is_array( $item ) ? $item : [ 'url' => (string) $item ];
return [
'url' => $page['url'],
'title' => fetch_title( $page['url'] ),
'index' => $index,
];
}
public function config(): array {
return [
'max_attempts' => 3,
'backoff' => 'exponential',
];
}
}
config() içinde backoff bir strateji adı alır: exponential, linear veya fixed. Buradaki deneme başına gecikme listesi şu anda atılır ve anında yeniden denemelere dönüşür (#16); deneme başına gecikmeleri bunun yerine adım tanımındaki backoff içine ekleyin.
$state iş akışının tam durumunu, $item tekil for-each öğesini, $index ise sıfır tabanlı konumunu içerir.
Tamamlanma kipleri
ForEachMode::All
Adım, tüm dallar başarıyla tamamlanana kadar sonuçlanmaz. Herhangi bir kalıcı dal hatası, for-each adımının başarısız olmasına neden olur.
ForEachMode::FirstSuccess
Adım, ilk dal başarıya ulaşır ulaşmaz sonuçlanır. Etkin kalan dallar, yerini yenilerine bırakmış olarak arşivlenir.
ForEachMode::Quorum
Adım, en az quorum dal başarıya ulaştığında sonuçlanır. Kalan dallar yeter sayı koşulunu artık karşılayamıyorsa iş akışı başarısız olur.
İndirgemeciler
Varsayılan olarak Queuety, yapılandırılmış bir toplamı result_key altında saklar:
modequorumtotalsucceededfailedsettledwinnerresultsfailures
Özel bir özet istiyorsanız Contracts\ForEachReducer uygulayan bir indirgemeci sınıfı iletin. Toplam yine result_key altında saklanır ve indirgemecinin döndürdüğü anahtarlar, iş akışı durumuna yanına eklenerek birleştirilir:
use Queuety\Contracts\ForEachReducer;
final class IndexSummaryReducer implements ForEachReducer {
public function reduce( array $state, array $for_each ): array {
return [
'indexed_count' => count( $for_each['results'] ),
'winning_url' => $for_each['winner']['output']['url'] ?? null,
];
}
}
İndirgemeci çıktısı, diğer tüm adım çıktıları gibi iş akışı durumuyla birleştirilir. For-each tamamlandıktan sonra dallanmak için _next_step da döndürebilir.
Yeniden deneme davranışı
For-each dalları, dal işleyicisinin config() ayarına göre birbirinden bağımsız olarak yeniden denenir. For-each adımı başarısız olur ve retry_workflow() çağrılırsa Queuety for-each adımını yeniden genişletir ve yalnızca hâlâ eksik veya başarısız olan dalları yeniden kuyruğa alır. Başarılı dal sonuçları iş akışı durumunda kalır.
parallel() ile for_each() arasında seçim
Dal listesi kodda sabitse parallel() kullanın.
Dal listesi çalışma zamanında iş akışı durumundan keşfediliyorsa ve ilk başarı veya yeter sayı gibi tamamlanma kiplerine ihtiyacınız varsa for_each() kullanın.