See doc/mgr/hello.rst for more info.
"""
-from mgr_module import MgrModule, HandleCommandResult
+from mgr_module import CLIReadCommand, HandleCommandResult, MgrModule, Option
from threading import Event
+from typing import cast, Any, Optional, TYPE_CHECKING
import errno
-class Hello(MgrModule):
- # these are CLI commands we implement
- COMMANDS = [
- {
- "cmd": "hello "
- "name=person_name,type=CephString,req=false",
- "desc": "Say hello",
- "perm": "r"
- },
- {
- "cmd": "count "
- "name=num,type=CephInt",
- "desc": "Do some counting",
- "perm": "r"
- },
- ]
+class Hello(MgrModule):
# These are module options we understand. These can be set with
#
# ceph config set global mgr/hello/<name> <value>
# ceph config set global mgr/hello/place Earth
#
MODULE_OPTIONS = [
- {
- 'name': 'place',
- 'default': 'world',
- 'desc': 'a place in the world',
- 'runtime': True, # can be updated at runtime (no mgr restart)
- },
- {
- 'name': 'emphatic',
- 'type': 'bool',
- 'desc': 'whether to say it loudly',
- 'default': True,
- 'runtime': True,
- },
- {
- 'name': 'foo',
- 'type': 'enum',
- 'enum_allowed': [ 'a', 'b', 'c' ],
- 'default': 'a',
- 'runtime': True,
- },
+ Option(name='place',
+ default='world',
+ desc='a place in the world',
+ runtime=True), # can be updated at runtime (no mgr restart)
+ Option(name='emphatic',
+ type='bool',
+ desc='whether to say it loudly',
+ default=True,
+ runtime=True),
+ Option(name='foo',
+ type='str',
+ enum_allowed=['a', 'b', 'c'],
+ default='a',
+ runtime=True)
]
# These are "native" Ceph options that this module cares about.
'mgr_tick_period',
]
- def __init__(self, *args, **kwargs):
- super(Hello, self).__init__(*args, **kwargs)
+ def __init__(self, *args: Any, **kwargs: Any):
+ super().__init__(*args, **kwargs)
# set up some members to enable the serve() method and shutdown()
self.run = True
# ensure config options members are initialized; see config_notify()
self.config_notify()
+ # for mypy which does not run the code
+ if TYPE_CHECKING:
+ self.mgr_tick_period = 0
- def config_notify(self):
+ def config_notify(self) -> None:
"""
This method is called whenever one of our config options is changed.
"""
self.get_ceph_option(opt))
self.log.debug(' native option %s = %s', opt, getattr(self, opt))
- def handle_command(self, inbuf, cmd):
+ # there are CLI commands we implement
+ @CLIReadCommand('hello')
+ def hello(self, person_name: Optional[str] = None) -> HandleCommandResult:
+ """
+ Say hello
+ """
+ if person_name is None:
+ who = cast(str, self.get_module_option('place'))
+ else:
+ who = person_name
+ fin = '!' if self.get_module_option('emphatic') else ''
+ return HandleCommandResult(stdout=f'Hello, {who}{fin}')
+
+ @CLIReadCommand('count')
+ def count(self, num: int) -> HandleCommandResult:
+ """
+ Do some counting
+ """
ret = 0
out = ''
err = ''
- if cmd['prefix'] == 'hello':
- if 'person_name' in cmd:
- out = "Hello, " + cmd['person_name']
- else:
- out = "Hello " + self.get_module_option('place')
- if self.get_module_option('emphatic'):
- out += '!'
- elif cmd['prefix'] == 'count':
- num = cmd.get('num', 0)
- if num < 1:
- err = 'That\'s too small a number'
- ret = -errno.EINVAL
- elif num > 10:
- err = 'That\'s too big a number'
- ret = -errno.EINVAL
- else:
- out = 'Hello, I am the count!\n'
- out += ', '.join([str(x) for x in range(1, num + 1)]) + '!'
- return HandleCommandResult(
- retval=ret, # exit code
- stdout=out, # stdout
- stderr=err)
-
- def serve(self):
+ if num < 1:
+ err = 'That\'s too small a number'
+ ret = -errno.EINVAL
+ elif num > 10:
+ err = 'That\'s too big a number'
+ ret = -errno.EINVAL
+ else:
+ out = 'Hello, I am the count!\n'
+ out += ', '.join([str(x) for x in range(1, num + 1)]) + '!'
+ return HandleCommandResult(retval=ret,
+ stdout=out,
+ stderr=err)
+
+ def serve(self) -> None:
"""
This method is called by the mgr when the module starts and can be
used for any background activity.
# would presumably have some more appropriate frequency.
sleep_interval = self.mgr_tick_period
self.log.debug('Sleeping for %d seconds', sleep_interval)
- ret = self.event.wait(sleep_interval)
+ self.event.wait(sleep_interval)
self.event.clear()
- def shutdown(self):
+ def shutdown(self) -> None:
"""
This method is called by the mgr when the module needs to shut
down (i.e., when the serve() function needs to exit).