hetznercloud 1.0.0

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 (47) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +5 -0
  3. data/Gemfile +6 -0
  4. data/LICENSE.md +21 -0
  5. data/README.md +123 -0
  6. data/config/inflections.rb +19 -0
  7. data/lib/core_ext/send_wrap.rb +15 -0
  8. data/lib/hcloud/action_collection.rb +37 -0
  9. data/lib/hcloud/client.rb +38 -0
  10. data/lib/hcloud/collection.rb +77 -0
  11. data/lib/hcloud/concerns/actionable.rb +29 -0
  12. data/lib/hcloud/concerns/concerns.rb +29 -0
  13. data/lib/hcloud/concerns/creatable.rb +46 -0
  14. data/lib/hcloud/concerns/deletable.rb +20 -0
  15. data/lib/hcloud/concerns/queryable.rb +41 -0
  16. data/lib/hcloud/concerns/updatable.rb +24 -0
  17. data/lib/hcloud/entities/amount.rb +8 -0
  18. data/lib/hcloud/entities/applied_to.rb +7 -0
  19. data/lib/hcloud/entities/applied_to_resource.rb +9 -0
  20. data/lib/hcloud/entities/apply_to.rb +15 -0
  21. data/lib/hcloud/entities/datacenter_server_type.rb +9 -0
  22. data/lib/hcloud/entities/dns_pointer.rb +8 -0
  23. data/lib/hcloud/entities/error.rb +8 -0
  24. data/lib/hcloud/entities/metrics.rb +12 -0
  25. data/lib/hcloud/entities/price.rb +9 -0
  26. data/lib/hcloud/entities/protection.rb +11 -0
  27. data/lib/hcloud/entities/rule.rb +15 -0
  28. data/lib/hcloud/entity.rb +23 -0
  29. data/lib/hcloud/errors.rb +36 -0
  30. data/lib/hcloud/http.rb +100 -0
  31. data/lib/hcloud/resource.rb +42 -0
  32. data/lib/hcloud/resource_type.rb +73 -0
  33. data/lib/hcloud/resources/action.rb +49 -0
  34. data/lib/hcloud/resources/datacenter.rb +43 -0
  35. data/lib/hcloud/resources/firewall.rb +80 -0
  36. data/lib/hcloud/resources/floating_ip.rb +144 -0
  37. data/lib/hcloud/resources/image.rb +140 -0
  38. data/lib/hcloud/resources/iso.rb +36 -0
  39. data/lib/hcloud/resources/location.rb +37 -0
  40. data/lib/hcloud/resources/placement_group.rb +75 -0
  41. data/lib/hcloud/resources/server.rb +179 -0
  42. data/lib/hcloud/resources/server_type.rb +42 -0
  43. data/lib/hcloud/resources/ssh_key.rb +77 -0
  44. data/lib/hcloud/resources/volume.rb +147 -0
  45. data/lib/hcloud/version.rb +17 -0
  46. data/lib/hcloud.rb +42 -0
  47. metadata +286 -0
@@ -0,0 +1,140 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a image
6
+ #
7
+ # == List all images
8
+ #
9
+ # HCloud::Image.all
10
+ # # => [#<HCloud::Image id: 1, ...>, ...]
11
+ #
12
+ # == Sort images
13
+ #
14
+ # HCloud::Image.all.sort(name: :desc)
15
+ # # => [#<HCloud::Image id: 1, ...>, ...]
16
+ #
17
+ # HCloud::Image.all.sort(:id, name: :asc)
18
+ # # => [#<HCloud::Image id: 1, ...>, ...]
19
+ #
20
+ # == Search images
21
+ #
22
+ # HCloud::Image.all.where(name: "my_image")
23
+ # # => #<HCloud::Image id: 1, ...>
24
+ #
25
+ # HCloud::Image.all.where(status: "available", include_deprecated: false)
26
+ # # => #<HCloud::Image id: 1, ...>
27
+ #
28
+ # HCloud::Image.all.where(type: "backup", bound_to: 1)
29
+ # # => #<HCloud::Image id: 1, ...>
30
+ #
31
+ # == Find image by ID
32
+ #
33
+ # HCloud::Image.find(1)
34
+ # # => #<HCloud::Image id: 1, ...>
35
+ #
36
+ # == Update image
37
+ #
38
+ # image = HCloud::Image.find(1)
39
+ # image.type = "snapshot"
40
+ # image.description = "#{image.description} (snapshot)"
41
+ # image.update
42
+ #
43
+ # == Delete image
44
+ #
45
+ # image = HCloud::Image.find(1)
46
+ # image.delete
47
+ # image.deleted?
48
+ # # => true
49
+ #
50
+ # = Actions
51
+ # == List actions
52
+ #
53
+ # actions = HCloud::Image.find(1).actions
54
+ # # => [#<HCloud::Action id: 1, ...>, ...]
55
+ #
56
+ # == Sort actions
57
+ #
58
+ # HCloud::Image.find(1).actions.sort(finished: :desc)
59
+ # # => [#<HCloud::Action id: 1, ...>, ...]
60
+ #
61
+ # HCloud::Image.find(1).actions.sort(:command, finished: :asc)
62
+ # # => [#<HCloud::Actions id: 1, ...>, ...]
63
+ #
64
+ # == Search actions
65
+ #
66
+ # HCloud::Image.find(1).actions.where(command: "change_protection")
67
+ # # => #<HCloud::Action id: 1, ...>
68
+ #
69
+ # HCloud::Image.find(1).actions.where(status: "success")
70
+ # # => #<HCloud::Action id: 1, ...>
71
+ #
72
+ # == Find action by ID
73
+ #
74
+ # HCloud::Image.find(1).actions.find(1)
75
+ # # => #<HCloud::Action id: 1, ...>
76
+ #
77
+ # = Image-specific actions
78
+ # == Change protection
79
+ #
80
+ # HCloud::Image.find(1).change_protection(delete: true)
81
+ # # => #<HCloud::Action id: 1, ...>
82
+ #
83
+ class Image < Resource
84
+ actionable
85
+ queryable
86
+ updatable
87
+ deletable
88
+
89
+ attribute :id, :integer
90
+ attribute :name
91
+ attribute :description
92
+
93
+ attribute :type
94
+ attribute :status
95
+
96
+ attribute :build_id
97
+
98
+ attribute :disk_size, :integer
99
+ attribute :image_size, :integer
100
+
101
+ attribute :os_flavor
102
+ attribute :os_version
103
+
104
+ attribute :protection, :protection
105
+
106
+ attribute :bound_to, :server
107
+ attribute :created_from, :server
108
+
109
+ # Explicitly specify created attribute, because resource is not Creatable
110
+ attribute :created, :datetime
111
+ attribute :deleted, :datetime
112
+ attribute :deprecated, :datetime
113
+
114
+ attribute :rapid_deploy
115
+
116
+ attribute :labels, default: -> { {} }
117
+
118
+ action :change_protection
119
+
120
+ def created?
121
+ created.present?
122
+ end
123
+
124
+ def deleted?
125
+ deleted.present?
126
+ end
127
+
128
+ def deprecated?
129
+ deprecated.present?
130
+ end
131
+
132
+ def rapid_deploy?
133
+ rapid_deploy.present?
134
+ end
135
+
136
+ def updatable_attributes
137
+ [:description, :type, :labels]
138
+ end
139
+ end
140
+ end
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents an ISO image
6
+ #
7
+ # == List all ISOs
8
+ #
9
+ # HCloud::ISO.all
10
+ # # => [#<HCloud::ISO id: 7631, ...>, ...]
11
+ #
12
+ # == Search ISOs
13
+ #
14
+ # HCloud::ISO.all.where(name: "debian-10.10.0-amd64-netinst.iso")
15
+ # # => #<HCloud::ISO id: 7631, ...>
16
+ #
17
+ # == Find ISO by ID
18
+ #
19
+ # HCloud::ISO.find(1)
20
+ # # => #<HCloud::ISO id: 7631, ...>
21
+ #
22
+ class ISO < Resource
23
+ queryable
24
+
25
+ attribute :id, :integer
26
+ attribute :name
27
+ attribute :description
28
+
29
+ attribute :type
30
+ attribute :deprecated, :datetime
31
+
32
+ def deprecated?
33
+ deprecated.present?
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a location
6
+ #
7
+ # == List all locations
8
+ #
9
+ # HCloud::Location.all
10
+ # # => [#<HCloud::Location id: 1, ...>, ...]
11
+ #
12
+ # == Search locations
13
+ #
14
+ # HCloud::Location.all.where(name: "fsn1")
15
+ # # => #<HCloud::Location id: 1, ...>
16
+ #
17
+ # == Find location by ID
18
+ #
19
+ # HCloud::Location.find(1)
20
+ # # => #<HCloud::Location id: 1, ...>
21
+ #
22
+ class Location < Resource
23
+ queryable
24
+
25
+ attribute :id, :integer
26
+ attribute :name
27
+ attribute :description
28
+
29
+ attribute :network_zone
30
+
31
+ attribute :city
32
+ attribute :country
33
+
34
+ attribute :latitude, :decimal
35
+ attribute :longitude, :decimal
36
+ end
37
+ end
@@ -0,0 +1,75 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a placement group
6
+ #
7
+ # == List all placement group
8
+ #
9
+ # HCloud::PlacementGroup.all
10
+ # # => [#<HCloud::PlacementGroup id: 2, ...>, ...]
11
+ #
12
+ # == Sort placement groups
13
+ #
14
+ # HCloud::PlacementGroup.all.sort(name: :desc)
15
+ # # => [#<HCloud::PlacementGroup id: 1, ...>, ...]
16
+ #
17
+ # HCloud::PlacementGroup.all.sort(:id, name: :asc)
18
+ # # => [#<HCloud::PlacementGroup id: 1, ...>, ...]
19
+ #
20
+ # == Search placement groups
21
+ #
22
+ # HCloud::PlacementGroup.all.where(name: "my_placement_group")
23
+ # # => #<HCloud::PlacementGroup id: 2, ...>
24
+ #
25
+ # == Find placement group by ID
26
+ #
27
+ # HCloud::PlacementGroup.find(2)
28
+ # # => #<HCloud::PlacementGroup id: 2, ...>
29
+ #
30
+ # == Create placement group
31
+ #
32
+ # placement_group = HCloud::PlacementGroup.new(name: "my_placement_group", type: "spread")
33
+ # placement_group.create
34
+ # placement_group.created?
35
+ # # => true
36
+ #
37
+ # firewall = HCloud::PlacementGroup.create(name: "my_placement_group")
38
+ # # => #<HCloud::PlacementGroup id: 1, ...>
39
+ #
40
+ # == Update placement group
41
+ #
42
+ # placement_group = HCloud::PlacementGroup.find(1)
43
+ # placement_group.name = "another_placement_group"
44
+ # placement_group.update
45
+ #
46
+ # == Delete placement group
47
+ #
48
+ # placement_group = HCloud::PlacementGroup.find(1)
49
+ # placement_group.delete
50
+ # placement_group.deleted?
51
+ # # => true
52
+ #
53
+ class PlacementGroup < Resource
54
+ queryable
55
+ creatable
56
+ updatable
57
+ deletable
58
+
59
+ attribute :id, :integer
60
+ attribute :name
61
+ attribute :type
62
+
63
+ attribute :servers, :server, array: true, default: -> { [] }
64
+
65
+ attribute :labels, default: -> { {} }
66
+
67
+ def creatable_attributes
68
+ [:name, :type, :labels]
69
+ end
70
+
71
+ def updatable_attributes
72
+ [:name, :labels]
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,179 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a server
6
+ #
7
+ # == List all servers
8
+ #
9
+ # HCloud::Server.all
10
+ # # => [#<HCloud::Server id: 1, ...>, ...]
11
+ #
12
+ # == Sort servers
13
+ #
14
+ # HCloud::Server.all.sort(name: :desc)
15
+ # # => [#<HCloud::Server id: 1, ...>, ...]
16
+ #
17
+ # HCloud::Server.all.sort(:id, name: :asc)
18
+ # # => [#<HCloud::Server id: 1, ...>, ...]
19
+ #
20
+ # == Search servers
21
+ #
22
+ # HCloud::Server.all.where(name: "my_server")
23
+ # # => #<HCloud::Server id: 1, ...>
24
+ #
25
+ # HCloud::Server.all.where(status: "running")
26
+ # # => #<HCloud::Server id: 1, ...>
27
+ #
28
+ # == Find server by ID
29
+ #
30
+ # HCloud::Server.find(1)
31
+ # # => #<HCloud::Server id: 1, ...>
32
+ #
33
+ # == Create server
34
+ #
35
+ # user_data = File.read("user_data.yml")
36
+ # server = HCloud::Server.new(name: "my_server", image: "debian-11", server_type: "cx11")
37
+ # server.create
38
+ # server.created?
39
+ # # => true
40
+ #
41
+ # firewall = HCloud::Server.create(name: "my_server", image: "debian-11", server_type: "cx11")
42
+ # # => #<HCloud::Server id: 1, ...>
43
+ #
44
+ # == Update server
45
+ #
46
+ # server = HCloud::Server.find(1)
47
+ # server.name = "another_server"
48
+ # server.update
49
+ #
50
+ # == Delete server
51
+ #
52
+ # server = HCloud::Server.find(1)
53
+ # server.delete
54
+ # server.deleted?
55
+ # # => true
56
+ #
57
+ # == Get metrics
58
+ #
59
+ # server = HCloud::Server.find(1)
60
+ # server.metrics(type: :cpu, from: 2.minutes.ago, to: 1.minute.ago)
61
+ # # => #<HCloud::Metrics ...>
62
+ #
63
+ # server.metrics(type: [:cpu, :disk, :network], from: 2.minutes.ago, to: 1.minute.ago, step: 60)
64
+ # # => #<HCloud::Metrics ...>
65
+ #
66
+ # TODO: actions
67
+ # TODO: return root_password if ssh_keys is empty
68
+ #
69
+ class Server < Resource
70
+ actionable
71
+ queryable
72
+ creatable
73
+ updatable
74
+ deletable
75
+
76
+ attribute :id, :integer
77
+ attribute :name
78
+
79
+ attribute :server_type, :server_type
80
+
81
+ attribute :status
82
+
83
+ attribute :backup_window
84
+
85
+ # TODO: use only for creation
86
+ attribute :location, :location
87
+
88
+ # TODO: use only for creation
89
+ attribute :ssh_keys, :ssh_key, array: true, default: -> { [] }
90
+
91
+ # TODO: use only for creation
92
+ attribute :firewalls, array: true, default: -> { [] }
93
+
94
+ # TODO: use only for creation
95
+ attribute :networks, array: true, default: -> { [] }
96
+
97
+ attribute :datacenter, :datacenter
98
+
99
+ attribute :included_traffic, :integer
100
+ attribute :ingoing_traffic, :integer
101
+ attribute :outgoing_traffic, :integer
102
+
103
+ attribute :primary_disk_size, :integer
104
+
105
+ attribute :protection, :protection
106
+
107
+ attribute :image, :image
108
+
109
+ # TODO: network resource
110
+ attribute :public_net
111
+ attribute :private_net
112
+
113
+ attribute :placement_group, :placement_group
114
+
115
+ attribute :iso, :iso
116
+
117
+ attribute :labels, default: -> { {} }
118
+
119
+ # TODO: load balancer resource
120
+ attribute :load_balancers, array: true, default: -> { [] }
121
+
122
+ attribute :volumes, :volume, array: true, default: -> { [] }
123
+
124
+ attribute :locked
125
+ attribute :rescue_enabled
126
+
127
+ alias rescue_enabled? rescue_enabled
128
+
129
+ alias locked? locked
130
+
131
+ action :add_to_placement_group
132
+ action :remove_from_placement_group
133
+
134
+ action :attach_iso
135
+ action :detach_iso
136
+
137
+ action :attach_to_network
138
+ action :detach_from_network
139
+
140
+ action :change_alias_ips
141
+ action :change_dns_ptr
142
+
143
+ action :change_protection
144
+ action :change_type
145
+ action :create_image
146
+
147
+ action :enable_backup
148
+ action :disable_backup
149
+
150
+ action :enable_rescue
151
+ action :disable_rescue
152
+
153
+ action :poweron
154
+ action :poweroff
155
+ action :reboot
156
+ action :reset
157
+ action :shutdown
158
+
159
+ action :reset_password
160
+
161
+ action :rebuild
162
+
163
+ action :request_console
164
+
165
+ def metrics(type:, from:, to:, step: nil)
166
+ Metrics.new client
167
+ .get("/servers/#{id}/metrics", type: Array(type).join(","), start: from.iso8601, end: to.iso8601, step: step)
168
+ .fetch(:metrics)
169
+ end
170
+
171
+ def creatable_attributes
172
+ [:name, :automount, :start_after_create, :user_data, :labels, datacenter: [:id, :name], image: [:id, :name], location: [:id, :name], server_type: [:id, :name], ssh_keys: [:id, :name], firewalls: :id, networks: :id, volumes: :id]
173
+ end
174
+
175
+ def updatable_attributes
176
+ [:name, :labels]
177
+ end
178
+ end
179
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a server type
6
+ #
7
+ # == List all server types
8
+ #
9
+ # HCloud::ServerType.all
10
+ # # => [#<HCloud::ServerType id: 1, ...>, ...]
11
+ #
12
+ # == Search server types
13
+ #
14
+ # HCloud::ServerType.all.where(name: "cx11")
15
+ # # => #<HCloud::ServerType id: 1, ...>
16
+ #
17
+ # == Find server type by ID
18
+ #
19
+ # HCloud::ServerType.find(1)
20
+ # # => #<HCloud::ServerType id: 1, ...>
21
+ #
22
+ class ServerType < Resource
23
+ queryable
24
+
25
+ attribute :id, :integer
26
+ attribute :name
27
+ attribute :description
28
+
29
+ attribute :cores, :integer
30
+ attribute :disk, :integer
31
+ attribute :memory, :integer
32
+
33
+ attribute :cpu_type
34
+ attribute :storage_type
35
+
36
+ attribute :prices, :price, array: true, default: -> { [] }
37
+
38
+ attribute :deprecated, :boolean
39
+
40
+ alias deprecated? deprecated
41
+ end
42
+ end
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+
3
+ module HCloud
4
+ ##
5
+ # Represents a SSH key
6
+ #
7
+ # == List all SSH keys
8
+ #
9
+ # HCloud::SSHKey.all
10
+ # # => [#<HCloud::SSHKey id: 1, ...>, ...]
11
+ #
12
+ # == Sort SSH keys
13
+ #
14
+ # HCloud::SSHKey.all.sort(name: :desc)
15
+ # # => [#<HCloud::SSHKey id: 1, ...>, ...]
16
+ #
17
+ # HCloud::SSHKey.all.sort(:id, name: :asc)
18
+ # # => [#<HCloud::SSHKey id: 1, ...>, ...]
19
+ #
20
+ # == Search SSH keys
21
+ #
22
+ # HCloud::SSHKey.all.where(name: "cx11")
23
+ # # => #<HCloud::SSHKey id: 1, ...>
24
+ #
25
+ # HCloud::SSHKey.all.where(fingerprint: "B6:6C:CD:DA:A2:24:43:39:98:80:0F:F5:51:17:7E")
26
+ # # => #<HCloud::SSHKey id: 1, ...>
27
+ #
28
+ # == Find SSH key by ID
29
+ #
30
+ # HCloud::SSHKey.find(1)
31
+ # # => #<HCloud::SSHKey id: 1, ...>
32
+ #
33
+ # == Create SSH key
34
+ #
35
+ # ssh_key = HCloud::SSHKey.new(name: "my_ssh_key", public_key: File.read("id_rsa.pub"))
36
+ # ssh_key.create
37
+ # ssh_key.created?
38
+ # # => true
39
+ #
40
+ # firewall = HCloud::SSHKey.create(name: "my_ssh_key", public_key: File.read("id_rsa.pub"))
41
+ # # => #<HCloud::SSHKey id: 1, ...>
42
+ #
43
+ # == Update SSH key
44
+ #
45
+ # ssh_key = HCloud::SSHKey.find(1)
46
+ # ssh_key.name = "another_ssh_key"
47
+ # ssh_key.update
48
+ #
49
+ # == Delete SSH key
50
+ #
51
+ # ssh_key = HCloud::SSHKey.find(1)
52
+ # ssh_key.delete
53
+ # ssh_key.deleted?
54
+ # # => true
55
+ #
56
+ class SSHKey < Resource
57
+ queryable
58
+ creatable
59
+ updatable
60
+ deletable
61
+
62
+ attribute :id, :integer
63
+ attribute :name
64
+ attribute :public_key
65
+ attribute :fingerprint
66
+
67
+ attribute :labels, default: -> { {} }
68
+
69
+ def creatable_attributes
70
+ [:name, :public_key, :labels]
71
+ end
72
+
73
+ def updatable_attributes
74
+ [:name, :labels]
75
+ end
76
+ end
77
+ end