'Fault' in rpc call

Hi guys,

I’m reopening an older script by @romana, that makes an rpc call from Grasshopper.

The script used to run without problems, but on different machines I now get the following error.

I have no idea what goes wrong. Can anyone point me in the right direction?

Runtime error (Exception): Fault

Traceback:
  line 1316, in single_request, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 1283, in request, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 1598, in _ServerProxy__request, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 800, in close, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 1493, in parse_response, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 1243, in __call__, "C:\Program Files\Rhino 7\Plug-ins\IronPython\Lib\xmlrpclib.py"
  line 406, in _proxy, "C:\Users\shwde\AppData\Roaming\McNeel\Rhinoceros\7.0\scripts\compas\rpc\proxy.py"
  line 12, in script
1 Like

can you check if acoustic_panel.panel_creator.create_panel is importable from the active environment outside of Rhino? for example by activating the environment in the anaconda prompt and importing it from an interactive python interpreter…

Thanks for your reply!

Like this?

(base) C:\Users\shwde>conda activate acoustic_panel_system

(acoustic_panel_system) C:\Users\shwde>python
Python 3.7.12 | packaged by conda-forge | (default, Oct 26 2021, 05:35:01) [MSC v.1916 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import acoustic_panel_system.panel_creator
>>> print(acoustic_panel_system.panel_creator.create_panel)
<function create_panel at 0x0000025E408D13A8>
>>>

and is that the environment that is installed in Rhino?

It’s installed according to this procedure:

  1. Clone the repository.
  2. Create a virtual environment. Open an Anaconda Promt and type the following:

$ conda create -n acoustic_panel_system python=3.7 compas compas_nurbs -c conda-forge --yes
$ conda activate acoustic_panel_system

  1. Install development dependencies:

$ cd C:\Users\YOUR_LOCAL_GITHUB_REPO $ pip install -r requirements.txt

  1. Make the project accessible from Rhino

$ python -m compas_rhino.install -v 6.0

  1. Open GH located in src\acoustic_panel_system\grasshopper\main.ghx
  2. Start RPC: Open an Anaconda Promt and type the following:

$ conda activate acoustic_panel_system $ compas_rpc start

  • what is the return type of the create_panel function?
  • what happens when you run the function from the command line?
  • what happens when you run the function from the command line via RPC?
Returns
-------
:class:`PanelSystem`
    The result as a container class containing the surface and other relevant settings.

A PanelSystem object.

>>>from compas.geometry import Point
>>>acoustic_panel_system.panel_creator.create_panel({'low_res_y': 0.050000000000000003, 'low_res_x': 0.84999999999999998, 'surface_degree_v': 5, 'high_res_distortion': 0.074999999999999997, 'low_res_distortion': 0.29999999999999999, 'high_res_y': 0.037499999999999999, 'high_res_x': 0.21249999999999999, 'panel_height': 0.29999999999999999}, 24, 0.1, [Point(0.013, 2.033, 0.000), Point(10.523, 2.033, 0.000), Point(10.523, 4.278, 0.000), Point(0.013, 4.278, 0.000)], 0.1, [Point(0.013, 3.377, 0.000), Point(0.013, 2.432, 0.000), Point(1.083, 2.432, 0.000), Point(1.095, 2.432, 0.000), Point(2.255, 2.432, 0.000), Point(2.267, 2.432, 0.000), Point(2.267, 2.033, 0.000), Point(3.117, 2.033, 0.000), Point(3.117, 2.283, 0.000), Point(3.129, 2.283, 0.000), Point(3.979, 2.283, 0.000), Point(3.979, 2.533, 0.000), Point(3.991, 2.533, 0.000), Point(4.841, 2.533, 0.000), Point(4.853, 2.533, 0.000), Point(4.853, 2.283, 0.000), Point(5.703, 2.283, 0.000), Point(5.715, 2.283, 0.000), Point(5.715, 2.033, 0.000), Point(6.565, 2.033, 0.000), Point(6.565, 2.283, 0.000), Point(6.577, 2.283, 0.000), Point(7.427, 2.283, 0.000), Point(7.427, 2.533, 0.000), Point(7.439, 2.533, 0.000), Point(8.289, 2.533, 0.000), Point(8.301, 2.533, 0.000), Point(8.301, 2.432, 0.000), Point(9.461, 2.432, 0.000), Point(9.473, 2.432, 0.000), Point(10.523, 2.432, 0.000), Point(10.523, 3.377, 0.000), Point(9.473, 3.377, 0.000), Point(9.461, 3.377, 0.000), Point(9.461, 3.778, 0.000), Point(8.301, 3.778, 0.000), Point(8.301, 3.278, 0.000), Point(8.289, 3.278, 0.000), Point(7.439, 3.278, 0.000), Point(7.427, 3.278, 0.000), Point(7.427, 4.028, 0.000), Point(6.577, 4.028, 0.000), Point(6.577, 3.528, 0.000), Point(6.565, 3.528, 0.000), Point(5.715, 3.528, 0.000), Point(5.703, 3.528, 0.000), Point(5.703, 4.278, 0.000), Point(4.853, 4.278, 0.000), Point(4.853, 3.778, 0.000), Point(4.841, 3.778, 0.000), Point(3.991, 3.778, 0.000), Point(3.991, 3.278, 0.000), Point(3.979, 3.278, 0.000), Point(3.129, 3.278, 0.000), Point(3.117, 3.278, 0.000), Point(3.117, 4.028, 0.000), Point(2.267, 4.028, 0.000), Point(2.267, 3.778, 0.000), Point(2.255, 3.778, 0.000), Point(1.095, 3.778, 0.000), Point(1.095, 3.377, 0.000), Point(1.083, 3.377, 0.000)], [Point(-0.000, 0.000, 0.000), Point(0.201, 0.000, 0.000), Point(0.463, 0.220, 0.000), Point(10.110, 0.220, 0.000), Point(10.372, 0.000, 0.000), Point(10.525, 0.000, 0.000)])
<acoustic_panel_system.panel_system.PanelSystem object at 0x00000248BA5F2808>

So that seems alright.

proxy.create_panel({'low_res_y': 0.050000000000000003, 'low_res_x': 0.84999999999999998, 'surface_degree_v': 5, 'high_res_distortion': 0.074999999999999997, 'low_res_distortion': 0.29999999999999999, 'high_res_y': 0.037499999999999999, 'high_res_x': 0.21249999999999999, 'panel_height': 0.29999999999999999}, 24, 0.1, [Point(0.013, 2.033, 0.000), Point(10.523, 2.033, 0.000), Point(10.523, 4.278, 0.000), Point(0.013, 4.278, 0.000)], 0.1, [Point(0.013, 3.377, 0.000), Point(0.013, 2.432, 0.000), Point(1.083, 2.432, 0.000), Point(1.095, 2.432, 0.000), Point(2.255, 2.432, 0.000), Point(2.267, 2.432, 0.000), Point(2.267, 2.033, 0.000), Point(3.117, 2.033, 0.000), Point(3.117, 2.283, 0.000), Point(3.129, 2.283, 0.000), Point(3.979, 2.283, 0.000), Point(3.979, 2.533, 0.000), Point(3.991, 2.533, 0.000), Point(4.841, 2.533, 0.000), Point(4.853, 2.533, 0.000), Point(4.853, 2.283, 0.000), Point(5.703, 2.283, 0.000), Point(5.715, 2.283, 0.000), Point(5.715, 2.033, 0.000), Point(6.565, 2.033, 0.000), Point(6.565, 2.283, 0.000), Point(6.577, 2.283, 0.000), Point(7.427, 2.283, 0.000), Point(7.427, 2.533, 0.000), Point(7.439, 2.533, 0.000), Point(8.289, 2.533, 0.000), Point(8.301, 2.533, 0.000), Point(8.301, 2.432, 0.000), Point(9.461, 2.432, 0.000), Point(9.473, 2.432, 0.000), Point(10.523, 2.432, 0.000), Point(10.523, 3.377, 0.000), Point(9.473, 3.377, 0.000), Point(9.461, 3.377, 0.000), Point(9.461, 3.778, 0.000), Point(8.301, 3.778, 0.000), Point(8.301, 3.278, 0.000), Point(8.289, 3.278, 0.000), Point(7.439, 3.278, 0.000), Point(7.427, 3.278, 0.000), Point(7.427, 4.028, 0.000), Point(6.577, 4.028, 0.000), Point(6.577, 3.528, 0.000), Point(6.565, 3.528, 0.000), Point(5.715, 3.528, 0.000), Point(5.703, 3.528, 0.000), Point(5.703, 4.278, 0.000), Point(4.853, 4.278, 0.000), Point(4.853, 3.778, 0.000), Point(4.841, 3.778, 0.000), Point(3.991, 3.778, 0.000), Point(3.991, 3.278, 0.000), Point(3.979, 3.278, 0.000), Point(3.129, 3.278, 0.000), Point(3.117, 3.278, 0.000), Point(3.117, 4.028, 0.000), Point(2.267, 4.028, 0.000), Point(2.267, 3.778, 0.000), Point(2.255, 3.778, 0.000), Point(1.095, 3.778, 0.000), Point(1.095, 3.377, 0.000), Point(1.083, 3.377, 0.000)], [Point(-0.000, 0.000, 0.000), Point(0.201, 0.000, 0.000), Point(0.463, 0.220, 0.000), Point(10.110, 0.220, 0.000), Point(10.372, 0.000, 0.000), Point(10.525, 0.000, 0.000)])
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\site-packages\compas\rpc\proxy.py", line 406, in _proxy
    ostring = self._function(istring, self._path or "")
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 1112, in __call__
    return self.__send(self.__name, args)
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 1452, in __request
    verbose=self.__verbose
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 1154, in request
    return self.single_request(host, handler, request_body, verbose)
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 1170, in single_request
    return self.parse_response(resp)
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 1342, in parse_response
    return u.close()
  File "C:\Users\shwde\anaconda3\envs\acoustic_panel_system\lib\xmlrpc\client.py", line 656, in close
    raise Fault(**self._stack[0])
xmlrpc.client.Fault: <Fault 1: "<class 'AttributeError'>:'PanelSystem' object has no attribute '_guid'">

Which gives some more information, but I’m not sure how to interpreted it…

the return type of the function is a custom class.

COMPAS RPC does not support custom data types since it has no way of knowing how to serialize and unserialize this to and from JSON.

if you want to use custom data types, you will have to base them on compas.data.Data and define a data property that is compatible with JSON serialization.

Thanks for your clarification,

Did this change recently?

This function used to run without problems.

no, it was always like this…

sorry, i only just now notice this. perhaps worth to investigate what the problem is with the _guid attribute…

Sorry for coming late to the conversation:
The problem was that the repo requirements did not point to a specific compas version. And so when reinstalling, the latest compas version (1.17) was downloaded.
earlier compas versions only required from_data, to_data methods for data objects to be serialized via rpc. As of compas version 1.16 they additionally require guid.
The solution was simply to base the class correctly on compas.data.Data and update the repo requirements.

1 Like