Skip to content

Commit

Permalink
Finish initial docs and add with hack to eval line
Browse files Browse the repository at this point in the history
  • Loading branch information
creationix committed Oct 8, 2009
1 parent 572142a commit b2bbab1
Show file tree
Hide file tree
Showing 4 changed files with 102 additions and 13 deletions.
61 changes: 57 additions & 4 deletions README.markdown
@@ -1,12 +1,12 @@
# haml-js
# haml-js - Server side templating language for JavaScript

What's left in this project is the server-side haml language. It has much of the same functionality as the traditional haml. Syntax based on [haml][] from the ruby world.

## NOTE, Project was split

If you're looking for the old haml-js (It was a jQuery plugin that made dom-building easy using a haml like syntax), it's now renamed to [jquery-haml][]
If you're looking for the old haml-js (It was a jQuery plugin that made dom-building easy using a haml-like syntax), it's now renamed to [jquery-haml][]

## Sample usage
## About the language

Here is the first example from the [haml][] site converted to haml-js:

Expand Down Expand Up @@ -35,7 +35,60 @@ Here is the first example from the [haml][] site converted to haml-js:

Note that this works almost the same as ruby's [haml][].

...More to come...
## API

There are three exported functions in the haml.js library. They are:

### parse(text) -> json data

Parse takes a block of haml template and parses it into an s-expression like json construct.

The following input:

#home
%ul.menu
%li Go Home
%li Go Back

Produces the following JSON output

[{"tag":"div","id":"home"},
[{"tag":"ul","class":"menu"},
[{"tag":"li"},"Go Home"],
[{"tag":"li"},"Go Back"]
]
]

### to_html(json) -> html text

This takes the json data from the parse step and converts it into html ready for a browser

The input from the previous example outputs this:

<div id="home">
<ul class="menu">
<li>Go Home</li>
<li>Go Back</li>
</ul>
</div>

### render(scope, filename, callback)

Render is a shortcut for the most common use of haml-js from within a node server. It takes a scope, filename, and callback and calls the callback with the generated html when ready.

Scope is the custom scope for the JavaScript in the template. Haml uses the "with" trick to make prefixing all variable and function references with "this". So if I had a scope of {first: "Tim", last: "Caswell"}, then in the template the variables "first" and "last" would be available for use as local variables.

Since reading files is asynchronous in NodeJS, a Callback is required to pass the generated html to when done.

See test.js for an example usage of Haml.render

## Plugins

There are plugins in the parser for things like inline script tags, css blocks, and experimental support for if statements and for loops. There are to be documented soon...

## Get Involved

If you want to use this project and something is missing then send me a message. I'm very busy and have several open source projects I manage. I'll contribute to this project as I have time, but if there is more interest for some particular aspect, I'll work on it a lot faster. Also you're welcome to fork this project and send me patches/pull-requests.


[jquery-haml]: http://github.com/creationix/jquery-haml
Expand Down
14 changes: 5 additions & 9 deletions haml.js
Expand Up @@ -10,14 +10,14 @@ Haml.to_html = function (json) {
if (typeof json === 'string') {

if (json.substr(0, 3) === '!!!') {
switch (json.substr(4)) {
case 'XML':
switch (json.substr(4).toLowerCase()) {
case 'xml':
return "<?xml version='1.0' encoding='utf-8' ?>\n";
case '':
return '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">\n';
case '1.1':
return '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">\n';
case 'Strict':
case 'strict':
return '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">\n';
}
}
Expand Down Expand Up @@ -69,14 +69,10 @@ Haml.parse = function (text) {
scope = this,
haml, element, stack, indent, buffer, old_indent, mode, last_insert;

// The closest thing to instance_eval you can get in javascript
// Sortof an instance_eval for Javascript
function instance_eval(input) {
var block;
if (typeof input === 'string') {
block = function () { return eval("(" + input + ")"); };
} else {
block = input;
}
block = function () { with(scope) { return eval("(" + input + ")"); } };
return block.call(scope);
}

Expand Down
14 changes: 14 additions & 0 deletions test.haml
@@ -0,0 +1,14 @@
!!! XML
!!! strict
%html{ xmlns: "http://www.w3.org/1999/xhtml" }
%head
%title
Sample haml template
%body
.profile
.left.column
#date= print_date()
#address= current_user.address
.right.column
#email= current_user.email
#bio= current_user.bio
26 changes: 26 additions & 0 deletions test.js
@@ -0,0 +1,26 @@
// Requires nodeJS 0.1.13 or greater to run <http://nodejs.org/>
// just type `node test.js` on the command line

// Load the puts function and friends
node.mixin(require("/utils.js"));

// Load the haml-js library from the current directory
var Haml = require("haml.js");

// Set up a scope for our view to render in
var scope = {
print_date: function () {
return (new Date()).toDateString();
},
current_user: {
address: "Richardson, TX",
email: "tim@creationix.com",
bio: "Experienced software professional..."
}
};


// Load, parse, and render the html. The result it passed to the callback puts
// which prints it to the terminal.
Haml.render(scope, "test.haml", puts);

0 comments on commit b2bbab1

Please sign in to comment.