Skip to content

Commit 1072558

Browse files
committed
Split server and library wrapping to separate classes
1 parent 7ba6e10 commit 1072558

File tree

3 files changed

+73
-49
lines changed

3 files changed

+73
-49
lines changed

src/robotremoteserver.py

Lines changed: 62 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,6 @@
4646

4747
class RobotRemoteServer(SimpleXMLRPCServer):
4848
allow_reuse_address = True
49-
_generic_exceptions = (AssertionError, RuntimeError, Exception)
50-
_fatal_exceptions = (SystemExit, KeyboardInterrupt)
5149

5250
def __init__(self, library, host='127.0.0.1', port=8270, port_file=None,
5351
allow_stop=True):
@@ -65,7 +63,7 @@ def __init__(self, library, host='127.0.0.1', port=8270, port_file=None,
6563
``Stop Remote Server`` keyword.
6664
"""
6765
SimpleXMLRPCServer.__init__(self, (host, int(port)), logRequests=False)
68-
self._library = library
66+
self._library = RemoteLibrary(library, self.stop_remote_server)
6967
self._allow_stop = allow_stop
7068
self._shutdown = False
7169
self._register_functions()
@@ -117,6 +115,38 @@ def stop_remote_server(self):
117115
self._log(prefix + 'does not allow stopping.', 'WARN')
118116
return self._shutdown
119117

118+
def _log(self, msg, level=None):
119+
if level:
120+
msg = '*%s* %s' % (level.upper(), msg)
121+
self._write_to_stream(msg, sys.stdout)
122+
if sys.__stdout__ is not sys.stdout:
123+
self._write_to_stream(msg, sys.__stdout__)
124+
125+
def _write_to_stream(self, msg, stream):
126+
stream.write(msg + '\n')
127+
stream.flush()
128+
129+
def get_keyword_names(self):
130+
return self._library.get_keyword_names()
131+
132+
def run_keyword(self, name, args, kwargs=None):
133+
return self._library.run_keyword(name, args, kwargs)
134+
135+
def get_keyword_arguments(self, name):
136+
return self._library.get_keyword_arguments(name)
137+
138+
def get_keyword_documentation(self, name):
139+
return self._library.get_keyword_documentation(name)
140+
141+
142+
class RemoteLibrary(object):
143+
_generic_exceptions = (AssertionError, RuntimeError, Exception)
144+
_fatal_exceptions = (SystemExit, KeyboardInterrupt)
145+
146+
def __init__(self, library, stop_remote_server=None):
147+
self._library = library
148+
self._stop_remote_server = stop_remote_server
149+
120150
def get_keyword_names(self):
121151
get_kw_names = (getattr(self._library, 'get_keyword_names', None) or
122152
getattr(self._library, 'getKeywordNames', None))
@@ -125,7 +155,9 @@ def get_keyword_names(self):
125155
else:
126156
names = [attr for attr in dir(self._library) if attr[0] != '_' and
127157
self._is_function_or_method(getattr(self._library, attr))]
128-
return names + ['stop_remote_server']
158+
if self._stop_remote_server:
159+
names.append('stop_remote_server')
160+
return names
129161

130162
def _is_function_or_method(self, item):
131163
return inspect.isfunction(item) or inspect.ismethod(item)
@@ -178,35 +210,9 @@ def _add_to_result(self, result, key, value, default=''):
178210
if value != default:
179211
result[key] = value
180212

181-
def get_keyword_arguments(self, name):
182-
kw = self._get_keyword(name)
183-
if not kw:
184-
return []
185-
return self._arguments_from_kw(kw)
186-
187-
def _arguments_from_kw(self, kw):
188-
args, varargs, kwargs, defaults = inspect.getargspec(kw)
189-
if inspect.ismethod(kw):
190-
args = args[1:] # drop 'self'
191-
if defaults:
192-
args, names = args[:-len(defaults)], args[-len(defaults):]
193-
args += ['%s=%s' % (n, d) for n, d in zip(names, defaults)]
194-
if varargs:
195-
args.append('*%s' % varargs)
196-
if kwargs:
197-
args.append('**%s' % kwargs)
198-
return args
199-
200-
def get_keyword_documentation(self, name):
201-
if name == '__intro__':
202-
return inspect.getdoc(self._library) or ''
203-
if name == '__init__' and inspect.ismodule(self._library):
204-
return ''
205-
return inspect.getdoc(self._get_keyword(name)) or ''
206-
207213
def _get_keyword(self, name):
208214
if name == 'stop_remote_server':
209-
return self.stop_remote_server
215+
return self._stop_remote_server
210216
kw = getattr(self._library, name, None)
211217
if not self._is_function_or_method(kw):
212218
return None
@@ -301,19 +307,35 @@ def _restore_std_streams(self):
301307
stdout += '\n'
302308
return self._handle_binary_result(stdout + stderr)
303309

304-
def _log(self, msg, level=None):
305-
if level:
306-
msg = '*%s* %s' % (level.upper(), msg)
307-
self._write_to_stream(msg, sys.stdout)
308-
if sys.__stdout__ is not sys.stdout:
309-
self._write_to_stream(msg, sys.__stdout__)
310+
def get_keyword_arguments(self, name):
311+
kw = self._get_keyword(name)
312+
if not kw:
313+
return []
314+
return self._arguments_from_kw(kw)
310315

311-
def _write_to_stream(self, msg, stream):
312-
stream.write(msg + '\n')
313-
stream.flush()
316+
def _arguments_from_kw(self, kw):
317+
args, varargs, kwargs, defaults = inspect.getargspec(kw)
318+
if inspect.ismethod(kw):
319+
args = args[1:] # drop 'self'
320+
if defaults:
321+
args, names = args[:-len(defaults)], args[-len(defaults):]
322+
args += ['%s=%s' % (n, d) for n, d in zip(names, defaults)]
323+
if varargs:
324+
args.append('*%s' % varargs)
325+
if kwargs:
326+
args.append('**%s' % kwargs)
327+
return args
328+
329+
def get_keyword_documentation(self, name):
330+
if name == '__intro__':
331+
return inspect.getdoc(self._library) or ''
332+
if name == '__init__' and inspect.ismodule(self._library):
333+
return ''
334+
return inspect.getdoc(self._get_keyword(name)) or ''
314335

315336

316337
if __name__ == '__main__':
338+
317339
def stop(uri):
318340
server = test(uri, log_success=False)
319341
if server is not None:

test/utest/test_argsdocs.py

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
import unittest
44

5-
from test_robotremoteserver import NonServingRemoteServer
5+
from robotremoteserver import RemoteLibrary
66

77

88
class LibraryWithArgsAndDocs:
@@ -37,11 +37,13 @@ def test_init_doc(self):
3737
self._test_doc('__init__', 'Init doc')
3838

3939
def test_init_doc_when_old_style_lib_has_no_init(self):
40-
class OldStyleLibraryWithoutInit: pass
40+
class OldStyleLibraryWithoutInit:
41+
pass
4142
self._test_doc('__init__', '', OldStyleLibraryWithoutInit())
4243

4344
def test_init_doc_when_new_style_lib_has_no_init(self):
44-
class NewStyleLibraryWithoutInit(object): pass
45+
class NewStyleLibraryWithoutInit(object):
46+
pass
4547
self._test_doc('__init__', '', NewStyleLibraryWithoutInit())
4648

4749
def test_keyword_doc_from_module_keyword(self):
@@ -57,8 +59,8 @@ def test_intro_doc_from_module(self):
5759
self._test_doc('__intro__', 'Module doc - used in tests', test_argsdocs)
5860

5961
def _test_doc(self, name, expected, library=LibraryWithArgsAndDocs(None)):
60-
server = NonServingRemoteServer(library)
61-
self.assertEquals(server.get_keyword_documentation(name), expected)
62+
library = RemoteLibrary(library)
63+
self.assertEquals(library.get_keyword_documentation(name), expected)
6264

6365

6466
class TestArgs(unittest.TestCase):
@@ -75,8 +77,8 @@ def test_keyword_args_from_module_keyword(self):
7577
test_argsdocs)
7678

7779
def _test_args(self, name, expected, library=LibraryWithArgsAndDocs(None)):
78-
server = NonServingRemoteServer(library)
79-
self.assertEquals(server.get_keyword_arguments(name), expected)
80+
library = RemoteLibrary(library)
81+
self.assertEquals(library.get_keyword_arguments(name), expected)
8082

8183

8284
if __name__ == '__main__':

test/utest/test_robotremoteserver.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,13 +3,13 @@
33
import unittest
44
import sys
55

6-
from robotremoteserver import RobotRemoteServer
6+
from robotremoteserver import RobotRemoteServer, RemoteLibrary
77

88

99
class NonServingRemoteServer(RobotRemoteServer):
1010

1111
def __init__(self, library):
12-
self._library = library
12+
self._library = RemoteLibrary(library, self.stop_remote_server)
1313

1414

1515
class StaticLibrary:

0 commit comments

Comments
 (0)