Class: Pvectl::Presenters::Vm

Inherits:
Base
  • Object
show all
Defined in:
lib/pvectl/presenters/vm.rb

Overview

Presenter for QEMU virtual machines.

Defines column layout and formatting for table output. Used by formatters to render VM data in various formats.

Standard columns: NAME, VMID, STATUS, NODE, CPU, MEMORY Wide columns add: UPTIME, TEMPLATE, TAGS, DISK, IP, AGENT, HA, BACKUP

Examples:

Using with formatter

presenter = Vm.new
formatter = Formatters::Table.new
output = formatter.format(vms, presenter)

See Also:

Direct Known Subclasses

TopVm

Instance Method Summary collapse

Methods inherited from Base

#tags_array, #tags_display, #template_display, #to_wide_row, #uptime_human, #wide_columns

Instance Method Details

#columnsArray<String>

Returns column headers for standard table output.

Returns:

  • (Array<String>)

    column headers



27
28
29
# File 'lib/pvectl/presenters/vm.rb', line 27

def columns
  %w[NAME VMID STATUS NODE CPU MEMORY]
end

#cpu_percentString

Returns CPU usage as percentage string.

For running VMs, shows actual usage percentage. For stopped VMs, shows “-” for usage but includes core count if available.

Returns:

  • (String)

    CPU percentage (e.g., “12%”) or “-/4” for stopped VMs



179
180
181
182
183
184
185
# File 'lib/pvectl/presenters/vm.rb', line 179

def cpu_percent
  return "-" if vm.maxcpu.nil?
  return "-/#{vm.maxcpu}" unless vm.running?
  return "-/#{vm.maxcpu}" if vm.cpu.nil?

  "#{(vm.cpu * 100).round}%/#{vm.maxcpu}"
end

#disk_displayString

Returns disk formatted as “used/total GB”.

Returns:

  • (String)

    formatted disk (e.g., “15/50 GB”) or “-” if unavailable



240
241
242
243
244
# File 'lib/pvectl/presenters/vm.rb', line 240

def disk_display
  return "-" if disk_used_gb.nil?

  "#{disk_used_gb}/#{disk_total_gb} GB"
end

#disk_total_gbInteger?

Returns total disk in GB.

Returns:

  • (Integer, nil)

    total disk in GB, or nil if unavailable



231
232
233
234
235
# File 'lib/pvectl/presenters/vm.rb', line 231

def disk_total_gb
  return nil if vm.maxdisk.nil?

  (vm.maxdisk.to_f / 1024 / 1024 / 1024).round
end

#disk_used_gbInteger?

Returns disk used in GB.

Returns:

  • (Integer, nil)

    disk used in GB, or nil if unavailable



222
223
224
225
226
# File 'lib/pvectl/presenters/vm.rb', line 222

def disk_used_gb
  return nil if vm.disk.nil?

  (vm.disk.to_f / 1024 / 1024 / 1024).round
end

#display_nameString

Returns display name, falling back to “VM-vmid” if name is nil.

Returns:

  • (String)

    display name



169
170
171
# File 'lib/pvectl/presenters/vm.rb', line 169

def display_name
  vm.name || "VM-#{vm.vmid}"
end

#extra_columnsArray<String>

Returns additional column headers for wide output.

Returns:

  • (Array<String>)

    extra column headers



34
35
36
# File 'lib/pvectl/presenters/vm.rb', line 34

def extra_columns
  %w[UPTIME TEMPLATE TAGS DISK IP AGENT HA BACKUP]
end

#extra_values(model, **_context) ⇒ Array<String>

Returns additional values for wide output.

Note: IP, AGENT, and BACKUP are placeholders for future implementation that would require additional API calls to the QEMU guest agent.

Parameters:

  • model (Models::Vm)

    VM model

  • context (Hash)

    optional context

Returns:

  • (Array<String>)

    extra values matching extra_columns order



63
64
65
66
67
68
69
70
71
72
73
74
75
# File 'lib/pvectl/presenters/vm.rb', line 63

def extra_values(model, **_context)
  @vm = model
  [
    uptime_human,
    template_display,
    tags_display,
    disk_display,
    "-",              # IP - requires QEMU agent (future enhancement)
    "-",              # AGENT status (future enhancement)
    vm.hastate || "-",
    "-"               # BACKUP schedule (future enhancement)
  ]
end

#memory_displayString

Returns memory formatted as “used/total GB”.

For running VMs, shows actual usage and total. For stopped VMs, shows “-” for usage but includes total if available.

Returns:

  • (String)

    formatted memory (e.g., “2.1/4.0 GB”) or “-/4.0 GB” for stopped VMs



211
212
213
214
215
216
217
# File 'lib/pvectl/presenters/vm.rb', line 211

def memory_display
  return "-" if memory_total_gb.nil?
  return "-/#{memory_total_gb} GB" unless vm.running?
  return "-/#{memory_total_gb} GB" if memory_used_gb.nil?

  "#{memory_used_gb}/#{memory_total_gb} GB"
end

#memory_total_gbFloat?

Returns total memory in GB.

Returns:

  • (Float, nil)

    total memory in GB, or nil if unavailable



199
200
201
202
203
# File 'lib/pvectl/presenters/vm.rb', line 199

def memory_total_gb
  return nil if vm.maxmem.nil?

  (vm.maxmem.to_f / 1024 / 1024 / 1024).round(1)
end

#memory_used_gbFloat?

Returns memory used in GB.

Returns:

  • (Float, nil)

    memory used in GB, or nil if unavailable



190
191
192
193
194
# File 'lib/pvectl/presenters/vm.rb', line 190

def memory_used_gb
  return nil if vm.mem.nil?

  (vm.mem.to_f / 1024 / 1024 / 1024).round(1)
end

#to_description(model) ⇒ Hash

Converts VM model to description format for describe command.

Returns a structured Hash organized by Proxmox VE web UI tabs: Summary, Hardware, Cloud-Init, Options, Task History, Snapshots, Pending Changes. Nested Hashes create indented subsections. Arrays of Hashes render as inline tables.

Parameters:

  • model (Models::Vm)

    VM model with describe details

Returns:

  • (Hash)

    structured hash for describe formatter



132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
# File 'lib/pvectl/presenters/vm.rb', line 132

def to_description(model)
  @vm = model
  @consumed_keys = Set.new
  data = vm.describe_data || {}
  config = data[:config] || {}
  status = data[:status] || {}

  consume(:name, :description, :tags, :pool, :template)

  {
    "Name" => display_name,
    "VMID" => vm.vmid,
    "Status" => vm.status,
    "Node" => vm.node,
    "Tags" => tags_display,
    "Description" => config[:description] || "-",
    "Summary" => format_summary(config, status),
    "Block Device Statistics" => format_blockstat(status),
    "Hardware" => format_hardware(config, data),
    "Cloud-Init" => format_cloud_init(config),
    "Options" => format_options(config),
    "Firewall" => format_firewall(data[:firewall]),
    "Firewall Rules" => format_firewall_rules(data[:firewall]),
    "Task History" => format_task_history(data[:tasks]),
    "Snapshots" => format_snapshots(data[:snapshots]),
    "Pending Changes" => format_pending_changes(data[:pending]),
    "Additional Configuration" => format_remaining(config)
  }
end

#to_hash(model) ⇒ Hash

Converts VM model to hash for JSON/YAML output.

Returns a structured hash with nested objects for complex data like CPU, memory, disk, uptime, and network.

Parameters:

Returns:

  • (Hash)

    hash representation with string keys



84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
# File 'lib/pvectl/presenters/vm.rb', line 84

def to_hash(model)
  @vm = model
  {
    "vmid" => vm.vmid,
    "name" => vm.name,
    "status" => vm.status,
    "node" => vm.node,
    "template" => vm.template?,
    "cpu" => {
      "usage_percent" => vm.cpu.nil? ? nil : (vm.cpu * 100).round,
      "cores" => vm.maxcpu
    },
    "memory" => {
      "used_gb" => memory_used_gb,
      "total_gb" => memory_total_gb,
      "used_bytes" => vm.mem,
      "total_bytes" => vm.maxmem
    },
    "disk" => {
      "used_gb" => disk_used_gb,
      "total_gb" => disk_total_gb,
      "used_bytes" => vm.disk,
      "total_bytes" => vm.maxdisk
    },
    "uptime" => {
      "seconds" => vm.uptime,
      "human" => uptime_human
    },
    "network" => {
      "in_bytes" => vm.netin,
      "out_bytes" => vm.netout
    },
    "ha" => {
      "state" => vm.hastate
    },
    "tags" => tags_array
  }
end

#to_row(model, **_context) ⇒ Array<String>

Converts VM model to table row values.

Parameters:

  • model (Models::Vm)

    VM model

  • context (Hash)

    optional context

Returns:

  • (Array<String>)

    row values matching columns order



43
44
45
46
47
48
49
50
51
52
53
# File 'lib/pvectl/presenters/vm.rb', line 43

def to_row(model, **_context)
  @vm = model
  [
    display_name,
    vm.vmid.to_s,
    vm.status,
    vm.node,
    cpu_percent,
    memory_display
  ]
end