#!/usr/bin/perl package PVE::CLI::pveclient; use strict; use warnings; use Cwd 'abs_path'; use Data::Dumper; use PVE::APIClient::JSONSchema qw(register_standard_option get_standard_option); use PVE::APIClient::CLIHandler; use PVE::APIClient::LWP; use PVE::APIClient::Helpers; use PVE::APIClient::Config; use PVE::APIClient::Commands::config; use PVE::APIClient::Commands::remote; use PVE::APIClient::Commands::list; use PVE::APIClient::Commands::lxc; use PVE::APIClient::Commands::GuestStatus; use JSON; sub call_api_method { my ($method, $param) = @_; my $path = PVE::APIClient::Tools::extract_param($param, 'api_path'); die "missing API path\n" if !defined($path); my $remote = PVE::APIClient::Tools::extract_param($param, 'remote'); die "missing remote\n" if !defined($remote); my $format = PVE::APIClient::Tools::extract_param($param, 'format'); PVE::APIClient::Helpers::set_output_format($format); my $config = PVE::APIClient::Config->load(); # test if api path exists my $info = PVE::APIClient::Helpers::lookup_api_method($path, $method); my $conn = PVE::APIClient::Config->remote_conn($config, $remote); my $res = $conn->call($method, "api2/json/$path", $param); die "undefined result" if !defined($res); die "undefined result data" if !exists($res->{data}); return $res->{data}; } use base qw(PVE::APIClient::CLIHandler); my $cmd = $ARGV[0]; if ($cmd && $cmd eq 'packagedepends') { # experimental code to print required perl packages my $packages = {}; my $dir = Cwd::getcwd; foreach my $k (keys %INC) { my $file = abs_path($INC{$k}); next if $file =~ m/^\Q$dir\E/; my $res = `dpkg -S '$file'`; if ($res && $res =~ m/^(\S+): $file$/) { my $debian_package = $1; $debian_package =~ s/:amd64$//; $packages->{$debian_package} = 1; } else { die "unable to find package for '$file'\n"; } } print join("\n", sort(keys %$packages)) . "\n"; exit(0); } my $path_properties = {}; my $path_returns = { type => 'null' }; # dynamically update schema definition for direct API call # like: pveclient api if (my $info = PVE::APIClient::Helpers::extract_path_info()) { $path_properties = $info->{parameters}->{properties}; $path_returns = $info->{returns}; } $path_properties->{format} = get_standard_option('pveclient-output-format'), $path_properties->{remote} = get_standard_option('pveclient-remote-name'); $path_properties->{api_path} = { description => "API path.", type => 'string', completion => sub { my ($cmd, $pname, $cur, $args) = @_; return PVE::APIClient::Helpers::complete_api_path($cur); }, }; my $format_result = sub { my ($data) = @_; PVE::APIClient::Helpers::print_result($data, $path_returns); }; __PACKAGE__->register_method ({ name => 'pveclient_get', path => 'pveclient_get', method => 'GET', description => "call API GET on .", parameters => { additionalProperties => 0, properties => $path_properties, }, returns => $path_returns, code => sub { my ($param) = @_; return call_api_method('GET', $param); }}); __PACKAGE__->register_method ({ name => 'pveclient_set', path => 'pveclient_set', method => 'PUT', description => "call API PUT on .", parameters => { additionalProperties => 0, properties => $path_properties, }, returns => $path_returns, code => sub { my ($param) = @_; return call_api_method('PUT', $param); }}); __PACKAGE__->register_method ({ name => 'pveclient_create', path => 'pveclient_create', method => 'PUSH', description => "call API PUSH on .", parameters => { additionalProperties => 0, properties => $path_properties, }, returns => $path_returns, code => sub { my ($param) = @_; return call_api_method('PUSH', $param); }}); __PACKAGE__->register_method ({ name => 'pveclient_delete', path => 'pveclient_delete', method => 'DELETE', description => "call API DELETE on .", parameters => { additionalProperties => 0, properties => $path_properties, }, returns => $path_returns, code => sub { my ($param) = @_; return call_api_method('DELETE', $param); }}); our $cmddef = { config => $PVE::APIClient::Commands::config::cmddef, list => $PVE::APIClient::Commands::list::cmddef, lxc => $PVE::APIClient::Commands::lxc::cmddef, remote => $PVE::APIClient::Commands::remote::cmddef, spice => [ 'PVE::APIClient::Commands::GuestStatus', 'spice', ['remote', 'vmid']], start => [ 'PVE::APIClient::Commands::GuestStatus', 'start', ['remote', 'vmid']], stop => [ 'PVE::APIClient::Commands::GuestStatus', 'stop', ['remote', 'vmid']], api => { get => [ __PACKAGE__, 'pveclient_get', ['remote', 'api_path'], {}, $format_result ], set => [ __PACKAGE__, 'pveclient_set', ['remote', 'api_path'], {}, $format_result ], create => [ __PACKAGE__, 'pveclient_create', ['remote', 'api_path'], {}, $format_result ], delete => [ __PACKAGE__, 'pveclient_delete', ['remote', 'api_path'], {}, $format_result ], }, }; __PACKAGE__->run_cli_handler();