ãã€ã¯ããµãŒãã¹ãéžã°ããçç±
æè¿ããã€ã¯ããµãŒãã¹ã¯éåžžã«æµè¡ã®ãããã¯ã«ãªã£ãŠãããå€ãã®äººã¯ããããäžèŠãªå Žåã§ããã€ã¯ããµãŒãã¹ãæãã§ããŸãã ããã¯ããªãæ»ãããããã¹ã§ãããå ã«ãããã®ãç解ããå¿ èŠããããŸãã ç§ãã¡ã¯ããã¬ã³ãã®ããã§ã¯ãªããå¿ ç¶çã«ãç§ãã¡ãçŽé¢ããªããã°ãªããªããã¹ãŠã®å°é£ãèªèããŠããã€ã¯ããµãŒãã¹ã«æ¥ãŸããã
åœåãCarPriceã¯ãå€éšå§èšãããéçºè ãé¢äžããéçºé床ã«éç¹ã眮ããŠãBitrixäžã®ã¢ããªã·ãã¯ã¢ããªã±ãŒã·ã§ã³ãšããŠæ§ç¯ãããŸããã äžå®ã®æéãããã¯åžå Žã§ã®ãããžã§ã¯ãã®æåããç«ã¡äžãã«ãããŠéèŠãªåœ¹å²ã®1ã€ãæãããŸããã
æéãçµã€ã«ã€ããŠãã¢ããªã¹ã®å®å®ããåäœãç¶æããããšãäžå¯èœã«ãªããŸãã-åãªãªãŒã¹ã¯ããã¹ã¿ãŒãéçºè ãããã³ç®¡çè åãã®ãã¹ãã«å€ãããŸããã ç°ãªãããã»ã¹ãçžäºã®æ£åžžãªåäœã劚ããŸããã ããšãã°ãã¯ãŒã¯ãããŒã®å¥³ã®åã¯ãå®äºãããªãŒã¯ã·ã§ã³ã®ããã¥ã¡ã³ãã®çæãéå§ã§ããŸããããã®æç¹ã§ãããã¯ãšã³ãã®ãã¬ãŒããåå ã§ãã£ãŒã©ãŒã¯é垞亀æžã§ããŸããã§ããã
ç§ãã¡ã¯å€ããå§ããŸããã ããžãã¹ããžãã¯ã®å€§éšåã¯ãåå¥ã®ãµãŒãã¹ã§å®è¡ãããŸããïŒç©æµãèªåè»ã®æ³çãªæ³çæž æµåãµãŒãã¹ãç»ååŠçãµãŒãã¹ãæ€æ»ãšçºè¡ã®ããã®èšé²ãã£ãŒã©ãŒã®ãµãŒãã¹ãè«æ±ãå ¥æã®åãå ¥ããµãŒãã¹ãèªèšŒãµãŒãã¹ãæšå¥šã·ã¹ãã ãã¢ãã€ã«ã¢ããªã±ãŒã·ã§ã³ããã³ãªã¢ã¯ã·ã§ã³ã¢ããªã±ãŒã·ã§ã³ã®APIã
äœãæžããŠããã®
çŸæç¹ã§ã¯ããããã¯ãŒã¯ãä»ããŠéä¿¡ããããŸããŸãªãã¯ãããžãŒã«é¢ããæ°åã®ãµãŒãã¹ããããŸãã
åºæ¬çã«ããããã¯ç¹å®ã®ããžãã¹äžã®åé¡ã解決ããå°ããªLaravelïŒphpïŒã¢ããªã±ãŒã·ã§ã³ã§ãã ãã®ãããªãµãŒãã¹ã¯HTTP APIãæäŸãã管çWeb UIïŒVue.jsïŒãåããŠããå ŽåããããŸã
ComposerãæäŸããã©ã€ãã©ãªã«å ±éã³ã³ããŒãã³ããé 眮ããããšããŸãã ããã«ããµãŒãã¹ã¯äžè¬çãªphp-fpmããã«ãŒã€ã¡ãŒãžãç¶æ¿ããŸãã ããã«ãããæŽæ°æã®é çã解æ¶ãããŸãã ããšãã°ãã»ãŒãã¹ãŠã®å Žæã«php7.1ããããŸãã
Golangã§é床éèŠã®ãµãŒãã¹ãäœæããŸãã
ããšãã°ãjwtèªèšŒãµãŒãã¹ã¯ããŒã¯ã³ãæžãåºããŠæ€èšŒãã眪ã®ç®¡çè ããªãŒã¯ã·ã§ã³ãã©ãããã©ãŒã ããåæããæªåŸ³ãã£ãŒã©ãŒããã°ã¢ãŠãããæ¹æ³ãç¥ã£ãŠããŸãã
è³ããµãŒãã¹ã¯ãã£ãŒã©ãŒã®è³ããåŠçããããããããŒã¿ããŒã¹ã«ä¿åããã€ãã³ããrabbitmqãšRTéç¥ãµãŒãã¹ã«å»¶æããŠéä¿¡ããŸãã
Golangã®ãµãŒãã¹ã§ã¯ãgo-kitãšgin / chiã䜿çšããŸãã
go-kitã¯ããã®æœè±¡åãããŸããŸãªãã©ã³ã¹ããŒããšã¡ããªãã¯çšã®ã©ãããŒã䜿çšããæ©èœã«é äºãããŸããããæ©èœæ§ãšåé·æ§ãžã®æã«å°ãç²ããã®ã§ãè±å¯ãªããžãã¹ããžãã¯ãåããéŠéœãã«ã§äœ¿çšããŸãã
ãžã³ãšããŒã§ã¯ãç°¡åãªhttpãµãŒãã¹ãæ§ç¯ãããšäŸ¿å©ã§ãã ããã¯ãæ¬çªç°å¢ã§å°ããªãµãŒãã¹ãéå§ããããã®æå°éã®åŽåã§è¿ éã«è¡ãã®ã«æé©ã§ãã è€éãªãšã³ãã£ãã£ãããå Žåã¯ããµãŒãã¹ãgo-kitã«è»¢éããããšããŸãã
ç£èŠã®é²å
ã¢ããªã¹ã®æç¹ã§ã¯ãnewrelicã§ååã§ããã ãã€ã¯ããµãŒãã¹ã®æ®µéã«ãžã£ã³ãããããããµãŒããŒã®æ°ãå¢ããçµæžçãªçç±ã§ãããæŸæ£ããææªã®ç¶æ ã«æ¥ããŸããïŒZabbix-éãELKãGrafanaãPrometheus-APMã
ãŸããELKã®ãã¹ãŠã®ãµãŒãã¹ããnginxãã°ãè¿œå ããGrafanaã§ã°ã©ããäœæãã99ããŒã»ã³ã¿ã€ã«ãå°ç¡ãã«ãããªã¯ãšã¹ãã®ããã«Kibanaã«è¡ããŸããã
ãããŠãããã§æ¢æ±ãå§ãŸããŸãã-ãªã¯ãšã¹ãã§äœãèµ·ãã£ãŠããããç解ããããã«ã
ã¢ããªã·ãã¯ã¢ããªã±ãŒã·ã§ã³ã§ã¯ããã¹ãŠãã·ã³ãã«ã§ãããPHPã®å Žåãxhprofã䜿çšãããŠãããããããã§äœãèµ·ãã£ãŠããã®ããç解ã§ããŸããã ãªã¯ãšã¹ããè€æ°ã®ãµãŒãã¹ãééããããã«ã¯ç°ãªããã¯ãããžãŒã䜿çšãããã€ã¯ããµãŒãã¹ã§ã¯ããã®ããªãã¯ã¯æ©èœããŸããã ã©ããã§ãããã¯ãŒã¯ãã©ããã§åæèŠæ±ãŸãã¯äžè¯ãã£ãã·ã¥ã
APIã®é ããªã¯ãšã¹ããèŠã€ãããšããŸãã ã³ãŒãã«ãããšãèŠæ±ã3ã€ã®ãµãŒãã¹ã«å€æãããçµæãåéããŠè¿ãããšã確ç«ãããŸããã ããã§ãéæ¥ãµã€ã³ïŒã¿ã€ã ã¹ã¿ã³ããèŠæ±ãã©ã¡ãŒã¿ãŒïŒã«åºã¥ããŠåŸå±èŠæ±ãèŠã€ããã©ã®ãµãŒãã¹ãèŠæ±ã®é 延ã®åå ã§ããããç解ããå¿ èŠããããŸãã ãã®ãµãŒãã¹ãèŠã€ãã£ãå Žåã§ããã¡ããªãã¯ãŸãã¯ãµãŒãã¹ãã°ã«ç§»åããŠãã®çç±ã調ã¹ãå¿ èŠããããŸããå€ãã®å Žåãäžäœã®ãµãŒãã¹ãè¿ éã«æ©èœããçµæã®èŠæ±ãé ããªããŸãã Vobschemã¯ãšãŠã楜ããã§ãã
ãããŠãç§ãã¡ã¯ãã®æã ãšããããšã«æ°ä»ããŸãã-åæ£ãã¬ãŒã¹ãå¿ èŠã§ããã
ã€ã§ãŒã¬ãŒãããããïŒ
åæ©ïŒ
- ç°åžžã®æ€çŽ¢-99ããŒã»ã³ã¿ã€ã«ããã¬ãŒã¯ãããŠããçç±ïŒãããã¯ãŒã¯ã¿ã€ã ã¢ãŠãããµãŒãã¹ãããããããŒã¿ããŒã¹ã®ãããã¯ãªã©ïŒã
- å±éããµãŒãã¹æ§æã®å€æŽããŸãã¯ã€ã³ã¹ã¿ã³ã¹ã®æ°ã®åŸã®è³ªéã®åé¡ïŒ50ãŸãã¯75ããŒã»ã³ã¿ã€ã«ïŒã®èšºæ
- åæ£ãããã¡ã€ãªã³ã°-é
ããµãŒãã¹ãã³ã³ããŒãã³ãããŸãã¯æ©èœãèŠã€ããŸãã
ãªã¯ãšã¹ãã¹ããŒãžã®èŠèŠåïŒã¬ã³ãïŒ-å éšã§äœãèµ·ãã£ãŠããããç解ã§ããŸã
Googleã®DapperãæãåºããŠãç§ãã¡ã¯ãŸãåæ£ãã¬ãŒãã£ã³ã°ã®æ®éçãªæšæºã§ããOpentracingã«è¡ããŸããã è€æ°ã®ãã¬ãŒãµãŒã§ãµããŒããããŠããŸãã æãæåãªã®ã¯ã Zipkin ïŒJavaïŒãšAppdash ïŒGolangïŒã§ãã
ããããæè¿ããã®æšæºããµããŒãããå€ãã¿ã€ããŒã®äžã«ãUber Technologiesã®æ°ããææãªJaegerãç»å ŽããŸããã 圌ã«ã€ããŠè©±ããŸãããã
ããã±ã³ã-ãŽãŒ
UI-React
ã¹ãã¬ãŒãž-Cassandra / Elasticsearch
ããšããšã¯OpenTracingæšæºã®äžã§éçºãããŸããã
åãZipkinãšã¯ç°ãªããJaegerã¢ãã«ã¯ããŒãšå€ã®ãã®ã³ã°ããã€ãã£ãã§ãµããŒããããã¬ãŒã¹ã¯ã¹ãã³ããªãŒã ãã§ãªããæåé埪ç°ã°ã©ãïŒDAGïŒãšããŠæ瀺ãããŸãã
ããã«ãæè¿ã§ã¯LAã®ãªãŒãã³ãœãŒã¹ãµãããã§ãã€ã§ãŒã¬ãŒã¯ KubernetesãPrometheusãªã©ã®åèªãããããžã§ã¯ããšåçã«ãªããŸããã
建ç¯
åãµãŒãã¹ã¯ãã¿ã€ãã³ã°ãšè¿œå æ å ±ãã¹ãã³ã«åéããudpã«ãã£ãŠè¿ãã®jaeger-agentã«ã¹ããŒããŸãã 次ã«ãããããjaeger-collectorã«éä¿¡ããŸãã ãã®åŸããã¬ãŒã¹ã¯jaeger-uiã§å©çšå¯èœã«ãªããŸãã of.sayteã¢ãŒããã¯ãã£ã¯æ¬¡ã®ããã«è¡šãããŸãã
çç£äžã®ã€ã§ãŒã¬ãŒ
ã»ãšãã©ã®ãµãŒãã¹ã¯Dockerã³ã³ãããŒã«ãããã€ãããŸãã ãããŒã³ã¯ããããåéããAnsibleãå±éããŸãã æ®å¿µãªããïŒãããïŒãk8ãnomadããŸãã¯openshiftã®ãããªãªãŒã±ã¹ãã¬ãŒã·ã§ã³ã·ã¹ãã ã«ãŸã åãæ¿ããŠããããã³ã³ãããŒã¯Docker Composeãå®è¡ããŠããŸãã
jaegerãšçµã¿åãããå žåçãªãµãŒãã¹ã¯æ¬¡ã®ããã«ãªããŸãã
å®çšŒåç°å¢ã§ã®Jaegerã®ã€ã³ã¹ããŒã«ã¯ãããã€ãã®ãµãŒãã¹ãšã¹ãã¬ãŒãžã®ã³ã¬ã¯ã·ã§ã³ã§ãã
âã³ã¬ã¯ã¿ãŒ-ãµãŒãã¹ããã¹ãã³ãåãåããã¹ãã¬ãŒãžã«æžã蟌ã¿ãŸã
âã¯ãšãª-ã¹ãã¬ãŒãžããã¹ãã³ãèªã¿åãããã®Web UIãšAPI
âã¹ãã¬ãŒãž-ãã¹ãŠã®ã¹ãã³ãä¿åããŸãã cassandraãŸãã¯elasticsearchã䜿çšã§ããŸã
ãŽã¡ãŒãžã³ããã³ããŒã«ã«éçºã®å Žåã
jaegertracing/all-in-one:latest
ã¡ã¢ãªå ã¹ãã¬ãŒãžã
jaegertracing/all-in-one:latest
ãJaeger
jaegertracing/all-in-one:latest
ãã«ãã䜿çšãããšäŸ¿å©
jaegertracing/all-in-one:latest
ä»çµã¿
ãã®ãµãŒãã¹ã¯ãã¿ã€ãã³ã°ã«é¢ããæ å ±ãšã¡ã¿ãªã¯ãšã¹ãæ å ±ãã¹ãã³ã§åéããŸãã ã³ã³ããã¹ããä»ããŠã¡ãœããéã§ã¹ãã³ãæž¡ãããããããŒã«ã³ã³ããã¹ããæ¿å ¥ããããšã§ããŠã³ã¹ããªãŒã ãµãŒãã¹ãæž¡ãããŸãã
å®èšŒããããã«ãuberããŒã ã¯ãã©ã€ããŒæ€çŽ¢ãµãŒãã¹ã§ã®ãã¬ãŒã¹ã瀺ãè¯ãäŸãçšæããŸããïŒ Hotrod
ã³ãŒãã®ããã«
ãŸãããã¬ãŒãµãŒèªäœãäœæããå¿ èŠããããŸã
import ( "github.com/uber/jaeger-client-go" "github.com/uber/jaeger-client-go/config" ... ) jcfg := config.Configuration{ Disabled: false, // Nop tracer if True Sampler: &config.SamplerConfig{ Type: "const", Param: 1, }, Reporter: &config.ReporterConfig{ LogSpans: true, BufferFlushInterval: 1 * time.Second, // jaeger-agent, LocalAgentHostPort: cfg.Jaeger.ReporterHostPort, }, } tracer, closer, err := jcfg.New( cfg.Jaeger.ServiceName, config.Logger(jaeger.StdLogger), )
ããã«ãŠã§ã¢ã®è¿œå ïŒopentracing.TraceServerïŒ-apiã¡ãœããã®ã«ãŒãã¹ãã³ãäœæããŸãã ãã¹ããããã¹ãã³ã¯ãã¹ãŠããã«é¢é£ä»ããããŸãã
endpoint := CreateEndpoint(svc) // Middleware api endpoint = opentracing.TraceServer(tracer, opName)(endpoint)
ããã«ãçä¿¡èŠæ±ã®ããããŒïŒopentracing.FromHTTPRequestïŒãããã¬ãŒã¹ã®æœåºã³ã³ããã¹ããæœåºããŸãã ãããã£ãŠãç§ãã¡ã®ãµãŒãã¹ã¯ã圌ããªã¯ãšã¹ãã®ãã¬ãŒã¹ã®ã³ã³ããã¹ãïŒInjectïŒãæž¡ããå ŽåãåªãããµãŒãã¹ã«é¢é£ä»ããããŸãã
r.Handle(path, kithttp.NewServer( endpoint, decodeRequestFn, encodeResponseFn, // context.Context append(opts, kithttp.ServerBefore(opentracing.FromHTTPRequest(tracer, opName, logger)))..., )).Methods("POST")
次ã«ãã¡ãœãããã€ã³ã¹ãã«ã¡ã³ãããŸãã
func (s Service) DoSmth() error { span := s.Tracing.StartSpan("DoSmth", ctx) defer span.Finish() // do smth return nil }
ããŠãã¹ãã³ã®éå§èªäœã¯æ¬¡ã®ããã«ãªããŸã
func (t AppTracing) StartSpan(name string, ctx context.Context) opentracing.Span { span := opentracing.SpanFromContext(ctx); if span != nil { span = t.Tracer.StartSpan(name, opentracing.ChildOf(span.Context())) } else { span = t.Tracer.StartSpan(name) } return span }
以äžã§ãã ããã§ããµãŒãã¹ã®åäœããªã¢ã«ã¿ã€ã ã§ç£èŠã§ããŸãã
ïŒ å šäœå ïŒ
ããšãã°ãäžã®å³ã§ã¯ããã¬ãŒãèŠæ±ãèŠã€ãããååã®æéããµãŒãã¹éã®ãããã¯ãŒã¯ã§æ¶è²»ãããæ®ãã®ååãããŒã¿ããŒã¹ã®æŽæ°ã§ããããšãããããŸããã ãã§ã«ããã§äœæ¥ã§ããŸãã
ãæž èŽããããšãããããŸããã ãã®ã¡ã¢ã圹ã«ç«ã€ããšãé¡ã£ãŠããŸããJaegerã¯ã誰ãããµãŒãã¹ã®ä»äºã«éææ§ãããããã®ãå©ããã§ãããã
䟿å©ãªãªã³ã¯
â ãããžã§ã¯ããµã€ãã®
â ãªããžããª
â Opentracing Webãµã€ã
â äŸ