Class: OsCtld::Container::RunConfiguration

Inherits:
Object
  • Object
show all
Includes:
OsCtl::Lib::Utils::File, OsCtl::Lib::Utils::Log, Lockable
Defined in:
lib/osctld/container/run_configuration.rb

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Lockable

#exclusively, included, #inclusively, #init_lock, #lock, #unlock

Constructor Details

#initialize(ct, load_conf: true) ⇒ RunConfiguration

Returns a new instance of RunConfiguration.

Parameters:



31
32
33
34
35
36
37
38
39
40
41
# File 'lib/osctld/container/run_configuration.rb', line 31

def initialize(ct, load_conf: true)
  init_lock
  @ct = ct
  @cpu_package = nil
  @init_pid = nil
  @aborted = false
  @do_reboot = false
  @exit_promise = Promise.new
  @dist_network_configured = false
  self.load_conf(from_file: load_conf)
end

Instance Attribute Details

#aborted=(value) ⇒ Object (writeonly)

Sets the attribute aborted

Parameters:

  • value

    the value to set the attribute aborted to.



138
139
140
# File 'lib/osctld/container/run_configuration.rb', line 138

def aborted=(value)
  @aborted = value
end

#archObject (readonly)

Returns the value of attribute arch



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def arch
  @arch
end

#cpu_packageObject

Returns the value of attribute cpu_package



27
28
29
# File 'lib/osctld/container/run_configuration.rb', line 27

def cpu_package
  @cpu_package
end

#ctContainer (readonly)

Returns:



24
25
26
# File 'lib/osctld/container/run_configuration.rb', line 24

def ct
  @ct
end

#datasetObject (readonly)

Returns the value of attribute dataset



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def dataset
  @dataset
end

#dist_network_configuredObject

Returns the value of attribute dist_network_configured



27
28
29
# File 'lib/osctld/container/run_configuration.rb', line 27

def dist_network_configured
  @dist_network_configured
end

#distributionObject (readonly)

Returns the value of attribute distribution



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def distribution
  @distribution
end

#init_pidObject

Returns the value of attribute init_pid



27
28
29
# File 'lib/osctld/container/run_configuration.rb', line 27

def init_pid
  @init_pid
end

#mountedObject (protected)

Returns the value of attribute mounted



242
243
244
# File 'lib/osctld/container/run_configuration.rb', line 242

def mounted
  @mounted
end

#run_idContainer::RunId (readonly)

Returns:



21
22
23
# File 'lib/osctld/container/run_configuration.rb', line 21

def run_id
  @run_id
end

#variantObject (readonly)

Returns the value of attribute variant



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def variant
  @variant
end

#vendorObject (readonly)

Returns the value of attribute vendor



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def vendor
  @vendor
end

#versionObject (readonly)

Returns the value of attribute version



26
27
28
# File 'lib/osctld/container/run_configuration.rb', line 26

def version
  @version
end

Class Method Details

.load(ct) ⇒ Object

Parameters:



11
12
13
14
15
16
17
18
# File 'lib/osctld/container/run_configuration.rb', line 11

def self.load(ct)
  ctrc = new(ct, load_conf: false)

  return unless ctrc.exist?

  ctrc.load_conf
  ctrc
end

Instance Method Details

#aborted?Boolean

Returns:

  • (Boolean)


140
141
142
# File 'lib/osctld/container/run_configuration.rb', line 140

def aborted?
  @aborted
end

#assets(add) ⇒ Object



43
44
45
46
47
48
49
50
51
52
# File 'lib/osctld/container/run_configuration.rb', line 43

def assets(add)
  add.file(
    file_path,
    desc: 'Container runtime configuration',
    user: 0,
    group: 0,
    mode: 0o400,
    optional: true
  )
end

#boot_from(dataset:, distribution:, version:, arch:, vendor:, variant:, destroy_dataset_on_stop: false) ⇒ Object

Set custom boot dataset



64
65
66
67
68
69
70
71
72
73
74
# File 'lib/osctld/container/run_configuration.rb', line 64

def boot_from(dataset:, distribution:, version:, arch:, vendor:, variant:, destroy_dataset_on_stop: false)
  exclusively do
    @dataset = dataset
    @distribution = distribution
    @version = version
    @arch = arch
    @vendor = vendor
    @variant = variant
    @destroy_dataset_on_stop = destroy_dataset_on_stop
  end
end

#destroyObject



234
235
236
237
238
# File 'lib/osctld/container/run_configuration.rb', line 234

def destroy
  File.unlink(file_path)
rescue Errno::ENOENT
  # ignore
end

#destroy_dataset_on_stop?Boolean

Returns:

  • (Boolean)


88
89
90
# File 'lib/osctld/container/run_configuration.rb', line 88

def destroy_dataset_on_stop?
  inclusively { @destroy_dataset_on_stop }
end

#dirString

Countainer dataset mountpoint

Returns:

  • (String)


94
95
96
# File 'lib/osctld/container/run_configuration.rb', line 94

def dir
  dataset.mountpoint
end

#dir_pathObject (protected)



244
245
246
# File 'lib/osctld/container/run_configuration.rb', line 244

def dir_path
  File.join(ct.pool.ct_dir, ct.id)
end

#dist_configure_network?Boolean

Returns:

  • (Boolean)


161
162
163
164
165
# File 'lib/osctld/container/run_configuration.rb', line 161

def dist_configure_network?
  inclusively do
    !dist_network_configured && can_dist_configure_network?
  end
end

#dumpObject



171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
# File 'lib/osctld/container/run_configuration.rb', line 171

def dump
  inclusively do
    {
      'id' => run_id.dump,
      'dataset' => dataset.to_s,
      'distribution' => distribution,
      'version' => version,
      'arch' => arch,
      'vendor' => vendor,
      'variant' => variant,
      'cpu_package' => cpu_package,
      'destroy_dataset_on_stop' => destroy_dataset_on_stop?
    }
  end
end

#exist?Boolean

Returns:

  • (Boolean)


167
168
169
# File 'lib/osctld/container/run_configuration.rb', line 167

def exist?
  File.exist?(file_path)
end

#file_pathObject (protected)



248
249
250
# File 'lib/osctld/container/run_configuration.rb', line 248

def file_path
  File.join(dir_path, 'config.yml')
end

#fulfil_exitObject



157
158
159
# File 'lib/osctld/container/run_configuration.rb', line 157

def fulfil_exit
  @exit_promise.fulfil
end

#get_exit_promiseObject



153
154
155
# File 'lib/osctld/container/run_configuration.rb', line 153

def get_exit_promise
  @exit_promise.add
end

#load_conf(from_file: true) ⇒ Object



187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
# File 'lib/osctld/container/run_configuration.rb', line 187

def load_conf(from_file: true)
  cfg =
    if from_file && File.exist?(file_path)
      OsCtl::Lib::ConfigFile.load_yaml_file(file_path)
    else
      {}
    end

  @run_id =
    if cfg.has_key?('id')
      Container::RunId.load(cfg['id'])
    else
      Container::RunId.new(pool_name: pool.name, container_id: id)
    end
  @dataset =
    if cfg['dataset']
      OsCtl::Lib::Zfs::Dataset.new(cfg['dataset'], base: cfg['dataset'])
    else
      ct.dataset
    end
  @distribution = cfg['distribution'] || ct.distribution
  @version = cfg['version'] || ct.version
  @arch = cfg['arch'] || ct.arch
  @vendor = cfg['vendor'] || ct.vendor
  @variant = cfg['variant'] || ct.variant
  @cpu_package = cfg['cpu_package']
  @destroy_dataset_on_stop =
    if cfg.has_key?('destroy_dataset_on_stop')
      cfg['destroy_dataset_on_stop']
    else
      false
    end
  nil
end

#mount(force: false) ⇒ Object

Mount the container’s dataset

Parameters:

  • force (Boolean) (defaults to: false)

    ensure the datasets are mounted even if osctld already mounted them



111
112
113
114
115
116
117
118
# File 'lib/osctld/container/run_configuration.rb', line 111

def mount(force: false)
  return if !force && mounted

  ct.mount
  dataset.mount(recursive: true) if ct.dataset.name != dataset.name

  self.mounted = true
end

#mounted?(force: false) ⇒ Boolean

Check if the container’s dataset is mounted

Parameters:

  • force (Boolean) (defaults to: false)

    check if the dataset is mounted even if osctld already mounted it

Returns:

  • (Boolean)


123
124
125
126
127
128
129
# File 'lib/osctld/container/run_configuration.rb', line 123

def mounted?(force: false)
  if force || mounted.nil?
    self.mounted = dataset.mounted?(recursive: true)
  else
    mounted
  end
end

#reboot?Boolean

Returns:

  • (Boolean)


149
150
151
# File 'lib/osctld/container/run_configuration.rb', line 149

def reboot?
  @do_reboot
end

#request_rebootObject

After the current container run stops, start it again



145
146
147
# File 'lib/osctld/container/run_configuration.rb', line 145

def request_reboot
  @do_reboot = true
end

#rootfsString

Container rootfs path

Returns:

  • (String)


100
101
102
103
104
105
106
# File 'lib/osctld/container/run_configuration.rb', line 100

def rootfs
  File.join(dir, 'private')
rescue SystemCommandFailed
  # Dataset for staged containers does not have to exist yet, relevant
  # primarily for ct show/list
  nil
end

#runtime_rootfsObject



131
132
133
134
135
136
# File 'lib/osctld/container/run_configuration.rb', line 131

def runtime_rootfs
  pid = init_pid
  raise 'init_pid not set' unless pid

  File.join('/proc', pid.to_s, 'root')
end

#saveObject



222
223
224
225
226
227
228
229
230
231
232
# File 'lib/osctld/container/run_configuration.rb', line 222

def save
  begin
    Dir.mkdir(dir_path)
  rescue Errno::EEXIST
    # ignore
  end

  regenerate_file(file_path, 0o400) do |new|
    new.write(OsCtl::Lib::ConfigFile.dump_yaml(dump))
  end
end

#set_distribution(distribution:, version:, arch:, vendor:, variant:) ⇒ Object

Update distribution info



77
78
79
80
81
82
83
84
85
86
# File 'lib/osctld/container/run_configuration.rb', line 77

def set_distribution(distribution:, version:, arch:, vendor:, variant:)
  exclusively do
    @distribution = distribution
    @version = version
    @arch = arch
    @vendor = vendor
    @variant = variant
    save
  end
end