Slide 1

Slide 1 text

Workflow Engine digdagͷಋೖ

Slide 2

Slide 2 text

ࣗݾ঺հ • @amesho • Quantͷ։ൃΛ͍ͯ͠·͢ • ୲౰Օॴ • όοΫΤϯυ • σʔλॲཧपΓͷνϡʔχϯά౳

Slide 3

Slide 3 text

Agenda • Workflow Engine • Digdag • ϫʔΫϑϩʔͷఆٛ • εέδϡʔϦϯά • ԋࢉࢠ • ղܾ͞ΕΔ໰୊

Slide 4

Slide 4 text

Workflow Engine • h#p:/ /regional.rubykaigi.org/tokyo11/interview/frsyuki/ • ݹڮ͞Μͷݴ༿ΛआΓΔͱ ϫʔΫϑϩʔΤϯδϯ͸ɺґଘؔ܎ͷ͋Δෳ਺ͷλεΫΛ࣮ߦ͢Δπʔϧ

Slide 5

Slide 5 text

Workflow Engine ݹڮ͞Μͱ͸ • Founder of Treasure Data, Inc. • MessagePack • Fluentd • Embulk

Slide 6

Slide 6 text

Workflow Engine • OSS΍঎༻ΛؚΊΔͱ͔ͳΓͷ਺͕ग़͍ͯΔ • ༗໊Ͳ͜Ζ • Azkaban • Luigi • Airflow

Slide 7

Slide 7 text

Workflow Engine Azkaban • h#ps:/ /azkaban.github.io/ • h#ps:/ /github.com/azkaban/azkaban

Slide 8

Slide 8 text

Workflow Engine luigi • h#ps:/ /github.com/spo1fy/luigi

Slide 9

Slide 9 text

Workflow Engine Airflow • h#ps:/ /github.com/apache/incubator-airflow

Slide 10

Slide 10 text

Digdag ֓ཁ • TD੡ͷϫʔΫϑϩʔΤϯδϯ • YAMLͰϑϩʔΛهड़ग़དྷΔ • YAMLͦͷ΋ͷ͕֦ு͞Ε͍ͯͯதͰεΫϦϓτ͕ॻ͚Δ • TD΍AmazonͷαʔϏεͱͷ࿈ܞ͕ڧྗ • λεΫΛάϧʔϓԽग़དྷΔ

Slide 11

Slide 11 text

Digdag TDͱ͸ • Treasure Dataࣾͷ͜ͱΛࢦ͠·͢ • Digdagͷ࡞ऀͰ͋Δݹڮ͞Μ΋ॴଐ͍ͯ͠·͢ • ৄࡉ͸ h/ps:/ /www.treasuredata.com/jp/ ͪ͜ΒΛ͝ཡͩ͘͞ ͍

Slide 12

Slide 12 text

Digdag ॏཁͳϙΠϯτ • ΞΠίϯ͕͔Θ͍͍

Slide 13

Slide 13 text

ϫʔΫϑϩʔͷఆٛํ๏ • .digϑΝΠϧͷ࡞੒ • "+"ͰλεΫ໊Λఆٛ • ">"ԋࢉࢠͰΞΫγϣϯΛ࣮ߦ • ม਺ͷຒΊࠐΈ • ฒྻ࣮ߦ • Τϥʔ௨஌

Slide 14

Slide 14 text

ϫʔΫϑϩʔͷఆٛ .digϑΝΠϧͷ࡞੒ • ఆٛ͸.digͱ͍͏֦ுࢠͷϑΝΠϧʹهड़͠·͢ vim hello_digdag.dig

Slide 15

Slide 15 text

ϫʔΫϑϩʔͷఆٛ "+"ͰλεΫ໊Λఆٛ timezone: UTC + task_name:

Slide 16

Slide 16 text

ϫʔΫϑϩʔͷఆٛ ">"ԋࢉࢠͰΞΫγϣϯΛ࣮ߦ • γΣϧεΫϦϓτͷ࣮ߦ • Python|Rubyͷϝιου • ిࢠϝʔϧͷૹ৴ • ౳ʑ

Slide 17

Slide 17 text

ϫʔΫϑϩʔͷఆٛ ">"ԋࢉࢠͰΞΫγϣϯΛ࣮ߦ timezone: UTC + task_name: sh> /bin/touch /tmp/hello_digdag

Slide 18

Slide 18 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ • ${...}ߏจͰJavaScriptΛ࢖༻ͯ͠ม਺Λѻ͑·͢ • ࣌ؒܭࢉʹMoment.jsΛόϯυϧ͍ͯ͠ΔͷͰmoment()Ͱܭࢉ ͕ग़དྷ·͢

Slide 19

Slide 19 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ timezone: UTC + task_name: sh> /bin/touch /tmp/hello_digdag + task_name2: echo> ${moment(session_time).utc().format("YYYY-MM-DD HH:mm:ss")}

Slide 20

Slide 20 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ • ݴޠAPIΛ༻͍ͯม਺͕ຒΊࠐΊ·͢ • Python|Ruby͕͋Γ·͢

Slide 21

Slide 21 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ • RubyΛྫʹͱΓ·͢ • ҎԼͷ2ͭͷϑΝΠϧ͕͋ͬͨ৔߹ • workflow.dig • tasks/my_workflow.rb

Slide 22

Slide 22 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ workflow.dig _export: rb: require: 'tasks/my_workflow' +step1: rb>: MyWorkflow.step1 +step2: rb>: MyWorkflow.step2

Slide 23

Slide 23 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ tasks/my_workflow.rb class MyWorkflow def step1 puts "step1" end def step2 puts "step2" end end

Slide 24

Slide 24 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ • ม਺ఆٛ • Digdag.env.store • Digdag.env.params

Slide 25

Slide 25 text

ϫʔΫϑϩʔͷఆٛ ม਺ͷຒΊࠐΈ class MyWorkflow def step1 Digdag.env.store(my_value: 1) end def step2 puts "step2: %s" % Digdag.env.params['my_value'] end end

Slide 26

Slide 26 text

ϫʔΫϑϩʔͷఆٛ ฒྻ࣮ߦ • _parallel: trueΛઃఆ͢Δͱάϧʔϓ಺ͷλεΫ͕ฒྻԽ ͞Ε·͢

Slide 27

Slide 27 text

ϫʔΫϑϩʔͷఆٛ ฒྻ࣮ߦ timezone: UTC +run: _parallel: true +task_name: sh>: /usr/bin/touch /tmp/hello_digdag +task_name2: sh>: /usr/bin/touch /tmp/hello_digdag2 +task_name3: sh>: /usr/bin/touch /tmp/hello_digdag3

Slide 28

Slide 28 text

ϫʔΫϑϩʔͷఆٛ ฒྻ࣮ߦ ฒྻʹ࣮ߦ͞Ε·͢ʢॱ൪͸อূ͞Εͳ͍ 2017-03-07 09:23:34 +0900 [INFO] (0018@+hoge+run+task_name2): sh>: /usr/bin/touch /tmp/hello_digdag2 2017-03-07 09:23:34 +0900 [INFO] (0017@+hoge+run+task_name): sh>: /usr/bin/touch /tmp/hello_digdag 2017-03-07 09:23:34 +0900 [INFO] (0019@+hoge+run+task_name3): sh>: /usr/bin/touch /tmp/hello_digdag3

Slide 29

Slide 29 text

ϫʔΫϑϩʔͷఆٛ Τϥʔ௨஌ • _error:ύϥϝʔλͰઃఆ͞Ε͍ͯΔ৔߹ • Τϥʔ͕ى͖ͨ৔߹௨஌͕͞Ε·͢

Slide 30

Slide 30 text

ϫʔΫϑϩʔͷఆٛ Τϥʔ௨஌ timezone: UTC +run: _error: sh>: /usr/bin/touch /tmp/error +task_name: sh>: /usr/touch /tmp/hello_digdag

Slide 31

Slide 31 text

ϫʔΫϑϩʔͷఆٛ Τϥʔ௨஌ 2017-03-07 09:30:34 +0900 [INFO] (0017@+error+run+task_name): sh>: /usr/touch /tmp/hello_digdag /bin/sh: line 1: /usr/touch: No such file or directory 2017-03-07 09:30:34 +0900 [ERROR] (0017@+error+run+task_name): Task failed with unexpected error: Command failed with code 127 java.lang.RuntimeException: Command failed with code 127 at io.digdag.standards.operator.ShOperatorFactory$ShOperator.runTask(ShOperatorFactory.java:143) at io.digdag.util.BaseOperator.run(BaseOperator.java:35) at io.digdag.core.agent.OperatorManager.callExecutor(OperatorManager.java:314) at io.digdag.cli.Run$OperatorManagerWithSkip.callExecutor(Run.java:674) at io.digdag.core.agent.OperatorManager.runWithWorkspace(OperatorManager.java:255) at io.digdag.core.agent.OperatorManager.lambda$runWithHeartbeat$2(OperatorManager.java:138) at io.digdag.core.agent.LocalWorkspaceManager.withExtractedArchive(LocalWorkspaceManager.java:25) at io.digdag.core.agent.OperatorManager.runWithHeartbeat(OperatorManager.java:136) at io.digdag.core.agent.OperatorManager.run(OperatorManager.java:120) at io.digdag.cli.Run$OperatorManagerWithSkip.run(Run.java:656) at io.digdag.core.agent.MultiThreadAgent.lambda$run$0(MultiThreadAgent.java:95) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) at java.lang.Thread.run(Thread.java:745) 2017-03-07 09:30:35 +0900 [INFO] (0017@+error+run^error): sh>: /usr/bin/touch /tmp/error 2017-03-07 09:30:35 +0900 [INFO] (0017@+error^failure-alert): type: notify error: * +error+run+task_name: Command failed with code 127 (runtime)

Slide 32

Slide 32 text

εέδϡʔϦϯάϫʔΫϑϩʔ • εέδϡʔϧͷઃఆ • εέδϡʔϥͷىಈ • εέδϡʔϥͷεςʔλε֬ೝ • ࣮ߦ࣌ؒʹؔ͢ΔΞϥʔτ

Slide 33

Slide 33 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϧͷઃఆ timezone: UTC schedule: daily>: 07:00:00 +step1: sh>: /usr/bin/touch /tmp/schedule

Slide 34

Slide 34 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϧͷઃఆ • CRONํࣜ΋࠾༻Ͱ͖·͢

Slide 35

Slide 35 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϧͷઃఆ timezone: UTC schedule: cron>: 42 4 1 * * +step1: sh>: /usr/bin/touch /tmp/schedule

Slide 36

Slide 36 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϥͷىಈ digdag sched --memory

Slide 37

Slide 37 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϥͷεςʔλε֬ೝ digdag check

Slide 38

Slide 38 text

εέδϡʔϦϯάϫʔΫϑϩʔ εέδϡʔϥͷεςʔλε֬ೝ Schedules (1 entries): mydag: daily>: "19:40:00" first session time: 2017-03-07 00:00:00 +0900 first scheduled to run at: 2017-03-07 19:40:00 +0900 (in 9h 4m 52s)

Slide 39

Slide 39 text

εέδϡʔϦϯάϫʔΫϑϩʔ ࣮ߦ࣌ؒʹؔ͢ΔΞϥʔτ • ੍ݶ࣌ؒΛઃఆͯͦ͠ΕΛ௒͑ͨΒΞϥʔτ͕ඈ͹ͤ·͢

Slide 40

Slide 40 text

εέδϡʔϦϯάϫʔΫϑϩʔ ࣮ߦ࣌ؒʹؔ͢ΔΞϥʔτ timezone: UTC schedule: daily>: 07:00:00 sla: # triggers this task at 02:00 time: 02:00 +notice: sh>: notice.sh +long_running_job: sh>: long_running_job.sh

Slide 41

Slide 41 text

ղܾ͞ΕΔ໰୊ • ෳࡶͳґଘؔ܎Λ࣋ͬͨCRONΛҰཡͰ͖Δ • Α͋͘ΔɺCRON͕͚ͨ͜ͱ͖ʹͦͷCRON͕ͺͬͱΈͲ͜ ʹґଘ͍ͯͯ͠ • ߋʹͦͷCRONʹґଘ͍ͯ͠ΔλεΫ͕ͳΜͳͷ͔෼͔Βͳ ͍໰୊ • ؅ཧը໘͕͋ΔͷͰ͔ͦ͜ΒͲ͜·Ͱ࣮ߦ͞Ε͍ͯΔ͔ͷLog Λ֬ೝՄೳ

Slide 42

Slide 42 text

ղܾ͞ΕΔ໰୊ • ฒྻॲཧΛؾܰʹߦ͑ΔΑ͏ʹͳΔͷͰ଎౓վળ͕ى͖Δ

Slide 43

Slide 43 text

ղܾ͞ΕΔ໰୊ ૉఢͳґଘؔ܎ʹ͋Δcron server A # 4࣌ʹىಈͯ͠ڪΒ͘2࣌ؒͰऴΘΔॲཧ 0 4 * * * /path/to/your_script.rb server B # server Aͷॲཧ͕6࣌ʹऴ͍ྃͯ͠Δ͸ͣͳͷͰͦΕΛݩʹॲཧ # ࠶࣮ߦ͢Δͱࠅ͍͜ͱʹͳΔͷͰ஫ҙ 0 8 * * * /path/to/your_script.rb

Slide 44

Slide 44 text

ղܾ͞ΕΔ໰୊ ૉఢͳґଘؔ܎ʹ͋Δcron ͖ͯ͢ͳٙ໰ • server Aͷॲཧͷ࣮ߦ͕࣌ؒԆͼ͍ͯͬͨΒͲ͏͢Δͷ͔ʁ • server Aͷॲཧ͕ෆ۩߹Ͱऴྃ͠ͳ͔ͬͨΒͲ͏͢Δͷ͔ʁ • ౳ʑ

Slide 45

Slide 45 text

ղܾ͞ΕΔ໰୊ ૉఢͳґଘؔ܎ͷcronΛdigdagͰॻ͖௚͢ timezone: "Asia/Tokyo" schedule: daily>: 04:00:00 +step1: sh>: ssh host:/path/to/your_script.rb +step2: sh>: /path/to/your_script2.rb

Slide 46

Slide 46 text

ԋࢉࢠ • ϫʔΫϑϩʔԋࢉࢠ • τϨδϟʔσʔλԋࢉࢠ • σʔλϕʔεԋࢉࢠ • ωοτϫʔΫԋࢉࢠ • AWSԋࢉࢠ • Google Cloud Pla0ormԋࢉࢠ

Slide 47

Slide 47 text

ԋࢉࢠ • ֎෦αʔϏεͱ࿈ܞ͍ͯ͠Δԋࢉࢠׂ͕ͱଟ͋͘Γ·͢ • τϨδϟʔσʔλԋࢉࢠ • AWSԋࢉࢠ • Google Cloud Pla0ormԋࢉࢠ

Slide 48

Slide 48 text

ԋࢉࢠ ϫʔΫϑϩʔԋࢉࢠ • call>: ผͷϫʔΫϑϩʔΛݺͼग़͢ • require>: ґଘ͢ΔϫʔΫϑϩʔΛ࣮ߦ • callͱ͕͍ͪଞͷϫʔΫϑϩʔΛ࣮ߦ͠ͳ͍ • loop>: λεΫΛ܁Γฦ͢ • ճ਺Λ͍ͯͯ͠͠_doҎԼͷλεΫΛ܁Γฦ͢

Slide 49

Slide 49 text

ԋࢉࢠ ωοτϫʔΫԋࢉࢠ • mail>: ిࢠϝʔϧΛૹ৴͢Δ • h*p>: HTTPϦΫΤετΛߦ͏

Slide 50

Slide 50 text

ԋࢉࢠ εΫϦϓτԋࢉࢠ • sh>: γΣϧ • py>: PythonεΫϦϓτ • rb>: RubyεΫϦϓτ • embulk>: embulkͷσʔλసૹ • ݱࡏഇࢭ͞Ε͍ͯ·͢

Slide 51

Slide 51 text

·ͱΊ • YAMLͰWorkFlowΛ͔͚Δ͜ͱʹΑΓෳࡶͳtaskΛҰཡͰ͖Δ Α͏ʹͳΔ • ґଘؔ܎ͰۭؾΛಡ·ͣʹࡁΉΑ͏ʹͳΔ • ฒྻԽ౳Λ؆୯ʹରԠͰ͖ΔͷͰ଎౓Ξοϓ͕๬ΊΔՕॴ͕Ͱ ͯ͘Δ

Slide 52

Slide 52 text

·ͱΊ • ؅ཧը໘͔ΒλεΫͷ࣮ߦঢ়گΛ೺ѲͰ͖Δ • ֎෦αʔϏεͱ࿈ܞ͍ͯ͠Δԋࢉࢠ͕ଟ͋͘ΔͷͰΫϥ΢υα ʔϏεͱͷ࿈ܞָ͕ʹͰ͖Δ

Slide 53

Slide 53 text

͝੩ௌ͋Γ͕ͱ͏͍͟͝·ͨ͠