- FLAME मौजूदा application code के कुछ हिस्से को function में wrap करके temporary application copy में चलाने देता है, ताकि code को अलग runtime में ले जाए बिना granular elastic scaling हासिल की जा सके
- पारंपरिक FaaS approach, video thumbnail generation जैसे कामों में भी HTTP, S3, SQS, API Gateway, encoder/decoder और workflow orchestration बढ़ाने वाली संरचना बना सकती है
- Elixir की flame library
FLAME.callके जरिए function execution को remote runner को delegate करती है, और Fly.io काFLAME.FlyBackendउसी Docker image से नई Fly Machine boot करके लगभग 3 सेकंड में parent node से जोड़ देता है - development और testing में
LocalBackendके साथ उसी runtime में execution होता है, और production मेंmin,max,max_concurrency,idle_shutdown_afterसे scale-to-zero और थोड़ी देर hot state बनाए रखने को tune किया जाता है - FLAME job queue को हटाने के बजाय durability guarantee और elastic execution को अलग करता है, ताकि queue dispatch, commit, retry संभाले और CPU-intensive काम FLAME call के अंदर process हों
FLAME pattern जिस समस्या को target करता है
- Elastic auto-scaling server management का बोझ घटाती है और usage-based cost का वादा करती है, लेकिन FaaS इस्तेमाल करने पर अलग queue, storage, glue code, और development/testing/CI की complexity भी साथ बढ़ सकती है
- FLAME का full form Fleeting Lambda Application for Modular Execution है; इसमें पूरे application को lambda की तरह treat किया जाता है और सिर्फ कुछ module-level काम short-lived infrastructure पर चलाए जाते हैं
- लक्ष्य तीन तरह से समझे जा सकते हैं
fly deploy,git push heroku,kubectlजैसे मौजूदा deployment flow से server management घटाना- application code के केवल खास हिस्सों को on-demand granular scaling देना
- application को दोबारा लिखना या कुछ code को proprietary runtime में move न करना
FLAME.call से मौजूदा function को move करना
- उदाहरण Elixir application में uploaded video को
ffmpegसे thumbnails में बदलने वालेgenerate_thumbnailsfunction का है - मौजूदा function temporary directory बनाता है,
ffmpegचलाता है, फिर बने thumbnails को durable storage में store करता है और URL को DB मेंRepo.insert_allसे record करता है - CPU-intensive video transcoding production में पूरी service को रोक सकती है, इसलिए पूरे code को FaaS या microservice में move करने के बजाय function body को
FLAME.call(MyApp.FFMpegRunner, fn -> ... end)से wrap किया जाता है FLAME.callrunner pool name और function लेकर पूरे application की नई copy खोजता या boot करता है, फिर केवल उस function को execute करता है- function ने जिन variables को close over किया है, जैसे
%Video{}struct औरinterval, वे automatically भेजे जाते हैं - FLAME runner boot होने के बाद parent node से connect करता है, execute करने वाला function पाता है, फिर result caller को return करता है
- configuration के हिसाब से runner extra work का इंतज़ार करते हुए idle state में shut down हो सकता है या तुरंत terminate हो सकता है
- function ने जिन variables को close over किया है, जैसे
- DB connection सहित पूरा application चल रहा होता है, इसलिए original code की तरह
Repo.insert_allवैसा ही इस्तेमाल किया जा सकता है
FaaS complexity और FLAME का फर्क
- FaaS problem solve करने के लिए components देता है, लेकिन FLAME अलग communication layer को ही कम करने वाली approach के ज्यादा करीब है
- video thumbnail example में simple AWS Lambda Function URL से शुरू करने पर भी जल्द complexity आ जाती है
- thumbnails को HTTP से app में वापस stream करना हो तो दोनों तरफ custom encoder और decoder लिखने पड़ते हैं
- video transcoding या upload 15 मिनट से ज्यादा हो जाए तो Lambda के hard timeout की वजह से video को chunks में बांटना और ज्यादा Lambda इस्तेमाल करना पड़ता है
- workflow orchestration और SQS, S3 जैसी additional services की जरूरत पड़ती है
- FaaS-based implementation आम तौर पर ये cost points बनाती है
- HTTP endpoint, S3, API Gateway से Lambda trigger करना
- video transcoding के लिए custom Lambda लिखना
- thumbnail results को SQS में store करना
- app side पर SQS consumer लिखना
- DB में store करना, और दूसरे instances से जुड़े active subscribers को events वापस भेजने का तरीका configure करना
- FLAME application के internal code और मौजूदा DB, PubSub, platform features को ज्यों का त्यों इस्तेमाल करने देता है, इसलिए अलग services और result retrieval storage घट सकते हैं
Fly.io backend और local execution
- Elixir flame library FLAME pattern की implementation है, और default रूप से
LocalBackendऔरFlyBackendदेती है FLAME.FlyBackendFly.io infrastructure में नई Machine पर application copy boot करता है और लगभग 3 सेकंड में parent node से connect करके काम ले सकता है- Fly.io applications को packaged Docker image के रूप में चलाता है, इसलिए Fly API से current app जैसी ही image वाली नई Machine boot करने का request किया जाता है
- Fly.io infrastructure में FLAME runner को parent के same region में start किया जा सकता है, जिससे parent और runner के बीच latency घटती है
FLAME.FlyBackenddocumentation सहित 200 LOC से कम है, और library dependency सिर्फ HTTP clientreqहै- development और testing में LocalBackend से laptop या CI server के existing runtime में वही code execute होता है
File transfer और development/testing को सरल बनाना
- FLAME application के बाहर code लिखे बिना business logic, DB settings, PubSub और platform features reuse कर सकता है
- Elixir में Erlang VM की distributed capabilities की वजह से parent node की file stream को remote FLAME application तक भेजा जा सकता है
- parent node पर video path की file stream open की जाती है
- FLAME child में temporary file stream open करके parent stream copy की जाती है
- इसके बाद
ffmpegremote runner की temporary file को input बनाकर thumbnails generate करता है
- इस approach में file को FLAME server तक भेजने के लिए अलग से S3 या HTTP interface configure करने की जरूरत नहीं होती
- अलग service deployment, endpoint management, S3/SQS से result retrieval, और development/testing/CI dependency configuration कम हो जाते हैं
Elixir के बाहर FLAME
- Elixir process supervision और distributed messaging देता है, इसलिए FLAME model के साथ अच्छी तरह fit होता है, लेकिन reasonable concurrency primitives वाली languages भी यह pattern इस्तेमाल कर सकती हैं
- JavaScript proof-of-concept example Fly Machine में application function को दूसरी machine पर execute करने के रूप में है: fly-run-this-function-on-another-machine
- JavaScript-based FLAME call का सामान्य flow module execution वाले हिस्से को नई file में move करके runner pool में execute करने का है
- अगर arguments JSON serialization के योग्य हों, तो पूरा flow Elixir example जैसा ही होता है: application code short-lived instance पर execute होता है
- पूरी FLAME library को ये चीजें handle करनी होंगी
- elastic pool scale-up और scale-down logic
- hot startup और cold startup को ध्यान में रखकर pool management
- orphaned resource रोकने के लिए remote runner monitoring
- deployment को latest state में रखने का तरीका
Background job queues से संबंध
- FLAME background job processor के अंदर भी काम करता है, लेकिन job queue के साथ role overlap वाला हिस्सा है
- job queue आम तौर पर तब इस्तेमाल होती है जब durability guarantee चाहिए; queue को load changes के हिसाब से ज्यादा jobs process करने के लिए tune किया जा सकता है
- durable jobs और elastic execution अलग-अलग concerns हैं
- queue को सिर्फ offload execution के लिए इस्तेमाल करें तो job में data डालने और result को caller या user device तक वापस भेजने के लिए glue code चाहिए
- video upload के बाद thumbnail generation की success guarantee करनी हो तो queue dispatch, commit, retry mechanisms संभाल सकती है
- actual transcoding job के अंदर FLAME call से execute करके durability और scalable execution को अलग किया जा सकता है
- save से पहले video preview या user के app छोड़ देने के बाद ML model execution जैसे jobs, जिन्हें durability नहीं चाहिए, durable storage में job लिखने वाली structure से match नहीं कर सकते
Elastic scaling के लिए runner pool
- Elixir FLAME implementation runners का elastic pool define करके scale-to-zero और concurrency limit दोनों support करती है
- example configuration में
FLAME.Poolको application केstart/2में add किया जाता हैmin: 0से scale-to-zero allow होता हैmax: 10से अधिकतम 10 runners boot होते हैंmax_concurrency: 5से प्रति runner 5ffmpegjobs support होते हैंidle_shutdown_after: 30_000से 30 सेकंड तक कोई call job न हो तो idle down होता है
- FLAME parent की मौजूदगी के आधार पर Phoenix web server conditionally start होता है
- web traffic handle न करने वाले FLAME runner में web server start करने की जरूरत नहीं है
- DB जैसा
MyApp.RepoFLAME runner के अंदर इस्तेमाल होना है, इसलिए उसे वैसे ही रखा जाता है
min: 1देने पर application start के समय से कम से कम एकffmpegrunner hot state में रखा जा सकता है
Stateful process placement
- Elixir application के stateful हिस्से message mailbox वाले lightweight process primitives के इर्द-गिर्द बने होते हैं
FLAME.callऔरFLAME.castअपेक्षाकृत stateless code के लिए suitable हैं, औरFLAME.place_childमौजूदा process spec को local के बजाय FLAME runner पर start करवाता हैFLAME.place_childकोTask.Supervisor.start_child,DynamicSupervisor.start_childजैसे interfaces इस्तेमाल करने वाली जगहों पर उपयोग किया जा सकता है- LiveView upload के दौरान thumbnail generation example में upload chunk को
ThumbnailGeneratorprocess को दिया जाता है, और वह processffmpegसे communicate करता हैffmpegstdout में PNG delimiter मिलने पर LiveView process को image message भेजता है- LiveView
handle_infoमें message लेकर UI में नई image add करता है
- मौजूदा
DynamicSupervisor.start_child(@sup, spec)call कोFLAME.place_child(Thumbs.FFMpegRunner, spec)से बदलने परThumbnailGeneratorprocess FLAME runner पर execute होता है - process location से स्वतंत्र होकर messages भेज/ले सकते हैं, इसलिए upload खत्म होने या browser tab बंद होने से process end हो जाए तो FLAME server termination detect करता है और कोई और काम न होने पर idle down हो जाता है
Remote monitoring और failure handling
- short-lived infrastructure में orphaned resource रोकने के लिए failsafe चाहिए
- parent जब runner launch करता है, तो runner को काम न होने पर खुद idle down होना चाहिए, और parent node से संपर्क न रह जाए तो failsafe shutdown handle करना चाहिए
- नए deployment से parent replace होने पर cluster में same code चलने की guarantee के लिए runner को भी terminate होना चाहिए
- runner job result का इंतज़ार कर रहे active callers को runner के किसी भी वजह से down होने की स्थिति को consider करना चाहिए
- Erlang VM द्वारा दिए गए primitives इस implementation को आसान बनाते हैं
- local/remote process monitoring और supervision
- node up/down detect करने वाली node monitoring
- application startup/shutdown order control करके new deployment के समय active runners को काम पूरा करने का समय देने वाला shutdown flow
- internal implementation details पर आगे एक अलग post में चर्चा होगी, और अभी flame source देख सकते हैं
वर्तमान स्थिति और अगले कदम
- Elixir FLAME library अभी शुरुआती चरण में है, लेकिन इसे अभी आजमाया जा सकता है
- आगे और advanced pool growth techniques और Elixir implementation approach पर deep dive planned है
- अन्य languages में FLAME pattern implement करने पर discussion भी संभव है
1 टिप्पणियां
Hacker News की राय
पिछले 4 सालों में 100 से ज़्यादा Lambda functions वाले ऐप की तकलीफ़ और complexity झेलने के बाद, मुझे लगता है कि यह लेख FaaS serverless architecture की कमियों पर बिल्कुल सही चोट करता है
शुरुआत में ये कमियां साफ़ नहीं दिखतीं। उल्टा, usage कम हो तो यह लगभग free होता है और maintenance भी लगभग नहीं चाहिए—ये फायदे बहुत स्पष्ट लगते हैं
बाद में, जब Lambda workflows आपस में उलझकर interdependencies की वजह से धीरे-धीरे rigid हो जाते हैं, तब पछतावा होता है कि काश monolith पर गए होते और कुछ सौ डॉलर ज़्यादा खर्च कर खुद manage किया होता। आजकल fly.io जैसी जगहों पर तो शायद इससे भी कम खर्च हो सकता है
अगर Elixir इस्तेमाल न करें तो क्या होता है, यह जानने की उत्सुकता है
जब हालात बिगड़ने लगते हैं, तब तक अक्सर नई job ढूंढने का समय भी आ जाता है। खासकर अगर joining के करीब एक साल बाद वे खुद लाए हुए process पर पछता रहे हों। खराब bosses, घटिया ‘unit tests’, Scrum वगैरह में यह कई बार देखा है
हालांकि पता नहीं लोग काम पर महसूस होने वाली असुविधा की वजह साफ़-साफ़ पहचानते हैं या उसे बस “अब निकलने का समय है” मान लेते हैं। जब भी असुविधाजनक चीज़ को नाम देने की कोशिश की, बहुत resistance मिला; Good to Great पढ़ने के बाद इस पर emotional energy खर्च करना काफी कम हो गया। कोई भी यह नहीं कहना चाहता, “अरे, यह तो मेरे actions का परिणाम है”
जिस Rube Goldberg-style system को मैं maintain करता हूं, उसे असल में बनाने वाले लोग सबसे पहले चले गए। उस जहाज़ के captain ने मेरे colleague से पूछा कि अगर हम अपना engine open source कर दें तो कैसा रहेगा, और colleague ने जवाब दिया कि कोई भी ऐसा system इस्तेमाल नहीं करना चाहेगा जिसने पहले से मौजूद और बेहतर wheel को फिर से invent किया हो। वह व्यक्ति 3–4 महीनों के भीतर खुद ही चला गया
अगर आप सामान्य service-oriented code लिख सकें जिसमें Lambdas एक-दूसरे को call कर सकें, तो application को सैकड़ों छोटे-छोटे, थोड़ी देर चलने वाले टुकड़ों में बांटने की ज़रूरत नहीं होगी। लेकिन अगर waiting time के लिए भी cost देनी पड़े तो यह संभव नहीं है। अगर Lambda I/O wait के दौरान execution pause कर सके, तो समस्या हल हो जाती है। इसलिए मुझे लगता है कि durable execution जवाब हो सकता है
पिछले कुछ हफ्तों से मैं इसे दिखाने वाला लेख लिख रहा था: https://restate.dev/blog/suspendable-functions-make-lambda-t...
captured variables serialization वाली functions जैसी usability, जो Elixir में मुफ्त मिल जाती है, पूरी तरह पाना मुश्किल होगा; लेकिन JavaScript जैसी languages में closure से wrap करने के बजाय module execution part को नई file में ले जाकर शायद 90% तक पहुंचा जा सकता है
FLAME library implement करने वाले को pooling, monitoring और remote communication वाले हिस्से भी लिखने होंगे। Elixir distributed messaging और monitoring में बहुत कुछ मुफ्त देता है। process placement से जुड़ी functionality भी असल में लगभग Elixir-specific है
आखिरकार हम एक fat Lambda monolith पर चले गए, जिसमें एक ही Lambda कई endpoints handle करता है
दूसरे शब्दों में, monolith पर जाते हुए भी AWS cost minimize कर सकते हैं। यह कोई either-or समस्या नहीं है
आजकल मैं asp.net इस्तेमाल कर रहा हूं, और optimized EF model सहित ready-to-run deploy किया गया काफ़ी बड़ा app भी अपेक्षाकृत जल्दी start हो जाता है
मैं लेखक हूं। आखिरकार इसे public करके खुशी हुई, और अगर सवाल हों तो जवाब दूंगा। उम्मीद है कि कुछ लोग FLAME pattern को JavaScript, Go और दूसरी languages में implement करने के लिए पर्याप्त प्रेरित होंगे
इसमें पहले से event bus के ऊपर reactive scaling, Future और coroutines के ज़रिए async execution handle करने के mechanisms हैं, और cluster भर में data serialization और distribution भी support करता है। कई popular languages के लिए event bus clients भी हैं, इसलिए कई languages मिलाकर applications बनाई जा सकती हैं
अगर problem को “…मौत से भी बदतर किस्मत” की तरह पेश किया जाए, और solution को इतना आसान और painless दिखाया जाए कि दूसरा approach न छोड़ने वाला बेवकूफ लगे, तो ऐसे लेख को आसानी से शुद्ध sales pitch मान लिया जाता है। यह panacea बेचने वालों का तरीका है
लेख की शुरुआत में problem खुद अच्छी तरह पहचानी गई है, इसलिए अगर कहीं ज़्यादा कम भावुक objective comparison होता, तो बेहतर approach के बारे में उत्सुक लोगों को कम resistance महसूस होता
लेख का वास्तविक content दिलचस्प था, लेकिन presentation की वजह से दूरी महसूस हुई। इसे constructive feedback की तरह लें
और ffmpeg.fly.dev पहले ले लेने पर मुझे थोड़ा-सा guilt हुआ
“कल्पना करें कि existing app code के किसी भी हिस्से को बस function में wrap करें और वह अपने-आप scale हो जाए, और वह code block app की temporary copy में execute हो” वाला हिस्सा दिलचस्प है
यह serverless के लिए fork जैसी चीज़ बनाने जैसा लगता है। शानदार काम
कुछ साल पहले मैंने एक ऐसी सेवा इस्तेमाल की थी जो असल में यही काम करती थी। PiCloud दुर्भाग्य से Dropbox में शामिल हो गया, लेकिन उससे पहले उसका बिल्कुल यही मॉडल था: काम को पारदर्शी तरीके से workers में फैला देना। तरीका यह था कि code को bundle करके workers पर चलाया जाता था
उदाहरण यहां है। आप देख सकते हैं कि यह बिल्कुल वही मॉडल है: https://github.com/picloud/basic-examples/blob/master/exampl...
मैंने Elixir कभी इस्तेमाल नहीं किया, लेकिन दशकों पहले Erlang इस्तेमाल किया था, और BEAM मूल रूप से बहुत बदला हुआ नहीं लगता। क्योंकि यह design का एक अहम हिस्सा है, इसलिए लगता है कि यह ऐसे कामों के लिए कहीं ज्यादा उपयुक्त होगा। फिर भी यह पूरी तरह मुफ्त का सौदा नहीं है, क्योंकि इंतजार करते समय मुख्य process के मर जाने की संभावना तो हो सकती है
पूरे तर्क से सहमत हूं। हमने https://www.windmill.dev पर अलग तरीका अपनाया है, जहां abstraction की unit को container level के बजाय source code level पर देखते हैं
main function और imports को parse करके arguments और dependencies निकाली जाती हैं, फिर चुने हुए runtime (TypeScript, Python, Go, Bash) में code को जैसा है वैसा चलाया जाता है। मुख्य trick cache को कुशलता से manage करना है, ताकि imports से स्वतंत्र होकर worker हमेशा hot state में बना रहे
यह तरीका codebase में FLAME जितना integrate नहीं होता, लेकिन target users अलग हैं। हमारे users जटिल workflows, cron jobs, या auto-generated UI वाली one-off scripts शुरू से बनाते हैं
FLAME में ऐसा लगता है कि पूरा context snapshot होकर target VM पर फिर restore होता है। एक दूसरा तरीका यह है कि ऐसा syntax लाया जाए जिससे बताया जा सके कि कौन सा context चाहिए और कौन सा नहीं, ताकि सिर्फ न्यूनतम चीजें load हों। मौजूदा codebase और Windmill को बेहतर integrate करने और HTTP calls पर निर्भर न रहने के लिए हम अभी इसे explore कर रहे हैं
इस process में सिर्फ जरूरी context भेजना implicitly handle हो जाता है। लेख में भी इसे ऐसे समझाया गया है: “FLAME.call runner pool का नाम और एक function लेता है। फिर यह पूरे application की नई copy ढूंढता या boot करता है, और वहां function को execute करता है। function ने closure के रूप में जिन variables को capture किया होता है, जैसे %Video{} struct और interval, वे अपने-आप साथ भेज दिए जाते हैं”
project का लक्ष्य पसंद आया। सच में उम्मीद है कि Windmill एक बेहतर open-source Retool/Airtable alternative बनेगा
यह बात अच्छी लगी कि “FLAME में development और test runners local backend पर ही चलते हैं।” अच्छी local development experience वाला serverless, यह अच्छा है
अगर “फिर पूरे application की एक नई copy ढूंढी या boot की जाती है और वह function वहां execute होता है,” तो क्या हर
Flame.callपर पूरा app process नए सिरे से start होता है और execution context copy करके उसमें डाला जाता है?scalability के लिहाज से यह बहुत सरल समाधान है, लेकिन इसके नुकसान भी होंगे
अगर app startup time में 10ms बढ़ते हैं, तो application के हर
Flame.callpoint पर 10ms जुड़ जाएंगे, और memory के साथ भी शायद यही होगाइस system को इस्तेमाल करते समय ऐसी चिंताओं को ध्यान में रखना होगा
load होने पर pool पहले से hot रहता है, इसलिए cold start cost लगभग नहीं लगती। इसके बाद Elixir library में और sophisticated pool growth techniques भी जोड़ी जा रही हैं, ताकि full runner मिलने पर नया cold start करने की स्थिति भी टाली जा सके
hot runner में overhead सिर्फ parent और child के बीच की latency है। वे same datacenter में होने चाहिए, इसलिए यह 1ms या उससे कम होगी
शानदार। यह https://www.inngest.com/ पर हमने जो बनाया है, उसके बहुत हल्के Elixir-only version जैसा लगता है
दोनों में समानता यह है कि existing code को किसी चीज से wrap करके serverless functions में इस्तेमाल लायक बनाया जाता है, और मूल रूप से remote RPC की तरह call किया जा सकता है
ऐसा code अक्सर imperative steps की series के रूप में चलता है। हर step एक अतिरिक्त Lambda के रूप में serial या parallel चल सकता है। लेकिन steps के बीच variables में capture हुई implicit state होती है। इसी वजह से function एक workflow बन जाता है। Inngest model में इस state को capture करके फिर function में inject किया जाता है ताकि durability मिले
durability के लिहाज से ऐसे processes queue पर आधारित होने चाहिए। इस model की अच्छी बात यह है कि queues सस्ती हैं। अगर queue को एक line of code जितना सस्ता बना दें, तो सब आसान हो जाता है। कोई भी developer infrastructure की चिंता किए बिना reliable code लिख सकता है
monitoring और observability भी महत्वपूर्ण हैं। dead letter queues वाकई भयानक होती हैं, और failing functions या steps को manage और rerun कर पाने की जरूरत होती है
FLAME और Inngest में फर्क भी है। Inngest queue-based, event-driven है, और किसी भी भाषा में HTTP के जरिए provide किया जा सकता है। चूंकि Inngest state को बाहर store करता है, इसलिए आप workflow Elixir में लिखकर TypeScript में फिर से लिखें और redeploy करें, तब भी running function CRIU जैसा backend languages के पार live migrate हो सकता है
event-driven तरीके से flow control भी संभव है। debounce, batch, throttling, fan-out तक किसी भी runtime या language में handle किया जा सकता है। उदाहरण के लिए, Fly पर चल रहा एक Elixir app event भेजकर TypeScript + Lambda में function execute करा सकता है
FLAME आगे कहां जाता है, यह देखने की उम्मीद है। मुझे लगता है कि goals में कुछ समानता है
Elixir में durability, retries और workflows की जरूरत होने पर आम तौर पर Oban इस्तेमाल करते हैं, और यहां भी आगे ऐसा ही रहेगा। Oban job FLAME को call करके elastic execution handle कराएगी
HN द्वारा थोपे जाने वाले अमेरिकी-style title capitalization से मुझे सचमुच नफ़रत होने की एक वजह यही है। Serverless ऐसा दिखता है जैसे बड़े S वाली कंपनी serverless.com पर फिर से सोचने की बात हो, न कि छोटे s वाले सिद्धांत पर फिर से सोचने की
वैसे, काश कोई Serverless पर फिर से सोचता
पता नहीं आपने https://sst.dev/ देखा है या नहीं, लेकिन लगता है उन्होंने ठीक वही किया है। उदाहरण के लिए Live Lambda Development है, जिससे कोड को cloud पर चढ़ाकर deploy होने का इंतज़ार करने की ज़रूरत नहीं पड़ती और feedback loop काफ़ी छोटा हो जाता है, इसलिए local development सच में आसान हो जाता है
आइडिया काफ़ी शानदार है और API भी बेहतरीन है
“वीडियो transcoding जैसे CPU-bound काम production में पूरी service को जल्दी रोक सकते हैं” वाले हिस्से पर—क्या बस CPU-based autoscaling नहीं कर सकते?
किसी खास hot task को संभालने के लिए आप webserver समेत पूरी application को scale कर देते हैं। हमें जो चाहिए, और FaaS की ओर जाने की वजह, fine-grained elastic scaling है। यहाँ आइडिया यह है कि webserver या worker का scale बटन अंधाधुंध दबाकर सब ठीक होने की उम्मीद करने के बजाय, existing app code के लिए इस तरह की fine-grained scaling संभव बनाई जाए
या फिर GPU की ज़रूरत भी हो सकती है
core service के लिए 1–2 servers काफ़ी हो सकते हैं, लेकिन दिन में शायद एक बार होने वाले task के लिए ज़रूरत पड़ने पर दर्जनों, सैकड़ों या हज़ारों servers तक scale करना पड़ सकता है