vagrant-bosh 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (147) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +12 -0
  3. data/.gitmodules +6 -0
  4. data/Gemfile +3 -0
  5. data/LICENSE +20 -0
  6. data/README.md +73 -0
  7. data/Rakefile +2 -0
  8. data/dev/.gitignore +1 -0
  9. data/dev/Vagrantfile +30 -0
  10. data/dev/example-bosh-manifest.yml +188 -0
  11. data/dev/example-winston-manifest.yml +70 -0
  12. data/go/.gitignore +11 -0
  13. data/go/bin/build +10 -0
  14. data/go/bin/build-linux-amd64 +9 -0
  15. data/go/bin/env +13 -0
  16. data/go/bin/go +5 -0
  17. data/go/bin/golint +19 -0
  18. data/go/bin/test +37 -0
  19. data/go/src/boshprovisioner/agent/client/client_interface.go +73 -0
  20. data/go/src/boshprovisioner/agent/client/fakes/fake_client.go +81 -0
  21. data/go/src/boshprovisioner/agent/client/http_client.go +299 -0
  22. data/go/src/boshprovisioner/agent/client/http_client_envelope.go +107 -0
  23. data/go/src/boshprovisioner/deployment/deployment.go +221 -0
  24. data/go/src/boshprovisioner/deployment/instance.go +54 -0
  25. data/go/src/boshprovisioner/deployment/manifest/deployment.go +80 -0
  26. data/go/src/boshprovisioner/deployment/manifest/ips.go +23 -0
  27. data/go/src/boshprovisioner/deployment/manifest/manifest.go +143 -0
  28. data/go/src/boshprovisioner/deployment/manifest/manifest_suite_test.go +13 -0
  29. data/go/src/boshprovisioner/deployment/manifest/manifest_test.go +86 -0
  30. data/go/src/boshprovisioner/deployment/manifest/syntax_validator.go +186 -0
  31. data/go/src/boshprovisioner/deployment/manifest/watch_time.go +47 -0
  32. data/go/src/boshprovisioner/deployment/manifest_reader.go +46 -0
  33. data/go/src/boshprovisioner/deployment/reader_factory.go +25 -0
  34. data/go/src/boshprovisioner/deployment/semantic_validator.go +111 -0
  35. data/go/src/boshprovisioner/downloader/blobstore_downloader.go +55 -0
  36. data/go/src/boshprovisioner/downloader/default_mux_downloader.go +22 -0
  37. data/go/src/boshprovisioner/downloader/downloader_interface.go +6 -0
  38. data/go/src/boshprovisioner/downloader/http_downloader.go +53 -0
  39. data/go/src/boshprovisioner/downloader/local_fs_downloader.go +48 -0
  40. data/go/src/boshprovisioner/downloader/mux_downloader.go +69 -0
  41. data/go/src/boshprovisioner/eventlog/log.go +72 -0
  42. data/go/src/boshprovisioner/eventlog/stage.go +39 -0
  43. data/go/src/boshprovisioner/eventlog/task.go +58 -0
  44. data/go/src/boshprovisioner/index/file_index.go +289 -0
  45. data/go/src/boshprovisioner/index/file_index_test.go +296 -0
  46. data/go/src/boshprovisioner/index/index_interface.go +18 -0
  47. data/go/src/boshprovisioner/index/index_suite_test.go +13 -0
  48. data/go/src/boshprovisioner/instance/templatescompiler/concrete_templates_compiler.go +273 -0
  49. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/erb_renderer.go +117 -0
  50. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/erbrenderer_suite_test.go +13 -0
  51. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/render_properties.go +77 -0
  52. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/render_properties_test.go +142 -0
  53. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/template_evaluation_context.go +85 -0
  54. data/go/src/boshprovisioner/instance/templatescompiler/erbrenderer/template_evaluation_context_rb.go +155 -0
  55. data/go/src/boshprovisioner/instance/templatescompiler/jobsrepo/concrete_jobs_repository.go +64 -0
  56. data/go/src/boshprovisioner/instance/templatescompiler/jobsrepo/concrete_runtime_packages_repository.go +105 -0
  57. data/go/src/boshprovisioner/instance/templatescompiler/jobsrepo/concrete_template_to_job_repository.go +76 -0
  58. data/go/src/boshprovisioner/instance/templatescompiler/jobsrepo/jobs_repository_interface.go +31 -0
  59. data/go/src/boshprovisioner/instance/templatescompiler/rendered_archives_compiler.go +81 -0
  60. data/go/src/boshprovisioner/instance/templatescompiler/templates_compiler_interface.go +20 -0
  61. data/go/src/boshprovisioner/instance/templatescompiler/templatesrepo/ct_repository.go +54 -0
  62. data/go/src/boshprovisioner/instance/templatescompiler/templatesrepo/templates_repository_interface.go +16 -0
  63. data/go/src/boshprovisioner/instance/updater/applier/applier.go +93 -0
  64. data/go/src/boshprovisioner/instance/updater/applier/empty_state.go +66 -0
  65. data/go/src/boshprovisioner/instance/updater/applier/job_state.go +178 -0
  66. data/go/src/boshprovisioner/instance/updater/drainer.go +72 -0
  67. data/go/src/boshprovisioner/instance/updater/preparer.go +39 -0
  68. data/go/src/boshprovisioner/instance/updater/starter.go +36 -0
  69. data/go/src/boshprovisioner/instance/updater/stopper.go +36 -0
  70. data/go/src/boshprovisioner/instance/updater/updater.go +102 -0
  71. data/go/src/boshprovisioner/instance/updater/updater_factory.go +83 -0
  72. data/go/src/boshprovisioner/instance/updater/updater_suite_test.go +13 -0
  73. data/go/src/boshprovisioner/instance/updater/waiter.go +77 -0
  74. data/go/src/boshprovisioner/instance/updater/waiter_test.go +103 -0
  75. data/go/src/boshprovisioner/main/config.go +77 -0
  76. data/go/src/boshprovisioner/main/main.go +183 -0
  77. data/go/src/boshprovisioner/main/repos_factory.go +96 -0
  78. data/go/src/boshprovisioner/packagescompiler/compiledpackagesrepo/compiled_packages_repository_interface.go +17 -0
  79. data/go/src/boshprovisioner/packagescompiler/compiledpackagesrepo/concrete_compiled_packages_repository.go +61 -0
  80. data/go/src/boshprovisioner/packagescompiler/concrete_packages_compiler.go +179 -0
  81. data/go/src/boshprovisioner/packagescompiler/concrete_packages_compiler_factory.go +48 -0
  82. data/go/src/boshprovisioner/packagescompiler/packages_compiler_interface.go +20 -0
  83. data/go/src/boshprovisioner/packagescompiler/packagesrepo/concrete_packages_repository.go +65 -0
  84. data/go/src/boshprovisioner/packagescompiler/packagesrepo/packages_repository_interface.go +16 -0
  85. data/go/src/boshprovisioner/provisioner/blobstore_config.go +65 -0
  86. data/go/src/boshprovisioner/provisioner/blobstore_provisioner.go +38 -0
  87. data/go/src/boshprovisioner/provisioner/deployment_provisioner.go +97 -0
  88. data/go/src/boshprovisioner/provisioner/instance_provisioner.go +48 -0
  89. data/go/src/boshprovisioner/provisioner/release_compiler.go +133 -0
  90. data/go/src/boshprovisioner/release/job/job.go +86 -0
  91. data/go/src/boshprovisioner/release/job/manifest/manifest.go +79 -0
  92. data/go/src/boshprovisioner/release/job/manifest/manifest_suite_test.go +13 -0
  93. data/go/src/boshprovisioner/release/job/manifest/manifest_test.go +42 -0
  94. data/go/src/boshprovisioner/release/job/manifest/syntax_validator.go +43 -0
  95. data/go/src/boshprovisioner/release/job/reader_factory.go +34 -0
  96. data/go/src/boshprovisioner/release/job/tar_reader.go +133 -0
  97. data/go/src/boshprovisioner/release/manifest/manifest.go +96 -0
  98. data/go/src/boshprovisioner/release/manifest_reader.go +29 -0
  99. data/go/src/boshprovisioner/release/reader_factory.go +34 -0
  100. data/go/src/boshprovisioner/release/release.go +144 -0
  101. data/go/src/boshprovisioner/release/release_suite_test.go +13 -0
  102. data/go/src/boshprovisioner/release/release_test.go +129 -0
  103. data/go/src/boshprovisioner/release/tar_reader.go +139 -0
  104. data/go/src/boshprovisioner/releasesrepo/blobstore_releases_repository.go +114 -0
  105. data/go/src/boshprovisioner/releasesrepo/releases_repository_interface.go +15 -0
  106. data/go/src/boshprovisioner/tar/cmd_compressor.go +68 -0
  107. data/go/src/boshprovisioner/tar/cmd_extractor.go +47 -0
  108. data/go/src/boshprovisioner/tar/compressor_interface.go +6 -0
  109. data/go/src/boshprovisioner/tar/extractor_interface.go +6 -0
  110. data/go/src/boshprovisioner/util/string_keyed.go +70 -0
  111. data/go/src/boshprovisioner/vm/agent_provisioner.go +266 -0
  112. data/go/src/boshprovisioner/vm/asset_manager.go +61 -0
  113. data/go/src/boshprovisioner/vm/deps_provisioner.go +92 -0
  114. data/go/src/boshprovisioner/vm/monit_provisioner.go +83 -0
  115. data/go/src/boshprovisioner/vm/runit_provisioner.go +225 -0
  116. data/go/src/boshprovisioner/vm/simple_cmds.go +54 -0
  117. data/go/src/boshprovisioner/vm/vcap_user_provisioner.go +120 -0
  118. data/go/src/boshprovisioner/vm/vm.go +19 -0
  119. data/go/src/boshprovisioner/vm/vm_provisioner.go +57 -0
  120. data/go/src/boshprovisioner/vm/vm_provisioner_factory.go +97 -0
  121. data/lib/vagrant-bosh/asset_uploader.rb +53 -0
  122. data/lib/vagrant-bosh/assets/agent/agent-log +5 -0
  123. data/lib/vagrant-bosh/assets/agent/agent-run +12 -0
  124. data/lib/vagrant-bosh/assets/agent/agent.cert +18 -0
  125. data/lib/vagrant-bosh/assets/agent/agent.json +9 -0
  126. data/lib/vagrant-bosh/assets/agent/agent.key +27 -0
  127. data/lib/vagrant-bosh/assets/agent/bosh-agent +0 -0
  128. data/lib/vagrant-bosh/assets/agent/bosh-agent-rc +18 -0
  129. data/lib/vagrant-bosh/assets/agent/bosh-blobstore-dav +0 -0
  130. data/lib/vagrant-bosh/assets/monit/monit +0 -0
  131. data/lib/vagrant-bosh/assets/monit/monit-log +5 -0
  132. data/lib/vagrant-bosh/assets/monit/monit-run +9 -0
  133. data/lib/vagrant-bosh/assets/monit/monitrc +8 -0
  134. data/lib/vagrant-bosh/assets/provisioner +0 -0
  135. data/lib/vagrant-bosh/bootstrapper.rb +59 -0
  136. data/lib/vagrant-bosh/communicator.rb +50 -0
  137. data/lib/vagrant-bosh/config.rb +15 -0
  138. data/lib/vagrant-bosh/errors.rb +11 -0
  139. data/lib/vagrant-bosh/plugin.rb +25 -0
  140. data/lib/vagrant-bosh/provisioner.rb +46 -0
  141. data/lib/vagrant-bosh/provisioner_tracker.rb +41 -0
  142. data/lib/vagrant-bosh/ui.rb +77 -0
  143. data/lib/vagrant-bosh/version.rb +5 -0
  144. data/lib/vagrant-bosh.rb +15 -0
  145. data/templates/locales/en.yml +15 -0
  146. data/vagrant-bosh.gemspec +20 -0
  147. metadata +191 -0
@@ -0,0 +1,66 @@
1
+ package applier
2
+
3
+ import (
4
+ boshas "bosh/agent/applier/applyspec"
5
+
6
+ bpdep "boshprovisioner/deployment"
7
+ )
8
+
9
+ // EmptyState represents state for a VM
10
+ // that should not be running any job templates.
11
+ type EmptyState struct {
12
+ instance bpdep.Instance
13
+ }
14
+
15
+ func NewEmptyState(instance bpdep.Instance) EmptyState {
16
+ return EmptyState{instance: instance}
17
+ }
18
+
19
+ func (s EmptyState) AsApplySpec() boshas.V1ApplySpec {
20
+ var spec boshas.V1ApplySpec
21
+
22
+ jobName := s.instance.JobName
23
+ jobIndex := s.instance.Index
24
+
25
+ spec = boshas.V1ApplySpec{
26
+ ConfigurationHash: "fake-configuration-hash", // todo
27
+
28
+ Deployment: s.instance.DeploymentName,
29
+
30
+ JobSpec: boshas.JobSpec{
31
+ Name: &jobName,
32
+ },
33
+
34
+ Index: &jobIndex,
35
+
36
+ NetworkSpecs: s.buildNetworkSpecs(),
37
+
38
+ // todo find out whats here
39
+ ResourcePoolSpecs: s.buildResourcePoolSpecs(),
40
+ }
41
+
42
+ return spec
43
+ }
44
+
45
+ func (s EmptyState) buildNetworkSpecs() map[string]boshas.NetworkSpec {
46
+ specs := map[string]boshas.NetworkSpec{}
47
+
48
+ for _, netAssoc := range s.instance.NetworkAssociations {
49
+ netConfig := s.instance.NetworkConfigurationForNetworkAssociation(netAssoc)
50
+
51
+ specs[netAssoc.Network.Name] = boshas.NetworkSpec{
52
+ Fields: map[string]interface{}{
53
+ "type": netAssoc.Network.Type,
54
+ "ip": netConfig.IP,
55
+ "netmask": netConfig.Netmask,
56
+ "gateway": netConfig.Gateway,
57
+ },
58
+ }
59
+ }
60
+
61
+ return specs
62
+ }
63
+
64
+ func (s EmptyState) buildResourcePoolSpecs() map[string]interface{} {
65
+ return map[string]interface{}{}
66
+ }
@@ -0,0 +1,178 @@
1
+ package applier
2
+
3
+ import (
4
+ boshas "bosh/agent/applier/applyspec"
5
+ bosherr "bosh/errors"
6
+
7
+ bpdep "boshprovisioner/deployment"
8
+ bptplcomp "boshprovisioner/instance/templatescompiler"
9
+ bppkgscomp "boshprovisioner/packagescompiler"
10
+ )
11
+
12
+ // JobState represents state for a VM
13
+ // that should be running 1+ job templates.
14
+ type JobState struct {
15
+ depJob bpdep.Job
16
+ instance bpdep.Instance
17
+
18
+ templatesCompiler bptplcomp.TemplatesCompiler
19
+ packagesCompiler bppkgscomp.PackagesCompiler
20
+
21
+ emptyState EmptyState
22
+ }
23
+
24
+ func NewJobState(
25
+ depJob bpdep.Job,
26
+ instance bpdep.Instance,
27
+ templatesCompiler bptplcomp.TemplatesCompiler,
28
+ packagesCompiler bppkgscomp.PackagesCompiler,
29
+ ) JobState {
30
+ return JobState{
31
+ depJob: depJob,
32
+ instance: instance,
33
+
34
+ templatesCompiler: templatesCompiler,
35
+ packagesCompiler: packagesCompiler,
36
+
37
+ emptyState: NewEmptyState(instance),
38
+ }
39
+ }
40
+
41
+ func (s JobState) AsApplySpec() (boshas.V1ApplySpec, error) {
42
+ var err error
43
+
44
+ spec := s.emptyState.AsApplySpec()
45
+
46
+ // JobTemplateSpecs list templates names; however,
47
+ // actual template content would come from RenderedTemplatesArchiveSpec
48
+ spec.JobSpec.JobTemplateSpecs = s.buildJobTemplateSpecs()
49
+
50
+ // Package dependencies for all job templates
51
+ spec.PackageSpecs, err = s.buildPackageSpecs()
52
+ if err != nil {
53
+ return spec, err
54
+ }
55
+
56
+ // Provides content for JobTemplateSpecs
57
+ spec.RenderedTemplatesArchiveSpec, err = s.buildRenderedTemplatesArchive()
58
+ if err != nil {
59
+ return spec, err
60
+ }
61
+
62
+ return spec, nil
63
+ }
64
+
65
+ func (s JobState) buildJobTemplateSpecs() []boshas.JobTemplateSpec {
66
+ var specs []boshas.JobTemplateSpec
67
+
68
+ for _, template := range s.depJob.Templates {
69
+ spec := boshas.JobTemplateSpec{
70
+ Name: template.Name,
71
+ Version: "fake-job-template-version", // todo
72
+
73
+ Sha1: "", // deprecated
74
+ BlobstoreID: "", // deprecated
75
+ }
76
+
77
+ specs = append(specs, spec)
78
+ }
79
+
80
+ return specs
81
+ }
82
+
83
+ func (s JobState) buildPackageSpecs() (map[string]boshas.PackageSpec, error) {
84
+ specs := map[string]boshas.PackageSpec{}
85
+
86
+ for _, template := range s.depJob.Templates {
87
+ pkgs, err := s.templatesCompiler.FindPackages(template)
88
+ if err != nil {
89
+ return specs, bosherr.WrapError(err, "Finding packages for template %s", template.Name)
90
+ }
91
+
92
+ for _, pkg := range pkgs {
93
+ rec, err := s.packagesCompiler.FindCompiledPackage(pkg)
94
+ if err != nil {
95
+ return specs, bosherr.WrapError(err, "Finding compiled package %s", pkg.Name)
96
+ }
97
+
98
+ specs[pkg.Name] = boshas.PackageSpec{
99
+ Name: pkg.Name,
100
+ Version: pkg.Version,
101
+
102
+ Sha1: rec.SHA1,
103
+ BlobstoreID: rec.BlobID,
104
+ }
105
+ }
106
+ }
107
+
108
+ return specs, nil
109
+ }
110
+
111
+ func (s JobState) buildRenderedTemplatesArchive() (boshas.RenderedTemplatesArchiveSpec, error) {
112
+ var archive boshas.RenderedTemplatesArchiveSpec
113
+
114
+ rec, err := s.templatesCompiler.FindRenderedArchive(s.depJob, s.instance)
115
+ if err != nil {
116
+ return archive, bosherr.WrapError(
117
+ err, "Finding rendered archive %s", s.depJob.Name)
118
+ }
119
+
120
+ // todo uppercase Sha1
121
+ archive.Sha1 = rec.SHA1
122
+ archive.BlobstoreID = rec.BlobID
123
+
124
+ return archive, nil
125
+ }
126
+
127
+ /*
128
+ // Example apply spec
129
+ {
130
+ "job": {
131
+ "name": "router",
132
+ "template": "router template",
133
+ "version": "1.0",
134
+ "sha1": "router sha1",
135
+ "blobstore_id": "router-blob-id-1",
136
+ "templates": [{
137
+ "name": "template 1",
138
+ "version": "0.1",
139
+ "sha1": "template 1 sha1",
140
+ "blobstore_id": "template-blob-id-1"
141
+ }]
142
+ },
143
+
144
+ "index": 1,
145
+
146
+ "packages": {
147
+ "package 1": {
148
+ "name": "package 1",
149
+ "version": "0.1",
150
+ "sha1": "package 1 sha1",
151
+ "blobstore_id": "package-blob-id-1"
152
+ }
153
+ },
154
+
155
+ "networks": {
156
+ "manual-net": {
157
+ "ip": "xx.xx.xx.xx",
158
+ "gateway": "xx.xx.xx.xx",
159
+ "netmask": "xx.xx.xx.xx",
160
+ "dns": ["xx.xx.xx.xx"],
161
+ "default": ["dns", "gateway"],
162
+ "cloud_properties": {"subnet": "subnet-xxxxxx"},
163
+ "dns_record_name": "job-index.job-name.manual-net.deployment-name.bosh"
164
+ },
165
+ "vip-net": {
166
+ "type": "vip",
167
+ "ip": "xx.xx.xx.xx",
168
+ "cloud_properties": {"security_groups": ["bosh"]},
169
+ "dns_record_name": "job-index.job-name.vip-net.deployment-name.bosh"
170
+ }
171
+ },
172
+
173
+ "rendered_templates_archive": {
174
+ "sha1": "archive sha 1",
175
+ "blobstore_id": "archive-blob-id-1"
176
+ }
177
+ }
178
+ */
@@ -0,0 +1,72 @@
1
+ package updater
2
+
3
+ import (
4
+ "math"
5
+ "time"
6
+
7
+ boshaction "bosh/agent/action"
8
+ boshas "bosh/agent/applier/applyspec"
9
+ bosherr "bosh/errors"
10
+ boshlog "bosh/logger"
11
+
12
+ bpagclient "boshprovisioner/agent/client"
13
+ )
14
+
15
+ const drainerLogTag = "Drainer"
16
+
17
+ type Drainer struct {
18
+ agentClient bpagclient.Client
19
+ logger boshlog.Logger
20
+ }
21
+
22
+ func NewDrainer(
23
+ agentClient bpagclient.Client,
24
+ logger boshlog.Logger,
25
+ ) Drainer {
26
+ return Drainer{
27
+ agentClient: agentClient,
28
+ logger: logger,
29
+ }
30
+ }
31
+
32
+ func (d Drainer) Drain() error {
33
+ d.logger.Debug(drainerLogTag, "Draining instance")
34
+
35
+ drainType := boshaction.DrainTypeUpdate
36
+ spec := boshas.V1ApplySpec{}
37
+
38
+ drainTime, err := d.agentClient.Drain(drainType, spec)
39
+ if err != nil {
40
+ return bosherr.WrapError(err, "Sending drain update")
41
+ }
42
+
43
+ if drainTime > 0 {
44
+ d.logger.Debug(drainerLogTag, "Waiting for static drain to finish")
45
+ time.Sleep(time.Duration(drainTime) * time.Second)
46
+ return nil
47
+ }
48
+
49
+ d.logger.Debug(drainerLogTag, "Waiting for dynamic drain to finish")
50
+
51
+ return d.waitForDynamicDrain(drainTime)
52
+ }
53
+
54
+ func (d Drainer) waitForDynamicDrain(drainTime int) error {
55
+ var err error
56
+
57
+ for {
58
+ waitTime := int(math.Abs(float64(drainTime)))
59
+ if waitTime > 0 {
60
+ time.Sleep(time.Duration(waitTime) * time.Second)
61
+ }
62
+
63
+ if drainTime >= 0 {
64
+ return nil
65
+ }
66
+
67
+ drainTime, err = d.agentClient.Drain(boshaction.DrainTypeStatus)
68
+ if err != nil {
69
+ return bosherr.WrapError(err, "Sending drain status")
70
+ }
71
+ }
72
+ }
@@ -0,0 +1,39 @@
1
+ package updater
2
+
3
+ import (
4
+ boshas "bosh/agent/applier/applyspec"
5
+ bosherr "bosh/errors"
6
+ boshlog "bosh/logger"
7
+
8
+ bpagclient "boshprovisioner/agent/client"
9
+ )
10
+
11
+ const preparerLogTag = "Preparer"
12
+
13
+ type Preparer struct {
14
+ agentClient bpagclient.Client
15
+ logger boshlog.Logger
16
+ }
17
+
18
+ func NewPreparer(
19
+ agentClient bpagclient.Client,
20
+ logger boshlog.Logger,
21
+ ) Preparer {
22
+ return Preparer{
23
+ agentClient: agentClient,
24
+ logger: logger,
25
+ }
26
+ }
27
+
28
+ func (p Preparer) Prepare() error {
29
+ p.logger.Debug(preparerLogTag, "Preparing instance")
30
+
31
+ spec := boshas.V1ApplySpec{}
32
+
33
+ _, err := p.agentClient.Prepare(spec)
34
+ if err != nil {
35
+ return bosherr.WrapError(err, "Sending prepare")
36
+ }
37
+
38
+ return nil
39
+ }
@@ -0,0 +1,36 @@
1
+ package updater
2
+
3
+ import (
4
+ bosherr "bosh/errors"
5
+ boshlog "bosh/logger"
6
+
7
+ bpagclient "boshprovisioner/agent/client"
8
+ )
9
+
10
+ const starterLogTag = "Starter"
11
+
12
+ type Starter struct {
13
+ agentClient bpagclient.Client
14
+ logger boshlog.Logger
15
+ }
16
+
17
+ func NewStarter(
18
+ agentClient bpagclient.Client,
19
+ logger boshlog.Logger,
20
+ ) Starter {
21
+ return Starter{
22
+ agentClient: agentClient,
23
+ logger: logger,
24
+ }
25
+ }
26
+
27
+ func (s Starter) Start() error {
28
+ s.logger.Debug(starterLogTag, "Starting instance")
29
+
30
+ _, err := s.agentClient.Start()
31
+ if err != nil {
32
+ return bosherr.WrapError(err, "Starting")
33
+ }
34
+
35
+ return nil
36
+ }
@@ -0,0 +1,36 @@
1
+ package updater
2
+
3
+ import (
4
+ bosherr "bosh/errors"
5
+ boshlog "bosh/logger"
6
+
7
+ bpagclient "boshprovisioner/agent/client"
8
+ )
9
+
10
+ const stopperLogTag = "Stopper"
11
+
12
+ type Stopper struct {
13
+ agentClient bpagclient.Client
14
+ logger boshlog.Logger
15
+ }
16
+
17
+ func NewStopper(
18
+ agentClient bpagclient.Client,
19
+ logger boshlog.Logger,
20
+ ) Stopper {
21
+ return Stopper{
22
+ agentClient: agentClient,
23
+ logger: logger,
24
+ }
25
+ }
26
+
27
+ func (s Stopper) Stop() error {
28
+ s.logger.Debug(stopperLogTag, "Stopping instance")
29
+
30
+ _, err := s.agentClient.Stop()
31
+ if err != nil {
32
+ return bosherr.WrapError(err, "Stopping")
33
+ }
34
+
35
+ return nil
36
+ }
@@ -0,0 +1,102 @@
1
+ package updater
2
+
3
+ import (
4
+ "fmt"
5
+
6
+ bosherr "bosh/errors"
7
+ boshlog "bosh/logger"
8
+
9
+ bpeventlog "boshprovisioner/eventlog"
10
+ bpapplier "boshprovisioner/instance/updater/applier"
11
+ )
12
+
13
+ const updaterLogTag = "Updater"
14
+
15
+ type Updater struct {
16
+ instanceDesc string
17
+
18
+ preparer Preparer
19
+ drainer Drainer
20
+ stopper Stopper
21
+ applier bpapplier.Applier
22
+ starter Starter
23
+ waiter Waiter
24
+
25
+ eventLog bpeventlog.Log
26
+ logger boshlog.Logger
27
+ }
28
+
29
+ func NewUpdater(
30
+ instanceDesc string,
31
+ preparer Preparer,
32
+ drainer Drainer,
33
+ stopper Stopper,
34
+ applier bpapplier.Applier,
35
+ starter Starter,
36
+ waiter Waiter,
37
+ eventLog bpeventlog.Log,
38
+ logger boshlog.Logger,
39
+ ) Updater {
40
+ return Updater{
41
+ instanceDesc: instanceDesc,
42
+
43
+ preparer: preparer,
44
+ drainer: drainer,
45
+ stopper: stopper,
46
+ applier: applier,
47
+ starter: starter,
48
+ waiter: waiter,
49
+
50
+ eventLog: eventLog,
51
+ logger: logger,
52
+ }
53
+ }
54
+
55
+ func (u Updater) Update() error {
56
+ stage := u.eventLog.BeginStage(
57
+ fmt.Sprintf("Updating instance %s", u.instanceDesc), 6)
58
+
59
+ task := stage.BeginTask("Preparing")
60
+
61
+ err := task.End(u.preparer.Prepare())
62
+ if err != nil {
63
+ return bosherr.WrapError(err, "Preparing")
64
+ }
65
+
66
+ task = stage.BeginTask("Draining")
67
+
68
+ err = task.End(u.drainer.Drain())
69
+ if err != nil {
70
+ return bosherr.WrapError(err, "Draining")
71
+ }
72
+
73
+ task = stage.BeginTask("Stopping")
74
+
75
+ err = task.End(u.stopper.Stop())
76
+ if err != nil {
77
+ return bosherr.WrapError(err, "Stopping")
78
+ }
79
+
80
+ task = stage.BeginTask("Applying")
81
+
82
+ err = task.End(u.applier.Apply())
83
+ if err != nil {
84
+ return bosherr.WrapError(err, "Applying")
85
+ }
86
+
87
+ task = stage.BeginTask("Starting")
88
+
89
+ err = task.End(u.starter.Start())
90
+ if err != nil {
91
+ return bosherr.WrapError(err, "Starting")
92
+ }
93
+
94
+ task = stage.BeginTask("Waiting")
95
+
96
+ err = task.End(u.waiter.Wait())
97
+ if err != nil {
98
+ return bosherr.WrapError(err, "Waiting")
99
+ }
100
+
101
+ return nil
102
+ }
@@ -0,0 +1,83 @@
1
+ package updater
2
+
3
+ import (
4
+ "fmt"
5
+ "time"
6
+
7
+ boshlog "bosh/logger"
8
+
9
+ bpagclient "boshprovisioner/agent/client"
10
+ bpdep "boshprovisioner/deployment"
11
+ bpeventlog "boshprovisioner/eventlog"
12
+ bptplcomp "boshprovisioner/instance/templatescompiler"
13
+ bpapplier "boshprovisioner/instance/updater/applier"
14
+ bppkgscomp "boshprovisioner/packagescompiler"
15
+ )
16
+
17
+ type UpdaterFactory struct {
18
+ templatesCompiler bptplcomp.TemplatesCompiler
19
+ packagesCompilerFactory bppkgscomp.ConcretePackagesCompilerFactory
20
+
21
+ eventLog bpeventlog.Log
22
+ logger boshlog.Logger
23
+ }
24
+
25
+ func NewUpdaterFactory(
26
+ templatesCompiler bptplcomp.TemplatesCompiler,
27
+ packagesCompilerFactory bppkgscomp.ConcretePackagesCompilerFactory,
28
+ eventLog bpeventlog.Log,
29
+ logger boshlog.Logger,
30
+ ) UpdaterFactory {
31
+ return UpdaterFactory{
32
+ templatesCompiler: templatesCompiler,
33
+ packagesCompilerFactory: packagesCompilerFactory,
34
+
35
+ eventLog: eventLog,
36
+ logger: logger,
37
+ }
38
+ }
39
+
40
+ func (f UpdaterFactory) NewUpdater(
41
+ agentClient bpagclient.Client,
42
+ depJob bpdep.Job,
43
+ instance bpdep.Instance,
44
+ ) Updater {
45
+ preparer := NewPreparer(agentClient, f.logger)
46
+
47
+ drainer := NewDrainer(agentClient, f.logger)
48
+
49
+ stopper := NewStopper(agentClient, f.logger)
50
+
51
+ applier := bpapplier.NewApplier(
52
+ depJob,
53
+ instance,
54
+ f.templatesCompiler,
55
+ f.packagesCompilerFactory.NewCompiler(agentClient),
56
+ agentClient,
57
+ f.logger,
58
+ )
59
+
60
+ starter := NewStarter(agentClient, f.logger)
61
+
62
+ waiter := NewWaiter(
63
+ instance.WatchTime.Start(),
64
+ instance.WatchTime.End(),
65
+ time.Sleep,
66
+ agentClient,
67
+ f.logger,
68
+ )
69
+
70
+ updater := NewUpdater(
71
+ fmt.Sprintf("%s/%d", instance.JobName, instance.Index),
72
+ preparer,
73
+ drainer,
74
+ stopper,
75
+ applier,
76
+ starter,
77
+ waiter,
78
+ f.eventLog,
79
+ f.logger,
80
+ )
81
+
82
+ return updater
83
+ }
@@ -0,0 +1,13 @@
1
+ package updater_test
2
+
3
+ import (
4
+ . "github.com/onsi/ginkgo"
5
+ . "github.com/onsi/gomega"
6
+
7
+ "testing"
8
+ )
9
+
10
+ func TestUpdater(t *testing.T) {
11
+ RegisterFailHandler(Fail)
12
+ RunSpecs(t, "Updater Suite")
13
+ }
@@ -0,0 +1,77 @@
1
+ package updater
2
+
3
+ import (
4
+ "time"
5
+
6
+ bosherr "bosh/errors"
7
+ boshlog "bosh/logger"
8
+
9
+ bpagclient "boshprovisioner/agent/client"
10
+ )
11
+
12
+ const waiterLogTag = "Waiter"
13
+
14
+ var (
15
+ ErrNotRunning = bosherr.New("Instance did not reach running state")
16
+ )
17
+
18
+ type Waiter struct {
19
+ watchSchedule []time.Duration
20
+ sleepFunc SleepFunc
21
+ agentClient bpagclient.Client
22
+ logger boshlog.Logger
23
+ }
24
+
25
+ type SleepFunc func(time.Duration)
26
+
27
+ func NewWaiter(
28
+ startWatchTime int,
29
+ endWatchTime int,
30
+ sleepFunc SleepFunc,
31
+ agentClient bpagclient.Client,
32
+ logger boshlog.Logger,
33
+ ) Waiter {
34
+ return Waiter{
35
+ watchSchedule: buildWatchSchedule(startWatchTime, endWatchTime),
36
+ sleepFunc: sleepFunc,
37
+ agentClient: agentClient,
38
+ logger: logger,
39
+ }
40
+ }
41
+
42
+ // Wait waits for an instance to reach running state.
43
+ // It polls agent based on a watch schedule and inspects its job state.
44
+ func (w Waiter) Wait() error {
45
+ w.logger.Debug(waiterLogTag, "Waiting for instance to reach running state")
46
+ w.logger.Debug(waiterLogTag, "Using schedule %v", w.watchSchedule)
47
+
48
+ for _, timeGap := range w.watchSchedule {
49
+ w.logger.Debug(waiterLogTag, "Sleeping for %v", timeGap)
50
+ w.sleepFunc(timeGap)
51
+
52
+ state, err := w.agentClient.GetState()
53
+ if err != nil {
54
+ return bosherr.WrapError(err, "Sending get_state")
55
+ }
56
+
57
+ // todo stopped state
58
+ if state.JobState == "running" {
59
+ return nil
60
+ }
61
+ }
62
+
63
+ return ErrNotRunning
64
+ }
65
+
66
+ // buildWatchSchedule returns list of millisecond interval
67
+ // at which instance should be checked for its running state.
68
+ // ([3000, 1000, 1000] =~ wait for 3000ms, then 1000ms, and 1000ms again)
69
+ func buildWatchSchedule(start, end int) []time.Duration {
70
+ timeGaps := []time.Duration{time.Duration(start) * time.Millisecond}
71
+
72
+ for total := start; total < end; total += 1000 {
73
+ timeGaps = append(timeGaps, 1000*time.Millisecond)
74
+ }
75
+
76
+ return timeGaps
77
+ }