Merge pull request #38599 from tchaikov/wip-47977

ceph.in: try harder if asok path does not exist

Reviewed-by: Mykola Golub <mgolub@suse.com>
Reviewed-by: Xiubo Li <xiubli@redhat.com>
This commit is contained in:
Kefu Chai 2020-12-18 00:03:51 +08:00 committed by GitHub
commit 8bcfdad3a0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 39 additions and 49 deletions

View File

@ -84,6 +84,13 @@ Options
For example, if we specify ``--name osd.0``, the following sections will be
searched: [osd.0], [osd], [global]
.. option:: --pid *pid*
override the ``$pid`` when expanding options. For example, if an option is
configured like ``/var/log/$name.$pid.log``, the ``$pid`` portion in its
value will be substituded using the PID of **ceph-conf** instead of the
PID of the process specfied using the ``--name`` option.
.. option:: -r, --resolve-search
search for the first file that exists and can be opened in the resulted

View File

@ -20,11 +20,11 @@ Foundation. See file COPYING.
"""
from time import sleep
import codecs
import grp
import os
import pwd
import shutil
import stat
import sys
import time
import platform
@ -495,7 +495,7 @@ def format_help(cmddict, partial=None):
return fullusage
def ceph_conf(parsed_args, field, name):
def ceph_conf(parsed_args, field, name, pid=None):
cmd = 'ceph-conf'
bindir = os.path.dirname(__file__)
if shutil.which(cmd):
@ -507,6 +507,8 @@ def ceph_conf(parsed_args, field, name):
if name:
args.extend(['--name', name])
if pid:
args.extend(['--pid', pid])
# add any args in GLOBAL_ARGS
for key, val in GLOBAL_ARGS.items():
@ -526,6 +528,7 @@ def ceph_conf(parsed_args, field, name):
raise RuntimeError('unable to get conf option %s for %s: %s' % (field, name, errdata))
return outdata.rstrip()
PROMPT = 'ceph> '
if sys.stdin.isatty():
@ -730,6 +733,23 @@ def ping_monitor(cluster_handle, name, timeout):
return 0
def get_admin_socket(parsed_args, name):
path = ceph_conf(parsed_args, 'admin_socket', name)
try:
if stat.S_ISSOCK(os.stat(path).st_mode):
return path
except OSError:
pass
# try harder, probably the "name" option is in the form of
# "${name}.${pid}"?
parts = name.rsplit('.', 1)
if len(parts) > 1 and parts[-1].isnumeric():
name, pid = parts
return ceph_conf(parsed_args, 'admin_socket', name, pid)
else:
return path
def maybe_daemon_command(parsed_args, childargs):
"""
Check if --admin-socket, daemon, or daemonperf command
@ -751,8 +771,7 @@ def maybe_daemon_command(parsed_args, childargs):
else:
# try resolve daemon name
try:
sockpath = ceph_conf(parsed_args, 'admin_socket',
childargs[1])
sockpath = get_admin_socket(parsed_args, childargs[1])
except Exception as e:
print('Can\'t get admin socket path: ' + str(e), file=sys.stderr)
return True, errno.EINVAL

View File

@ -28,6 +28,7 @@
[--format plain|json|json-pretty]
dump variables in plain text, json or pretty
json
[--pid <pid>] Override the $pid when expanding options
If there is no action given, the action will default to --lookup.

View File

@ -30,7 +30,7 @@ Name option test to strip the PID
> [global]
> admin socket = \$name.asok
> EOF
$ ceph-conf --name client.admin.133423 --show-config-value admin_socket -c $TESTDIR/ceph.conf
$ ceph-conf --name client.admin --pid 133423 --show-config-value admin_socket -c $TESTDIR/ceph.conf
client.admin.133423.asok
$ ceph-conf --name mds.a --show-config-value admin_socket -c $TESTDIR/ceph.conf
mds.a.asok

View File

@ -55,6 +55,7 @@ FLAGS
[--format plain|json|json-pretty]
dump variables in plain text, json or pretty
json
[--pid <pid>] Override the $pid when expanding options
If there is no action given, the action will default to --lookup.
@ -163,45 +164,15 @@ static int dump_all(const string& format)
}
}
bool is_name_pid(std::string name, std::string& id)
{
if (id.empty()) {
return false;
}
static const char* daemon_types[] = {"mon", "osd", "mds", "mgr"};
if (std::find(std::begin(daemon_types), std::end(daemon_types), name) !=
std::end(daemon_types)) {
// only override name and pid for non-daemon names
return false;
}
try {
std::stoi(id);
} catch (const std::logic_error&) {
// only override pid for $id which looks like pid
return false;
}
return true;
}
std::pair<std::string, std::string>
maybe_override_name_pid(vector<const char*> args)
static void maybe_override_pid(vector<const char*>& args)
{
for (auto i = args.begin(); i != args.end(); ++i) {
string val;
if (ceph_argparse_witharg(args, i, &val, "--name", "-n", (char*)NULL)) {
size_t dot_pos = val.rfind('.');
if (dot_pos != val.npos) {
string name = val.substr(0, dot_pos);
string id = val.substr(dot_pos + 1);
if (is_name_pid(name, id)) {
// override name
return {name, id};
}
}
return {val, ""};
if (ceph_argparse_witharg(args, i, &val, "--pid", (char*)NULL)) {
setenv("PID", val.c_str(), 1);
break;
}
}
return {};
}
int main(int argc, const char **argv)
@ -220,16 +191,8 @@ int main(int argc, const char **argv)
auto orig_args = args;
auto cct = [&args] {
// override the name and PID for non-daemon names
auto [name, pid] = maybe_override_name_pid(args);
if (!name.empty()) {
// push the name option back
args.push_back("--name");
args.push_back(name.c_str());
}
if (!pid.empty()) {
setenv("PID", pid.c_str(), 1);
}
// override the PID before options are expanded
maybe_override_pid(args);
std::map<std::string,std::string> defaults = {{"log_to_file", "false"}};
return global_init(&defaults, args, CEPH_ENTITY_TYPE_CLIENT,
CODE_ENVIRONMENT_DAEMON,