[{"data":1,"prerenderedAt":2444},["ShallowReactive",2],{"navigation":3,"docs-path-index":268,"-docs-modules-queue-consumers":348,"-docs-modules-queue-consumers-surround":2439},[4],{"title":5,"icon":6,"path":7,"stem":8,"children":9,"page":56},"Docs","i-lucide-book-marked","\u002Fdocs","docs",[10,26,57,229,250],{"title":11,"path":12,"stem":13,"children":14,"icon":25},"Getting Started","\u002Fdocs\u002Fgetting-started","docs\u002F1.getting-started\u002F1.index",[15,17,21],{"title":16,"path":12,"stem":13},"Introduction",{"title":18,"path":19,"stem":20},"Installation","\u002Fdocs\u002Fgetting-started\u002Finstallation","docs\u002F1.getting-started\u002F2.installation",{"title":22,"path":23,"stem":24},"Examples","\u002Fdocs\u002Fgetting-started\u002Fexamples","docs\u002F1.getting-started\u002F3.examples","i-lucide-rocket",{"title":27,"icon":28,"path":29,"stem":30,"children":31,"page":56},"Core features","i-lucide-square-function","\u002Fdocs\u002Fcore-features","docs\u002F2.core-features",[32,36,40,44,48,52],{"title":33,"path":34,"stem":35},"Configuration","\u002Fdocs\u002Fcore-features\u002Fconfiguration","docs\u002F2.core-features\u002F0.configuration",{"title":37,"path":38,"stem":39},"Dependency Injection","\u002Fdocs\u002Fcore-features\u002Fcontainer","docs\u002F2.core-features\u002F1.container",{"title":41,"path":42,"stem":43},"Controllers","\u002Fdocs\u002Fcore-features\u002Fcontrollers","docs\u002F2.core-features\u002F2.controllers",{"title":45,"path":46,"stem":47},"Middlewares","\u002Fdocs\u002Fcore-features\u002Fmiddlewares","docs\u002F2.core-features\u002F3.middlewares",{"title":49,"path":50,"stem":51},"Validation","\u002Fdocs\u002Fcore-features\u002Fvalidation","docs\u002F2.core-features\u002F4.validation",{"title":53,"path":54,"stem":55},"Introspection","\u002Fdocs\u002Fcore-features\u002Fintrospection","docs\u002F2.core-features\u002F5.introspection",false,{"title":58,"icon":59,"defaultOpen":60,"path":61,"stem":62,"children":63,"page":56},"Modules","i-lucide-boxes",true,"\u002Fdocs\u002Fmodules","docs\u002F3.modules",[64,81,92,108,127,142,150,165,176,191,210,218],{"title":65,"icon":56,"defaultOpen":56,"path":66,"stem":67,"children":68,"page":56},"Auth","\u002Fdocs\u002Fmodules\u002Fauth","docs\u002F3.modules\u002F1.auth",[69,73,77],{"title":70,"path":71,"stem":72},"Overview","\u002Fdocs\u002Fmodules\u002Fauth\u002Foverview","docs\u002F3.modules\u002F1.auth\u002F0.overview",{"title":74,"path":75,"stem":76},"Decorators","\u002Fdocs\u002Fmodules\u002Fauth\u002Fdecorators","docs\u002F3.modules\u002F1.auth\u002F1.decorators",{"title":78,"path":79,"stem":80},"API Reference","\u002Fdocs\u002Fmodules\u002Fauth\u002Fapi","docs\u002F3.modules\u002F1.auth\u002F2.api",{"title":82,"icon":56,"defaultOpen":56,"path":83,"stem":84,"children":85,"page":56},"Devtools","\u002Fdocs\u002Fmodules\u002Fdevtools","docs\u002F3.modules\u002F10.devtools",[86,89],{"title":70,"path":87,"stem":88},"\u002Fdocs\u002Fmodules\u002Fdevtools\u002Foverview","docs\u002F3.modules\u002F10.devtools\u002F0.overview",{"title":33,"path":90,"stem":91},"\u002Fdocs\u002Fmodules\u002Fdevtools\u002Fconfiguration","docs\u002F3.modules\u002F10.devtools\u002F1.configuration",{"title":93,"path":94,"stem":95,"children":96,"page":56},"Telemetry","\u002Fdocs\u002Fmodules\u002Ftelemetry","docs\u002F3.modules\u002F11.telemetry",[97,100,104],{"title":70,"path":98,"stem":99},"\u002Fdocs\u002Fmodules\u002Ftelemetry\u002Foverview","docs\u002F3.modules\u002F11.telemetry\u002F0.overview",{"title":101,"path":102,"stem":103},"API","\u002Fdocs\u002Fmodules\u002Ftelemetry\u002Fapi","docs\u002F3.modules\u002F11.telemetry\u002F1.api",{"title":105,"path":106,"stem":107},"Instrumentation","\u002Fdocs\u002Fmodules\u002Ftelemetry\u002Finstrumentation","docs\u002F3.modules\u002F11.telemetry\u002F2.instrumentation",{"title":109,"path":110,"stem":111,"children":112,"page":56},"Queue","\u002Fdocs\u002Fmodules\u002Fqueue","docs\u002F3.modules\u002F12.queue",[113,116,120,124],{"title":70,"path":114,"stem":115},"\u002Fdocs\u002Fmodules\u002Fqueue\u002Foverview","docs\u002F3.modules\u002F12.queue\u002F0.overview",{"title":117,"path":118,"stem":119},"Consumers","\u002Fdocs\u002Fmodules\u002Fqueue\u002Fconsumers","docs\u002F3.modules\u002F12.queue\u002F1.consumers",{"title":121,"path":122,"stem":123},"Strategies","\u002Fdocs\u002Fmodules\u002Fqueue\u002Fstrategies","docs\u002F3.modules\u002F12.queue\u002F2.strategies",{"title":101,"path":125,"stem":126},"\u002Fdocs\u002Fmodules\u002Fqueue\u002Fapi","docs\u002F3.modules\u002F12.queue\u002F3.api",{"title":128,"icon":56,"defaultOpen":56,"path":129,"stem":130,"children":131,"page":56},"Logger","\u002Fdocs\u002Fmodules\u002Flogger","docs\u002F3.modules\u002F2.logger",[132,135,139],{"title":70,"path":133,"stem":134},"\u002Fdocs\u002Fmodules\u002Flogger\u002Foverview","docs\u002F3.modules\u002F2.logger\u002F0.overview",{"title":136,"path":137,"stem":138},"Drains & Adapters","\u002Fdocs\u002Fmodules\u002Flogger\u002Fdrivers","docs\u002F3.modules\u002F2.logger\u002F1.drivers",{"title":101,"path":140,"stem":141},"\u002Fdocs\u002Fmodules\u002Flogger\u002Fapi","docs\u002F3.modules\u002F2.logger\u002F2.api",{"title":143,"icon":56,"defaultOpen":56,"path":144,"stem":145,"children":146,"page":56},"Serverless","\u002Fdocs\u002Fmodules\u002Fserverless","docs\u002F3.modules\u002F3.serverless",[147],{"title":70,"path":148,"stem":149},"\u002Fdocs\u002Fmodules\u002Fserverless\u002Foverview","docs\u002F3.modules\u002F3.serverless\u002F0.overview",{"title":151,"icon":56,"defaultOpen":56,"path":152,"stem":153,"children":154,"page":56},"Storage","\u002Fdocs\u002Fmodules\u002Fstorage","docs\u002F3.modules\u002F4.storage",[155,158,162],{"title":70,"path":156,"stem":157},"\u002Fdocs\u002Fmodules\u002Fstorage\u002Foverview","docs\u002F3.modules\u002F4.storage\u002F0.overview",{"title":159,"path":160,"stem":161},"Drivers","\u002Fdocs\u002Fmodules\u002Fstorage\u002Fdrivers","docs\u002F3.modules\u002F4.storage\u002F1.drivers",{"title":101,"path":163,"stem":164},"\u002Fdocs\u002Fmodules\u002Fstorage\u002Fapi","docs\u002F3.modules\u002F4.storage\u002F2.api",{"title":166,"icon":56,"defaultOpen":56,"path":167,"stem":168,"children":169,"page":56},"Web Sockets","\u002Fdocs\u002Fmodules\u002Fweb-sockets","docs\u002F3.modules\u002F5.web-sockets",[170,173],{"title":70,"path":171,"stem":172},"\u002Fdocs\u002Fmodules\u002Fweb-sockets\u002Foverview","docs\u002F3.modules\u002F5.web-sockets\u002F0.overview",{"title":101,"path":174,"stem":175},"\u002Fdocs\u002Fmodules\u002Fweb-sockets\u002Fapi","docs\u002F3.modules\u002F5.web-sockets\u002F1.api",{"title":177,"icon":56,"defaultOpen":56,"path":178,"stem":179,"children":180,"page":56},"Schema","\u002Fdocs\u002Fmodules\u002Fschema","docs\u002F3.modules\u002F6.schema",[181,184,187],{"title":70,"path":182,"stem":183},"\u002Fdocs\u002Fmodules\u002Fschema\u002Foverview","docs\u002F3.modules\u002F6.schema\u002F0.overview",{"title":74,"path":185,"stem":186},"\u002Fdocs\u002Fmodules\u002Fschema\u002Fdecorators","docs\u002F3.modules\u002F6.schema\u002F1.decorators",{"title":188,"path":189,"stem":190},"Scalar","\u002Fdocs\u002Fmodules\u002Fschema\u002Fscalar","docs\u002F3.modules\u002F6.schema\u002F2.scalar",{"title":192,"icon":56,"defaultOpen":56,"path":193,"stem":194,"children":195,"page":56},"Nitro","\u002Fdocs\u002Fmodules\u002Fnitro","docs\u002F3.modules\u002F7.nitro",[196,199,202,206],{"title":70,"path":197,"stem":198},"\u002Fdocs\u002Fmodules\u002Fnitro\u002Foverview","docs\u002F3.modules\u002F7.nitro\u002F0.overview",{"title":151,"path":200,"stem":201},"\u002Fdocs\u002Fmodules\u002Fnitro\u002Fstorage","docs\u002F3.modules\u002F7.nitro\u002F1.storage",{"title":203,"path":204,"stem":205},"File-Based Routes","\u002Fdocs\u002Fmodules\u002Fnitro\u002Ffile-based-routes","docs\u002F3.modules\u002F7.nitro\u002F2.file-based-routes",{"title":207,"path":208,"stem":209},"Middleware","\u002Fdocs\u002Fmodules\u002Fnitro\u002Fmiddleware","docs\u002F3.modules\u002F7.nitro\u002F3.middleware",{"title":211,"icon":56,"defaultOpen":56,"path":212,"stem":213,"children":214,"page":56},"Vite","\u002Fdocs\u002Fmodules\u002Fvite","docs\u002F3.modules\u002F8.vite",[215],{"title":70,"path":216,"stem":217},"\u002Fdocs\u002Fmodules\u002Fvite\u002Foverview","docs\u002F3.modules\u002F8.vite\u002F0.overview",{"title":219,"icon":56,"defaultOpen":56,"path":220,"stem":221,"children":222,"page":56},"Cache","\u002Fdocs\u002Fmodules\u002Fcache","docs\u002F3.modules\u002F9.cache",[223,226],{"title":70,"path":224,"stem":225},"\u002Fdocs\u002Fmodules\u002Fcache\u002Foverview","docs\u002F3.modules\u002F9.cache\u002F0.overview",{"title":101,"path":227,"stem":228},"\u002Fdocs\u002Fmodules\u002Fcache\u002Fapi","docs\u002F3.modules\u002F9.cache\u002F1.api",{"title":230,"icon":231,"path":232,"stem":233,"children":234,"page":56},"Deployment","i-lucide-cloud-upload","\u002Fdocs\u002Fdeployment","docs\u002F4.deployment",[235,238,242,246],{"title":70,"path":236,"stem":237},"\u002Fdocs\u002Fdeployment\u002Foverview","docs\u002F4.deployment\u002F0.overview",{"title":239,"path":240,"stem":241},"Vercel","\u002Fdocs\u002Fdeployment\u002Fvercel","docs\u002F4.deployment\u002F1.vercel",{"title":243,"path":244,"stem":245},"AWS Lambda","\u002Fdocs\u002Fdeployment\u002Faws-lambda","docs\u002F4.deployment\u002F2.aws-lambda",{"title":247,"path":248,"stem":249},"Azure Functions","\u002Fdocs\u002Fdeployment\u002Fazure-functions","docs\u002F4.deployment\u002F3.azure-functions",{"title":251,"icon":252,"path":253,"stem":254,"children":255,"page":56},"Advanced","i-lucide-brain","\u002Fdocs\u002Fadvanced","docs\u002F99.advanced",[256,260,264],{"title":257,"path":258,"stem":259},"Custom Decorator","\u002Fdocs\u002Fadvanced\u002Fcustom-decorator","docs\u002F99.advanced\u002F1.custom-decorator",{"title":261,"path":262,"stem":263},"Plugins","\u002Fdocs\u002Fadvanced\u002Fcustom-plugin","docs\u002F99.advanced\u002F2.custom-plugin",{"title":265,"path":266,"stem":267},"Custom CLI Command","\u002Fdocs\u002Fadvanced\u002Fcustom-cli-command","docs\u002F99.advanced\u002F3.custom-cli-command",[269,271,273,274,275,276,278,279,280,281,282,283,284,286,288,289,290,291,293,294,295,296,297,298,299,300,301,302,304,305,306,307,309,310,312,313,314,315,317,318,319,321,322,323,324,326,327,328,329,330,332,333,335,336,337,339,340,341,342,343,345,346,347],{"path":270},"\u002Fdocs\u002F.navigation",{"path":272},"\u002Fdocs\u002Fgetting-started\u002F.navigation",{"path":12},{"path":19},{"path":23},{"path":277},"\u002Fdocs\u002Fcore-features\u002F.navigation",{"path":34},{"path":38},{"path":42},{"path":46},{"path":50},{"path":54},{"path":285},"\u002Fdocs\u002Fmodules\u002F.navigation",{"path":287},"\u002Fdocs\u002Fmodules\u002Fauth\u002F.navigation",{"path":71},{"path":75},{"path":79},{"path":292},"\u002Fdocs\u002Fmodules\u002Fdevtools\u002F.navigation",{"path":87},{"path":90},{"path":98},{"path":102},{"path":106},{"path":114},{"path":118},{"path":122},{"path":125},{"path":303},"\u002Fdocs\u002Fmodules\u002Flogger\u002F.navigation",{"path":133},{"path":137},{"path":140},{"path":308},"\u002Fdocs\u002Fmodules\u002Fserverless\u002F.navigation",{"path":148},{"path":311},"\u002Fdocs\u002Fmodules\u002Fstorage\u002F.navigation",{"path":156},{"path":160},{"path":163},{"path":316},"\u002Fdocs\u002Fmodules\u002Fweb-sockets\u002F.navigation",{"path":171},{"path":174},{"path":320},"\u002Fdocs\u002Fmodules\u002Fschema\u002F.navigation",{"path":182},{"path":185},{"path":189},{"path":325},"\u002Fdocs\u002Fmodules\u002Fnitro\u002F.navigation",{"path":197},{"path":200},{"path":204},{"path":208},{"path":331},"\u002Fdocs\u002Fmodules\u002Fvite\u002F.navigation",{"path":216},{"path":334},"\u002Fdocs\u002Fmodules\u002Fcache\u002F.navigation",{"path":224},{"path":227},{"path":338},"\u002Fdocs\u002Fdeployment\u002F.navigation",{"path":236},{"path":240},{"path":244},{"path":248},{"path":344},"\u002Fdocs\u002Fadvanced\u002F.navigation",{"path":258},{"path":262},{"path":266},{"id":349,"title":117,"body":350,"description":2433,"extension":2434,"links":2435,"meta":2436,"navigation":60,"path":118,"seo":2437,"stem":119,"__hash__":2438},"docs\u002Fdocs\u002F3.modules\u002F12.queue\u002F1.consumers.md",{"type":351,"value":352,"toc":2422},"minimark",[353,357,362,365,468,562,565,586,589,593,596,826,829,884,887,891,894,950,962,970,977,998,1002,1008,1162,1168,1349,1352,1369,1373,1376,1562,1572,1576,1587,1781,1784,1798,1802,1812,2137,2140,2187,2190,2198,2251,2254,2258,2265,2415,2418],[354,355,356],"p",{},"A consumer is a container service that reads one queue. The class decorator says which queue, the method decorators say which jobs.",[358,359,361],"h2",{"id":360},"consumer","@Consumer",[354,363,364],{},"Marks a class as the consumer of a queue and sets the defaults for every handler in it.",[366,367,372],"pre",{"className":368,"code":369,"language":370,"meta":371,"style":371},"language-ts shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","@Consumer({ queue: 'emails', concurrency: 5, attempts: 2, timeout: 10_000 })\nexport class EmailConsumer {}\n","ts","",[373,374,375,450],"code",{"__ignoreMap":371},[376,377,380,384,388,392,395,399,402,405,409,412,415,418,420,424,426,429,431,434,436,439,441,444,447],"span",{"class":378,"line":379},"line",1,[376,381,383],{"class":382},"sMK4o","@",[376,385,387],{"class":386},"s2Zo4","Consumer",[376,389,391],{"class":390},"sTEyZ","(",[376,393,394],{"class":382},"{",[376,396,398],{"class":397},"swJcz"," queue",[376,400,401],{"class":382},":",[376,403,404],{"class":382}," '",[376,406,408],{"class":407},"sfazB","emails",[376,410,411],{"class":382},"'",[376,413,414],{"class":382},",",[376,416,417],{"class":397}," concurrency",[376,419,401],{"class":382},[376,421,423],{"class":422},"sbssI"," 5",[376,425,414],{"class":382},[376,427,428],{"class":397}," attempts",[376,430,401],{"class":382},[376,432,433],{"class":422}," 2",[376,435,414],{"class":382},[376,437,438],{"class":397}," timeout",[376,440,401],{"class":382},[376,442,443],{"class":422}," 10_000",[376,445,446],{"class":382}," }",[376,448,449],{"class":390},")\n",[376,451,453,457,461,465],{"class":378,"line":452},2,[376,454,456],{"class":455},"s7zQu","export",[376,458,460],{"class":459},"spNyl"," class",[376,462,464],{"class":463},"sBMFI"," EmailConsumer",[376,466,467],{"class":382}," {}\n",[469,470,471,484],"table",{},[472,473,474],"thead",{},[475,476,477,481],"tr",{},[478,479,480],"th",{},"Option",[478,482,483],{},"Description",[485,486,487,498,512,522,532,542,552],"tbody",{},[475,488,489,495],{},[490,491,492],"td",{},[373,493,494],{},"queue",[490,496,497],{},"Queue the class reads from. Required.",[475,499,500,505],{},[490,501,502],{},[373,503,504],{},"strategy",[490,506,507,508,511],{},"Mounted strategy to consume from. Defaults to ",[373,509,510],{},"default",".",[475,513,514,519],{},[490,515,516],{},[373,517,518],{},"concurrency",[490,520,521],{},"How many jobs of this queue may run in parallel. Defaults to 1.",[475,523,524,529],{},[490,525,526],{},[373,527,528],{},"attempts",[490,530,531],{},"Default attempts for every handler of the class.",[475,533,534,539],{},[490,535,536],{},[373,537,538],{},"backoff",[490,540,541],{},"Default backoff for every handler of the class.",[475,543,544,549],{},[490,545,546],{},[373,547,548],{},"timeout",[490,550,551],{},"Default time limit for every handler of the class.",[475,553,554,559],{},[490,555,556],{},[373,557,558],{},"schema",[490,560,561],{},"Default payload schema for every handler of the class.",[354,563,564],{},"The queue starts being consumed when the class is bound in the container:",[366,566,568],{"className":368,"code":567,"language":370,"meta":371,"style":371},"container.bind(EmailConsumer);\n",[373,569,570],{"__ignoreMap":371},[376,571,572,575,577,580,583],{"class":378,"line":379},[376,573,574],{"class":390},"container",[376,576,511],{"class":382},[376,578,579],{"class":386},"bind",[376,581,582],{"class":390},"(EmailConsumer)",[376,584,585],{"class":382},";\n",[354,587,588],{},"Nothing happens without that binding, exactly like a controller that is never bound. A handler declared on a subclass inherits the queue of its base class, so shared consumer bases work as expected.",[358,590,592],{"id":591},"job","@Job",[354,594,595],{},"Marks a method as the handler of one job name. The method receives the payload and the job context.",[366,597,599],{"className":368,"code":598,"language":370,"meta":371,"style":371},"@Consumer({ queue: 'emails' })\nexport class EmailConsumer {\n  @Job('welcome')\n  public async welcome(payload: { userId: string }, context: QueueTypes.JobContext): Promise\u003Cvoid> {\n    context.logger?.info(`attempt ${context.attempt} of ${context.attempts}`);\n\n    await this.gMailer.sendWelcome(payload.userId);\n  }\n}\n",[373,600,601,625,636,656,720,778,784,814,820],{"__ignoreMap":371},[376,602,603,605,607,609,611,613,615,617,619,621,623],{"class":378,"line":379},[376,604,383],{"class":382},[376,606,387],{"class":386},[376,608,391],{"class":390},[376,610,394],{"class":382},[376,612,398],{"class":397},[376,614,401],{"class":382},[376,616,404],{"class":382},[376,618,408],{"class":407},[376,620,411],{"class":382},[376,622,446],{"class":382},[376,624,449],{"class":390},[376,626,627,629,631,633],{"class":378,"line":452},[376,628,456],{"class":455},[376,630,460],{"class":459},[376,632,464],{"class":463},[376,634,635],{"class":382}," {\n",[376,637,639,642,645,647,649,652,654],{"class":378,"line":638},3,[376,640,641],{"class":382},"  @",[376,643,644],{"class":386},"Job",[376,646,391],{"class":390},[376,648,411],{"class":382},[376,650,651],{"class":407},"welcome",[376,653,411],{"class":382},[376,655,449],{"class":390},[376,657,659,662,665,668,670,674,676,679,682,684,687,690,693,695,698,700,703,706,709,712,715,718],{"class":378,"line":658},4,[376,660,661],{"class":459},"  public",[376,663,664],{"class":459}," async",[376,666,667],{"class":397}," welcome",[376,669,391],{"class":382},[376,671,673],{"class":672},"sHdIc","payload",[376,675,401],{"class":382},[376,677,678],{"class":382}," {",[376,680,681],{"class":397}," userId",[376,683,401],{"class":382},[376,685,686],{"class":463}," string",[376,688,689],{"class":382}," },",[376,691,692],{"class":672}," context",[376,694,401],{"class":382},[376,696,697],{"class":463}," QueueTypes",[376,699,511],{"class":382},[376,701,702],{"class":463},"JobContext",[376,704,705],{"class":382},"):",[376,707,708],{"class":463}," Promise",[376,710,711],{"class":382},"\u003C",[376,713,714],{"class":463},"void",[376,716,717],{"class":382},">",[376,719,635],{"class":382},[376,721,723,726,728,731,734,737,739,742,745,748,751,753,756,759,762,764,766,768,770,773,776],{"class":378,"line":722},5,[376,724,725],{"class":390},"    context",[376,727,511],{"class":382},[376,729,730],{"class":390},"logger",[376,732,733],{"class":382},"?.",[376,735,736],{"class":386},"info",[376,738,391],{"class":397},[376,740,741],{"class":382},"`",[376,743,744],{"class":407},"attempt ",[376,746,747],{"class":382},"${",[376,749,750],{"class":390},"context",[376,752,511],{"class":382},[376,754,755],{"class":390},"attempt",[376,757,758],{"class":382},"}",[376,760,761],{"class":407}," of ",[376,763,747],{"class":382},[376,765,750],{"class":390},[376,767,511],{"class":382},[376,769,528],{"class":390},[376,771,772],{"class":382},"}`",[376,774,775],{"class":397},")",[376,777,585],{"class":382},[376,779,781],{"class":378,"line":780},6,[376,782,783],{"emptyLinePlaceholder":60},"\n",[376,785,787,790,793,796,798,801,803,805,807,810,812],{"class":378,"line":786},7,[376,788,789],{"class":455},"    await",[376,791,792],{"class":382}," this.",[376,794,795],{"class":390},"gMailer",[376,797,511],{"class":382},[376,799,800],{"class":386},"sendWelcome",[376,802,391],{"class":397},[376,804,673],{"class":390},[376,806,511],{"class":382},[376,808,809],{"class":390},"userId",[376,811,775],{"class":397},[376,813,585],{"class":382},[376,815,817],{"class":378,"line":816},8,[376,818,819],{"class":382},"  }\n",[376,821,823],{"class":378,"line":822},9,[376,824,825],{"class":382},"}\n",[354,827,828],{},"Options given here override the ones the class declared:",[469,830,831,839],{},[472,832,833],{},[475,834,835,837],{},[478,836,480],{},[478,838,483],{},[485,840,841,853,866,875],{},[475,842,843,847],{},[490,844,845],{},[373,846,528],{},[490,848,849,850,852],{},"Total attempts, the first one included. Applies when the published job carries no ",[373,851,528],{}," of its own.",[475,854,855,859],{},[490,856,857],{},[373,858,538],{},[490,860,861,862,865],{},"Delay between attempts. A number is a fixed delay in milliseconds, ",[373,863,864],{},"{ type: 'exponential', delay }"," doubles it every attempt.",[475,867,868,872],{},[490,869,870],{},[373,871,548],{},[490,873,874],{},"Milliseconds after which the attempt is failed.",[475,876,877,881],{},[490,878,879],{},[373,880,558],{},[490,882,883],{},"Standard Schema validating the payload before the handler runs.",[354,885,886],{},"Returning marks the job done, throwing marks the attempt failed. There is nothing to acknowledge by hand.",[358,888,890],{"id":889},"where-the-job-name-comes-from","Where the job name comes from",[354,892,893],{},"A job name is not a broker concept. It is a label the module writes into the message metadata, so that one queue can carry several kinds of work, each with its own handler, retries and schema. Every transport keeps it where it naturally belongs:",[469,895,896,906],{},[472,897,898],{},[475,899,900,903],{},[478,901,902],{},"Transport",[478,904,905],{},"Job name lives in",[485,907,908,916,932,942],{},[475,909,910,913],{},[490,911,912],{},"BullMQ",[490,914,915],{},"the native job name",[475,917,918,921],{},[490,919,920],{},"RabbitMQ",[490,922,923,924,927,928,931],{},"the ",[373,925,926],{},"type"," message property, falling back to the ",[373,929,930],{},"x-job"," header",[475,933,934,937],{},[490,935,936],{},"Kafka",[490,938,923,939,941],{},[373,940,930],{}," record header",[475,943,944,947],{},[490,945,946],{},"Memory",[490,948,949],{},"the job record",[354,951,952,953,956,957,959,960,401],{},"So a job published as ",[373,954,955],{},"add({ queue: 'emails', job: 'welcome', payload: { userId } })"," arrives on RabbitMQ as an ordinary AMQP message whose body is the payload and whose ",[373,958,926],{}," is ",[373,961,651],{},[366,963,968],{"className":964,"code":966,"language":967},[965],"language-text","queue: emails\nproperties:\n  type:      'welcome'\n  messageId: '0f2c…'\n  headers:   { x-job: 'welcome', x-attempt: '1' }\nbody: {\"userId\":\"u-42\"}\n","text",[373,969,966],{"__ignoreMap":371},[354,971,972,973,976],{},"If a queue only ever carries one kind of work, the name is close to cosmetic: declare a single ",[373,974,975],{},"@Job('process')"," and be done. Modelling it the other way round, one queue per job, works just as well.",[354,978,979,980,983,984,987,988,990,991,993,994,997],{},"A message carrying none of that metadata arrives as the job ",[373,981,982],{},"unknown",", which is what ",[373,985,986],{},"@AnyJob()"," is for. A foreign producer that does set the field its transport uses, an AMQP ",[373,989,926],{}," or a Kafka ",[373,992,930],{}," header, names its jobs just as this module does, and a ",[373,995,996],{},"@Job()"," handler picks them up by name.",[358,999,1001],{"id":1000},"anyjob","@AnyJob",[354,1003,1004,1005,1007],{},"Handles every job of the queue that no ",[373,1006,996],{}," claims. A named handler always wins, so this is a fallback rather than a replacement, and there can be one per queue.",[366,1009,1011],{"className":368,"code":1010,"language":370,"meta":371,"style":371},"\u002F\u002F a queue another application fills, whose messages carry no job name\n@Consumer({ queue: 'legacy-events' })\nexport class LegacyConsumer {\n  @AnyJob({ attempts: 3 })\n  public async handle(payload: unknown, context: QueueTypes.JobContext): Promise\u003Cvoid> {\n    \u002F\u002F context.job is whatever arrived, or 'unknown' when nothing did\n    await this.gEvents.ingest(payload, context.job);\n  }\n}\n",[373,1012,1013,1019,1044,1055,1077,1119,1124,1154,1158],{"__ignoreMap":371},[376,1014,1015],{"class":378,"line":379},[376,1016,1018],{"class":1017},"sHwdD","\u002F\u002F a queue another application fills, whose messages carry no job name\n",[376,1020,1021,1023,1025,1027,1029,1031,1033,1035,1038,1040,1042],{"class":378,"line":452},[376,1022,383],{"class":382},[376,1024,387],{"class":386},[376,1026,391],{"class":390},[376,1028,394],{"class":382},[376,1030,398],{"class":397},[376,1032,401],{"class":382},[376,1034,404],{"class":382},[376,1036,1037],{"class":407},"legacy-events",[376,1039,411],{"class":382},[376,1041,446],{"class":382},[376,1043,449],{"class":390},[376,1045,1046,1048,1050,1053],{"class":378,"line":638},[376,1047,456],{"class":455},[376,1049,460],{"class":459},[376,1051,1052],{"class":463}," LegacyConsumer",[376,1054,635],{"class":382},[376,1056,1057,1059,1062,1064,1066,1068,1070,1073,1075],{"class":378,"line":658},[376,1058,641],{"class":382},[376,1060,1061],{"class":386},"AnyJob",[376,1063,391],{"class":390},[376,1065,394],{"class":382},[376,1067,428],{"class":397},[376,1069,401],{"class":382},[376,1071,1072],{"class":422}," 3",[376,1074,446],{"class":382},[376,1076,449],{"class":390},[376,1078,1079,1081,1083,1086,1088,1090,1092,1095,1097,1099,1101,1103,1105,1107,1109,1111,1113,1115,1117],{"class":378,"line":722},[376,1080,661],{"class":459},[376,1082,664],{"class":459},[376,1084,1085],{"class":397}," handle",[376,1087,391],{"class":382},[376,1089,673],{"class":672},[376,1091,401],{"class":382},[376,1093,1094],{"class":463}," unknown",[376,1096,414],{"class":382},[376,1098,692],{"class":672},[376,1100,401],{"class":382},[376,1102,697],{"class":463},[376,1104,511],{"class":382},[376,1106,702],{"class":463},[376,1108,705],{"class":382},[376,1110,708],{"class":463},[376,1112,711],{"class":382},[376,1114,714],{"class":463},[376,1116,717],{"class":382},[376,1118,635],{"class":382},[376,1120,1121],{"class":378,"line":780},[376,1122,1123],{"class":1017},"    \u002F\u002F context.job is whatever arrived, or 'unknown' when nothing did\n",[376,1125,1126,1128,1130,1133,1135,1138,1140,1142,1144,1146,1148,1150,1152],{"class":378,"line":786},[376,1127,789],{"class":455},[376,1129,792],{"class":382},[376,1131,1132],{"class":390},"gEvents",[376,1134,511],{"class":382},[376,1136,1137],{"class":386},"ingest",[376,1139,391],{"class":397},[376,1141,673],{"class":390},[376,1143,414],{"class":382},[376,1145,692],{"class":390},[376,1147,511],{"class":382},[376,1149,591],{"class":390},[376,1151,775],{"class":397},[376,1153,585],{"class":382},[376,1155,1156],{"class":378,"line":816},[376,1157,819],{"class":382},[376,1159,1160],{"class":378,"line":822},[376,1161,825],{"class":382},[354,1163,1164,1165,1167],{},"It takes the same options as ",[373,1166,996],{},", and they apply to every job it catches:",[366,1169,1171],{"className":368,"code":1170,"language":370,"meta":371,"style":371},"@Consumer({ queue: 'emails' })\nexport class EmailConsumer {\n  @Job('welcome')\n  public async welcome(payload: Welcome): Promise\u003Cvoid> {}\n\n  @AnyJob()\n  public async rest(payload: unknown, context: QueueTypes.JobContext): Promise\u003Cvoid> {\n    context.logger?.warn(`unrecognised job ${context.job}`);\n  }\n}\n",[373,1172,1173,1197,1207,1223,1252,1256,1265,1306,1340,1344],{"__ignoreMap":371},[376,1174,1175,1177,1179,1181,1183,1185,1187,1189,1191,1193,1195],{"class":378,"line":379},[376,1176,383],{"class":382},[376,1178,387],{"class":386},[376,1180,391],{"class":390},[376,1182,394],{"class":382},[376,1184,398],{"class":397},[376,1186,401],{"class":382},[376,1188,404],{"class":382},[376,1190,408],{"class":407},[376,1192,411],{"class":382},[376,1194,446],{"class":382},[376,1196,449],{"class":390},[376,1198,1199,1201,1203,1205],{"class":378,"line":452},[376,1200,456],{"class":455},[376,1202,460],{"class":459},[376,1204,464],{"class":463},[376,1206,635],{"class":382},[376,1208,1209,1211,1213,1215,1217,1219,1221],{"class":378,"line":638},[376,1210,641],{"class":382},[376,1212,644],{"class":386},[376,1214,391],{"class":390},[376,1216,411],{"class":382},[376,1218,651],{"class":407},[376,1220,411],{"class":382},[376,1222,449],{"class":390},[376,1224,1225,1227,1229,1231,1233,1235,1237,1240,1242,1244,1246,1248,1250],{"class":378,"line":658},[376,1226,661],{"class":459},[376,1228,664],{"class":459},[376,1230,667],{"class":397},[376,1232,391],{"class":382},[376,1234,673],{"class":672},[376,1236,401],{"class":382},[376,1238,1239],{"class":463}," Welcome",[376,1241,705],{"class":382},[376,1243,708],{"class":463},[376,1245,711],{"class":382},[376,1247,714],{"class":463},[376,1249,717],{"class":382},[376,1251,467],{"class":382},[376,1253,1254],{"class":378,"line":722},[376,1255,783],{"emptyLinePlaceholder":60},[376,1257,1258,1260,1262],{"class":378,"line":780},[376,1259,641],{"class":382},[376,1261,1061],{"class":386},[376,1263,1264],{"class":390},"()\n",[376,1266,1267,1269,1271,1274,1276,1278,1280,1282,1284,1286,1288,1290,1292,1294,1296,1298,1300,1302,1304],{"class":378,"line":786},[376,1268,661],{"class":459},[376,1270,664],{"class":459},[376,1272,1273],{"class":397}," rest",[376,1275,391],{"class":382},[376,1277,673],{"class":672},[376,1279,401],{"class":382},[376,1281,1094],{"class":463},[376,1283,414],{"class":382},[376,1285,692],{"class":672},[376,1287,401],{"class":382},[376,1289,697],{"class":463},[376,1291,511],{"class":382},[376,1293,702],{"class":463},[376,1295,705],{"class":382},[376,1297,708],{"class":463},[376,1299,711],{"class":382},[376,1301,714],{"class":463},[376,1303,717],{"class":382},[376,1305,635],{"class":382},[376,1307,1308,1310,1312,1314,1316,1319,1321,1323,1326,1328,1330,1332,1334,1336,1338],{"class":378,"line":816},[376,1309,725],{"class":390},[376,1311,511],{"class":382},[376,1313,730],{"class":390},[376,1315,733],{"class":382},[376,1317,1318],{"class":386},"warn",[376,1320,391],{"class":397},[376,1322,741],{"class":382},[376,1324,1325],{"class":407},"unrecognised job ",[376,1327,747],{"class":382},[376,1329,750],{"class":390},[376,1331,511],{"class":382},[376,1333,591],{"class":390},[376,1335,772],{"class":382},[376,1337,775],{"class":397},[376,1339,585],{"class":382},[376,1341,1342],{"class":378,"line":822},[376,1343,819],{"class":382},[376,1345,1347],{"class":378,"line":1346},10,[376,1348,825],{"class":382},[354,1350,1351],{},"The real job name is on the context, is what the retry republishes under, and is what the counters and the devtools panel report. The fallback never changes a job's identity, it only decides who runs it.",[1353,1354,1355],"warning",{},[354,1356,1357,1358,1360,1361,1364,1365,1368],{},"Without an ",[373,1359,986],{},", a job no handler claims is counted as unhandled and, with the default ",[373,1362,1363],{},"onUnhandled: 'ignore'",", acknowledged and dropped with a warning. Set ",[373,1366,1367],{},"onUnhandled: 'fail'"," to have the transport dead-letter it instead of dropping it.",[358,1370,1372],{"id":1371},"the-job-context","The job context",[354,1374,1375],{},"The second argument describes the attempt being processed.",[366,1377,1379],{"className":368,"code":1378,"language":370,"meta":371,"style":371},"@Job('report')\npublic async report(payload: Report, context: QueueTypes.JobContext\u003CReport>): Promise\u003Cvoid> {\n  \u002F\u002F where it came from\n  context.queue;     \u002F\u002F 'reports'\n  context.job;       \u002F\u002F 'report'\n  context.strategy;  \u002F\u002F name of the mounted strategy\n  context.id;        \u002F\u002F job id, as assigned by the transport\n  context.headers;   \u002F\u002F transport headers received with the job\n\n  \u002F\u002F which attempt this is\n  context.attempt;   \u002F\u002F 1 on the first run\n  context.attempts;  \u002F\u002F how many attempts this job may take\n\n  \u002F\u002F reporting back\n  context.logger?.info('halfway');\n  await context.updateProgress(50);\n\n  \u002F\u002F the transport-native job, when you really need it\n  context.raw;\n}\n",[373,1380,1381,1398,1435,1440,1448,1456,1464,1472,1480,1484,1489,1498,1507,1512,1518,1534,1540,1545,1551,1557],{"__ignoreMap":371},[376,1382,1383,1385,1387,1389,1391,1394,1396],{"class":378,"line":379},[376,1384,383],{"class":382},[376,1386,644],{"class":386},[376,1388,391],{"class":390},[376,1390,411],{"class":382},[376,1392,1393],{"class":407},"report",[376,1395,411],{"class":382},[376,1397,449],{"class":390},[376,1399,1400,1403,1405,1408,1410,1413,1415,1417,1419,1422,1424,1427,1430,1433],{"class":378,"line":452},[376,1401,1402],{"class":390},"public async ",[376,1404,1393],{"class":386},[376,1406,1407],{"class":390},"(payload: Report",[376,1409,414],{"class":382},[376,1411,1412],{"class":390}," context: QueueTypes",[376,1414,511],{"class":382},[376,1416,702],{"class":390},[376,1418,711],{"class":382},[376,1420,1421],{"class":390},"Report",[376,1423,717],{"class":382},[376,1425,1426],{"class":390},"): ",[376,1428,1429],{"class":463},"Promise",[376,1431,1432],{"class":382},"\u003Cvoid>",[376,1434,635],{"class":382},[376,1436,1437],{"class":378,"line":638},[376,1438,1439],{"class":1017},"  \u002F\u002F where it came from\n",[376,1441,1442,1445],{"class":378,"line":658},[376,1443,1444],{"class":390},"  context.queue;     ",[376,1446,1447],{"class":1017},"\u002F\u002F 'reports'\n",[376,1449,1450,1453],{"class":378,"line":722},[376,1451,1452],{"class":390},"  context.job;       ",[376,1454,1455],{"class":1017},"\u002F\u002F 'report'\n",[376,1457,1458,1461],{"class":378,"line":780},[376,1459,1460],{"class":390},"  context.strategy;  ",[376,1462,1463],{"class":1017},"\u002F\u002F name of the mounted strategy\n",[376,1465,1466,1469],{"class":378,"line":786},[376,1467,1468],{"class":390},"  context.id;        ",[376,1470,1471],{"class":1017},"\u002F\u002F job id, as assigned by the transport\n",[376,1473,1474,1477],{"class":378,"line":816},[376,1475,1476],{"class":390},"  context.headers;   ",[376,1478,1479],{"class":1017},"\u002F\u002F transport headers received with the job\n",[376,1481,1482],{"class":378,"line":822},[376,1483,783],{"emptyLinePlaceholder":60},[376,1485,1486],{"class":378,"line":1346},[376,1487,1488],{"class":1017},"  \u002F\u002F which attempt this is\n",[376,1490,1492,1495],{"class":378,"line":1491},11,[376,1493,1494],{"class":390},"  context.attempt;   ",[376,1496,1497],{"class":1017},"\u002F\u002F 1 on the first run\n",[376,1499,1501,1504],{"class":378,"line":1500},12,[376,1502,1503],{"class":390},"  context.attempts;  ",[376,1505,1506],{"class":1017},"\u002F\u002F how many attempts this job may take\n",[376,1508,1510],{"class":378,"line":1509},13,[376,1511,783],{"emptyLinePlaceholder":60},[376,1513,1515],{"class":378,"line":1514},14,[376,1516,1517],{"class":1017},"  \u002F\u002F reporting back\n",[376,1519,1521,1524,1526,1529,1531],{"class":378,"line":1520},15,[376,1522,1523],{"class":390},"  context.logger?.info(",[376,1525,411],{"class":382},[376,1527,1528],{"class":397},"halfway",[376,1530,411],{"class":382},[376,1532,1533],{"class":397},");\n",[376,1535,1537],{"class":378,"line":1536},16,[376,1538,1539],{"class":397},"  await context.updateProgress(50);\n",[376,1541,1543],{"class":378,"line":1542},17,[376,1544,783],{"emptyLinePlaceholder":60},[376,1546,1548],{"class":378,"line":1547},18,[376,1549,1550],{"class":1017},"  \u002F\u002F the transport-native job, when you really need it\n",[376,1552,1554],{"class":378,"line":1553},19,[376,1555,1556],{"class":397},"  context.raw;\n",[376,1558,1560],{"class":378,"line":1559},20,[376,1561,825],{"class":397},[354,1563,1564,1567,1568,1571],{},[373,1565,1566],{},"updateProgress()"," is a no-op on transports that do not track progress, so calling it is always safe. ",[373,1569,1570],{},"context.logger"," is the application logger with the queue, job, id and attempt already attached, and is null when no logger is bound.",[358,1573,1575],{"id":1574},"validating-payloads","Validating payloads",[354,1577,1578,1579,1586],{},"A job payload comes from outside the process, so it deserves the same treatment as a request body. Pass any ",[1580,1581,1585],"a",{"href":1582,"rel":1583},"https:\u002F\u002Fstandardschema.dev",[1584],"nofollow","Standard Schema"," and the payload is validated before the handler runs.",[366,1588,1590],{"className":368,"code":1589,"language":370,"meta":371,"style":371},"import { z } from 'zod';\n\nconst WelcomeSchema = z.object({ userId: z.string().uuid() });\n\n@Consumer({ queue: 'emails' })\nexport class EmailConsumer {\n  @Job('welcome', { schema: WelcomeSchema })\n  public async welcome(payload: z.infer\u003Ctypeof WelcomeSchema>): Promise\u003Cvoid> {}\n}\n",[373,1591,1592,1616,1620,1670,1674,1698,1708,1737,1777],{"__ignoreMap":371},[376,1593,1594,1597,1599,1602,1604,1607,1609,1612,1614],{"class":378,"line":379},[376,1595,1596],{"class":455},"import",[376,1598,678],{"class":382},[376,1600,1601],{"class":390}," z",[376,1603,446],{"class":382},[376,1605,1606],{"class":455}," from",[376,1608,404],{"class":382},[376,1610,1611],{"class":407},"zod",[376,1613,411],{"class":382},[376,1615,585],{"class":382},[376,1617,1618],{"class":378,"line":452},[376,1619,783],{"emptyLinePlaceholder":60},[376,1621,1622,1625,1628,1631,1633,1635,1638,1640,1642,1644,1646,1648,1650,1653,1656,1658,1661,1664,1666,1668],{"class":378,"line":638},[376,1623,1624],{"class":459},"const",[376,1626,1627],{"class":390}," WelcomeSchema ",[376,1629,1630],{"class":382},"=",[376,1632,1601],{"class":390},[376,1634,511],{"class":382},[376,1636,1637],{"class":386},"object",[376,1639,391],{"class":390},[376,1641,394],{"class":382},[376,1643,681],{"class":397},[376,1645,401],{"class":382},[376,1647,1601],{"class":390},[376,1649,511],{"class":382},[376,1651,1652],{"class":386},"string",[376,1654,1655],{"class":390},"()",[376,1657,511],{"class":382},[376,1659,1660],{"class":386},"uuid",[376,1662,1663],{"class":390},"() ",[376,1665,758],{"class":382},[376,1667,775],{"class":390},[376,1669,585],{"class":382},[376,1671,1672],{"class":378,"line":658},[376,1673,783],{"emptyLinePlaceholder":60},[376,1675,1676,1678,1680,1682,1684,1686,1688,1690,1692,1694,1696],{"class":378,"line":722},[376,1677,383],{"class":382},[376,1679,387],{"class":386},[376,1681,391],{"class":390},[376,1683,394],{"class":382},[376,1685,398],{"class":397},[376,1687,401],{"class":382},[376,1689,404],{"class":382},[376,1691,408],{"class":407},[376,1693,411],{"class":382},[376,1695,446],{"class":382},[376,1697,449],{"class":390},[376,1699,1700,1702,1704,1706],{"class":378,"line":780},[376,1701,456],{"class":455},[376,1703,460],{"class":459},[376,1705,464],{"class":463},[376,1707,635],{"class":382},[376,1709,1710,1712,1714,1716,1718,1720,1722,1724,1726,1729,1731,1733,1735],{"class":378,"line":786},[376,1711,641],{"class":382},[376,1713,644],{"class":386},[376,1715,391],{"class":390},[376,1717,411],{"class":382},[376,1719,651],{"class":407},[376,1721,411],{"class":382},[376,1723,414],{"class":382},[376,1725,678],{"class":382},[376,1727,1728],{"class":397}," schema",[376,1730,401],{"class":382},[376,1732,1627],{"class":390},[376,1734,758],{"class":382},[376,1736,449],{"class":390},[376,1738,1739,1741,1743,1745,1747,1749,1751,1753,1755,1758,1761,1764,1767,1769,1771,1773,1775],{"class":378,"line":816},[376,1740,661],{"class":459},[376,1742,664],{"class":459},[376,1744,667],{"class":397},[376,1746,391],{"class":382},[376,1748,673],{"class":672},[376,1750,401],{"class":382},[376,1752,1601],{"class":463},[376,1754,511],{"class":382},[376,1756,1757],{"class":463},"infer",[376,1759,1760],{"class":382},"\u003Ctypeof",[376,1762,1763],{"class":390}," WelcomeSchema",[376,1765,1766],{"class":382},">):",[376,1768,708],{"class":463},[376,1770,711],{"class":382},[376,1772,714],{"class":463},[376,1774,717],{"class":382},[376,1776,467],{"class":382},[376,1778,1779],{"class":378,"line":822},[376,1780,825],{"class":382},[354,1782,1783],{},"The handler receives the parsed value, so defaults and coercions the schema applies are visible inside it. A payload that does not match fails the job without retrying it.",[1785,1786,1787],"note",{},[354,1788,1789,1790,1793,1794,1797],{},"Validation needs a ",[373,1791,1792],{},"ValidationProvider"," in the container, which ",[373,1795,1796],{},"@vercube\u002Fcore"," binds by default. A job declaring a schema in a container without one fails with a clear error instead of running unvalidated.",[358,1799,1801],{"id":1800},"lifecycle-hooks","Lifecycle hooks",[354,1803,1804,1807,1808,1811],{},[373,1805,1806],{},"@OnJobCompleted()"," and ",[373,1809,1810],{},"@OnJobFailed()"," observe the queue of their consumer class. A hook never changes the outcome of a job: if a hook throws, the throw is logged and forgotten.",[366,1813,1815],{"className":368,"code":1814,"language":370,"meta":371,"style":371},"@Consumer({ queue: 'emails' })\nexport class EmailConsumer {\n  @Job('welcome', { attempts: 3 })\n  public async welcome(payload: { userId: string }): Promise\u003Cvoid> {}\n\n  @OnJobCompleted()\n  public async sent(context: QueueTypes.JobContext): Promise\u003Cvoid> {\n    this.gMetrics.increment(`emails.${context.job}.sent`);\n  }\n\n  @OnJobFailed()\n  public async failed(error: Error, context: QueueTypes.JobContext): Promise\u003Cvoid> {\n    \u002F\u002F called once per failed attempt, so tell a retry from a final failure\n    if (context.attempt === context.attempts) {\n      await this.gAlerts.report(error, context.id);\n    }\n  }\n}\n",[373,1816,1817,1841,1851,1879,1914,1918,1927,1960,1999,2003,2007,2016,2059,2064,2093,2124,2129,2133],{"__ignoreMap":371},[376,1818,1819,1821,1823,1825,1827,1829,1831,1833,1835,1837,1839],{"class":378,"line":379},[376,1820,383],{"class":382},[376,1822,387],{"class":386},[376,1824,391],{"class":390},[376,1826,394],{"class":382},[376,1828,398],{"class":397},[376,1830,401],{"class":382},[376,1832,404],{"class":382},[376,1834,408],{"class":407},[376,1836,411],{"class":382},[376,1838,446],{"class":382},[376,1840,449],{"class":390},[376,1842,1843,1845,1847,1849],{"class":378,"line":452},[376,1844,456],{"class":455},[376,1846,460],{"class":459},[376,1848,464],{"class":463},[376,1850,635],{"class":382},[376,1852,1853,1855,1857,1859,1861,1863,1865,1867,1869,1871,1873,1875,1877],{"class":378,"line":638},[376,1854,641],{"class":382},[376,1856,644],{"class":386},[376,1858,391],{"class":390},[376,1860,411],{"class":382},[376,1862,651],{"class":407},[376,1864,411],{"class":382},[376,1866,414],{"class":382},[376,1868,678],{"class":382},[376,1870,428],{"class":397},[376,1872,401],{"class":382},[376,1874,1072],{"class":422},[376,1876,446],{"class":382},[376,1878,449],{"class":390},[376,1880,1881,1883,1885,1887,1889,1891,1893,1895,1897,1899,1901,1904,1906,1908,1910,1912],{"class":378,"line":658},[376,1882,661],{"class":459},[376,1884,664],{"class":459},[376,1886,667],{"class":397},[376,1888,391],{"class":382},[376,1890,673],{"class":672},[376,1892,401],{"class":382},[376,1894,678],{"class":382},[376,1896,681],{"class":397},[376,1898,401],{"class":382},[376,1900,686],{"class":463},[376,1902,1903],{"class":382}," }):",[376,1905,708],{"class":463},[376,1907,711],{"class":382},[376,1909,714],{"class":463},[376,1911,717],{"class":382},[376,1913,467],{"class":382},[376,1915,1916],{"class":378,"line":722},[376,1917,783],{"emptyLinePlaceholder":60},[376,1919,1920,1922,1925],{"class":378,"line":780},[376,1921,641],{"class":382},[376,1923,1924],{"class":386},"OnJobCompleted",[376,1926,1264],{"class":390},[376,1928,1929,1931,1933,1936,1938,1940,1942,1944,1946,1948,1950,1952,1954,1956,1958],{"class":378,"line":786},[376,1930,661],{"class":459},[376,1932,664],{"class":459},[376,1934,1935],{"class":397}," sent",[376,1937,391],{"class":382},[376,1939,750],{"class":672},[376,1941,401],{"class":382},[376,1943,697],{"class":463},[376,1945,511],{"class":382},[376,1947,702],{"class":463},[376,1949,705],{"class":382},[376,1951,708],{"class":463},[376,1953,711],{"class":382},[376,1955,714],{"class":463},[376,1957,717],{"class":382},[376,1959,635],{"class":382},[376,1961,1962,1965,1968,1970,1973,1975,1977,1980,1982,1984,1986,1988,1990,1993,1995,1997],{"class":378,"line":816},[376,1963,1964],{"class":382},"    this.",[376,1966,1967],{"class":390},"gMetrics",[376,1969,511],{"class":382},[376,1971,1972],{"class":386},"increment",[376,1974,391],{"class":397},[376,1976,741],{"class":382},[376,1978,1979],{"class":407},"emails.",[376,1981,747],{"class":382},[376,1983,750],{"class":390},[376,1985,511],{"class":382},[376,1987,591],{"class":390},[376,1989,758],{"class":382},[376,1991,1992],{"class":407},".sent",[376,1994,741],{"class":382},[376,1996,775],{"class":397},[376,1998,585],{"class":382},[376,2000,2001],{"class":378,"line":822},[376,2002,819],{"class":382},[376,2004,2005],{"class":378,"line":1346},[376,2006,783],{"emptyLinePlaceholder":60},[376,2008,2009,2011,2014],{"class":378,"line":1491},[376,2010,641],{"class":382},[376,2012,2013],{"class":386},"OnJobFailed",[376,2015,1264],{"class":390},[376,2017,2018,2020,2022,2025,2027,2030,2032,2035,2037,2039,2041,2043,2045,2047,2049,2051,2053,2055,2057],{"class":378,"line":1500},[376,2019,661],{"class":459},[376,2021,664],{"class":459},[376,2023,2024],{"class":397}," failed",[376,2026,391],{"class":382},[376,2028,2029],{"class":672},"error",[376,2031,401],{"class":382},[376,2033,2034],{"class":463}," Error",[376,2036,414],{"class":382},[376,2038,692],{"class":672},[376,2040,401],{"class":382},[376,2042,697],{"class":463},[376,2044,511],{"class":382},[376,2046,702],{"class":463},[376,2048,705],{"class":382},[376,2050,708],{"class":463},[376,2052,711],{"class":382},[376,2054,714],{"class":463},[376,2056,717],{"class":382},[376,2058,635],{"class":382},[376,2060,2061],{"class":378,"line":1509},[376,2062,2063],{"class":1017},"    \u002F\u002F called once per failed attempt, so tell a retry from a final failure\n",[376,2065,2066,2069,2072,2074,2076,2078,2081,2083,2085,2087,2090],{"class":378,"line":1514},[376,2067,2068],{"class":455},"    if",[376,2070,2071],{"class":397}," (",[376,2073,750],{"class":390},[376,2075,511],{"class":382},[376,2077,755],{"class":390},[376,2079,2080],{"class":382}," ===",[376,2082,692],{"class":390},[376,2084,511],{"class":382},[376,2086,528],{"class":390},[376,2088,2089],{"class":397},") ",[376,2091,2092],{"class":382},"{\n",[376,2094,2095,2098,2100,2103,2105,2107,2109,2111,2113,2115,2117,2120,2122],{"class":378,"line":1520},[376,2096,2097],{"class":455},"      await",[376,2099,792],{"class":382},[376,2101,2102],{"class":390},"gAlerts",[376,2104,511],{"class":382},[376,2106,1393],{"class":386},[376,2108,391],{"class":397},[376,2110,2029],{"class":390},[376,2112,414],{"class":382},[376,2114,692],{"class":390},[376,2116,511],{"class":382},[376,2118,2119],{"class":390},"id",[376,2121,775],{"class":397},[376,2123,585],{"class":382},[376,2125,2126],{"class":378,"line":1536},[376,2127,2128],{"class":382},"    }\n",[376,2130,2131],{"class":378,"line":1542},[376,2132,819],{"class":382},[376,2134,2135],{"class":378,"line":1547},[376,2136,825],{"class":382},[354,2138,2139],{},"Both accept a job filter when a hook should only watch one kind of job:",[366,2141,2143],{"className":368,"code":2142,"language":370,"meta":371,"style":371},"@OnJobFailed({ job: 'digest' })\npublic async digestFailed(error: Error): Promise\u003Cvoid> {}\n",[373,2144,2145,2171],{"__ignoreMap":371},[376,2146,2147,2149,2151,2153,2155,2158,2160,2162,2165,2167,2169],{"class":378,"line":379},[376,2148,383],{"class":382},[376,2150,2013],{"class":386},[376,2152,391],{"class":390},[376,2154,394],{"class":382},[376,2156,2157],{"class":397}," job",[376,2159,401],{"class":382},[376,2161,404],{"class":382},[376,2163,2164],{"class":407},"digest",[376,2166,411],{"class":382},[376,2168,446],{"class":382},[376,2170,449],{"class":390},[376,2172,2173,2175,2178,2181,2183,2185],{"class":378,"line":452},[376,2174,1402],{"class":390},[376,2176,2177],{"class":386},"digestFailed",[376,2179,2180],{"class":390},"(error: Error): ",[376,2182,1429],{"class":463},[376,2184,1432],{"class":382},[376,2186,467],{"class":382},[358,2188,2189],{"id":518},"Concurrency",[354,2191,2192,2194,2195,2197],{},[373,2193,518],{}," is per queue and per process. The highest value requested by any handler of a queue wins, and the manager's ",[373,2196,518],{}," setting is the floor for every queue.",[366,2199,2201],{"className":368,"code":2200,"language":370,"meta":371,"style":371},"\u002F\u002F up to 10 jobs of 'emails' at a time in this process\n@Consumer({ queue: 'emails', concurrency: 10 })\nexport class EmailConsumer {}\n",[373,2202,2203,2208,2241],{"__ignoreMap":371},[376,2204,2205],{"class":378,"line":379},[376,2206,2207],{"class":1017},"\u002F\u002F up to 10 jobs of 'emails' at a time in this process\n",[376,2209,2210,2212,2214,2216,2218,2220,2222,2224,2226,2228,2230,2232,2234,2237,2239],{"class":378,"line":452},[376,2211,383],{"class":382},[376,2213,387],{"class":386},[376,2215,391],{"class":390},[376,2217,394],{"class":382},[376,2219,398],{"class":397},[376,2221,401],{"class":382},[376,2223,404],{"class":382},[376,2225,408],{"class":407},[376,2227,411],{"class":382},[376,2229,414],{"class":382},[376,2231,417],{"class":397},[376,2233,401],{"class":382},[376,2235,2236],{"class":422}," 10",[376,2238,446],{"class":382},[376,2240,449],{"class":390},[376,2242,2243,2245,2247,2249],{"class":378,"line":638},[376,2244,456],{"class":455},[376,2246,460],{"class":459},[376,2248,464],{"class":463},[376,2250,467],{"class":382},[354,2252,2253],{},"On BullMQ it becomes the worker concurrency, on RabbitMQ the channel prefetch, on Kafka the number of partitions consumed concurrently, and in memory the number of handlers running at once.",[358,2255,2257],{"id":2256},"registering-handlers-by-hand","Registering handlers by hand",[354,2259,2260,2261,2264],{},"The decorators are a thin layer over ",[373,2262,2263],{},"QueueManager.registerConsumer()",". Consumers built at runtime can call it directly:",[366,2266,2268],{"className":368,"code":2267,"language":370,"meta":371,"style":371},"queueManager.registerConsumer({\n  strategy: 'default',\n  queue: 'emails',\n  job: 'welcome',\n  handler: async (payload, context) => this.send(payload),\n  options: { attempts: 3 },\n  concurrency: 2,\n  source: 'runtime',\n});\n",[373,2269,2270,2284,2300,2315,2330,2362,2380,2391,2407],{"__ignoreMap":371},[376,2271,2272,2275,2277,2280,2282],{"class":378,"line":379},[376,2273,2274],{"class":390},"queueManager",[376,2276,511],{"class":382},[376,2278,2279],{"class":386},"registerConsumer",[376,2281,391],{"class":390},[376,2283,2092],{"class":382},[376,2285,2286,2289,2291,2293,2295,2297],{"class":378,"line":452},[376,2287,2288],{"class":397},"  strategy",[376,2290,401],{"class":382},[376,2292,404],{"class":382},[376,2294,510],{"class":407},[376,2296,411],{"class":382},[376,2298,2299],{"class":382},",\n",[376,2301,2302,2305,2307,2309,2311,2313],{"class":378,"line":638},[376,2303,2304],{"class":397},"  queue",[376,2306,401],{"class":382},[376,2308,404],{"class":382},[376,2310,408],{"class":407},[376,2312,411],{"class":382},[376,2314,2299],{"class":382},[376,2316,2317,2320,2322,2324,2326,2328],{"class":378,"line":658},[376,2318,2319],{"class":397},"  job",[376,2321,401],{"class":382},[376,2323,404],{"class":382},[376,2325,651],{"class":407},[376,2327,411],{"class":382},[376,2329,2299],{"class":382},[376,2331,2332,2335,2337,2339,2341,2343,2345,2347,2349,2352,2354,2357,2360],{"class":378,"line":722},[376,2333,2334],{"class":386},"  handler",[376,2336,401],{"class":382},[376,2338,664],{"class":459},[376,2340,2071],{"class":382},[376,2342,673],{"class":672},[376,2344,414],{"class":382},[376,2346,692],{"class":672},[376,2348,775],{"class":382},[376,2350,2351],{"class":459}," =>",[376,2353,792],{"class":382},[376,2355,2356],{"class":386},"send",[376,2358,2359],{"class":390},"(payload)",[376,2361,2299],{"class":382},[376,2363,2364,2367,2369,2371,2373,2375,2377],{"class":378,"line":780},[376,2365,2366],{"class":397},"  options",[376,2368,401],{"class":382},[376,2370,678],{"class":382},[376,2372,428],{"class":397},[376,2374,401],{"class":382},[376,2376,1072],{"class":422},[376,2378,2379],{"class":382}," },\n",[376,2381,2382,2385,2387,2389],{"class":378,"line":786},[376,2383,2384],{"class":397},"  concurrency",[376,2386,401],{"class":382},[376,2388,433],{"class":422},[376,2390,2299],{"class":382},[376,2392,2393,2396,2398,2400,2403,2405],{"class":378,"line":816},[376,2394,2395],{"class":397},"  source",[376,2397,401],{"class":382},[376,2399,404],{"class":382},[376,2401,2402],{"class":407},"runtime",[376,2404,411],{"class":382},[376,2406,2299],{"class":382},[376,2408,2409,2411,2413],{"class":378,"line":822},[376,2410,758],{"class":382},[376,2412,775],{"class":390},[376,2414,585],{"class":382},[354,2416,2417],{},"Registering a second handler for the same job of the same queue is an error, so a copy-pasted job name fails loudly instead of silently shadowing the first handler.",[2419,2420,2421],"style",{},"html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .swJcz, html code.shiki .swJcz{--shiki-light:#E53935;--shiki-default:#F07178;--shiki-dark:#F07178}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html pre.shiki code .sbssI, html code.shiki .sbssI{--shiki-light:#F76D47;--shiki-default:#F78C6C;--shiki-dark:#F78C6C}html pre.shiki code .s7zQu, html code.shiki .s7zQu{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#89DDFF;--shiki-default-font-style:italic;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .spNyl, html code.shiki .spNyl{--shiki-light:#9C3EDA;--shiki-default:#C792EA;--shiki-dark:#C792EA}html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .sHdIc, html code.shiki .sHdIc{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#EEFFFF;--shiki-default-font-style:italic;--shiki-dark:#BABED8;--shiki-dark-font-style:italic}html pre.shiki code .sHwdD, html code.shiki .sHwdD{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#546E7A;--shiki-default-font-style:italic;--shiki-dark:#676E95;--shiki-dark-font-style:italic}",{"title":371,"searchDepth":379,"depth":452,"links":2423},[2424,2425,2426,2427,2428,2429,2430,2431,2432],{"id":360,"depth":452,"text":361},{"id":591,"depth":452,"text":592},{"id":889,"depth":452,"text":890},{"id":1000,"depth":452,"text":1001},{"id":1371,"depth":452,"text":1372},{"id":1574,"depth":452,"text":1575},{"id":1800,"depth":452,"text":1801},{"id":518,"depth":452,"text":2189},{"id":2256,"depth":452,"text":2257},"Decorators, job context, validation and lifecycle hooks","md",null,{},{"title":117,"description":2433},"lhyKYj2Mn7YH4mL48Y_LUwheuK4YVF8jThWbmODu0tQ",[2440,2442],{"title":70,"path":114,"stem":115,"description":2441,"children":-1},"Background jobs for Vercube, with one job model over BullMQ, RabbitMQ, Kafka and memory",{"title":121,"path":122,"stem":123,"description":2443,"children":-1},"Memory, BullMQ, RabbitMQ and Kafka transports, their options and their limits",1791443501734]