ã¢ã¹ã¯ã¯Python Conf ++ã§ã®Celeryã«é¢ããOleg Churkinã®ã¹ããŒãªãŒã®çŸããã¯ãè² è·ã®ããã£ãCeleryã®èšå®æ¹æ³ãšç£èŠæ¹æ³ã«é¢ãã詳现ãªæ瀺ã«å ããŠãæçšãªã¢ã€ãã¢ãåããããšãã§ãããšããããšã§ãã
è¬æŒè ãšãããžã§ã¯ãã«ã€ããŠïŒ Oleg ChurkinïŒ Bahusss ïŒã¯8幎éããŸããŸãªè€éãã®Pythonãããžã§ã¯ããéçºããŠãããYandexãRamblerãRBCãKaspersky Labãªã©ã®æåäŒæ¥ã§åããŠããŸãã çŸåšãtechlideã¯fintech-status StatusMoneyã«ãªã£ãŠããŸãã
ãããžã§ã¯ãã¯ãã¢ã«ãŠã³ãããã©ã³ã¶ã¯ã·ã§ã³ãå人ãªã©ã®ãŠãŒã¶ãŒã®å€§éã®è²¡åããŒã¿ïŒ1.5ãã©ãã€ãïŒã§åäœããŸãã æ¯æ¥æ倧100äžã®ã¿ã¹ã¯ãå®è¡ããŸãã ãã¶ãããã®æ°å€ã¯èª°ãã«ãšã£ãŠã¯ããã»ã©å€§ãããªãããã«æãããããããŸããããé©åºŠãªå®¹éã®å°ããªã¹ã¿ãŒãã¢ããã®å Žåãããã¯å€§éã®ããŒã¿ã§ãããéçºè ã¯å®å®ããããã»ã¹ã«åããéäžã§ããŸããŸãªåé¡ã«çŽé¢ããªããã°ãªããŸããã§ããã
ãªã¬ã°ã¯ä»äºã®ããŒãã€ã³ãã«ã€ããŠè©±ããŸããïŒ
- ãã¬ãŒã ã¯ãŒã¯ã䜿çšããŠè§£æ±ºãããã¿ã¹ã¯ã¯äœã§ããããªãCeleryãéžæããã®ã§ããã
- ã»ããªãã©ã®ããã«åœ¹ç«ã£ããã
- è² è·ãããã£ãç¶æ ã§Celeryãæ§æããæ¹æ³ã
- ã»ããªã®ç¶æ ãç£èŠããæ¹æ³ã
ãããŠã圌ã¯Celeryã«æ¬ ããŠããæ©èœãå®è£ ããããã€ãã®èšèšãŠãŒãã£ãªãã£ãå ±æããŸããã å€æããããã«ã2018幎ã«ã¯ãããå¯èœã«ãªããŸãã 以äžã¯ãäžäººç§°ã¬ããŒãã®ããã¹ãçã§ãã
çºè¡
次ã®ã¿ã¹ã¯ãå¿ èŠã§ããïŒ
- åå¥ã®ããã¯ã°ã©ãŠã³ãã¿ã¹ã¯ãå®è¡ããŸãã
- ã¿ã¹ã¯ã®ãããåŠçãè¡ããŸã ãã€ãŸããäžåºŠã«å€ãã®ã¿ã¹ã¯ãèµ·åããŸãã
- ããã»ã¹ExtractãTransformãLoadãåã蟌ã¿ãŸãã
- éåæAPIãå®è£ ããŸã ã éåæãã¬ãŒã ã¯ãŒã¯ã䜿çšããŠéåæAPIãå®è£ ã§ããã ãã§ãªããå®å šã«åæããããšãã§ããŸãã
- å®æçãªã¿ã¹ã¯ãå®è¡ããŸãã Cronã䜿çšããŠå®è¡ã§ãããããžã§ã¯ãããããŸãããå®æçãªã¿ã¹ã¯ãªãã§å®è¡ã§ãããããžã§ã¯ãã¯1ã€ã§ã¯ãããŸãããããã䟿å©ãªããŒã«ããããŸãã
- ããªã¬ãŒã¢ãŒããã¯ãã£ã®æ§ç¯ïŒããªã¬ãŒãããªã¬ãŒããã«ã¯ãããŒã¿ãæŽæ°ããã¿ã¹ã¯ãå®è¡ããŸãã ããã¯ãããã¯ã°ã©ãŠã³ãã§ããŒã¿ãäºåã«èšç®ããããšã«ãããã©ã³ã¿ã€ã 容éã®äžè¶³ãè£ãããã«è¡ãããŸãã
ããã¯ã°ã©ãŠã³ãã¿ã¹ã¯ã«ã¯ãé»åã¡ãŒã«ãããã·ã¥ããã¹ã¯ããããªã© ãããããçš®é¡ã®éç¥ãå«ãŸããŸãããããã¯ãã¹ãŠãããªã¬ãŒã«ãã£ãŠããã¯ã°ã©ãŠã³ãã¿ã¹ã¯ã§éä¿¡ãããŸãã åæ§ã«ã財åããŒã¿ã®å®æçãªæŽæ°ãéå§ãããŸãã
ããã¯ã°ã©ãŠã³ãã§ã¯ãããšãã°ãŠãŒã¶ãŒã®äžæ£è¡çºããã§ãã¯ãããªã©ãããŸããŸãªç¹å®ã®ãã§ãã¯ãå®è¡ãããŸãã éèç³»ã®æ°èäŒæ¥ã§ã¯ããŠãŒã¶ãŒãéè¡å£åº§ãã·ã¹ãã ã«è¿œå ã§ããããã«ãããã¹ãŠã®ãã©ã³ã¶ã¯ã·ã§ã³ã確èªã§ããããã ããŒã¿ã»ãã¥ãªãã£ã«ç¹ã«å€ãã®åŽåãšæ³šæãæãããŠããŸã ã è©æ¬ºåž«ã¯ãããšãã°ãçãŸããã¢ã«ãŠã³ãã®æ®é«ããã§ãã¯ããããã«ãç§ãã¡ã®ãµãŒãã¹ãæªçšããããšãã§ããŸãã
ããã¯ã°ã©ãŠã³ãã¿ã¹ã¯ã®æåŸã®ã«ããŽãªã¯ã ã¡ã³ããã³ã¹ã¿ã¹ã¯ã§ã ãäœãã埮調æŽãã確èªãä¿®æ£ãç£èŠãªã©ãè¡ããŸãã
äžæ¬éç¥ã®å Žåã ãããåŠçã䜿çšãããŸãã ãŠãŒã¶ãŒããåãåã倧éã®ããŒã¿ã¯ã次ã®ãããªç¹å®ã®æ¹æ³ã§èšç®ããã³åŠçããå¿ èŠããããŸãã ãããã¢ãŒãã
åãæŠå¿µã«ã¯ãåŸæ¥ã®ExtractãTransformãLoadãå«ãŸããŸãã
- å€éšãœãŒã¹ããããŒã¿ãèªã¿èŸŒãïŒå€éšAPIïŒ;
- æªåŠçã®ãŸãŸã«ããŠãã ããã
- ããŒã¿ãèªã¿åã£ãŠåŠçããã¿ã¹ã¯ãå®è¡ããŸãã
- åŠçãããããŒã¿ãé©åãªå Žæã«é©åãªåœ¢åŒã§ä¿åãããããããšãã°åŸã§UIã§äœ¿çšããã®ã«äŸ¿å©ã§ãã
éåæAPIãåçŽãªããŒãªã³ã°ãªã¯ãšã¹ãã䜿çšããŠå®è¡ã§ããããšã¯ç§å¯ã§ã¯ãããŸãããããã³ããšã³ãã¯ããã¯ãšã³ãã§ããã»ã¹ãéå§ããããã¯ãšã³ãã¯å®æçã«èªèº«ãèµ·åããã¿ã¹ã¯ãèµ·åããçµæãã泚ãããããŒã¿ããŒã¹ã®ç¶æ ãæŽæ°ããŸãã ããã³ããšã³ãã¯ããŠãŒã¶ãŒã«ãã®ã€ã³ã¿ã©ã¯ãã£ããªç¶æ ã瀺ããŸã-ç¶æ ãå€åããŠããŸãã ããã«ããã次ã®ããšãå¯èœã«ãªããŸãã
- ä»ã®ã¿ã¹ã¯ããããŒãªã³ã°ã¿ã¹ã¯ãå®è¡ããŸãã
- æ¡ä»¶ã«å¿ããŠç°ãªãã¿ã¹ã¯ãå®è¡ããŸãã
ç§ãã¡ã®ãµãŒãã¹ã§ã¯ãä»ã®ãšããããã§ååã§ãããå°æ¥ã¯ããããäœãä»ã®ãã®ãæžãçŽãå¿ èŠããããŸãã
ããŒã«èŠä»¶
ãããã®ã¿ã¹ã¯ãå®è£ ããã«ã¯ãããŒã«ã«æ¬¡ã®èŠä»¶ããããŸããã
- éå¿ãå®çŸããããã«å¿ èŠãªæ©èœã
- æŸèæã®ãªãã¹ã±ãŒã©ããªã㣠ã
- ä»çµã¿ãç解ããããã«ã·ã¹ãã ãç£èŠããŸãã ãã°ã¬ããŒãã䜿çšããŠãããããSentryãšã®çµ±åã¯ãDjangoãšã®å Žéãã§ã¯ãããŸããã
- å€ãã®ã¿ã¹ã¯ãããããã ããã©ãŒãã³ã¹ ã
- æç床ãä¿¡é Œæ§ãç©æ¥µçãªéçºã¯æããã§ãã ãµããŒãããã³éçºãããããŒã«ãæ¢ããŠããŸããã
- ããã¥ã¡ã³ããŒã·ã§ã³ã®åŠ¥åœæ§- ã©ãã«ãããã¥ã¡ã³ããŒã·ã§ã³ã¯ãããŸãã ã
ã©ã®ããŒã«ãéžæããŸããïŒ
ãããã®åé¡ã解決ããããã®2018幎ã®åžå Žã®éžæè¢ã¯äœã§ããïŒ
ãã€ãŠããã»ã©éå¿çã§ã¯ãªãã£ãã¿ã¹ã¯ã®ããã«ãç§ã¯ããã€ãã®ãããžã§ã¯ãã§ãŸã 䜿çšãããŠãã䟿å©ãªã©ã€ãã©ãªãæžããŸããã æäœã¯ç°¡åã§ãããã¯ã°ã©ãŠã³ãã§ã¿ã¹ã¯ãå®è¡ããŸãã ããããåæã«ããããŒã«ãŒã¯å¿ èŠãããŸããïŒ Celeryãä»ã®ãŠãŒã¶ãŒãïŒãã¹ããŒã©ãŒãåããuwsgiã¢ããªã±ãŒã·ã§ã³ãµãŒããŒã®ã¿ããå¥ã®ã¯ãŒã«ãŒãšããŠéå§ãããŸãã ããã¯éåžžã«ç°¡åãªãœãªã¥ãŒã·ã§ã³ã§ãããã¹ãŠã®ã¿ã¹ã¯ã¯æ¡ä»¶ä»ãã§ãã¡ã€ã«ã«ä¿åãããŸãã åçŽãªãããžã§ã¯ãã§ã¯ããã§ååã§ãããç§ãã¡ã®ãããžã§ã¯ãã§ã¯ååã§ã¯ãããŸããã§ããã
ã©ããããããç§ãã¡ã¯èããŸããïŒ
- ã»ããªïŒGitHubã§10Kã¹ã¿ãŒïŒ;
- RQïŒGitHubã§5Kã¹ã¿ãŒïŒ;
- HueyïŒGitHubã®2Kã¹ã¿ãŒïŒ;
- DramatiqïŒGitHubã®1Kã¹ã¿ãŒïŒ;
- TasktigerïŒGitHubã§0.5Kã¹ã¿ãŒïŒ;
- æ°æµïŒ ã«ã€ãŒãž
ææãªåè£è
2018
ããã§ã Dramatiqã«æ³šç®ããããšæããŸãã ããã¯ãã»ããªã®ãã¹ãŠã®çæãç¥ã£ãŠããŠããã¹ãŠãéåžžã«çŸããæžãçŽãããšã«ããçç·Žããã»ããªã®ã©ã€ãã©ãªã§ãã Dramatiqã®å©ç¹ïŒ
- å¿ èŠãªãã¹ãŠã®æ©èœã®ã»ããã
- çç£æ§ã®åäžã
- ããã«äœ¿ããããã¡ããŠã¹ã®æ©tryãšã¡ããªãã¯ã®ãµããŒã
- å°ãããŠæ確ã«èšè¿°ãããã³ãŒãããŒã¹ãã³ãŒãã®èªååèªã¿èŸŒã¿ã
ãã°ããåãDramatiqã«ã¯ã©ã€ã»ã³ã¹ã«é¢ããåé¡ããããŸãããæåã«AGPLãããã次ã«LGPLã«çœ®ãæããããŸããã ããããä»ã§ã¯è©Šãããšãã§ããŸãã
ãããã2016幎ã«ã¯ãã»ããªã«å ããŠãç¹å¥ãªããšã¯äœããããŸããã§ããã ç§ãã¡ã¯ãã®è±å¯ãªæ©èœãæ°ã«å ¥ã£ãŠãããããã§ãçæ³çãªã¿ã¹ã¯ã«é©ããŠããŸããã
- ããã«äœ¿çšã§ããå®æçãªã¿ã¹ã¯ããããŸããã
- ããã€ãã®ãããŒã«ãŒããµããŒãã
- Djangoããã³Sentryãšçµ±åã
ãããžã§ã¯ãã®ç¹åŸŽ
ãããªãã¹ããŒãªãŒãããç解ããããããã«ãç§ãã¡ã®èæ¯ã«ã€ããŠã話ããŸãã
Redisãã¡ãã»ãŒãžãããŒã«ãŒãšããŠäœ¿çšããŸã ã ç§ã¯ãRedisãã¡ãã»ãŒãžã倱ããã¡ãã»ãŒãžãããŒã«ãŒã«é©å¿ããŠããªããšããå€ãã®è©±ãšåãèããããšããããŸãã å®çšŒåç°å¢ã§ã¯ãããã¯ç¢ºèªãããŠããŸããããçµå±ã®ãšãããRedisã¯RabbitMQãããå¹ççã«åäœããããã«ãªããŸããïŒå°ãªããšããæããã«ãåé¡ã¯ãããŒã«ãŒãšã®çµ±åã³ãŒãã«ãããŸãïŒã ããŒãžã§ã³4ã§ã¯ãRedisãããŒã«ãŒãä¿®æ£ãããåèµ·åäžã«ã¿ã¹ã¯ã倱ãããããšããªããªããéåžžã«å®å®ããŠåäœããããã«ãªããŸããã 2016幎ãCeleryã¯RedisãæŸæ£ããŠRabbitMQãšã®çµ±åã«æ³šåããäºå®ã§ãããã幞ããªããšã«ãããã¯å®çŸããŸããã§ããã
Redisã§åé¡ãçºçããå Žåãæ·±å»ãªé«å¯çšæ§ãå¿ èŠã§ããã°ãAmazonã®ãã¯ãŒã䜿çšãããããAmazon SQSãŸãã¯Amazon MQã«åãæ¿ããŸãã
çµæãä¿åããããã«çµæããã¯ãšã³ãã䜿çšããŸãããå¿ èŠãªå Žæã«çµæãä¿åããåžæããæ¹æ³ã§ãã§ãã¯ããããšã奜ã¿ãŸãã Celeryããããè¡ãã®ã¯æãŸãããããŸããã
peforkããŒã«ã䜿çšããŸã ãã€ãŸãã 䞊è¡æ§ãé«ããããã«ããã»ã¹ã®å¥åã®ãã©ãŒã¯ãäœæããããã»ã¹ã¯ãŒã«ãŒã§ãã
äœæ¥åäœ
ã»ããªãè©Šããããšã¯ãªãããããããšããŠãã人ã ãææ°ã®ãã®ã«ããããã«ãåºæ¬çãªèŠçŽ ã«ã€ããŠè°è«ããŸãã ã»ããªã®äœæ¥åäœã¯èª²é¡ã§ãã é»åã¡ãŒã«ãéä¿¡ããç°¡åãªã¿ã¹ã¯ã®äŸã瀺ããŸãã
ã·ã³ãã«ãªé¢æ°ãšãã³ã¬ãŒã¿ãŒïŒ
@current_app.task def send_email(email: str): print(f'Sending email to email={email}')
ã¿ã¹ã¯ã®éå§ã¯ç°¡åã§ããé¢æ°ãåŒã³åºããšãã¿ã¹ã¯ã¯ã©ã³ã¿ã€ã ïŒsend_emailïŒemail = "python@example.com"ïŒïŒãŸãã¯ã¯ãŒã«ãŒã§å®è¡ãããŸããã€ãŸããããã¯ã°ã©ãŠã³ãã§ã®ã¿ã¹ã¯ã®å¹æã§ãã
send_email.delay(email="python@example.com") send_email.apply_async( kwargs={email: "python@example.com"} )
é«è² è·ã®ããšã§2幎éã»ããªãšä»äºãããŠããŸããããç§ãã¡ã¯è¯ã圢ã®èŠåãå°ãåºããŸããã ããããã®çæããããŸãããããããåé¿ããæ¹æ³ãåŠã³ãŸããããããŠãç§ã¯æ¹æ³ãå ±æããŸãã
ã³ãŒãèšèš
ã¿ã¹ã¯ã«ã¯ç°ãªãããžãã¯ãå«ãŸããå ŽåããããŸãã äžè¬ã«ãCeleryã¯ãã¿ã¹ã¯ããã¡ã€ã«ãŸãã¯ããã±ãŒãžã¿ã¹ã¯ã«ä¿æããããã©ãããã§ãã€ã³ããŒããããããã®ã«åœ¹ç«ã¡ãŸãã 1ã€ã®ã¢ãžã¥ãŒã«ã§å€æ°ã®ããžãã¹ããžãã¯ãååŸããããšããããŸãã ç§ãã¡ã®æèŠã§ã¯ãã¢ããªã±ãŒã·ã§ã³ã®ã¢ãžã¥ãŒã«æ§ã®èŠ³ç¹ããã®æ£ããã¢ãããŒãã¯ãã¿ã¹ã¯ã®ããžãã¯ãæå°éã«æããããšã§ãã ããºã«ã¯ã³ãŒãã®ãããªã¬ãŒããšããŠã®ã¿äœ¿çšããŸãã ã€ãŸããã¿ã¹ã¯èªäœã«ããžãã¯ã¯å«ãŸããŸããããããã¯ã°ã©ãŠã³ãã§ã³ãŒãã®èµ·åãããªã¬ãŒããŸãã
@celery_app.task(queue='...') def run_regular_update(provider_account_id, *args, **kwargs): """...""" flow = flows.RegularSyncProviderAccountFlow(provider_account_id) return flow.run(*args, **kwargs)
ä»ã®ã¯ã©ã¹ã䜿çšããå€éšã¯ã©ã¹ã«ãã¹ãŠã®ã³ãŒããé 眮ããŸãã ãã¹ãŠã®ã¿ã¹ã¯ã¯åºæ¬çã«2è¡ã§æ§æãããŸãã
ãã©ã¡ãŒã¿ãŒå
ã®åçŽãªãªããžã§ã¯ã
äžèšã®äŸã§ã¯ãç¹å®ã®IDãã¿ã¹ã¯ã«æž¡ãããŸãã 䜿çšãããã¹ãŠã®ã¿ã¹ã¯ã§ã å°ããªã¹ã«ã©ãŒããŒã¿ id ã®ã¿ã転éããŸãã Djangoã¢ãã«ãã·ãªã¢ã«åããŠéä¿¡ããŸããã ETLã§ãã倧ããªããŒã¿BLOBãå€éšãµãŒãã¹ããéãããŠããå ŽåããŸããããä¿åããŠãããIDã§ãã®BLOBããã¹ãŠèªã¿åã£ãŠåŠçããã¿ã¹ã¯ãå®è¡ããŸãã
ãããè¡ããªããšãRedisã§æ¶è²»ãããã¡ã¢ãªã®éåžžã«å€§ããªæ··åãèŠãããŸããã ã¡ãã»ãŒãžã¯ããå€ãã®ã¡ã¢ãªãå æãå§ãããããã¯ãŒã¯ã®è² è·ãé«ããªããåŠçãããã¿ã¹ã¯ïŒããã©ãŒãã³ã¹ïŒã®æ°ãäœäžããŸãã ãªããžã§ã¯ããå®äºããŠããéããã¿ã¹ã¯ã¯ç¡é¢ä¿ã«ãªãããªããžã§ã¯ãã¯ãã§ã«åé€ãããŠããŸãã ããŒã¿ãã·ãªã¢ã«åããå¿ èŠããããŸãã-ãã¹ãŠãPythonã®JSONã§ã·ãªã¢ã«åãããŠããããã§ã¯ãããŸããã ã¿ã¹ã¯ãåè©Šè¡ãããšãã«ããã®ããŒã¿ãã©ãåŠçãããããã°ãã決å®ããå床ååŸãããããã®ãã§ãã¯ãå®è¡ããæ©äŒãå¿ èŠã§ããã
ãã©ã¡ãŒã¿ãŒã§ããã°ããŒã¿ã転éããå Žåã¯ãããäžåºŠèããŠãã ããïŒ åé¡ã®æ å ±éãå°ãªãå°ããªã¹ã«ã©ãŒã転éããã¿ã¹ã¯ã®ãã®æ å ±ããå¿ èŠãªãã®ãã¹ãŠãååŸããããšããå§ãããŸãã
ã¹ãçåé¡
ã»ããªéçºè èªèº«ããã®ã¢ãããŒããæšå¥šããŠããŸãã ã³ãŒãã»ã¯ã·ã§ã³ãç¹°ãè¿ãããå Žåãå¯äœçšã¯çºçãããçµæã¯åãã«ãªããŸãã ããã¯ãç¹ã«å€ãã®ãµãŒãã¹ãšã®çžäºäœçšãããå ŽåããŸãã¯2ãã§ãŒãºã³ããããããå Žåãå¿ ãããç°¡åã«éæã§ãããšã¯éããŸããã
ãããããã¹ãŠãããŒã«ã«ã§å®è¡ãããšãåä¿¡ããŒã¿ãååšãé¢é£æ§ãããããšãåžžã«ç¢ºèªã§ããå®éã«äœæ¥ããŠãã©ã³ã¶ã¯ã·ã§ã³ã䜿çšã§ããŸãã 1ã€ã®ã¿ã¹ã¯ã«å¯ŸããŠããŒã¿ããŒã¹ãžã®ã¯ãšãªãå€æ°ãããå®è¡æã«åé¡ãçºçããå¯èœæ§ãããå Žåã¯ããã©ã³ã¶ã¯ã·ã§ã³ã䜿çšããŠäžèŠãªå€æŽãããŒã«ããã¯ããŸãã
äžäœäºææ§
ã¢ããªã±ãŒã·ã§ã³ããããã€ãããšãã«ãããã€ãã®èå³æ·±ãå¯äœçšããããŸããã 䜿çšãããããã€ã®ã¿ã€ãïŒé+ç·ãŸãã¯ããŒãªã³ã°æŽæ°ïŒã«é¢ä¿ãªããå€ããµãŒãã¹ã³ãŒããæ°ããã¯ãŒã«ãŒã³ãŒãã®ã¡ãã»ãŒãžãäœæããç¶æ³ãåžžã«ååšãããã®éãåæ§ã§ãããããŠããã«ãã©ãã£ãã¯ãè¡ããŸããã
ãªãªãŒã¹éã®åŸæ¹äºææ§ãç¶æããæ¹æ³ãåŠã¶ãŸã§ããã°ãèŠã€ããŠã¿ã¹ã¯ã倱ããŸãã ã äžäœäºææ§ãšã¯ããã®ã¿ã¹ã¯ã«ã©ã®ãã©ã¡ãŒã¿ãŒãå ¥åãããŠãããªãªãŒã¹éã§ã¿ã¹ã¯ãå®å šã«æ©èœããããšã§ãã ãããã£ãŠããã¹ãŠã®ã¿ã¹ã¯ã§ããŽã ã眲åïŒ** kwargsïŒãäœæããŠããŸãã 次ã®ãªãªãŒã¹ã§æ°ãããã©ã¡ãŒã¿ãŒãè¿œå ããå¿ èŠãããå Žåãæ°ãããªãªãŒã¹ã§ã¯** kwargsããååŸããŸãããå€ããªãªãŒã¹ã§ã¯ååŸããŸãã-äœãå£ããŸããã 眲åãå€æŽãããCeleryããã®ããšãç¥ããªããšããã«ãã¯ã©ãã·ã¥ããã¿ã¹ã¯ã«ãã®ãããªãã©ã¡ãŒã¿ãŒããªããšãããšã©ãŒã衚瀺ãããŸãã
ãã®ãããªåé¡ãåé¿ããããã®ããå³å¯ãªæ¹æ³ã¯ããªãªãŒã¹éã§ã¿ã¹ã¯ãã¥ãŒãããŒãžã§ã³ç®¡çããããšã§ãããå®è£ ããã®ã¯éåžžã«å°é£ã§ãããçŸæç¹ã§ã¯ããã¯ãã°ã«æ®ããŠããŸãã
ã¿ã€ã ã¢ãŠã
æ°ã足ããªãããã¿ã€ã ã¢ãŠããæ£ãããªãããã«åé¡ãçºçããå ŽåããããŸãã
ã¿ã¹ã¯ã«ã¿ã€ã ã¢ãŠããèšå®ããªãã®ã¯æªã§ãã ããã¯ãã¿ã¹ã¯ã§äœãèµ·ãã£ãŠããããããžãã¹ããžãã¯ãã©ã®ããã«æ©èœããããç解ããŠããªãããšãæå³ããŸãã
ãã®ããããã¹ãŠã®ã¿ã¹ã¯ã®ã°ããŒãã«ãªãã®ãå«ããŠããã¹ãŠã®ã¿ã¹ã¯ãã¿ã€ã ã¢ãŠãã§ãã³ã°ã¢ããããã¿ã€ã ã¢ãŠããç¹å®ã®ã¿ã¹ã¯ããšã«èšå®ãããŸãã
æ·»ä»ããå¿ èŠããããŸã ïŒsoft_limit_timeoutããã³expires ã
Expiresã¯ãã¿ã¹ã¯ãã©ãã ã䞊ãã§ããããšãã§ãããã§ãã åé¡ãçºçããå Žåã«ãã¿ã¹ã¯ããã¥ãŒã«èç©ãããªãããã«ããå¿ èŠããããŸãã ããšãã°ããŠãŒã¶ãŒã«äœããå ±åãããããäœããèµ·ãããææ¥ã ãã¿ã¹ã¯ãå®äºããããšãã§ããå Žå-ããã¯æå³ããªããææ¥ã¯ã¡ãã»ãŒãžãé¢é£ããªããªããŸãã ãããã£ãŠãéç¥ã®æå¹æéã¯ããªãçããªã£ãŠããŸãã
etaïŒcountdownïŒ+ visibility _timeoutã®äœ¿çšã«æ³šæããŠãã ããã FAQã§ã¯ãRedisã®ãã®ãããªåé¡ãã€ãŸãRedisãããŒã«ãŒã®ããããå¯èŠæ§ã¿ã€ã ã¢ãŠãã«ã€ããŠèª¬æããŠããŸãã ããã©ã«ãã§ã¯ããã®å€ã¯1æéã§ãã1æéåŸã«ã¯ãŒã«ãŒãã¿ã¹ã¯ã®å®è¡ãéå§ããŠããªãããšãããããšãã¯ãŒã«ãŒã¯ããããã¥ãŒã«å床远å ããŸãã ãããã£ãŠãã«ãŠã³ãããŠã³ã2æéã®å Žåã1æéåŸã«ãããŒã«ãŒã¯ãã®ã¿ã¹ã¯ããŸã å®äºããŠããªãããšãæ€åºããåãã¿ã¹ã¯ããã1ã€äœæããŸãã ãããŠ2æéã§ã2ã€ã®åäžã®ã¿ã¹ã¯ãå®äºããŸãã
äºæ³ãããæéãŸãã¯ã«ãŠã³ãããŠã³ã1æéãè¶ ããå ŽåãRedisã䜿çšãããšãåœç¶ããããŒã«ãŒæ¥ç¶èšå®ã§visibility_timeoutå€ãå€æŽããªãéããã¿ã¹ã¯ãéè€ããŸãã
åè©Šè¡ããªã·ãŒ
ç¹°ãè¿ãå®è¡ã§ããã¿ã¹ã¯ããŸãã¯å€±æããå¯èœæ§ã®ããã¿ã¹ã¯ã«ã¯ãåè©Šè¡ããªã·ãŒã䜿çšããŸãã ãã ããå€éšãµãŒãã¹ãå§åããªãããã«æ éã«äœ¿çšããŸãã ææ°é¢æ°çãªããã¯ãªããæå®ããã«ã¿ã¹ã¯ããã°ããç¹°ãè¿ããšãå€éšãµãŒãã¹ããŸãã¯ããããå éšãµãŒãã¹ãããã«èããããªãå¯èœæ§ããããŸãã
ãã©ã¡ãŒã¿retry_backoff ã retry_jitterããã³max_retriesã¯ãç¹ã«max_retriesãæ瀺çã«æå®ãããšäŸ¿å©ã§ãã retry_jitter-å°ãã®æ··ä¹±ããããããã¿ã¹ã¯ãåæã«ç¹°ãè¿ãããªãããã«ãããã©ã¡ãŒã¿ãŒã
ã¡ã¢ãªãªãŒã¯
æ®å¿µãªãããã¡ã¢ãªãªãŒã¯ã¯éåžžã«ç°¡åã§ãããããããèŠã€ããŠä¿®æ£ããããšã¯å°é£ã§ãã
äžè¬ã«ãPythonã§ã¡ã¢ãªãæäœããããšã¯éåžžã«è°è«ã®çã§ãã ãªãŒã¯ãçºçããçç±ãç解ããããã«å€ãã®æéãšç¥çµãè²»ãããŸãããããŠãã³ãŒãã«ããæŒããŠããªãããšãããããŸãã ãããã£ãŠããããžã§ã¯ããéå§ãããšãã¯åžžã«ãworker_max_memory_per_child ãšããã¯ãŒã«ãŒã«ã¡ã¢ãªå¶éãèšå®ããŸãã
ããã«ãããOOM Killerããã€ãã¯ç»å Žããããã¹ãŠã®ã¯ãŒã«ãŒã殺ãããããšã¯ãªãããã¹ãŠã®ã¿ã¹ã¯ã倱ãããããšã¯ãããŸããã ã»ããªã¯ãå¿ èŠã«å¿ããŠã¯ãŒã«ãŒãåèµ·åããŸãã
ã¿ã¹ã¯ã®åªå
床
ä»ã®èª°ãããæ©ããä»ã®èª°ãããæ©ãå®äºããªããã°ãªããªãã¿ã¹ã¯ãåžžã«ãããŸã-ä»ããå®äºããªããã°ãªããŸããïŒ ããã»ã©éèŠã§ã¯ãªãã¿ã¹ã¯ããããŸã-æ¥äžã«å®äºãããŠãã ããã ãã®ãããã¿ã¹ã¯ã«ã¯åªå 床ãã©ã¡ãŒã¿ãŒããããŸãã Redisã§ã¯ãéåžžã«èå³æ·±ãåäœãããŸã-åªå 床ãè¿œå ãããååã§æ°ãããã¥ãŒãäœæãããŸãã
ç§ãã¡ã¯ç°ãªãã¢ãããŒãã䜿çšããŸã- åªå é äœã®ããã«å¥ã ã®ã¯ãŒã«ãŒ ãã€ãŸã æãªããã®æ¹æ³ã§ãç°ãªããéèŠæ§ããæã€ã»ããªã®åŽåè ãäœæããŸãã
celery multi start high_priority low_priority -c:high_priority 2 -c:low_priority 6 -Q:high_priority urgent_notifications -Q:low_priority emails,urgent_notifications
Celery multi startã¯ã1å°ã®ãã·ã³ã§åãã³ãã³ãã©ã€ã³ããCeleryæ§æå šäœãå®è¡ããã®ã«åœ¹ç«ã€ãã«ããŒã§ãã ãã®äŸã§ã¯ãããŒãïŒãŸãã¯ã¯ãŒã«ãŒïŒãäœæããŸãïŒhigh_priorityãšlow_priorityã2ãš6ã¯åæå®è¡ã§ãã
2ã€ã®high_priorityã¯ãŒã«ãŒã¯ãåžžã«urgent_notificationsãã¥ãŒãåŠçããŸãã 誰ããããã®ã¯ãŒã«ãŒã䜿çšããŸããã圌ãã¯urgent_notificationsãã¥ãŒããéèŠãªã¿ã¹ã¯ã®ã¿ãèªã¿åããŸãã
éèŠã§ãªãã¿ã¹ã¯ã«ã¯ãlow_priorityãã¥ãŒããããŸãã ä»ã®ãã¹ãŠã®ãã¥ãŒããã¡ãã»ãŒãžãåä¿¡ãã6人ã®ã¯ãŒã«ãŒãããŸãã ãŸããlow_priorityã¯ãŒã«ãŒãurgent_notificationsã«ãµãã¹ã¯ã©ã€ãããhigh_priorityã¯ãŒã«ãŒã察åŠã§ããªãå Žåã«æ¯æŽã§ããããã«ããŸãã
ãã®å€å žçãªã¹ããŒã ã䜿çšããŠãã¿ã¹ã¯ã«åªå é äœãä»ããŸãã
æœåºãå€æãããŒã
ã»ãšãã©ã®å ŽåãETLã¯äžé£ã®ã¿ã¹ã¯ã®ããã«èŠããåã¿ã¹ã¯ã¯åã®ã¿ã¹ã¯ããå ¥åãåãåããŸãã
@task def download_account_data(account_id) ⊠return account_id @task def process_account_data(account_id, processing_type) ⊠return account_data @task def store_account_data(account_data) âŠ
ãã®äŸã«ã¯3ã€ã®ã¿ã¹ã¯ããããŸãã Celeryã«ã¯ãåæ£åŠçãžã®ã¢ãããŒããšã ãã§ãŒã³é¢æ°ãå«ãããã€ãã®æçšãªãŠãŒãã£ãªãã£ãããã3ã€ã®ã¿ã¹ã¯ãã1ã€ã®ãã€ãã©ã€ã³ãäœæããŸãã
chain( download_account_data.s(account_id), process_account_data.s(processing_type='fast'), store_account_data.s() ).delay()
ã»ããªã¯ãã€ãã©ã€ã³ãå解ããæåã®ã¿ã¹ã¯ãæåã«å®è¡ãã次ã«åä¿¡ããããŒã¿ã2çªç®ã«è»¢éãã2çªç®ã®ã¿ã¹ã¯ãè¿ãããŒã¿ã¯3çªç®ã«æž¡ãããŸãã ããããã·ã³ãã«ãªETLãã€ãã©ã€ã³ã®å®è£ æ¹æ³ã§ãã
ããè€éãªãã§ãŒã³ã®å Žåãè¿œå ã®ããžãã¯ãæ¥ç¶ããå¿ èŠããããŸãã ãã ãã1ã€ã®ã¿ã¹ã¯ã§ãã®ãã§ãŒã³ã«åé¡ãçºçãããšããã§ãŒã³å šäœããã©ãã©ã«ãªãããšã«æ³šæããŠãã ãã ã ãã®åäœãæãŸãããªãå Žåã¯ãäŸå€ãåŠçããŠå®è¡ãç¶ç¶ããããäŸå€ã«ãã£ãŠãã§ãŒã³å šäœãåæ¢ããŸãã
å®éãå éšã®ãã®ãã§ãŒã³ã¯ããã¹ãŠã®ãã©ã¡ãŒã¿ãŒãæã€ãã¹ãŠã®ã¿ã¹ã¯ãå«ã1ã€ã®å€§ããªã¿ã¹ã¯ã®ããã«èŠããŸãã ãããã£ãŠããã§ãŒã³å ã®ã¿ã¹ã¯ã®æ°ãä¹±çšãããšãéåžžã«é«ãã¡ã¢ãªæ¶è²»ãšããã»ã¹å šäœã®ã¹ããŒããŠã³ãçºçããŸãã æ°åã®ã¿ã¹ã¯ã®ãã§ãŒã³ãäœæããã®ã¯æªãèãã§ãã
ãããã¿ã¹ã¯åŠç
ããã§æãèå³æ·±ãã®ã¯ã200äžäººã®ãŠãŒã¶ãŒã«ã¡ãŒã«ãéä¿¡ããå¿ èŠãããå Žåã«äœãèµ·ãããã§ãã
ãã¹ãŠã®ãŠãŒã¶ãŒã«å¯ŸããŠãã®ãããªãã€ãã¹é¢æ°ãäœæããŸãã
@task def send_report_emails_to_users(): for user_id in User.get_active_ids(): send_report_email.delay(user_id=user_id)
ãã ããã»ãšãã©ã®å Žåãé¢æ°ã¯ãŠãŒã¶ãŒIDãåãåãã ãã§ãªããäžè¬çã«ãŠãŒã¶ãŒããŒãã«å šäœãæ¶å»ããŸãã åãŠãŒã¶ãŒã«ã¯ç¬èªã®ã¿ã¹ã¯ããããŸãã
ãã®ã¿ã¹ã¯ã«ã¯ããã€ãã®åé¡ããããŸãã
- ã¿ã¹ã¯ã¯é çªã«èµ·åãããŸããã€ãŸããæåŸã®ã¿ã¹ã¯ïŒ200äžçªç®ã®ãŠãŒã¶ãŒïŒã¯20åã§éå§ããããã®ã¿ã€ã ã¢ãŠããŸã§ã«æ¢ã«åäœããå¯èœæ§ããããŸãã
- ãã¹ãŠã®ãŠãŒã¶ãŒIDã¯æåã«ã¢ããªã±ãŒã·ã§ã³ã¡ã¢ãªã«ããŒãããã次ã«ãã¥ãŒã«ããŒããããŸã-delayïŒïŒã¯200äžã¿ã¹ã¯ãå®è¡ããŸãã
ã¿ã¹ã¯ãã©ãããšåŒã³ãŸãããã£ãŒãã¯æ¬¡ã®ããã«ãªããŸãã
åŽåè ããã£ãããšåŠçãéå§ããã¿ã¹ã¯ã®æµå ¥ããããŸãã ã¿ã¹ã¯ããã¹ã¿ãŒã¬ããªã«ã䜿çšãããããžã§ã¯ãå šäœãã¯ã©ãã¯ãå§ããäœãæ©èœããªãå Žåã次ã®ããšãèµ·ãããŸãã 以äžã¯ãæ°æéã«ããã£ãŠDB CPU䜿çšçã100ïŒ ã ã£ããã©ã¯ãã£ã¹ã®äŸã§ããæ£çŽãªãšããããªããšãæãã£ãŠããŸããŸããã
åé¡ã¯ããŠãŒã¶ãŒæ°ã®å¢å ã«äŒŽã£ãŠã·ã¹ãã ãå€§å¹ ã«å£åããããšã§ãã ã¹ã±ãžã¥ãŒãªã³ã°ãæ±ãã¿ã¹ã¯ïŒ
- ããå€ãã®ã¡ã¢ãªãå¿ èŠã§ãã
- ããé·ãå®è¡ãããã¿ã€ã ã¢ãŠãã«ãã£ãŠã殺ããããããšãã§ããŸãã
ã¿ã¹ã¯ã®ãã©ããã£ã³ã°ãçºçããŸããã¿ã¹ã¯ã¯ãã¥ãŒã«èç©ãããå éšãµãŒãã¹ã ãã§ãªãå€éšãµãŒãã¹ã«ã倧ããªè² è·ãããããŸãã
åŽåè ã®ç«¶äºåãäœäžãããããšããŸããã ãããã¯ããæå³ã§åœ¹ç«ã¡ãŸã-ãµãŒãã¹ã®è² è·ã軜æžãããŸãã ãŸãã¯ãå éšãµãŒãã¹ãã¹ã±ãŒãªã³ã°ã§ããŸã ã ããããããã¯ãžã§ãã¬ãŒã¿ãŒã®åé¡ã®è§£æ±ºã«ã¯ãªããŸããã ãããŠãå€éšãµãŒãã¹ã®ããã©ãŒãã³ã¹ãžã®äŸåã«åœ±é¿ãäžããããšã¯ãããŸããã
ã¿ã¹ã¯çæ
ç§ãã¡ã¯å¥ã®éãåãããšã«ããŸããã ãããŠãã®å Žåãä»ãã200äžã¿ã¹ã¯ãã¹ãŠãå®è¡ããå¿ èŠã¯ãããŸããã ãããã®æåãããã»ã©éèŠã§ãªãå Žåããã¹ãŠã®ãŠãŒã¶ãŒã«éç¥ãéä¿¡ããã®ã«éåžž4æéãããããšããããŸãã
ãŸãã Celery.chunksã䜿çšããŠã¿ãŸãã ã
send_report_email.chunks( ({'user_id': user.id} for user in User.objects.active()), n=100 ).apply_async()
ã€ãã¬ãŒã¿ã«ããããããããã¹ãŠã®user_idãã¡ã¢ãªã«ããŒãããããããããã«ããç¶æ³ã¯å€ãããŸããã§ããã ãããŠããã¹ãŠã®åŽåè ã¯äžé£ã®ã¿ã¹ã¯ãååŸããåŽåè ã¯å°ãäŒã¿ãŸãããæçµçã«ã¯ãã®æ±ºå®ã«æºè¶³ããŸããã§ããã
ã¯ãŒã«ãŒã«rate_limitãèšå®ããŠã1ç§ãããç¹å®ã®æ°ã®ã¿ã¹ã¯ã®ã¿ãåŠçããããã«ããŸãããå®éã«ã¿ã¹ã¯ã«å¯ŸããŠæå®ãããrate_limitã¯ã¯ãŒã«ãŒã®rate_limitã§ããããšãããããŸããã ã€ãŸããã¿ã¹ã¯ã«rate_limitãæå®ããå Žåãããã¯ã¿ã¹ã¯ãæ¯ç§70åå®è¡ãããããšãæå³ããŸããã ããã¯ãã¯ãŒã«ãŒã1ç§éã«70åå®è¡ããããšãæå³ããŸãããŸããã¯ãŒã«ãŒã«äœããããã«ãã£ãŠããã®å¶éã¯åçã«å€æŽãããå¯èœæ§ããããŸãã å®éã®å¶érate_limit * lenïŒã¯ãŒã«ãŒïŒã
ã¯ãŒã«ãŒãéå§ãŸãã¯åæ¢ãããšãåèšrate_limitãå€æŽãããŸãã ããã«ãã¿ã¹ã¯ãé ãå Žåãã¯ãŒã«ãŒãåããŠãããã¥ãŒå ã®ãã¹ãŠã®ããªãã§ããããããã®é ãã¿ã¹ã¯ã§è©°ãŸããŸãã ã¯ãŒã«ãŒã¯ããããããã®ã¿ã¹ã¯ã¯rate_limitã«ãããŸããããå®è¡ã§ããŸããã ãããŠããã¥ãŒå ã®æ¬¡ã®ã¿ã¹ã¯ã¯ãã¹ãŠãŸã£ããåãã§ã-ãã³ã°ãããŠãã ããïŒã-ãããŠåœŒã¯åŸ ã£ãŠããŸãã
ãã£ã³ãã£ãã£ã±ãŒã¿ãŒ
æçµçã«ãç§ãã¡ã¯ç¬èªã®ã©ã€ãã©ãªãäœæããããšã決å®ããChunkificatorãšåŒã°ããå°ããªã©ã€ãã©ãªãäœæããŸããã
@task @chunkify_task(sleep_timeout=...l initial_chunk=...) def send_report_emails_to_users(chunk: Chunk): for user_id in User.get_active_ids(chunk=chunk): send_report_email.delay(user_id=user_id)
sleep_timeoutãšinitial_chunkãåããæ°ãããã£ã³ã¯ã§èªåèªèº«ãåŒã³åºããŸãã ãã£ã³ã¯ã¯ãæŽæ°ãªã¹ãããŸãã¯æ¥ä»ãŸãã¯æ¥æãªã¹ãã®æœè±¡åã§ãã ãã®ãã£ã³ã¯ãæã€ãŠãŒã¶ãŒã®ã¿ãåãåãé¢æ°ã«ãã£ã³ã¯ãæž¡ãããã®ãã£ã³ã¯ã«å¯ŸããŠã®ã¿ã¿ã¹ã¯ãå®è¡ããŸãã
ãããã£ãŠãã¿ã¹ã¯ãžã§ãã¬ãŒã¿ãŒã¯å¿ èŠãªæ°ã®ã¿ã¹ã¯ã®ã¿ãå®è¡ãã倧éã®ã¡ã¢ãªãæ¶è²»ããŸããã åçã¯ãããªæãã«ãªã£ãŠããŸãã
ãã€ã©ã€ãã¯ãã¹ããŒã¹ãã£ã³ã¯ã䜿çšããããšã§ããã€ãŸããããŒã¿ããŒã¹å ã®ã€ã³ã¹ã¿ã³ã¹ããã£ã³ã¯IDãšããŠäœ¿çšããŸãïŒäžéšã¯ã¹ããããããå¯èœæ§ããããããã¿ã¹ã¯ãå°ãªããªãå¯èœæ§ããããŸãïŒã ãã®çµæãè² è·ã¯ããåäžã«ãªããããã»ã¹ã¯é·ããªããŸãããã誰ããçããŠããŠãããŒã¹ã¯ç·åŒµããŠããŸããã
ãã®ã©ã€ãã©ãªã¯ Python 3.6+çšã«å®è£ ãããŠãããGitHubã§å ¥æã§ããŸãã ä¿®æ£ããäºå®ã®ãã¥ã¢ã³ã¹ããããŸãããä»ã®ãšããdatetime-chunkã«ã¯pickleã·ãªã¢ã©ã€ã¶ãŒãå¿ èŠã§ã-å€ãã¯ãããè¡ãããšãã§ããŸããã
ããã€ãã®ä¿®èŸçãªè³ªå-ãããã®æ å ±ã¯ã©ãããæ¥ãã®ã§ããïŒ åé¡ãããããšãã©ã®ããã«ããŠçºèŠããã®ã§ããïŒ åé¡ããŸããªãéèŠã«ãªãããã§ã«è§£æ±ºãå§ããå¿ èŠãããããšãã©ã®ããã«ç¥ã£ãŠããŸããïŒ
çãã¯ããã¡ããç£èŠã§ãã
ã¢ãã¿ãªã³ã°
ç§ã¯ã¢ãã¿ãªã³ã°ãæ¬åœã«å¥œãã§ããç§ã¯ãã¹ãŠãã¢ãã¿ãŒããèæã«æãåœãŠãã®ã奜ãã§ãã ãã«ã¹ã«æã眮ããªãå Žåãã¬ãŒããåžžã«èžãããšã«ãªããŸãã
æšæºçãªç£èŠã®è³ªåïŒ
- çŸåšã®ã¯ãŒã«ãŒ/åæå®è¡æ§æ§æã¯è² è·ãåŠçããŸããïŒ
- ã¿ã¹ã¯å®è¡æéã®äœäžãšã¯äœã§ããïŒ
- ã¿ã¹ã¯ã¯ã©ããããã®æé䞊ãã§ãã³ã°ããŸããïŒ çªç¶ãè¡ã¯ãã§ã«æ··éããŠããŸããïŒ
ããã€ãã®ãªãã·ã§ã³ãè©ŠããŸããã Celeryã«ã¯CLIã€ã³ã¿ãŒãã§ãŒã¹ããããéåžžã«è±å¯ã§ããã以äžãæäŸããŸãã
- æ€æ»-ã·ã¹ãã ã«é¢ããæ å ±ã
- å¶åŸ¡-ã·ã¹ãã èšå®ã®ç®¡çã
- ããŒãž-ãã¥ãŒãã¯ãªã¢ïŒäžå¯æåïŒ;
- ã€ãã³ã-å®è¡äžã®ã¿ã¹ã¯ã«é¢ããæ å ±ã衚瀺ããããã®ã³ã³ãœãŒã«UIã
ããããå®éã«äœããç£èŠããã®ã¯é£ããã§ãã ããŒã«ã«ã®ããªã«ããå®è¡æã«rate_limitãå€æŽãããå Žåã«é©ããŠããŸãã
æ³šïŒ CLIã€ã³ã¿ãŒãã§ãŒã¹ã䜿çšããã«ã¯ãå®åãããŒã«ãŒã«ã¢ã¯ã»ã¹ããå¿ èŠããããŸãã
Celery Flowerã䜿çšãããšãCLIãšåãããšãã§ããŸãããWebã€ã³ã¿ãŒãã§ãŒã¹ã䜿çšããå¿ èŠããããŸãããããã ãã§ã¯ãããŸããã ãã ããããã€ãã®åçŽãªã°ã©ããäœæãããã®å Žã§èšå®ãå€æŽã§ããŸãã
äžè¬ã«ãã»ããªãã©ã¯ãŒã¯ãå°ããªã»ããã¢ããã§ãã¹ãŠãã©ã®ããã«æ©èœãããã確èªããã®ã«é©ããŠããŸãã ããã«ãHTTP APIããµããŒãããŠããŸããã€ãŸããèªååãèšè¿°ããŠããå Žåã«äŸ¿å©ã§ãã
ããããç§ãã¡ã¯ããã¡ããŠã¹ã«èœã¡çããŸããã 圌ãã¯çŸåšã®ãšã¯ã¹ããŒã¿ãŒã奪ããŸããïŒããã®ã¡ã¢ãªãªãŒã¯ãä¿®æ£ããŸããã ã¿ã€ãäŸå€å¥ã«ã¡ããªãã¯ãè¿œå ã ãã¥ãŒå ã®ã¡ãã»ãŒãžæ°ã®ã¡ããªãã¯ãè¿œå ã Grafanaã®ã¢ã©ãŒããšçµ±åããåã¶ã GitHubã«ãæçš¿ãããŠããŸã ã ãã¡ãã§ç¢ºèªã§ããŸã ã
Grafanaã®äŸ
äžèšã¯ãã¹ãŠã®äŸå€ã®çµ±èšã§ãïŒã©ã®ã¿ã¹ã¯ã®ã©ã®äŸå€ã 以äžã¯ãã¿ã¹ã¯ãå®äºããæéã§ãã
Celeryã«ã¯äœãæ¬ ããŠããŸããïŒ
ããã¯ç·è±ããªãã¬ãŒã ã¯ãŒã¯ã§ãããå€ãã®ãã®ããããŸãããæ¬ èœããŠããŸãïŒ æ¬¡ã®ãããªååãªå°ããªæ©èœããããŸããã
- éçºäžã«ã³ãŒããèªåçã«ãªããŒãããŸã -ãã®CeleryããµããŒãããŠããŸãã-åèµ·åããŸãã
- Prometheusã®ã¡ããªãã¯ã¯ãã®ãŸãŸäœ¿çšã§ããŸãããDramatiqã¯å¯èœã§ãã
- ã¿ã¹ã¯ããã¯ã® ãµããŒã -äžåºŠã«1ã€ã®ã¿ã¹ã¯ã®ã¿ãå®è¡ãããŸãã ããªãã¯èªåã§ãããè¡ãããšãã§ããŸãããDramatiqãšTasktigerã«ã¯ãåãçš®é¡ã®ä»ã®ãã¹ãŠã®ã¿ã¹ã¯ããããã¯ãããããšãä¿èšŒãã䟿å©ãªãã³ã¬ãŒã¿ããããŸãã
- 1ã€ã®ã¿ã¹ã¯ã®Rate_limit-ã¯ãŒã«ãŒã§ã¯ãããŸããã
çµè«
Celeryã¯å€ãã®å®çšŒåç°å¢ã§äœ¿çšããããã¬ãŒã ã¯ãŒã¯ã§ãããšããäºå®ã«ããããããã3ã€ã®ã©ã€ãã©ãªïŒCeleryãKombuãããã³BilliardïŒã§æ§æãããŠããŸãã ããã3ã€ã®ã©ã€ãã©ãªã¯ãã¹ãŠå ±åéçºè ã«ãã£ãŠéçºãããŠããã1ã€ã®äŸåé¢ä¿ã解æŸããŠã¢ã»ã³ããªãç Žå£ããå¯èœæ§ããããŸãã
ãããã£ãŠãäœããã®æ¹æ³ã§æ¢ã«æŽçããã¢ã»ã³ããªã決å®è«çã«ããããšãé¡ã£ãŠããŸãã
å®éãçµè«ã¯ããã»ã©æ²ãããã®ã§ã¯ãããŸããã ã»ããªã¯ãåœç€Ÿã®è² è·äžã§ãã£ã³ããã¯ãããžã§ã¯ãã®ã¿ã¹ã¯ã«å¯Ÿå¿ããŠããŸãã ç§ãã¡ã¯ããªããšå ±æããçµéšãåŸãŸãããããªãã¯ç§ãã¡ã®è§£æ±ºçãé©çšããããããããæ¹è¯ããããããªãã®ãã¹ãŠã®å°é£ãå æãããããããšãã§ããŸãã
ç£èŠã¯ãããžã§ã¯ãã®éèŠãªéšåã§ããã¹ãã§ããããšãå¿ããªãã§ãã ãã ã ç£èŠã«ãã£ãŠã®ã¿ãã©ãã«åé¡ãããã®ãââãäœãä¿®æ£ãè¿œå ãä¿®æ£ããå¿ èŠãããã®ãââãèŠã€ããããšãã§ããŸãã
ã³ã³ã¿ã¯ãã¹ããŒã«ãŒOleg Churkin ïŒ Bahusss ã facebook ã github ã
次ã®å€§ããªã¢ã¹ã¯ã¯Python Conf ++ã¯ã4æ5æ¥ã«ã¢ã¹ã¯ã¯ã§éå¬ãããŸãã ä»å¹Žã¯ãå®éšã¢ãŒãã§ãã¹ãŠã®ã¡ãªããã1æ¥ã§æºããããšããŸãã ããã«å£ããªãã¬ããŒãããããã¹ããªãŒã å šäœããæåãªã©ã€ãã©ãªãšè£œåã®å€åœã®éçºè ã«å²ãåœãŠãããŸãã ããã«ãéææ¥ã¯ã¢ãã¿ãŒããŒãã£ã«ãšã£ãŠçæ³çãªæ¥ã§ããããåç¥ã®ããã«ãããã¯ã³ãã¥ãã±ãŒã·ã§ã³äŒè°ã®äžå¯æ¬ ãªéšåã§ãã
å°éã®Pythonã«ã³ãã¡ã¬ã³ã¹ã«åå ããŠãã ããã ããã§ã¬ããŒããéä¿¡ãããã±ãããäºçŽããŠãã ããã ãããŸã§ã®éãæºåãé²è¡äžã§ããã¢ã¹ã¯ã¯Python Conf ++ 2018ã«é¢ããèšäºãããã«è¡šç€ºãããŸãã