So, Roger from the Crossbar forums suggested I write a blog post describing how to use my new IDE to build some of the Crossbar examples, sounded like a good idea. What could possibly go wrong?!

Well, problem number one is the complete change in emphasis. The examples are designed to just "get something going", whereas the IDE is dedicated to churning out finished applications, so my first problem is that most of the code in the examples is obsolete .. which makes it 'look' like I'm cheating in some way, but that's pretty much the point - the stuff that looks hard, it's not there any more.

So, I decided to go for the slow squared example .. now I ended up doing things I don't normally do so found a gaggle of minor bugs (which is good!) but essentially it went Ok.

Create a Project

Choose "New Project" from the drop-down and enter "Examples" as a project title. This opens a file-tree on the left and creates a "project" tab and a new drop-down menu called "Examples".

Next we paste in the config.json file from the example into crossbar_io/config/config.json and amend slightly to reflect that we're using WSGI rather than static file handling (Note: to be automated);

"/": {
    "type": "wsgi",
    "module": "lib_wsgi",
    "object": "app"
},        

Now from the "Examples" project drop-down we select "New Microservice", and call it "slowsquare". This will produce a new tree fragment on the left hand side. Next, open up the default config.ini file as we're going to need to customise a little to match the credentials used in the demo;

So we now need to create the two RPC calls used by the example, topic titles are implicit based on the path, so we go into slowsquare/rpc and create a subfolder com and a further sub-folder math, and inside here we paste in the two procedures from the demo;

(the little yellow triangle in the border is just pylint complaining that self and details are unused in the function)

Next we have a couple of static assets to add, namely the demo HTML file and associated JS files. So we paste frontend.js into static/app and the HTML file as index.html into static/html, and prepend app to the include path inside the index.html, like so;

And that should pretty much be it!

Launch Control

All that remains is to see what we've missed, so F5 will build and run all open projects. All being well we should see two windows appear, one containing a Crossbar instance, and another containing the slowsquare microservice .. just for fun each service window shows the real-time CPU usage of the service, together with accumulated SYS and USR time for the process;

Moment of truth

All that remains is to point a browser at http://localhost:8080/ and we're away ...

Moving on ...

Yes there are some "rules" to learn, but much of the code used can be "overridden", it's just that the majority of the configuration I'm using has been built on years of experience of using Crossbar and can be (re)applied in many contexts without starting from scratch. Although for example the demo works with http and static authentication, the standard templates I use work with https, dynamic authentication, dynamic authorization, and a bunch of other useful stuff "out of the box".

You can open and run multiple projects simultaneously, drag/drop between projects, upload groups of files, or indeed archive files and right-click + unpack.

If you make a change anywhere in the tree then request "run", it will attempt to discover "which" of the Crossbar + microservices have been affected and automatically restart as required in the same windows. The Run screen is a drag-drop resize to which you can add your own terminal sessions, etc etc.

Anyway I have some bugs to work on and lots more features to add, but in principle the demo's "could" be provided as an archive that you could load into the GUI and simply "run", so this process is way more "long-winded" than technically "necessary", but useful for demonstration purposes.

Footnote ..

The generated code for slowsquare.py, for anyone interested, looks something like this ...

"""Custom module for microservice implementation"""
from twisted.internet.defer import inlineCallbacks
from autobahn.wamp.types import RegisterOptions
from microservice import Config, ServerComponent

import rpc_com_math_square
import rpc_com_math_slowsquare

class MicroService(ServerComponent):
    """Microservice wrapper class"""
    pass

@inlineCallbacks
def onJoin(self, details):
    """Override class onJoin with dynamically generated registers"""
    options = RegisterOptions(details_arg='details')
    yield self.register(self.square, 'com.math.square', options)
    yield self.register(self.slowsquare, 'com.math.slowsquare', options)
    if hasattr(self, 'onJoined'):
        self.onJoined(details)

ServerComponent.onJoin = onJoin
MicroService.square = rpc_com_math_square.function
MicroService.slowsquare = rpc_com_math_slowsquare.function

application = Config('config.ini', MicroService).application()

Nice and clean innit ?! :)
When working by hand, this is started up with; twistd [-n] -y slowsquare.py