
Literate CoffeeScript - jedschmidt
http://coffeescript.org/#literate
======
jashkenas
I'm pretty excited to see some of the first programs that folks might write
with this -- I've got one of my own, a little 400 LOC (half of which is
comments) static blogging engine that's currently powering
<http://ashkenas.com>.

Part of the idea is that, because first and foremost you're writing a document
describing what you're doing, and then filling the the implementation in the
gaps ... you end up structuring the program differently than if you started
out with the code was at the top level, as usual. For me, it was a fun process
-- start with an outline, expand that into paragraphs below, then indent four
spaces and implement each paragraph...

I'll share the full bit when I make it out of the woods next week, but for
now, here's a sneak peek of a rough draft to give a flavor:
<http://cl.ly/N8Kx>

_Edit_ : If anyone wants a copy of the hybrid Markdown/CoffeeScript syntax
highlighter (for TextMate or Sublime Text), it's available here in the
"Syntaxes" folder. <https://github.com/jashkenas/coffee-script-tmbundle>
10,000 bonus points if you port it over to Pygments and send a pull request to
GitHub ;)

~~~
philbo
Beyond any educational benefit, what do you see as the advantages of
programming in this way?

I and most of the programmers I socialise with tend to see comments as a bad
smell; they're fine every now and then but if there are more than a few of
them, something is wrong.

How do you prevent the comments from becoming lies? By which I mean, how can
you ensure that people updates the comments in accordance with changes to the
code that occur over time.

Also what impact do you think this approach might have on the way people write
the code itself; naming variables and arguments, decomposing functions into
smaller units and so on?

~~~
jashkenas

        > Beyond any educational benefit, what do you see as the 
        > advantages of programming in this way?
    

For me (and I'm just getting started here, I've only been playing around with
this in earnest in the context of the little blog engine, and there are
certainly many different ways of going about it), it makes the process of
exploratory coding feel very different. Instead of thinking up a series of
classes or functions that might solve the problem, and starting to write them
-- I instead start by outlining (literally) what I want the program to do, and
then describe the functionality in paragraphs, and then implement those
paragraphs.

When the paragraphs have code below them that does what they say they do, the
thing works. When I end up coding myself into a corner, I rewrite the
paragraph and change the code. It's really a very different process than
usual. It's also definitely more work than just doing code and omitting
comments -- it takes a bit of elbow grease to prevent the comments from
becoming lies ... but it's the same type of work as preventing bits of your
codebase from becoming dead code.

For me, it seems to make me organize code into smaller functions grouped
together into sections, use less classes, and care more about putting things
in the place where you're talking about them, and less about putting similar
things together in one block of code. For example, I started to require things
close to the paragraph where I first mention them, instead of putting all
requires at the top of the file. At least, that's how it feels so far.

~~~
jeremyjh
I'm glad to know I'm not the only person who works this way. My source files
often have a paragraph or two at the top that explains my intentions for that
class/module as well as explains the usage of my domain language. I never see
this in other people's code though.

I agree with people who say that the code itself should read very clearly, but
the fact is that even when writing an article or paper you have to
disambiguate your own writing, clarify your usage of terms and present some
context up front. Otherwise people can take away a very mistaken impression of
your text, and it is certainly no less true for code.

------
arocks
Should the order of documentation be same as order of code? For e.g. if I
would like to start with explaining the main function at the bottom of the
code, can this support that?

If it does not it cannot be, strictly speaking, called Literate Programming:
[http://en.wikipedia.org/wiki/Literate_programming#Misconcept...](http://en.wikipedia.org/wiki/Literate_programming#Misconceptions)

~~~
jashkenas
Ah, that old canard ;)

Modern programming languages (and JavaScript especially so) support defining
your functions, creating your classes, and wiring things together, in any
order you see fit. These days, TANGLE'ing and WEAVE'ing together a source file
into a new line ordering, just to make a compiler happy, is unnecessary, and
more trouble than it's worth. Just do:

    
    
        ... bulk of the file goes here ...
    
            main = ->
              run program

~~~
mhd
Well, there's more than one way to write literature, and there's more than one
way to approach literate programs. So while I agree that you can do most of
what you want with a more simplified approach, I don't think that Knuth's
approach was just there to escape from Pascal's declaration syntax.

Out-of-order code can be quite useful if the literate document is the
_narrative_ of the code, how you derive your algorithms and create your
functions. The final untangled code is devoid of this, and presents a more
conventional structure. One example would be some global variables (or
configuration hash, if that statement made you faint a bit). In the end, you
probably would want at least one view of the code where this is collected in
one spot, even if the programming language would theoretically allow you to
declare it bit by bit all over the place.

On the other hand, this style doesn't lend itself that well to a constantly
revised code base, as that would mean reading a narrative all over again.

------
crazygringo
First, it looks great. It seems like such a trivial difference not to have #'s
or /* __/ or whatnot... but somehow it does make all the difference. Almost
like the code is meant to be read by people instead of computers (which is
what the priority almost always should be).

And second, the example [1] is a great model of _good_ commenting practice --
explaining the why's, the workings, clarifying special cases. Especially with
languages as concise and powerful as CoffeeScript, having as many lines of
comments as lines of code, is a great balance.

It seems like such a trivial idea, comments to the left, code indented, but
it's one of the best ideas I've seen pop up in a long time -- especially
because it heavily nudges you to treat comments as an integral part of the
file, not just an extra, and to treat the file, from the beginning, as
something for others to read. Bravo!

[1] <http://cl.ly/LxEu>

------
anonymouz
<http://en.wikipedia.org/wiki/Literate_programming> for some background on
literate programming. TeX is written in such a style.

------
gfodor
I'm interested to see where this goes, but one of the problems with literate
programming is that it means that in addition to being a good programmer you
also need to be a good writer. In other words, if you are a good programmer
and a bad writer you are going to produce net bad work since your writing will
confuse people who might otherwise have understood the code on its own, and if
you are a good writer and a bad programmer there is a chance this will make it
harder for others to realize your implementation sucks since it may be dressed
in the most brillant, clear prose possible. (Of course one can make the
argument that brilliant clear prose is a sign of brilliant clear thinking and
hence code, but I am not so sure.) It also opens up the door for an entirely
new dimension in code reviews. Imagine your resident grammar nazi jumping into
code reviews now to perform edits to paragraphs upon paragraphs of comments.
(This is probably the same person who agonizes over class names, so maybe
you're already used to this :))

I've found that there seems to be a decent correlation with writing skills and
programming skills, but that's far from a fact and I've worked with people in
every spot in the 2x2 skills matrix.

~~~
jashkenas

        > This is probably the same person who agonizes over 
        > class names, so maybe you're already used to this
    

Bingo. I think that for programming languages where clarity is already a
common virtue (think, Ruby, Python, Clojure) -- folks already need to be
writing clearly when they program: making the code clear to read, naming
variables and functions very well, doing logical ordering of sections of code
etc. That's already about halfway towards what you would do if you were
accompanying the code with a bit of essay. I think the two worlds aren't as
far apart as one might think.

------
protez
Don't update now!

I just updated it to checkout .litcoffee compilation and it worked out okay.
But suddenly, all my express.js apps stopped working due to the exception from
its connect module. I downgraded coffee to the previous version and all things
turned fine again. It seems the package needs fixes. I like most parts of node
except these surprising interconnections.

~~~
nadaviv
Try diffing the compiled source for 1.4 and 1.5.

~~~
kcbanner
rofl

------
Tichy
"you can write it as a Markdown document — a document that also happens to be
executable CoffeeScript code"

Am I missing something or is that line literally the only
explanation/documentation given as to what is literate CoffeeScript and how to
use it? Must admit I have no idea how to use it now.

~~~
talklittle
The next sentence includes links to bits of the compiler in literate
CoffeeScript. <https://gist.github.com/jashkenas/3fc3c1a8b1009c00d9df>

It's writing a Markdown document, where the code blocks, indented 4 spaces,
are executed. And the rest of the document is essentially nicely-formatted
comments in the form of Markdown.

~~~
mosselman
Thanks for explaining.

------
jahewson
Literate programming - why have terse comments when you can have a verbose and
rambling narrative? I actually tried reading the TeX source code, and it was
damn near impossible.

~~~
ajross
I mostly agree. For 95% of code, it's simply a waste of time to try to
"document" it like this. For the handful of situations where elaborate
documentation wants to be stored with code (which basically means "automatic
reference doc generation from API definitions") we have tools like Doxygen
already that work well.

But there does remain that tiny subset of code that is so complicated that it
can only be explained in prose. This includes things like, say, DCT
implementations, tight SIMD assembly, complicated threadsafety architectures,
oddball parser context dependency rules, etc... I can see wanting to read this
stuff in a "literate" environment.

But... is _anything_ you might use Coffeescript for going to contain code like
that? I can't think of any good candidates offhand, beyond (perhaps) the
coffeescript compiler itself...

------
quii
It's a cool idea, but I am struggling to understand why this is better than
say BDD; which not only effectively documents what your code does but also
verifies it does what it says it should do.

~~~
chrisdevereux
That was my though too. Are there any languages that let you write specs
inline with the functions/classes that they test? _That_ would be cool.

Edit: Having thought about it for a second, this could easily be done in most
languages (with some preprocessing to strip out for deployment. Super easy in
C-based languages). Not a convention I see anyone follow, though.

~~~
phpnode
i'm working on a project that does this with doc comments. Basically you add a
doc block like this:

    
    
        ###
        @it should return true
          expect(foo()).to.be.true
        ###
        foo = -> true
    

and the preprocessor extracts the test from the comment and associates it with
the foo declaration.

------
agentultra
It just needs the ability to include source blocks in other source blocks and
a way to tell the "compiler," how to organize the output files...

For that I just use babel in org-mode... but you have to be an emacs person
for that. I'm sure there are other literate systems (like the original:
<http://www-cs-faculty.stanford.edu/~uno/cweb.html>)

------
franze
has anyone figured out what the syntax for

    
    
      You can now loop over an array backwards,
      without having to manually deal with the indexes.
    

is?

~~~
jashkenas
Sorry, I should add that to the changelog. It's just like looping over a range
downwards (or by arbitrary increments).

    
    
        for item in list by -1

~~~
int3
Very nice! I've wanted this for a long time.

------
arianvanp
I'm not sure if I agree with making comments a first-class citizen in a
programming language.

Good code documents itself and should be first-class. Comments should be there
to clarify certain decisions that you've made while writing code.

Handing out citizenship to the comments just clutters the code flow and will
stimulate bad commenting behaviour.

I really don't see any pros for 'executable' markdown at the moment, apart
from being cool.

------
jimjeffers
Is anyone planning on some sort of support for .litcoffee in docco? It'd be
awesome if docco could compile the markdown documents into HTML files and keep
that swell dropdown navigation in the top right hand corner available.
Generating docs as I was in my earlier projects seems to be the only gap.
Otherwise I'm using litcoffee on a current client project and really loving
it!

------
andyjohnson0
I remember getting quite interested in literate programming back in the early
nineties, but I've barely heard anything about it since then.

Has anyone (apart from Knuth) used LP for any real work of significant size?
What was the justification of doing the, presumably substantial, work to add
literate programming to coffescript?

------
zbowling
I'm cofused by what "executable" means in this context with markdown. Is this
some kind of documentation support for coffeescript?

or is the code executable in the blocks in the markdown script and literate
mode is a way to invoke "documentation" basically if the file is a .litcoffee
document instead of a .coffee document?

~~~
jashkenas
If the file extension is ".litcoffee", it means that you're writing a Markdown
document, where the embedded bits of indented code are the executable part of
the program.

Basically, it just inverts the usual power relationship in a piece of source
code, where the code is primary and aligned along the left edge, and the
comments are set off in little fenced blocks. Now the comments are primary,
and the code is indented in little blocks -- but it's still the same
executable piece of source code.

The neat bit is when you have it all working properly in a text editor, your
prose being highlighted as Markdown, and your code being highlighted as
CoffeeScript.

~~~
mikeknoop
After reading the docs and comments, this was the comment/explanation that
made the light-bulb click.

------
pkorzeniewski
Very interesting idea, great for creating architecture outline, generating
documentation and understanding code.

------
ww520
Interesting development with the literate programming. Certainly a bold move.
Kudos for trying some new!

~~~
sambeau
I had to hand all my functional programming homework in in literate style in
1992 so 'New' is relative :-)

~~~
tanepiper
New to web development

------
arvidkahl
Could you please state the reasons for this change: 'cannot return a value
from a constructor'. Besides breaking working code, this feels more like an
added restriction than an added feature. I'd love to know why this is in 1.5.
Thanks!

~~~
jashkenas
It _is_ a restriction, and I'm a bit torn about it.

Apart from fixing bugs where you'd use a CoffeeScript `class` to extend from a
native object, returning "other" values from a constructor is a bad idea
because it makes your code lie.

    
    
        widget = new Widget
    

In CoffeeScript 1.5+, unless you go to great lengths to get around it, that's
always going to return a new Widget -- in JavaScript, that could return a
Dongle, an old and already used Widget, or anything else (that's not a
primitive). If you want a function that maybe returns a new Widget, and maybe
an old one, just use a normal function, not a constructor:

    
    
        widget = Widget.lookup()

------
transfire
Ruby's had something like this for awhile --a test framework called
[QED](<http://rubyworks.github.com/qed>). Made for testing, but technically it
could be used for anything.

------
ms123
I love that executable markdown style. I created a project some time ago that
does just that. For the records, here it is:
<https://github.com/mikaa123/lilp>

------
tbe
Cool idea to use Markdown's code snippet feature for literate programming :)

I guess you could do this in any language by incorporating something like the
following into your project's makefile:

    
    
      sed '/^\t/!d; s/^\t//'

------
vectorpush
This is cool. IMO, most comments are pretty superfluous, but I think this
would be awesome for setting up visual groupings of related code sections.

------
nateabele
Oh.

I was really hoping 'literate' meant you could read the _code_.

------
lastbookworm
I can see this being useful for writing tutorials or even a book. So many
ideas for educational material swirling around in my head.

------
namuol
I'm not sure this is a good direction.

We all want better documentation, but the problem with comments is that they
can _lie_.

~~~
libria
Commenting is still not required, AFAICT.

Are you positing that better formatting encourages worse
comments/documentation? I'm of the opinion that their presentation is
independent of their quality.

~~~
namuol
I fear that _emphasis_ of documentation, to this extent, encourages us to read
comments first and foremost, rather than the code.

I realize that the emphasis could be perceived the other way around (on the
code, rather than the comments), but the author's intention seems to be the
other way around.

------
nathell
Which editor is this in the screenshot?

~~~
oal
Sublime Text 2 with the Soda dark theme.

Edit: Link to Soda theme on Github: <https://github.com/buymeasoda/soda-theme>

~~~
mosselman
Do you also happen to know which colour scheme that is?

~~~
jashkenas
Brilliance Black (42), a Halloween edition from several years back.

~~~
mosselman
Thanks.

I can't seem to be able to find a version that looks like the screenshot
though. Maybe you have a link? That would be great!

------
acedip
This is brilliant. love it.

------
coldtea
Shouldn't they be working on the goddamn Source Map support instead of
literate gimmicks?

~~~
jashkenas
A bit of that is in this release as well, thanks to Jason Walton.
[https://github.com/jashkenas/coffee-
script/blob/master/src/g...](https://github.com/jashkenas/coffee-
script/blob/master/src/grammar.coffee#L43-L56)

Source location information is now preserved through the parse, although it's
not yet being emitted as a source map just yet. If you want to use
CoffeeScript source maps today, feel free to use the Redux compiler, which
does them just fine. Michael also has some other tools to make source maps
even more convenient: <https://github.com/michaelficarra/commonjs-everywhere>

That said, I don't personally care for source maps all that much, placing a
higher priority on generating readable and straightforward JavaScript output.
Things like Literate CoffeeScript rank higher on the priority list.

~~~
coldtea
Thanks for the response (well, given my tone).

But I think this literate thing never caught on for a reason. And I'd say the
reason is marginal returns (over comments and clean code) and too much fuss.

As for the "entitlement", it's because people have been saying source maps
would came to CS for 2 years now, and I've seen nothing related yet (even the
crowd-funded project is not there).

------
camus
So when does coffee-script becomes independent from javascript and gets its
own CS->machine code compiler ?

~~~
NoahTheDuke
I would guess when Javascript dies. So, never.

------
wildchild
Cool, imperative code diluted with some poetry looks much better.

------
Mahn
This won't be a popular comment, but I have to admit I never really liked
CoffeeScript. I've tried to like it, and it does seem more concise, but what's
the point, it always seems clearer (to me) what something written in vanilla
javascript is doing. I don't know, I guess I haven't done enough Python.

~~~
mratzloff
It won't be a popular comment because it's not germane to the conversation at
hand.

~~~
Mahn
We have all sorts of discussions here on HN that derail a bit from the topic
of the main article linked, e.g. discussing smart TVs in a thread about webOS;
I don't see how this is negative as long as there is still connection.

~~~
Cushman
This isn't negative so much as irrelevant; CoffeeScript has been around long
enough that we've had most of the discussion around what people like and don't
like about it. If you don't like it, that's fine, but there's not a lot to
talk about.

