Showing posts with label dojo. Show all posts
Showing posts with label dojo. Show all posts

Sunday, January 18, 2009

Moved to Flex/Actionscript

Why it was never mentioned that dojo toolkit is reimplementation of Flex framework? It would probably saved me many months of poking in dark corners of Javascript with mediocre results.

Today, one month after the 'discovery' my X Erlang IDE has a syntax highlighting editor, a build system, a process viewer, an Erlang console, etc running in Flash Player:



What I am still missing sorely is function call completion. The exact positioning of a small floating window near the cursor is nearly impossible to implement reliably in Javascript. Flex/Actionscript does this and many other things elegantly, is identical in all browsers and is present in 90% of computers around the globe.

I have to mention that it is not possible to process right mouse button click with Flex/Actionscript. There is always, they say, something.

Thursday, December 11, 2008

Javascript talks Erlang

When extending my web-based IDE for X Erlang I stumbled on the fact that I am doing much the same thing over and over again adding a small snippets of code on the server and corresponding integration-only additions to Javascript on the client. Many times the obtained result would be an Erlang term represented by opaque string for the user (me) not the software to understand and interpret.

The next big step was standardizing the way Javascript (JSON) objects are generated from a subset of possible Erlang terms. For instance, [{name:"Judas"}, {occupation:"priest"}] would be converted to { name: 'Judas', occupation: 'priest' } on the Javascript side. So far so good, but the encoding scheme would work only in one direction - from Erlang-based server to the web browser.

The enligtment came later when I recognized that it is not at all necessary to add a new server stub for each request the web application may want to send. The web application may just call Erlang functions directly by their names, provide properly-encoded parameters and expect results as JSON messages. The question was the two-way encoding between Erlang terms and JSON objects. Here comes the scheme:

1. Erlang strings, including empty string "", are represented by Javascript strings

"" -> ""
abc" -> "abc"

2. Atom 'true' and 'false' become Javascript boolean values

'true' -> true
'false' -> false

3. Numbers are just numbers

123 -> 123
123.5 -> 123.5

4. Erlang atoms become objects with a single property "atom"

'abc' -> {atom: "abc"}

5. Erlang binaries become similar objects with a single property, this time named "binary"

<<1,2,255>> -> {binary: "0102ff"}

Binary data is encoded into string, each byte represented by two hex digits
(more compact representations can be imagined)

6. PIDs, References and Ports are encoded as objects too

#Ref<1.2.3> -> {reference: 2, node: 1, creation: 3}
#Port<1.2.3> -> {port: 2, node: 1, creation: 3}
<1.2.3> -> {pid: 2, node: 1, creation: 3}

7. Tuples become objects with integer field names

{T1,T2,T3} -> {1: T1, 2: T2, 3: T3}

8. Lists (which happened not to be strings) are the easiest

[T1,T2,T3] -> [T1, T2, T3]

The described encoding allows to represent any Erlang term as a Javascript value (but not vice-versa). The small open is funs. Today, they are encoded as {fun: name} but this representation is not reversible. Besides it dificult to understand how to reconstract fun object in Erlang (binary_to_term()?).

The additional sugar to the above scheme is record descriptions. For known records, the representation of tuples could be made simpler and more manageable. For instance, the record 'req' is known to have 'module', 'function' and 'args' fields. Then, the Erlang tuple {req,Mod,Fun,Args} is represented by more concise Javascript object with explicit field names: {record: "req", module: Mod, function: Fun, args: Args}. Record description work both ways, during encoding and decoding.

The implementation of the described representation allowed my dojo-based web client to call Erlang functions on the server and pass complex structures back and forth with little or no hassle.

Now, the Erlang console which evaluated expressions using erl_parse and erl_eval stores the resulting bindings on the client as Javascript objects and passes them to subsequent calls as a context not heeding their alien nature.