PyCharm Integration

Rather than reinvent and implement the wheel, it would be super useful if Anvil made a PyCharm integration. Something where you can leverage the existing power of the platform. “Light weight” development on the anvil IDE if you want to.

4 Likes

I already requested something similar long time ago. Here is the answer: Anvil SDK for PyCharm

4 Likes

A lot of the autocomplete would be missing with that, I would have thought?

Be great to get an iframe-like-thing embedded in PyCharm for the Form building :slight_smile:
Best of all worlds.

2 Likes

Yes, running code outside of Anvil is useful. And now I realize it is possible that, you could copy server side code running in anvil to something like PyCharm, and then replace the server calls as uplink calls, but that seems error prone and tedious.

What I’m thinking of is an automated way to make that switch happen. Where you could say, click a button in PyCharm, link it to your app, and it automagically lets you switch between debugging on PyCharm, and letting the finished app run on the Anvil servers. And again, doing this switch manually for any project of any sort of production scale would be error prone, and tedious.

If you were running a greenfield project, you could just write all the server side calls as uplink calls to your local machine and then switch once the product was stable, but that also leaves the problem of not knowing how the app will perform on the anvil servers.

2 Likes

My guess is that creating a debugger for the client side code is difficult (python / skulpt / javascript / browser / …) and not worth, because usually the code on the client side is so little and simple that a few good old prints will do.

Debugging complex code that runs on the server side can be done with little effort by just running the server module locally (inside PyCharm) and having the form calling the functions defined in the uplink rather than in the server module.

You can have the same function defined on a server module and on an uplink module. When the uplink is running then its function will be called, when it is not running then the function with the same name defined in the server module will be called.

I haven’t used this technique in a long time because I haven’t worked with complex server modules in a long time, but I just did a quick test and everything seems to work fine.

I remember having some problems with some imports which I worked around using some try: import <from uplink> except: import <from server>.

I remember having also problems with performance: working with the database from here is slower than working from the server, so I wasn’t really comparing apples to apples. But this problem wouldn’t be solved by any PyCharm extension.

You will not be able to cover 100% of the Anvil functionalities (for example I couldn’t run SQL queries), but you will be able to debug complex modules inside PyCharm without problems.

In conclusion, I agree with you, I would really really really love to have an online debugger or one integrated with PyCharm, but I’m not expecting to see it any time soon. In the mean time there is a decent alternative worth using with complex server modules.

3 Likes

Hi Stefano

I use this a lot and works very well.
If there was a way to know, from server code, if it’s running in native Anvil environment, one could conditionally anvil.server.connect() and anvil.server.wait_forever().
That would make the code “universal” for both native and uplinked environments.

See https://anvil.works/docs/server/call-context

2 Likes

Oh that’s nice @p.colbert !
Many thanks!
So I have now this client code

  def form_show(self, **event_args):
    """This method is called when the HTML panel is shown on the screen"""
    server_call_result = anvil.server.call('my_server_function')
    self.text_area_1.text = server_call_result

This very same server code both on an Anvil server module and in PyCharm’s uplinked module:

import anvil.server

on_anvil = hasattr(anvil.server, 'context')
if not on_anvil:
  anvil.server.connect("<my-app-key>")


@anvil.server.callable
def my_server_function():
  ret_str = 'running on anvil' if on_anvil else 'running on uplink'
  return ret_str

if not on_anvil:
  anvil.server.wait_forever()

Works like a (py)charm…
Thanks again!

2 Likes

We’ve just upgraded the Uplink so that it has a call context with anvil.server.context.type set to uplink.

So @aldo.ercolani, if you pip install --upgrade anvil-uplink, you can change your code to use:

on_uplink = anvil.server.context.type == 'uplink'
if on_uplink:
  anvil.server.connect("<my-app-key>")

# ... etc ...

The anvil.server.context also contains remote_caller and client, so you can check what your Uplink was called by and the details of the user’s client.

8 Likes