pvectl 0.2.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 (558) hide show
  1. checksums.yaml +7 -0
  2. data/.claude/rules/branch-before-changes.md +52 -0
  3. data/.claude/rules/documentation-updates.md +104 -0
  4. data/.claude/rules/git-workflow.md +84 -0
  5. data/.claude/rules/proxmox-api-docs.md +58 -0
  6. data/.claude/rules/rbs-signatures.md +80 -0
  7. data/.claude/rules/refactoring-as-design-option.md +35 -0
  8. data/.claude/scheduled_tasks.lock +1 -0
  9. data/.claude/settings.json +51 -0
  10. data/.mcp.json +8 -0
  11. data/.ruby-gemset +1 -0
  12. data/.ruby-version +1 -0
  13. data/CHANGELOG.md +138 -0
  14. data/CLAUDE.md +211 -0
  15. data/CODE_OF_CONDUCT.md +132 -0
  16. data/LICENSE.txt +21 -0
  17. data/README.md +143 -0
  18. data/Rakefile +8 -0
  19. data/docs/proxmox-api-update.sh +96 -0
  20. data/exe/pvectl +5 -0
  21. data/lib/pvectl/argv_preprocessor.rb +334 -0
  22. data/lib/pvectl/cli.rb +102 -0
  23. data/lib/pvectl/commands/apt.rb +389 -0
  24. data/lib/pvectl/commands/clone_container.rb +230 -0
  25. data/lib/pvectl/commands/clone_vm.rb +331 -0
  26. data/lib/pvectl/commands/cloudinit/command.rb +122 -0
  27. data/lib/pvectl/commands/cloudinit/dump.rb +94 -0
  28. data/lib/pvectl/commands/cloudinit/pending.rb +137 -0
  29. data/lib/pvectl/commands/cloudinit/regenerate.rb +79 -0
  30. data/lib/pvectl/commands/config/command.rb +65 -0
  31. data/lib/pvectl/commands/config/get_contexts.rb +68 -0
  32. data/lib/pvectl/commands/config/set_cluster.rb +103 -0
  33. data/lib/pvectl/commands/config/set_context.rb +136 -0
  34. data/lib/pvectl/commands/config/set_credentials.rb +181 -0
  35. data/lib/pvectl/commands/config/use_context.rb +69 -0
  36. data/lib/pvectl/commands/config/view.rb +67 -0
  37. data/lib/pvectl/commands/console.rb +93 -0
  38. data/lib/pvectl/commands/console_ct.rb +187 -0
  39. data/lib/pvectl/commands/console_vm.rb +187 -0
  40. data/lib/pvectl/commands/container_lifecycle_command.rb +77 -0
  41. data/lib/pvectl/commands/create_backup.rb +173 -0
  42. data/lib/pvectl/commands/create_container.rb +141 -0
  43. data/lib/pvectl/commands/create_resource_command.rb +244 -0
  44. data/lib/pvectl/commands/create_snapshot.rb +242 -0
  45. data/lib/pvectl/commands/create_vm.rb +267 -0
  46. data/lib/pvectl/commands/delete_backup.rb +139 -0
  47. data/lib/pvectl/commands/delete_command.rb +119 -0
  48. data/lib/pvectl/commands/delete_container.rb +30 -0
  49. data/lib/pvectl/commands/delete_snapshot.rb +248 -0
  50. data/lib/pvectl/commands/delete_vm.rb +127 -0
  51. data/lib/pvectl/commands/describe/command.rb +251 -0
  52. data/lib/pvectl/commands/edit_container.rb +56 -0
  53. data/lib/pvectl/commands/edit_dns.rb +149 -0
  54. data/lib/pvectl/commands/edit_hosts.rb +135 -0
  55. data/lib/pvectl/commands/edit_node.rb +54 -0
  56. data/lib/pvectl/commands/edit_resource_command.rb +180 -0
  57. data/lib/pvectl/commands/edit_vm.rb +154 -0
  58. data/lib/pvectl/commands/edit_volume.rb +189 -0
  59. data/lib/pvectl/commands/feature_command.rb +230 -0
  60. data/lib/pvectl/commands/feature_container.rb +21 -0
  61. data/lib/pvectl/commands/feature_vm.rb +94 -0
  62. data/lib/pvectl/commands/get/command.rb +360 -0
  63. data/lib/pvectl/commands/get/handlers/backups.rb +76 -0
  64. data/lib/pvectl/commands/get/handlers/capabilities.rb +107 -0
  65. data/lib/pvectl/commands/get/handlers/containers.rb +148 -0
  66. data/lib/pvectl/commands/get/handlers/disks.rb +107 -0
  67. data/lib/pvectl/commands/get/handlers/dns.rb +94 -0
  68. data/lib/pvectl/commands/get/handlers/hosts.rb +94 -0
  69. data/lib/pvectl/commands/get/handlers/nodes.rb +162 -0
  70. data/lib/pvectl/commands/get/handlers/services.rb +81 -0
  71. data/lib/pvectl/commands/get/handlers/snapshots.rb +97 -0
  72. data/lib/pvectl/commands/get/handlers/storage.rb +118 -0
  73. data/lib/pvectl/commands/get/handlers/subscription.rb +69 -0
  74. data/lib/pvectl/commands/get/handlers/tasks.rb +89 -0
  75. data/lib/pvectl/commands/get/handlers/templates.rb +175 -0
  76. data/lib/pvectl/commands/get/handlers/time.rb +118 -0
  77. data/lib/pvectl/commands/get/handlers/vms.rb +145 -0
  78. data/lib/pvectl/commands/get/handlers/volume.rb +134 -0
  79. data/lib/pvectl/commands/get/resource_handler.rb +63 -0
  80. data/lib/pvectl/commands/get/resource_registry.rb +18 -0
  81. data/lib/pvectl/commands/get/watch_loop.rb +129 -0
  82. data/lib/pvectl/commands/irreversible_command.rb +265 -0
  83. data/lib/pvectl/commands/logs/command.rb +275 -0
  84. data/lib/pvectl/commands/logs/handlers/journal.rb +46 -0
  85. data/lib/pvectl/commands/logs/handlers/syslog.rb +53 -0
  86. data/lib/pvectl/commands/logs/handlers/task_detail.rb +52 -0
  87. data/lib/pvectl/commands/logs/handlers/task_logs.rb +115 -0
  88. data/lib/pvectl/commands/logs/resource_handler.rb +46 -0
  89. data/lib/pvectl/commands/logs/resource_registry.rb +22 -0
  90. data/lib/pvectl/commands/migrate_command.rb +282 -0
  91. data/lib/pvectl/commands/migrate_container.rb +23 -0
  92. data/lib/pvectl/commands/migrate_vm.rb +122 -0
  93. data/lib/pvectl/commands/move_disk_command.rb +239 -0
  94. data/lib/pvectl/commands/move_disk_container.rb +21 -0
  95. data/lib/pvectl/commands/move_disk_vm.rb +127 -0
  96. data/lib/pvectl/commands/ping.rb +249 -0
  97. data/lib/pvectl/commands/pull.rb +342 -0
  98. data/lib/pvectl/commands/push.rb +352 -0
  99. data/lib/pvectl/commands/reset.rb +64 -0
  100. data/lib/pvectl/commands/resource_lifecycle_command.rb +277 -0
  101. data/lib/pvectl/commands/resource_registry.rb +73 -0
  102. data/lib/pvectl/commands/restart.rb +70 -0
  103. data/lib/pvectl/commands/restart_container.rb +18 -0
  104. data/lib/pvectl/commands/restore_backup.rb +236 -0
  105. data/lib/pvectl/commands/resume.rb +57 -0
  106. data/lib/pvectl/commands/rollback_snapshot.rb +228 -0
  107. data/lib/pvectl/commands/sendkey_vm.rb +205 -0
  108. data/lib/pvectl/commands/service.rb +293 -0
  109. data/lib/pvectl/commands/set_container.rb +50 -0
  110. data/lib/pvectl/commands/set_node.rb +52 -0
  111. data/lib/pvectl/commands/set_resource_command.rb +185 -0
  112. data/lib/pvectl/commands/set_vm.rb +136 -0
  113. data/lib/pvectl/commands/set_volume.rb +212 -0
  114. data/lib/pvectl/commands/shared_config_parsers.rb +126 -0
  115. data/lib/pvectl/commands/shared_flags.rb +155 -0
  116. data/lib/pvectl/commands/shutdown.rb +73 -0
  117. data/lib/pvectl/commands/shutdown_container.rb +18 -0
  118. data/lib/pvectl/commands/start.rb +79 -0
  119. data/lib/pvectl/commands/start_container.rb +18 -0
  120. data/lib/pvectl/commands/stop.rb +75 -0
  121. data/lib/pvectl/commands/stop_container.rb +18 -0
  122. data/lib/pvectl/commands/suspend.rb +64 -0
  123. data/lib/pvectl/commands/template_command.rb +205 -0
  124. data/lib/pvectl/commands/template_container.rb +27 -0
  125. data/lib/pvectl/commands/template_vm.rb +106 -0
  126. data/lib/pvectl/commands/top/command.rb +206 -0
  127. data/lib/pvectl/commands/top/handlers/containers.rb +61 -0
  128. data/lib/pvectl/commands/top/handlers/nodes.rb +61 -0
  129. data/lib/pvectl/commands/top/handlers/vms.rb +61 -0
  130. data/lib/pvectl/commands/top/resource_handler.rb +46 -0
  131. data/lib/pvectl/commands/top/resource_registry.rb +22 -0
  132. data/lib/pvectl/commands/unlink_disk_vm.rb +232 -0
  133. data/lib/pvectl/commands/vm_lifecycle_command.rb +77 -0
  134. data/lib/pvectl/commands/wakeonlan_node.rb +153 -0
  135. data/lib/pvectl/config/errors.rb +62 -0
  136. data/lib/pvectl/config/models/cluster.rb +180 -0
  137. data/lib/pvectl/config/models/context.rb +100 -0
  138. data/lib/pvectl/config/models/resolved_config.rb +171 -0
  139. data/lib/pvectl/config/models/user.rb +133 -0
  140. data/lib/pvectl/config/provider.rb +297 -0
  141. data/lib/pvectl/config/service.rb +300 -0
  142. data/lib/pvectl/config/store.rb +161 -0
  143. data/lib/pvectl/config/wizard.rb +309 -0
  144. data/lib/pvectl/config_serializer.rb +1034 -0
  145. data/lib/pvectl/connection/retry_handler.rb +161 -0
  146. data/lib/pvectl/connection.rb +157 -0
  147. data/lib/pvectl/console/terminal_session.rb +449 -0
  148. data/lib/pvectl/editor_session.rb +157 -0
  149. data/lib/pvectl/exit_codes.rb +43 -0
  150. data/lib/pvectl/formatters/base.rb +55 -0
  151. data/lib/pvectl/formatters/color_support.rb +90 -0
  152. data/lib/pvectl/formatters/json.rb +45 -0
  153. data/lib/pvectl/formatters/output_helper.rb +77 -0
  154. data/lib/pvectl/formatters/registry.rb +72 -0
  155. data/lib/pvectl/formatters/table.rb +235 -0
  156. data/lib/pvectl/formatters/wide.rb +93 -0
  157. data/lib/pvectl/formatters/yaml.rb +49 -0
  158. data/lib/pvectl/manifest_serializer.rb +142 -0
  159. data/lib/pvectl/models/apt_package.rb +107 -0
  160. data/lib/pvectl/models/backup.rb +173 -0
  161. data/lib/pvectl/models/base.rb +49 -0
  162. data/lib/pvectl/models/capability.rb +62 -0
  163. data/lib/pvectl/models/container.rb +205 -0
  164. data/lib/pvectl/models/container_operation_result.rb +27 -0
  165. data/lib/pvectl/models/dns_config.rb +54 -0
  166. data/lib/pvectl/models/hosts_file.rb +47 -0
  167. data/lib/pvectl/models/journal_entry.rb +16 -0
  168. data/lib/pvectl/models/network_interface.rb +85 -0
  169. data/lib/pvectl/models/node.rb +195 -0
  170. data/lib/pvectl/models/node_operation_result.rb +45 -0
  171. data/lib/pvectl/models/operation_result.rb +110 -0
  172. data/lib/pvectl/models/physical_disk.rb +193 -0
  173. data/lib/pvectl/models/service.rb +80 -0
  174. data/lib/pvectl/models/snapshot.rb +101 -0
  175. data/lib/pvectl/models/snapshot_description.rb +39 -0
  176. data/lib/pvectl/models/storage.rb +180 -0
  177. data/lib/pvectl/models/subscription.rb +87 -0
  178. data/lib/pvectl/models/syslog_entry.rb +17 -0
  179. data/lib/pvectl/models/task.rb +95 -0
  180. data/lib/pvectl/models/task_entry.rb +52 -0
  181. data/lib/pvectl/models/task_log_line.rb +17 -0
  182. data/lib/pvectl/models/time_config.rb +47 -0
  183. data/lib/pvectl/models/vm.rb +137 -0
  184. data/lib/pvectl/models/vm_operation_result.rb +27 -0
  185. data/lib/pvectl/models/volume.rb +133 -0
  186. data/lib/pvectl/models/volume_operation_result.rb +26 -0
  187. data/lib/pvectl/parsers/cloud_init_config.rb +92 -0
  188. data/lib/pvectl/parsers/disk_config.rb +97 -0
  189. data/lib/pvectl/parsers/lxc_mount_config.rb +98 -0
  190. data/lib/pvectl/parsers/lxc_net_config.rb +97 -0
  191. data/lib/pvectl/parsers/net_config.rb +95 -0
  192. data/lib/pvectl/parsers/smart_text.rb +42 -0
  193. data/lib/pvectl/plugin_loader.rb +157 -0
  194. data/lib/pvectl/presenters/apt_package.rb +99 -0
  195. data/lib/pvectl/presenters/backup.rb +128 -0
  196. data/lib/pvectl/presenters/base.rb +283 -0
  197. data/lib/pvectl/presenters/capability.rb +104 -0
  198. data/lib/pvectl/presenters/config/context.rb +80 -0
  199. data/lib/pvectl/presenters/container.rb +574 -0
  200. data/lib/pvectl/presenters/container_operation_result.rb +109 -0
  201. data/lib/pvectl/presenters/disk.rb +184 -0
  202. data/lib/pvectl/presenters/dns_config.rb +68 -0
  203. data/lib/pvectl/presenters/hosts_file.rb +61 -0
  204. data/lib/pvectl/presenters/journal_entry.rb +20 -0
  205. data/lib/pvectl/presenters/node.rb +762 -0
  206. data/lib/pvectl/presenters/node_operation_result.rb +50 -0
  207. data/lib/pvectl/presenters/operation_result.rb +61 -0
  208. data/lib/pvectl/presenters/service.rb +76 -0
  209. data/lib/pvectl/presenters/snapshot.rb +239 -0
  210. data/lib/pvectl/presenters/snapshot_operation_result.rb +125 -0
  211. data/lib/pvectl/presenters/storage.rb +329 -0
  212. data/lib/pvectl/presenters/subscription.rb +189 -0
  213. data/lib/pvectl/presenters/syslog_entry.rb +20 -0
  214. data/lib/pvectl/presenters/task_entry.rb +69 -0
  215. data/lib/pvectl/presenters/task_log_line.rb +20 -0
  216. data/lib/pvectl/presenters/template.rb +76 -0
  217. data/lib/pvectl/presenters/time_config.rb +86 -0
  218. data/lib/pvectl/presenters/top_container.rb +112 -0
  219. data/lib/pvectl/presenters/top_node.rb +115 -0
  220. data/lib/pvectl/presenters/top_presenter.rb +59 -0
  221. data/lib/pvectl/presenters/top_vm.rb +105 -0
  222. data/lib/pvectl/presenters/vm.rb +853 -0
  223. data/lib/pvectl/presenters/vm_operation_result.rb +109 -0
  224. data/lib/pvectl/presenters/volume.rb +136 -0
  225. data/lib/pvectl/presenters/volume_operation_result.rb +58 -0
  226. data/lib/pvectl/repositories/apt.rb +93 -0
  227. data/lib/pvectl/repositories/backup.rb +186 -0
  228. data/lib/pvectl/repositories/base.rb +110 -0
  229. data/lib/pvectl/repositories/capabilities.rb +96 -0
  230. data/lib/pvectl/repositories/container.rb +503 -0
  231. data/lib/pvectl/repositories/disk.rb +87 -0
  232. data/lib/pvectl/repositories/dns.rb +54 -0
  233. data/lib/pvectl/repositories/hosts.rb +63 -0
  234. data/lib/pvectl/repositories/journal.rb +23 -0
  235. data/lib/pvectl/repositories/node.rb +537 -0
  236. data/lib/pvectl/repositories/service.rb +139 -0
  237. data/lib/pvectl/repositories/snapshot.rb +133 -0
  238. data/lib/pvectl/repositories/storage.rb +302 -0
  239. data/lib/pvectl/repositories/subscription.rb +77 -0
  240. data/lib/pvectl/repositories/syslog.rb +25 -0
  241. data/lib/pvectl/repositories/task.rb +82 -0
  242. data/lib/pvectl/repositories/task_list.rb +30 -0
  243. data/lib/pvectl/repositories/task_log.rb +31 -0
  244. data/lib/pvectl/repositories/time_config.rb +53 -0
  245. data/lib/pvectl/repositories/vm.rb +616 -0
  246. data/lib/pvectl/repositories/volume.rb +306 -0
  247. data/lib/pvectl/selectors/base.rb +201 -0
  248. data/lib/pvectl/selectors/container.rb +116 -0
  249. data/lib/pvectl/selectors/disk.rb +59 -0
  250. data/lib/pvectl/selectors/vm.rb +116 -0
  251. data/lib/pvectl/selectors/volume.rb +59 -0
  252. data/lib/pvectl/services/backup.rb +209 -0
  253. data/lib/pvectl/services/clone_container.rb +260 -0
  254. data/lib/pvectl/services/clone_vm.rb +265 -0
  255. data/lib/pvectl/services/cloudinit.rb +96 -0
  256. data/lib/pvectl/services/console.rb +152 -0
  257. data/lib/pvectl/services/container_lifecycle.rb +124 -0
  258. data/lib/pvectl/services/create_container.rb +179 -0
  259. data/lib/pvectl/services/create_vm.rb +191 -0
  260. data/lib/pvectl/services/edit_container.rb +125 -0
  261. data/lib/pvectl/services/edit_dns.rb +159 -0
  262. data/lib/pvectl/services/edit_hosts.rb +78 -0
  263. data/lib/pvectl/services/edit_node.rb +147 -0
  264. data/lib/pvectl/services/edit_vm.rb +125 -0
  265. data/lib/pvectl/services/edit_volume.rb +224 -0
  266. data/lib/pvectl/services/get/resource_service.rb +98 -0
  267. data/lib/pvectl/services/move_disk.rb +132 -0
  268. data/lib/pvectl/services/pull_config.rb +94 -0
  269. data/lib/pvectl/services/push_config.rb +524 -0
  270. data/lib/pvectl/services/resize_volume.rb +253 -0
  271. data/lib/pvectl/services/resource_delete.rb +169 -0
  272. data/lib/pvectl/services/resource_migration.rb +170 -0
  273. data/lib/pvectl/services/sendkey.rb +108 -0
  274. data/lib/pvectl/services/service_lifecycle.rb +89 -0
  275. data/lib/pvectl/services/set_container.rb +128 -0
  276. data/lib/pvectl/services/set_node.rb +236 -0
  277. data/lib/pvectl/services/set_vm.rb +128 -0
  278. data/lib/pvectl/services/set_volume.rb +126 -0
  279. data/lib/pvectl/services/snapshot.rb +261 -0
  280. data/lib/pvectl/services/task_listing.rb +75 -0
  281. data/lib/pvectl/services/unlink_disk.rb +86 -0
  282. data/lib/pvectl/services/vm_lifecycle.rb +124 -0
  283. data/lib/pvectl/services/wakeonlan.rb +79 -0
  284. data/lib/pvectl/utils/resource_resolver.rb +80 -0
  285. data/lib/pvectl/version.rb +13 -0
  286. data/lib/pvectl/wizards/create_container.rb +105 -0
  287. data/lib/pvectl/wizards/create_vm.rb +98 -0
  288. data/lib/pvectl.rb +439 -0
  289. data/sig/external/gli.rbs +16 -0
  290. data/sig/external/proxmox_api.rbs +10 -0
  291. data/sig/pvectl/argv_preprocessor.rbs +53 -0
  292. data/sig/pvectl/cli.rbs +26 -0
  293. data/sig/pvectl/commands/apt.rbs +47 -0
  294. data/sig/pvectl/commands/clone_container.rbs +31 -0
  295. data/sig/pvectl/commands/clone_vm.rbs +33 -0
  296. data/sig/pvectl/commands/cloudinit/command.rbs +13 -0
  297. data/sig/pvectl/commands/cloudinit/dump.rbs +13 -0
  298. data/sig/pvectl/commands/cloudinit/pending.rbs +17 -0
  299. data/sig/pvectl/commands/cloudinit/regenerate.rbs +11 -0
  300. data/sig/pvectl/commands/config/command.rbs +9 -0
  301. data/sig/pvectl/commands/config/get_contexts.rbs +11 -0
  302. data/sig/pvectl/commands/config/set_cluster.rbs +11 -0
  303. data/sig/pvectl/commands/config/set_context.rbs +15 -0
  304. data/sig/pvectl/commands/config/set_credentials.rbs +15 -0
  305. data/sig/pvectl/commands/config/use_context.rbs +11 -0
  306. data/sig/pvectl/commands/config/view.rbs +11 -0
  307. data/sig/pvectl/commands/console.rbs +9 -0
  308. data/sig/pvectl/commands/console_ct.rbs +27 -0
  309. data/sig/pvectl/commands/console_vm.rbs +27 -0
  310. data/sig/pvectl/commands/container_lifecycle_command.rbs +25 -0
  311. data/sig/pvectl/commands/create_backup.rbs +29 -0
  312. data/sig/pvectl/commands/create_container.rbs +30 -0
  313. data/sig/pvectl/commands/create_resource_command.rbs +53 -0
  314. data/sig/pvectl/commands/create_snapshot.rbs +35 -0
  315. data/sig/pvectl/commands/create_vm.rbs +30 -0
  316. data/sig/pvectl/commands/delete_backup.rbs +25 -0
  317. data/sig/pvectl/commands/delete_command.rbs +45 -0
  318. data/sig/pvectl/commands/delete_container.rbs +11 -0
  319. data/sig/pvectl/commands/delete_snapshot.rbs +35 -0
  320. data/sig/pvectl/commands/delete_vm.rbs +13 -0
  321. data/sig/pvectl/commands/describe/command.rbs +27 -0
  322. data/sig/pvectl/commands/edit_container.rbs +17 -0
  323. data/sig/pvectl/commands/edit_dns.rbs +25 -0
  324. data/sig/pvectl/commands/edit_hosts.rbs +23 -0
  325. data/sig/pvectl/commands/edit_node.rbs +17 -0
  326. data/sig/pvectl/commands/edit_resource_command.rbs +35 -0
  327. data/sig/pvectl/commands/edit_vm.rbs +19 -0
  328. data/sig/pvectl/commands/edit_volume.rbs +24 -0
  329. data/sig/pvectl/commands/feature_command.rbs +43 -0
  330. data/sig/pvectl/commands/feature_container.rbs +10 -0
  331. data/sig/pvectl/commands/feature_vm.rbs +12 -0
  332. data/sig/pvectl/commands/get/command.rbs +42 -0
  333. data/sig/pvectl/commands/get/handlers/backups.rbs +23 -0
  334. data/sig/pvectl/commands/get/handlers/capabilities.rbs +29 -0
  335. data/sig/pvectl/commands/get/handlers/containers.rbs +35 -0
  336. data/sig/pvectl/commands/get/handlers/disks.rbs +27 -0
  337. data/sig/pvectl/commands/get/handlers/dns.rbs +25 -0
  338. data/sig/pvectl/commands/get/handlers/hosts.rbs +25 -0
  339. data/sig/pvectl/commands/get/handlers/nodes.rbs +33 -0
  340. data/sig/pvectl/commands/get/handlers/services.rbs +23 -0
  341. data/sig/pvectl/commands/get/handlers/snapshots.rbs +27 -0
  342. data/sig/pvectl/commands/get/handlers/storage.rbs +25 -0
  343. data/sig/pvectl/commands/get/handlers/subscription.rbs +25 -0
  344. data/sig/pvectl/commands/get/handlers/tasks.rbs +28 -0
  345. data/sig/pvectl/commands/get/handlers/templates.rbs +35 -0
  346. data/sig/pvectl/commands/get/handlers/time.rbs +29 -0
  347. data/sig/pvectl/commands/get/handlers/vms.rbs +35 -0
  348. data/sig/pvectl/commands/get/handlers/volume.rbs +27 -0
  349. data/sig/pvectl/commands/get/resource_handler.rbs +13 -0
  350. data/sig/pvectl/commands/get/resource_registry.rbs +8 -0
  351. data/sig/pvectl/commands/get/watch_loop.rbs +33 -0
  352. data/sig/pvectl/commands/irreversible_command.rbs +32 -0
  353. data/sig/pvectl/commands/logs/command.rbs +35 -0
  354. data/sig/pvectl/commands/logs/handlers/journal.rbs +21 -0
  355. data/sig/pvectl/commands/logs/handlers/syslog.rbs +21 -0
  356. data/sig/pvectl/commands/logs/handlers/task_detail.rbs +21 -0
  357. data/sig/pvectl/commands/logs/handlers/task_logs.rbs +35 -0
  358. data/sig/pvectl/commands/logs/resource_handler.rbs +11 -0
  359. data/sig/pvectl/commands/logs/resource_registry.rbs +8 -0
  360. data/sig/pvectl/commands/migrate_command.rbs +45 -0
  361. data/sig/pvectl/commands/migrate_container.rbs +11 -0
  362. data/sig/pvectl/commands/migrate_vm.rbs +13 -0
  363. data/sig/pvectl/commands/move_disk_command.rbs +43 -0
  364. data/sig/pvectl/commands/move_disk_container.rbs +11 -0
  365. data/sig/pvectl/commands/move_disk_vm.rbs +13 -0
  366. data/sig/pvectl/commands/ping.rbs +39 -0
  367. data/sig/pvectl/commands/pull.rbs +33 -0
  368. data/sig/pvectl/commands/push.rbs +32 -0
  369. data/sig/pvectl/commands/reset.rbs +11 -0
  370. data/sig/pvectl/commands/resource_lifecycle_command.rbs +55 -0
  371. data/sig/pvectl/commands/resource_registry.rbs +19 -0
  372. data/sig/pvectl/commands/restart.rbs +11 -0
  373. data/sig/pvectl/commands/restart_container.rbs +9 -0
  374. data/sig/pvectl/commands/restore_backup.rbs +27 -0
  375. data/sig/pvectl/commands/resume.rbs +11 -0
  376. data/sig/pvectl/commands/rollback_snapshot.rbs +31 -0
  377. data/sig/pvectl/commands/sendkey_vm.rbs +25 -0
  378. data/sig/pvectl/commands/service.rbs +38 -0
  379. data/sig/pvectl/commands/set_container.rbs +13 -0
  380. data/sig/pvectl/commands/set_node.rbs +13 -0
  381. data/sig/pvectl/commands/set_resource_command.rbs +25 -0
  382. data/sig/pvectl/commands/set_vm.rbs +15 -0
  383. data/sig/pvectl/commands/set_volume.rbs +24 -0
  384. data/sig/pvectl/commands/shared_config_parsers.rbs +19 -0
  385. data/sig/pvectl/commands/shared_flags.rbs +10 -0
  386. data/sig/pvectl/commands/shutdown.rbs +11 -0
  387. data/sig/pvectl/commands/shutdown_container.rbs +9 -0
  388. data/sig/pvectl/commands/start.rbs +11 -0
  389. data/sig/pvectl/commands/start_container.rbs +9 -0
  390. data/sig/pvectl/commands/stop.rbs +11 -0
  391. data/sig/pvectl/commands/stop_container.rbs +9 -0
  392. data/sig/pvectl/commands/suspend.rbs +11 -0
  393. data/sig/pvectl/commands/template_command.rbs +21 -0
  394. data/sig/pvectl/commands/template_container.rbs +10 -0
  395. data/sig/pvectl/commands/template_vm.rbs +12 -0
  396. data/sig/pvectl/commands/top/command.rbs +31 -0
  397. data/sig/pvectl/commands/top/handlers/containers.rbs +21 -0
  398. data/sig/pvectl/commands/top/handlers/nodes.rbs +21 -0
  399. data/sig/pvectl/commands/top/handlers/vms.rbs +21 -0
  400. data/sig/pvectl/commands/top/resource_handler.rbs +11 -0
  401. data/sig/pvectl/commands/top/resource_registry.rbs +8 -0
  402. data/sig/pvectl/commands/unlink_disk_vm.rbs +27 -0
  403. data/sig/pvectl/commands/vm_lifecycle_command.rbs +25 -0
  404. data/sig/pvectl/commands/wakeonlan_node.rbs +21 -0
  405. data/sig/pvectl/config/errors.rbs +24 -0
  406. data/sig/pvectl/config/models/cluster.rbs +39 -0
  407. data/sig/pvectl/config/models/context.rbs +23 -0
  408. data/sig/pvectl/config/models/resolved_config.rbs +51 -0
  409. data/sig/pvectl/config/models/user.rbs +31 -0
  410. data/sig/pvectl/config/provider.rbs +40 -0
  411. data/sig/pvectl/config/service.rbs +65 -0
  412. data/sig/pvectl/config/store.rbs +14 -0
  413. data/sig/pvectl/config/wizard.rbs +48 -0
  414. data/sig/pvectl/config_serializer.rbs +121 -0
  415. data/sig/pvectl/connection/retry_handler.rbs +31 -0
  416. data/sig/pvectl/connection.rbs +35 -0
  417. data/sig/pvectl/console/terminal_session.rbs +63 -0
  418. data/sig/pvectl/editor_session.rbs +33 -0
  419. data/sig/pvectl/exit_codes.rbs +19 -0
  420. data/sig/pvectl/formatters/base.rbs +13 -0
  421. data/sig/pvectl/formatters/color_support.rbs +13 -0
  422. data/sig/pvectl/formatters/json.rbs +7 -0
  423. data/sig/pvectl/formatters/output_helper.rbs +9 -0
  424. data/sig/pvectl/formatters/registry.rbs +13 -0
  425. data/sig/pvectl/formatters/table.rbs +25 -0
  426. data/sig/pvectl/formatters/wide.rbs +15 -0
  427. data/sig/pvectl/formatters/yaml.rbs +7 -0
  428. data/sig/pvectl/manifest_serializer.rbs +18 -0
  429. data/sig/pvectl/models/apt_package.rbs +26 -0
  430. data/sig/pvectl/models/backup.rbs +31 -0
  431. data/sig/pvectl/models/base.rbs +11 -0
  432. data/sig/pvectl/models/capability.rbs +16 -0
  433. data/sig/pvectl/models/container.rbs +44 -0
  434. data/sig/pvectl/models/container_operation_result.rbs +9 -0
  435. data/sig/pvectl/models/dns_config.rbs +15 -0
  436. data/sig/pvectl/models/hosts_file.rbs +13 -0
  437. data/sig/pvectl/models/journal_entry.rbs +10 -0
  438. data/sig/pvectl/models/network_interface.rbs +20 -0
  439. data/sig/pvectl/models/node.rbs +47 -0
  440. data/sig/pvectl/models/node_operation_result.rbs +12 -0
  441. data/sig/pvectl/models/operation_result.rbs +21 -0
  442. data/sig/pvectl/models/physical_disk.rbs +35 -0
  443. data/sig/pvectl/models/service.rbs +18 -0
  444. data/sig/pvectl/models/snapshot.rbs +21 -0
  445. data/sig/pvectl/models/snapshot_description.rbs +18 -0
  446. data/sig/pvectl/models/storage.rbs +39 -0
  447. data/sig/pvectl/models/subscription.rbs +24 -0
  448. data/sig/pvectl/models/syslog_entry.rbs +10 -0
  449. data/sig/pvectl/models/task.rbs +22 -0
  450. data/sig/pvectl/models/task_entry.rbs +24 -0
  451. data/sig/pvectl/models/task_log_line.rbs +10 -0
  452. data/sig/pvectl/models/time_config.rbs +12 -0
  453. data/sig/pvectl/models/vm.rbs +32 -0
  454. data/sig/pvectl/models/vm_operation_result.rbs +9 -0
  455. data/sig/pvectl/models/volume.rbs +29 -0
  456. data/sig/pvectl/models/volume_operation_result.rbs +9 -0
  457. data/sig/pvectl/parsers/cloud_init_config.rbs +15 -0
  458. data/sig/pvectl/parsers/disk_config.rbs +19 -0
  459. data/sig/pvectl/parsers/lxc_mount_config.rbs +19 -0
  460. data/sig/pvectl/parsers/lxc_net_config.rbs +19 -0
  461. data/sig/pvectl/parsers/net_config.rbs +19 -0
  462. data/sig/pvectl/parsers/smart_text.rbs +7 -0
  463. data/sig/pvectl/plugin_loader.rbs +25 -0
  464. data/sig/pvectl/presenters/apt_package.rbs +19 -0
  465. data/sig/pvectl/presenters/backup.rbs +25 -0
  466. data/sig/pvectl/presenters/base.rbs +41 -0
  467. data/sig/pvectl/presenters/capability.rbs +19 -0
  468. data/sig/pvectl/presenters/config/context.rbs +17 -0
  469. data/sig/pvectl/presenters/container.rbs +78 -0
  470. data/sig/pvectl/presenters/container_operation_result.rbs +19 -0
  471. data/sig/pvectl/presenters/disk.rbs +31 -0
  472. data/sig/pvectl/presenters/dns_config.rbs +13 -0
  473. data/sig/pvectl/presenters/hosts_file.rbs +13 -0
  474. data/sig/pvectl/presenters/journal_entry.rbs +11 -0
  475. data/sig/pvectl/presenters/node.rbs +118 -0
  476. data/sig/pvectl/presenters/node_operation_result.rbs +11 -0
  477. data/sig/pvectl/presenters/operation_result.rbs +17 -0
  478. data/sig/pvectl/presenters/service.rbs +15 -0
  479. data/sig/pvectl/presenters/snapshot.rbs +35 -0
  480. data/sig/pvectl/presenters/snapshot_operation_result.rbs +27 -0
  481. data/sig/pvectl/presenters/storage.rbs +59 -0
  482. data/sig/pvectl/presenters/subscription.rbs +36 -0
  483. data/sig/pvectl/presenters/syslog_entry.rbs +11 -0
  484. data/sig/pvectl/presenters/task_entry.rbs +21 -0
  485. data/sig/pvectl/presenters/task_log_line.rbs +11 -0
  486. data/sig/pvectl/presenters/template.rbs +15 -0
  487. data/sig/pvectl/presenters/time_config.rbs +19 -0
  488. data/sig/pvectl/presenters/top_container.rbs +17 -0
  489. data/sig/pvectl/presenters/top_node.rbs +17 -0
  490. data/sig/pvectl/presenters/top_presenter.rbs +13 -0
  491. data/sig/pvectl/presenters/top_vm.rbs +17 -0
  492. data/sig/pvectl/presenters/vm.rbs +91 -0
  493. data/sig/pvectl/presenters/vm_operation_result.rbs +19 -0
  494. data/sig/pvectl/presenters/volume.rbs +23 -0
  495. data/sig/pvectl/presenters/volume_operation_result.rbs +11 -0
  496. data/sig/pvectl/repositories/apt.rbs +17 -0
  497. data/sig/pvectl/repositories/backup.rbs +27 -0
  498. data/sig/pvectl/repositories/base.rbs +23 -0
  499. data/sig/pvectl/repositories/capabilities.rbs +20 -0
  500. data/sig/pvectl/repositories/container.rbs +63 -0
  501. data/sig/pvectl/repositories/disk.rbs +17 -0
  502. data/sig/pvectl/repositories/dns.rbs +13 -0
  503. data/sig/pvectl/repositories/hosts.rbs +13 -0
  504. data/sig/pvectl/repositories/journal.rbs +7 -0
  505. data/sig/pvectl/repositories/node.rbs +68 -0
  506. data/sig/pvectl/repositories/service.rbs +27 -0
  507. data/sig/pvectl/repositories/snapshot.rbs +19 -0
  508. data/sig/pvectl/repositories/storage.rbs +37 -0
  509. data/sig/pvectl/repositories/subscription.rbs +17 -0
  510. data/sig/pvectl/repositories/syslog.rbs +7 -0
  511. data/sig/pvectl/repositories/task.rbs +19 -0
  512. data/sig/pvectl/repositories/task_list.rbs +7 -0
  513. data/sig/pvectl/repositories/task_log.rbs +11 -0
  514. data/sig/pvectl/repositories/time_config.rbs +13 -0
  515. data/sig/pvectl/repositories/vm.rbs +85 -0
  516. data/sig/pvectl/repositories/volume.rbs +43 -0
  517. data/sig/pvectl/selectors/base.rbs +37 -0
  518. data/sig/pvectl/selectors/container.rbs +19 -0
  519. data/sig/pvectl/selectors/disk.rbs +13 -0
  520. data/sig/pvectl/selectors/vm.rbs +19 -0
  521. data/sig/pvectl/selectors/volume.rbs +13 -0
  522. data/sig/pvectl/services/backup.rbs +27 -0
  523. data/sig/pvectl/services/clone_container.rbs +35 -0
  524. data/sig/pvectl/services/clone_vm.rbs +35 -0
  525. data/sig/pvectl/services/cloudinit.rbs +19 -0
  526. data/sig/pvectl/services/console.rbs +23 -0
  527. data/sig/pvectl/services/container_lifecycle.rbs +26 -0
  528. data/sig/pvectl/services/create_container.rbs +64 -0
  529. data/sig/pvectl/services/create_vm.rbs +72 -0
  530. data/sig/pvectl/services/edit_container.rbs +17 -0
  531. data/sig/pvectl/services/edit_dns.rbs +23 -0
  532. data/sig/pvectl/services/edit_hosts.rbs +13 -0
  533. data/sig/pvectl/services/edit_node.rbs +21 -0
  534. data/sig/pvectl/services/edit_vm.rbs +17 -0
  535. data/sig/pvectl/services/edit_volume.rbs +18 -0
  536. data/sig/pvectl/services/get/resource_service.rbs +23 -0
  537. data/sig/pvectl/services/move_disk.rbs +21 -0
  538. data/sig/pvectl/services/pull_config.rbs +18 -0
  539. data/sig/pvectl/services/push_config.rbs +37 -0
  540. data/sig/pvectl/services/resize_volume.rbs +47 -0
  541. data/sig/pvectl/services/resource_delete.rbs +27 -0
  542. data/sig/pvectl/services/resource_migration.rbs +29 -0
  543. data/sig/pvectl/services/sendkey.rbs +19 -0
  544. data/sig/pvectl/services/service_lifecycle.rbs +17 -0
  545. data/sig/pvectl/services/set_container.rbs +14 -0
  546. data/sig/pvectl/services/set_node.rbs +23 -0
  547. data/sig/pvectl/services/set_vm.rbs +14 -0
  548. data/sig/pvectl/services/set_volume.rbs +12 -0
  549. data/sig/pvectl/services/snapshot.rbs +35 -0
  550. data/sig/pvectl/services/task_listing.rbs +13 -0
  551. data/sig/pvectl/services/unlink_disk.rbs +17 -0
  552. data/sig/pvectl/services/vm_lifecycle.rbs +26 -0
  553. data/sig/pvectl/services/wakeonlan.rbs +17 -0
  554. data/sig/pvectl/utils/resource_resolver.rbs +17 -0
  555. data/sig/pvectl/wizards/create_container.rbs +21 -0
  556. data/sig/pvectl/wizards/create_vm.rbs +21 -0
  557. data/sig/pvectl.rbs +9 -0
  558. metadata +675 -0
@@ -0,0 +1,205 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents an LXC container in the Proxmox cluster.
6
+ #
7
+ # Immutable domain model containing container attributes and status predicates.
8
+ # Created by Repositories::Container from API data.
9
+ # Display/formatting methods are in Presenters::Container.
10
+ #
11
+ # @example Creating a Container model
12
+ # ct = Container.new(vmid: 100, name: "web", status: "running", node: "pve1")
13
+ # ct.running? #=> true
14
+ # ct.template? #=> false
15
+ #
16
+ # @example From API response
17
+ # data = { "vmid" => 100, "name" => "web", "status" => "running" }
18
+ # ct = Container.new(data)
19
+ #
20
+ # @see Pvectl::Repositories::Container Repository that creates Container instances
21
+ # @see Pvectl::Presenters::Container Presenter for formatting Container data
22
+ #
23
+ class Container < Base
24
+ # @!group Identifier Attributes
25
+
26
+ # @return [Integer] unique container identifier (CTID: 100-999999999)
27
+ attr_reader :vmid
28
+
29
+ # @return [String, nil] container name (hostname)
30
+ attr_reader :name
31
+
32
+ # @return [String] node name where container runs
33
+ attr_reader :node
34
+
35
+ # @return [String] container status (running, stopped)
36
+ attr_reader :status
37
+
38
+ # @!endgroup
39
+
40
+ # @!group Resource Attributes
41
+
42
+ # @return [Float, nil] current CPU usage (0.0-1.0 scale)
43
+ attr_reader :cpu
44
+
45
+ # @return [Integer, nil] allocated CPU cores
46
+ attr_reader :maxcpu
47
+
48
+ # @return [Integer, nil] current memory usage in bytes
49
+ attr_reader :mem
50
+
51
+ # @return [Integer, nil] memory limit in bytes
52
+ attr_reader :maxmem
53
+
54
+ # @return [Integer, nil] current swap usage in bytes
55
+ attr_reader :swap
56
+
57
+ # @return [Integer, nil] swap limit in bytes
58
+ attr_reader :maxswap
59
+
60
+ # @return [Integer, nil] current rootfs disk usage in bytes
61
+ attr_reader :disk
62
+
63
+ # @return [Integer, nil] rootfs disk limit in bytes
64
+ attr_reader :maxdisk
65
+
66
+ # @!endgroup
67
+
68
+ # @!group Metadata Attributes
69
+
70
+ # @return [Integer, nil] uptime in seconds
71
+ attr_reader :uptime
72
+
73
+ # @return [Integer, nil] template flag (1 if template, 0 otherwise)
74
+ attr_reader :template
75
+
76
+ # @return [String, nil] semicolon-separated tags
77
+ attr_reader :tags
78
+
79
+ # @return [String, nil] resource pool name
80
+ attr_reader :pool
81
+
82
+ # @return [String, nil] lock status (backup, migrate, etc.)
83
+ attr_reader :lock
84
+
85
+ # @!endgroup
86
+
87
+ # @!group Network I/O Attributes
88
+
89
+ # @return [Integer, nil] network input bytes
90
+ attr_reader :netin
91
+
92
+ # @return [Integer, nil] network output bytes
93
+ attr_reader :netout
94
+
95
+ # @!endgroup
96
+
97
+ # @!group Describe-Only Attributes
98
+
99
+ # @return [String, nil] OS type (debian, ubuntu, alpine, etc.)
100
+ attr_reader :ostype
101
+
102
+ # @return [String, nil] architecture (amd64, arm64)
103
+ attr_reader :arch
104
+
105
+ # @return [Integer, nil] unprivileged flag (1 if unprivileged, 0 otherwise)
106
+ attr_reader :unprivileged
107
+
108
+ # @return [String, nil] features configuration (nesting, keyctl, etc.)
109
+ attr_reader :features
110
+
111
+ # @return [String, nil] rootfs configuration string
112
+ attr_reader :rootfs
113
+
114
+ # @return [Array<Hash>] network interface configurations
115
+ attr_reader :network_interfaces
116
+
117
+ # @return [String, nil] container description
118
+ attr_reader :description
119
+
120
+ # @return [String, nil] container hostname (FQDN)
121
+ attr_reader :hostname
122
+
123
+ # @return [Integer, nil] runtime PID
124
+ attr_reader :pid
125
+
126
+ # @return [Hash, nil] HA state information
127
+ attr_reader :ha
128
+
129
+ # @return [String, nil] resource type from API ("lxc")
130
+ attr_reader :type
131
+
132
+ # @return [Hash, nil] raw API responses for describe command
133
+ attr_reader :describe_data
134
+
135
+ # @!endgroup
136
+
137
+ # Creates a new Container model from attributes.
138
+ #
139
+ # @param attrs [Hash] Container attributes from API (string or symbol keys)
140
+ def initialize(attrs = {})
141
+ super(attrs)
142
+ # Use @attributes which has normalized symbol keys from Base
143
+ @vmid = @attributes[:vmid]
144
+ @name = @attributes[:name]
145
+ @node = @attributes[:node]
146
+ @status = @attributes[:status]
147
+ @cpu = @attributes[:cpu]
148
+ @maxcpu = @attributes[:maxcpu]
149
+ @mem = @attributes[:mem]
150
+ @maxmem = @attributes[:maxmem]
151
+ @swap = @attributes[:swap]
152
+ @maxswap = @attributes[:maxswap]
153
+ @disk = @attributes[:disk]
154
+ @maxdisk = @attributes[:maxdisk]
155
+ @uptime = @attributes[:uptime]
156
+ @template = @attributes[:template]
157
+ @tags = @attributes[:tags]
158
+ @pool = @attributes[:pool]
159
+ @lock = @attributes[:lock]
160
+ @netin = @attributes[:netin]
161
+ @netout = @attributes[:netout]
162
+ @ostype = @attributes[:ostype]
163
+ @arch = @attributes[:arch]
164
+ @unprivileged = @attributes[:unprivileged]
165
+ @features = @attributes[:features]
166
+ @rootfs = @attributes[:rootfs]
167
+ @network_interfaces = @attributes[:network_interfaces] || []
168
+ @description = @attributes[:description]
169
+ @hostname = @attributes[:hostname]
170
+ @pid = @attributes[:pid]
171
+ @ha = @attributes[:ha]
172
+ @type = @attributes[:type]
173
+ @describe_data = @attributes[:describe_data]
174
+ end
175
+
176
+ # Checks if the container is running.
177
+ #
178
+ # @return [Boolean] true if status is "running"
179
+ def running?
180
+ status == "running"
181
+ end
182
+
183
+ # Checks if the container is stopped.
184
+ #
185
+ # @return [Boolean] true if status is "stopped"
186
+ def stopped?
187
+ status == "stopped"
188
+ end
189
+
190
+ # Checks if the container is a template.
191
+ #
192
+ # @return [Boolean] true if template flag is 1
193
+ def template?
194
+ template == 1
195
+ end
196
+
197
+ # Checks if the container is unprivileged.
198
+ #
199
+ # @return [Boolean] true if unprivileged flag is 1
200
+ def unprivileged?
201
+ unprivileged == 1
202
+ end
203
+ end
204
+ end
205
+ end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents the result of a lifecycle operation on a container.
6
+ #
7
+ # Extends OperationResult with container-specific attribute.
8
+ #
9
+ # @example Successful sync operation
10
+ # result = ContainerOperationResult.new(container: ct, task: task, success: task.successful?)
11
+ # result.container #=> #<Models::Container>
12
+ # result.successful? #=> true
13
+ #
14
+ class ContainerOperationResult < OperationResult
15
+ # @return [Models::Container] The container this result is for
16
+ attr_reader :container
17
+
18
+ # Creates a new ContainerOperationResult.
19
+ #
20
+ # @param attrs [Hash] Result attributes including :container
21
+ def initialize(attrs = {})
22
+ super
23
+ @container = @attributes[:container]
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,54 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents the DNS resolver configuration for a Proxmox node.
6
+ #
7
+ # Immutable value object. Created by Repositories::Dns from API data.
8
+ # Each node has its own DNS settings — there is no cluster-wide DNS config.
9
+ #
10
+ # @example Creating from API response
11
+ # dns = DnsConfig.new(node: "pve1", search: "example.com",
12
+ # dns1: "8.8.8.8", dns2: "1.1.1.1")
13
+ # dns.servers #=> ["8.8.8.8", "1.1.1.1"]
14
+ #
15
+ # @see Pvectl::Repositories::Dns Repository that creates DnsConfig instances
16
+ # @see Pvectl::Presenters::DnsConfig Presenter for formatting DnsConfig data
17
+ #
18
+ class DnsConfig < Base
19
+ # @return [String, nil] node name (not part of the API payload — added by repository)
20
+ attr_reader :node
21
+
22
+ # @return [String, nil] search domain for hostname lookup
23
+ attr_reader :search
24
+
25
+ # @return [String, nil] first nameserver IP address
26
+ attr_reader :dns1
27
+
28
+ # @return [String, nil] second nameserver IP address (optional)
29
+ attr_reader :dns2
30
+
31
+ # @return [String, nil] third nameserver IP address (optional)
32
+ attr_reader :dns3
33
+
34
+ # Creates a new DnsConfig.
35
+ #
36
+ # @param attributes [Hash] attribute key-value pairs (node, search, dns1, dns2, dns3)
37
+ def initialize(attributes = {})
38
+ super
39
+ @node = attributes[:node] || attributes["node"]
40
+ @search = attributes[:search] || attributes["search"]
41
+ @dns1 = attributes[:dns1] || attributes["dns1"]
42
+ @dns2 = attributes[:dns2] || attributes["dns2"]
43
+ @dns3 = attributes[:dns3] || attributes["dns3"]
44
+ end
45
+
46
+ # Returns the configured DNS servers in order, omitting unset entries.
47
+ #
48
+ # @return [Array<String>] nameserver IP addresses (may be empty)
49
+ def servers
50
+ [dns1, dns2, dns3].compact
51
+ end
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents the contents of /etc/hosts on a Proxmox node.
6
+ #
7
+ # Immutable value object. Created by Repositories::Hosts from API data.
8
+ # /etc/hosts is a per-node raw text file — pvectl does not parse or
9
+ # validate its contents.
10
+ #
11
+ # @example Creating from API response
12
+ # hosts = HostsFile.new(node: "pve1",
13
+ # data: "127.0.0.1 localhost\n",
14
+ # digest: "abc123")
15
+ #
16
+ # @see Pvectl::Repositories::Hosts Repository that creates HostsFile instances
17
+ # @see Pvectl::Presenters::HostsFile Presenter for formatting HostsFile data
18
+ #
19
+ class HostsFile < Base
20
+ # @return [String, nil] node name (not part of API payload — added by repository)
21
+ attr_reader :node
22
+
23
+ # @return [String] raw /etc/hosts content (may be empty)
24
+ attr_reader :data
25
+
26
+ # @return [String, nil] digest used for optimistic locking on update
27
+ attr_reader :digest
28
+
29
+ # Creates a new HostsFile.
30
+ #
31
+ # @param attributes [Hash] attribute key-value pairs (node, data, digest)
32
+ def initialize(attributes = {})
33
+ super
34
+ @node = attributes[:node] || attributes["node"]
35
+ @data = attributes[:data] || attributes["data"] || ""
36
+ @digest = attributes[:digest] || attributes["digest"]
37
+ end
38
+
39
+ # Number of lines in the file (for compact list display).
40
+ #
41
+ # @return [Integer] line count
42
+ def line_count
43
+ data.lines.count
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents a systemd journal line from GET /nodes/{node}/journal.
6
+ class JournalEntry < Base
7
+ attr_reader :n, :t
8
+
9
+ def initialize(attrs = {})
10
+ super(attrs)
11
+ @n = @attributes[:n]
12
+ @t = @attributes[:t]
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,85 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents a network interface on a Proxmox node.
6
+ #
7
+ # Immutable domain model containing network interface attributes and helper
8
+ # methods for display. Created by Repositories::Node from API data.
9
+ #
10
+ # @example Creating a NetworkInterface model
11
+ # iface = NetworkInterface.new(iface: "vmbr0", type: "bridge")
12
+ # iface.active? #=> true
13
+ #
14
+ # @example From API response
15
+ # data = { "iface" => "vmbr0", "type" => "bridge", "address" => "192.168.1.10/24" }
16
+ # iface = NetworkInterface.new(data)
17
+ #
18
+ # @see Pvectl::Repositories::Node Repository that creates NetworkInterface instances
19
+ #
20
+ class NetworkInterface < Base
21
+ # @return [String] interface name (e.g., "vmbr0", "eth0")
22
+ attr_reader :iface
23
+
24
+ # @return [String] interface type (bridge, bond, eth, vlan)
25
+ attr_reader :type
26
+
27
+ # @return [String, nil] IP address with CIDR (e.g., "192.168.1.10/24")
28
+ attr_reader :address
29
+
30
+ # @return [String, nil] gateway IP address
31
+ attr_reader :gateway
32
+
33
+ # @return [Integer] active flag (0/1)
34
+ attr_reader :active
35
+
36
+ # @return [Integer] autostart flag (0/1)
37
+ attr_reader :autostart
38
+
39
+ # @return [String, nil] bridge ports (for bridge type)
40
+ attr_reader :bridge_ports
41
+
42
+ # @return [String, nil] comments
43
+ attr_reader :comments
44
+
45
+ # Creates a new NetworkInterface model from attributes.
46
+ #
47
+ # @param attrs [Hash] NetworkInterface attributes from API (string or symbol keys)
48
+ def initialize(attrs = {})
49
+ super
50
+ @iface = attributes[:iface]
51
+ @type = attributes[:type]
52
+ @address = attributes[:address]
53
+ @gateway = attributes[:gateway]
54
+ @active = attributes[:active]
55
+ @autostart = attributes[:autostart]
56
+ @bridge_ports = attributes[:bridge_ports]
57
+ @comments = attributes[:comments]
58
+ end
59
+
60
+ # Checks if the interface is active.
61
+ #
62
+ # @return [Boolean] true if active flag is 1
63
+ def active?
64
+ active == 1
65
+ end
66
+
67
+ # Checks if the interface has a gateway configured.
68
+ #
69
+ # @return [Boolean] true if gateway is present and non-empty
70
+ def has_gateway?
71
+ !gateway.nil? && !gateway.to_s.empty?
72
+ end
73
+
74
+ # Returns IP address without CIDR suffix.
75
+ #
76
+ # @return [String, nil] IP address without CIDR, or nil if address is nil
77
+ # @example
78
+ # iface = NetworkInterface.new(address: "192.168.1.10/24")
79
+ # iface.ip_without_cidr #=> "192.168.1.10"
80
+ def ip_without_cidr
81
+ address&.split("/")&.first
82
+ end
83
+ end
84
+ end
85
+ end
@@ -0,0 +1,195 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents a node in the Proxmox cluster.
6
+ #
7
+ # Immutable domain model containing node attributes and domain predicates.
8
+ # Display formatting is handled by Presenters::Node.
9
+ # Created by Repositories::Node from API data.
10
+ #
11
+ # @example Creating a Node model
12
+ # node = Node.new(name: "pve1", status: "online", cpu: 0.23)
13
+ # node.online? #=> true
14
+ # node.guests_total #=> 42
15
+ #
16
+ # @example From API response
17
+ # data = { "node" => "pve1", "status" => "online", "cpu" => 0.23 }
18
+ # node = Node.new(data)
19
+ #
20
+ # @see Pvectl::Repositories::Node Repository that creates Node instances
21
+ # @see Pvectl::Presenters::Node Presenter for formatting Node data
22
+ #
23
+ class Node < Base
24
+ # @return [String] node name
25
+ attr_reader :name
26
+
27
+ # @return [String] node status (online/offline)
28
+ attr_reader :status
29
+
30
+ # @return [Float, nil] CPU usage (0-1 scale)
31
+ attr_reader :cpu
32
+
33
+ # @return [Integer, nil] total CPU cores
34
+ attr_reader :maxcpu
35
+
36
+ # @return [Integer, nil] memory used in bytes
37
+ attr_reader :mem
38
+
39
+ # @return [Integer, nil] total memory in bytes
40
+ attr_reader :maxmem
41
+
42
+ # @return [Integer, nil] local disk used in bytes
43
+ attr_reader :disk
44
+
45
+ # @return [Integer, nil] total local disk in bytes
46
+ attr_reader :maxdisk
47
+
48
+ # @return [Integer, nil] uptime in seconds
49
+ attr_reader :uptime
50
+
51
+ # @return [String, nil] subscription level (c=community, b=basic, etc.)
52
+ attr_reader :level
53
+
54
+ # @return [String, nil] Proxmox version (e.g., "8.3.2")
55
+ attr_reader :version
56
+
57
+ # @return [String, nil] kernel version (e.g., "6.8.12-1-pve")
58
+ attr_reader :kernel
59
+
60
+ # @return [Array<Float>, nil] load averages [1min, 5min, 15min]
61
+ attr_reader :loadavg
62
+
63
+ # @return [Integer, nil] swap used in bytes
64
+ attr_reader :swap_used
65
+
66
+ # @return [Integer, nil] total swap in bytes
67
+ attr_reader :swap_total
68
+
69
+ # @return [Integer] number of VMs on this node
70
+ attr_reader :guests_vms
71
+
72
+ # @return [Integer] number of containers on this node
73
+ attr_reader :guests_cts
74
+
75
+ # @return [String, nil] node IP address (from interface with gateway)
76
+ attr_reader :ip
77
+
78
+ # Extended attributes for describe command
79
+ # @return [Hash, nil] CPU info (model, cores, sockets)
80
+ attr_reader :cpuinfo
81
+
82
+ # @return [Hash, nil] boot info (mode: efi/bios)
83
+ attr_reader :boot_info
84
+
85
+ # @return [Hash, nil] root filesystem (used, total, free)
86
+ attr_reader :rootfs
87
+
88
+ # @return [Hash, nil] subscription info (status, level, productname)
89
+ attr_reader :subscription
90
+
91
+ # @return [Hash, nil] DNS configuration (search, dns1, dns2, dns3)
92
+ attr_reader :dns
93
+
94
+ # @return [Hash, nil] time configuration (timezone, localtime, time)
95
+ attr_reader :time_info
96
+
97
+ # @return [Array<Hash>] network interfaces
98
+ attr_reader :network_interfaces
99
+
100
+ # @return [Array<Hash>] system services
101
+ attr_reader :services
102
+
103
+ # @return [Array<Models::Storage>] storage pools
104
+ attr_reader :storage_pools
105
+
106
+ # @return [Array<Hash>] physical disks
107
+ attr_reader :physical_disks
108
+
109
+ # @return [Array<Hash>] QEMU CPU models
110
+ attr_reader :qemu_cpu_models
111
+
112
+ # @return [Array<Hash>] QEMU machine types
113
+ attr_reader :qemu_machines
114
+
115
+ # @return [Integer] number of available updates
116
+ attr_reader :updates_available
117
+
118
+ # @return [Array<Hash>] available updates
119
+ attr_reader :updates
120
+
121
+ # @return [String, nil] offline note message
122
+ attr_reader :offline_note
123
+
124
+ # @return [Hash, nil] firewall configuration data
125
+ attr_reader :firewall
126
+
127
+ # @return [Array] recent task history entries
128
+ attr_reader :tasks
129
+
130
+ # Creates a new Node model from attributes.
131
+ #
132
+ # @param attrs [Hash] Node attributes from API (string or symbol keys)
133
+ def initialize(attrs = {})
134
+ super(attrs)
135
+ @name = @attributes[:name] || @attributes[:node]
136
+ @status = @attributes[:status]
137
+ @cpu = @attributes[:cpu]
138
+ @maxcpu = @attributes[:maxcpu]
139
+ @mem = @attributes[:mem]
140
+ @maxmem = @attributes[:maxmem]
141
+ @disk = @attributes[:disk]
142
+ @maxdisk = @attributes[:maxdisk]
143
+ @uptime = @attributes[:uptime]
144
+ @level = @attributes[:level]
145
+ @version = @attributes[:version]
146
+ @kernel = @attributes[:kernel]
147
+ @loadavg = @attributes[:loadavg]
148
+ @swap_used = @attributes[:swap_used]
149
+ @swap_total = @attributes[:swap_total]
150
+ @guests_vms = @attributes[:guests_vms] || 0
151
+ @guests_cts = @attributes[:guests_cts] || 0
152
+ @ip = @attributes[:ip]
153
+ # Extended attributes for describe
154
+ @cpuinfo = @attributes[:cpuinfo]
155
+ @boot_info = @attributes[:boot_info]
156
+ @rootfs = @attributes[:rootfs]
157
+ @subscription = @attributes[:subscription]
158
+ @dns = @attributes[:dns]
159
+ @time_info = @attributes[:time_info]
160
+ @network_interfaces = @attributes[:network_interfaces] || []
161
+ @services = @attributes[:services] || []
162
+ @storage_pools = @attributes[:storage_pools] || []
163
+ @physical_disks = @attributes[:physical_disks] || []
164
+ @qemu_cpu_models = @attributes[:qemu_cpu_models] || []
165
+ @qemu_machines = @attributes[:qemu_machines] || []
166
+ @updates_available = @attributes[:updates_available] || 0
167
+ @updates = @attributes[:updates] || []
168
+ @offline_note = @attributes[:offline_note]
169
+ @firewall = @attributes[:firewall]
170
+ @tasks = @attributes[:tasks] || []
171
+ end
172
+
173
+ # Checks if the node is online.
174
+ #
175
+ # @return [Boolean] true if status is "online"
176
+ def online?
177
+ status == "online"
178
+ end
179
+
180
+ # Checks if the node is offline.
181
+ #
182
+ # @return [Boolean] true if status is not "online"
183
+ def offline?
184
+ !online?
185
+ end
186
+
187
+ # Returns total guest count (VMs + containers).
188
+ #
189
+ # @return [Integer] total guests
190
+ def guests_total
191
+ guests_vms + guests_cts
192
+ end
193
+ end
194
+ end
195
+ end
@@ -0,0 +1,45 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pvectl
4
+ module Models
5
+ # Represents the result of a set/edit operation on a node.
6
+ #
7
+ # Extends OperationResult with node-specific attribute.
8
+ #
9
+ # @example Successful set operation
10
+ # result = NodeOperationResult.new(node_model: node, operation: :set, success: true)
11
+ # result.node_model #=> #<Models::Node>
12
+ # result.successful? #=> true
13
+ #
14
+ class NodeOperationResult < OperationResult
15
+ # @return [Models::Node, nil] The node this result is for
16
+ attr_reader :node_model
17
+
18
+ # @return [String, nil] optional info message describing the successful
19
+ # outcome (e.g., "Wake-on-LAN packet sent (MAC: AA:BB:CC:DD:EE:FF)")
20
+ attr_reader :info
21
+
22
+ # Creates a new NodeOperationResult.
23
+ #
24
+ # @param attrs [Hash] Result attributes including :node_model
25
+ def initialize(attrs = {})
26
+ super
27
+ @node_model = @attributes[:node_model]
28
+ @info = @attributes[:message]
29
+ end
30
+
31
+ # Returns the result message for display.
32
+ #
33
+ # On success, prefers the optional `:message` attribute (set by services
34
+ # that want to surface an outcome detail like a MAC address). Otherwise
35
+ # falls back to the generic OperationResult logic (error / task / status).
36
+ #
37
+ # @return [String]
38
+ def message
39
+ return @info if successful? && @info
40
+
41
+ super
42
+ end
43
+ end
44
+ end
45
+ end