Native compiler api

2012-05-28

Yeah, still not sure how to call this feature. But I'd like to propose a browser feature that will fix most of our problems. Well, probably not yet, but I feel it's a push in the right direction for more freedom.

Many coders would like to code in their own language of choice. Or even to experiment with new features for the next version of js. But we don't really like a compilation step. You should be able to just write code, include it in a webpage, save and run. Simple is win. This is currently not really possible though. You can work around it, but it involves a bit of boilerplate and hackiness. I'll get on it ;)

This is a proposal for being able to tell a browser to include some arbitrary code, tell the browser which type the code is, and to give it a url to a compiler script in case it's unfamiliar with that specific type of script. The compiler should be some js that compiles the arbitrary code to js. The browser should always run the (compiled) code, either because it compiled the source itself or because it downloaded the compiler and used that to compile the code.

Note that I'm not saying browsers should start to support other languages natively. Oh no, not at all. Somebody (I forgot..) pointed out to me that while this was a nice concept, it's not very realistic. Vendors have enough problems securing js. Let's not have them worry about even more environments to patch up. So no, browsers should not run "known" languages natively but if they have a compiler that matches the given type, they should use that one instead of downloading the compiler pointed to. Their built-in compiler should still compile to js. The rationale is that their own compiler might be faster (more money behind development, more and brighter people to develop it) and more suitable for that vendor's specific js engine (optimization). Because really, at that point the compiled code doesn't really matter anymore. Another side effect is that shipped compilers might result in better debugging compatibility.

So one important step in this whole thing is the source map api. Where you can map source code for, say, CoffeeScript to the compiled js. That way, if the debugger throws an error, the browser can show you the original (cs) code and point you to the line number that caused the problem. Without source maps debugging compiled code is a real pita.

So how might this doohicky work? In my eyes it could be very simple. Let's take a CS example:

Code:
<script src="magic.cs" type="coffeescript1.0" compiler="./compiler.cs.1.0.js"/>
or
<script src="magic.cs" type="coffeescript" version="1.0" compiler="./compiler.cs.1.0.js"/>

What would happen now is that the script tag is ignored. The type is not recognised and therefore the content is ignored. The new attribute compiler (you can bikeshed over the name, I think it's fitting) could change that. Instead of ignoring unknown types, browsers could download the compiler script and compile the code on the fly. The resulting code should then be executed in js, as usual.

So the next step is that browsers could ship some of these compilers for popular languages. They would still compile to js but they not require the downloading of the compiler. If the user wants to make sure the browser uses a specific compiler, the type could be set to custom or whatever.

For the sake of semantics, you could split up the type and version. It seems easier to parse the type and version as one string and have that serve as a unique identifier. But it's cleaner to separate them into their own attributes (and you could join them for the same result).

I still think this will be the future of coding in the web. We don't want manual compilation steps. But we do want more freedom. We want to work with our language of choice. Or even experiment with new features. This could help remove that burden. All we need is a simple (!) api to work with and restrict ourselves to have js as the target compilation platform (for security).

A workaround with fallback for this could be the following:

Code:
<script src="compiler.cs.1.0.js" iscompiler/>
<script src="foo.cs" type="cs1.0" compiler="compiler.cs.1.0.js"/>
<script iscompiler>CsCompiler.start();</script>

If the browser would support the compiler api, it would recognize the iscompiler attribute and ignore that script tag. Instead it will encounter the second script tag and run that through either the compiler that shipped with the browser, or download and run the compiler given. It would access methods specified in the compiler api to do its magic. The third script (which could preferably even be part of the first script, but somehow not trigger the search if the api is supported) would again be ignored.

If the browser would not support the compiler api, the first script is ran (initialising the compiler). The second script is ignored. The third script kicks off the compiler. This finds all the script tags with a type it supports. But it then has to download all the scripts (requiring ajax scripts and access...) in order to get the source code.

In both cases the cs source code is compiled to js and then executed. So for the end product, nothing changes. The compilers would also be written in js so it feels to me like there's a very small burden on vendors, beyond what is already possible.

I hope this becomes a reality. I want to experiment with certain features, like my tag literals, but don't want to manually compile everything before I refresh the browser.

What might be the downsides to this proposal? As I said, it doesn't really add anything that's not already possible. A possibly troubling area could be agreeing on unique identifiers for type, but I don't really see that becoming a problem. There might be some incompatibilities between the compilers that ship between browsers. But if you're worried about that, just use custom as type. At some point, certain types will stabilise.

What else? Thoughts? Let me know through twitter :)

(supplementals:)

- Slowing down the browser
This feature is more meant for development and experimenting. Although parsing and compiling shouldn't really take that much time, in a production environment you should just serve compiled js. Especially on high traffic sites where every millisecond counts. Imo, it's the developer's job to know about that.