test_celery.py 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281
  1. from __future__ import absolute_import, unicode_literals
  2. import pytest
  3. import sys
  4. from case import Mock, patch
  5. from celery import __main__
  6. from celery.five import WhateverIO
  7. from celery.platforms import EX_FAILURE, EX_USAGE, EX_OK
  8. from celery.bin.base import Error
  9. from celery.bin import celery as mod
  10. from celery.bin.celery import (
  11. Command,
  12. help,
  13. report,
  14. CeleryCommand,
  15. determine_exit_status,
  16. multi,
  17. main as mainfun,
  18. )
  19. class test__main__:
  20. def test_main(self):
  21. with patch('celery.__main__.maybe_patch_concurrency') as mpc:
  22. with patch('celery.bin.celery.main') as main:
  23. __main__.main()
  24. mpc.assert_called_with()
  25. main.assert_called_with()
  26. def test_main__multi(self):
  27. with patch('celery.__main__.maybe_patch_concurrency') as mpc:
  28. with patch('celery.bin.celery.main') as main:
  29. prev, sys.argv = sys.argv, ['foo', 'multi']
  30. try:
  31. __main__.main()
  32. mpc.assert_not_called()
  33. main.assert_called_with()
  34. finally:
  35. sys.argv = prev
  36. class test_Command:
  37. def test_Error_repr(self):
  38. x = Error('something happened')
  39. assert x.status is not None
  40. assert x.reason
  41. assert str(x)
  42. def setup(self):
  43. self.out = WhateverIO()
  44. self.err = WhateverIO()
  45. self.cmd = Command(self.app, stdout=self.out, stderr=self.err)
  46. def test_error(self):
  47. self.cmd.out = Mock()
  48. self.cmd.error('FOO')
  49. self.cmd.out.assert_called()
  50. def test_out(self):
  51. f = Mock()
  52. self.cmd.out('foo', f)
  53. def test_call(self):
  54. def ok_run():
  55. pass
  56. self.cmd.run = ok_run
  57. assert self.cmd() == EX_OK
  58. def error_run():
  59. raise Error('error', EX_FAILURE)
  60. self.cmd.run = error_run
  61. assert self.cmd() == EX_FAILURE
  62. def test_run_from_argv(self):
  63. with pytest.raises(NotImplementedError):
  64. self.cmd.run_from_argv('prog', ['foo', 'bar'])
  65. def test_pretty_list(self):
  66. assert self.cmd.pretty([])[1] == '- empty -'
  67. assert 'bar', self.cmd.pretty(['foo' in 'bar'][1])
  68. def test_pretty_dict(self, text='the quick brown fox'):
  69. assert 'OK' in str(self.cmd.pretty({'ok': text})[0])
  70. assert 'ERROR' in str(self.cmd.pretty({'error': text})[0])
  71. def test_pretty(self):
  72. assert 'OK' in str(self.cmd.pretty('the quick brown'))
  73. assert 'OK' in str(self.cmd.pretty(object()))
  74. assert 'OK' in str(self.cmd.pretty({'foo': 'bar'}))
  75. class test_report:
  76. def test_run(self):
  77. out = WhateverIO()
  78. r = report(app=self.app, stdout=out)
  79. assert r.run() == EX_OK
  80. assert out.getvalue()
  81. class test_help:
  82. def test_run(self):
  83. out = WhateverIO()
  84. h = help(app=self.app, stdout=out)
  85. h.parser = Mock()
  86. assert h.run() == EX_USAGE
  87. assert out.getvalue()
  88. assert h.usage('help')
  89. h.parser.print_help.assert_called_with()
  90. class test_CeleryCommand:
  91. def test_execute_from_commandline(self):
  92. x = CeleryCommand(app=self.app)
  93. x.handle_argv = Mock()
  94. x.handle_argv.return_value = 1
  95. with pytest.raises(SystemExit):
  96. x.execute_from_commandline()
  97. x.handle_argv.return_value = True
  98. with pytest.raises(SystemExit):
  99. x.execute_from_commandline()
  100. x.handle_argv.side_effect = KeyboardInterrupt()
  101. with pytest.raises(SystemExit):
  102. x.execute_from_commandline()
  103. x.respects_app_option = True
  104. with pytest.raises(SystemExit):
  105. x.execute_from_commandline(['celery', 'multi'])
  106. assert not x.respects_app_option
  107. x.respects_app_option = True
  108. with pytest.raises(SystemExit):
  109. x.execute_from_commandline(['manage.py', 'celery', 'multi'])
  110. assert not x.respects_app_option
  111. def test_with_pool_option(self):
  112. x = CeleryCommand(app=self.app)
  113. assert x.with_pool_option(['celery', 'events']) is None
  114. assert x.with_pool_option(['celery', 'worker'])
  115. assert x.with_pool_option(['manage.py', 'celery', 'worker'])
  116. def test_load_extensions_no_commands(self):
  117. with patch('celery.bin.celery.Extensions') as Ext:
  118. ext = Ext.return_value = Mock(name='Extension')
  119. ext.load.return_value = None
  120. x = CeleryCommand(app=self.app)
  121. x.load_extension_commands()
  122. def test_load_extensions_commands(self):
  123. with patch('celery.bin.celery.Extensions') as Ext:
  124. prev, mod.command_classes = list(mod.command_classes), Mock()
  125. try:
  126. ext = Ext.return_value = Mock(name='Extension')
  127. ext.load.return_value = ['foo', 'bar']
  128. x = CeleryCommand(app=self.app)
  129. x.load_extension_commands()
  130. mod.command_classes.append.assert_called_with(
  131. ('Extensions', ['foo', 'bar'], 'magenta'),
  132. )
  133. finally:
  134. mod.command_classes = prev
  135. def test_determine_exit_status(self):
  136. assert determine_exit_status('true') == EX_OK
  137. assert determine_exit_status('') == EX_FAILURE
  138. def test_relocate_args_from_start(self):
  139. x = CeleryCommand(app=self.app)
  140. assert x._relocate_args_from_start(None) == []
  141. relargs1 = x._relocate_args_from_start([
  142. '-l', 'debug', 'worker', '-c', '3', '--foo',
  143. ])
  144. assert relargs1 == ['worker', '-c', '3', '--foo', '-l', 'debug']
  145. relargs2 = x._relocate_args_from_start([
  146. '--pool=gevent', '-l', 'debug', 'worker', '--foo', '-c', '3',
  147. ])
  148. assert relargs2 == [
  149. 'worker', '--foo', '-c', '3',
  150. '--pool=gevent', '-l', 'debug',
  151. ]
  152. assert x._relocate_args_from_start(['foo', '--foo=1']) == [
  153. 'foo', '--foo=1',
  154. ]
  155. def test_register_command(self):
  156. prev, CeleryCommand.commands = dict(CeleryCommand.commands), {}
  157. try:
  158. fun = Mock(name='fun')
  159. CeleryCommand.register_command(fun, name='foo')
  160. assert CeleryCommand.commands['foo'] is fun
  161. finally:
  162. CeleryCommand.commands = prev
  163. def test_handle_argv(self):
  164. x = CeleryCommand(app=self.app)
  165. x.execute = Mock()
  166. x.handle_argv('celery', [])
  167. x.execute.assert_called_with('help', ['help'])
  168. x.handle_argv('celery', ['start', 'foo'])
  169. x.execute.assert_called_with('start', ['start', 'foo'])
  170. def test_execute(self):
  171. x = CeleryCommand(app=self.app)
  172. Help = x.commands['help'] = Mock()
  173. help = Help.return_value = Mock()
  174. x.execute('fooox', ['a'])
  175. help.run_from_argv.assert_called_with(x.prog_name, [], command='help')
  176. help.reset()
  177. x.execute('help', ['help'])
  178. help.run_from_argv.assert_called_with(x.prog_name, [], command='help')
  179. Dummy = x.commands['dummy'] = Mock()
  180. dummy = Dummy.return_value = Mock()
  181. exc = dummy.run_from_argv.side_effect = Error(
  182. 'foo', status='EX_FAILURE',
  183. )
  184. x.on_error = Mock(name='on_error')
  185. help.reset()
  186. x.execute('dummy', ['dummy'])
  187. x.on_error.assert_called_with(exc)
  188. dummy.run_from_argv.assert_called_with(
  189. x.prog_name, [], command='dummy',
  190. )
  191. help.run_from_argv.assert_called_with(
  192. x.prog_name, [], command='help',
  193. )
  194. exc = dummy.run_from_argv.side_effect = x.UsageError('foo')
  195. x.on_usage_error = Mock()
  196. x.execute('dummy', ['dummy'])
  197. x.on_usage_error.assert_called_with(exc)
  198. def test_on_usage_error(self):
  199. x = CeleryCommand(app=self.app)
  200. x.error = Mock()
  201. x.on_usage_error(x.UsageError('foo'), command=None)
  202. x.error.assert_called()
  203. x.on_usage_error(x.UsageError('foo'), command='dummy')
  204. def test_prepare_prog_name(self):
  205. x = CeleryCommand(app=self.app)
  206. main = Mock(name='__main__')
  207. main.__file__ = '/opt/foo.py'
  208. with patch.dict(sys.modules, __main__=main):
  209. assert x.prepare_prog_name('__main__.py') == '/opt/foo.py'
  210. assert x.prepare_prog_name('celery') == 'celery'
  211. class test_multi:
  212. def test_get_options(self):
  213. assert multi(app=self.app).get_options() is None
  214. def test_run_from_argv(self):
  215. with patch('celery.bin.multi.MultiTool') as MultiTool:
  216. m = MultiTool.return_value = Mock()
  217. multi(self.app).run_from_argv('celery', ['arg'], command='multi')
  218. m.execute_from_commandline.assert_called_with(['multi', 'arg'])
  219. class test_main:
  220. @patch('celery.bin.celery.CeleryCommand')
  221. def test_main(self, Command):
  222. cmd = Command.return_value = Mock()
  223. mainfun()
  224. cmd.execute_from_commandline.assert_called_with(None)
  225. @patch('celery.bin.celery.CeleryCommand')
  226. def test_main_KeyboardInterrupt(self, Command):
  227. cmd = Command.return_value = Mock()
  228. cmd.execute_from_commandline.side_effect = KeyboardInterrupt()
  229. mainfun()
  230. cmd.execute_from_commandline.assert_called_with(None)