

We've Open-sourced Rendr - frontendbeauty
http://nerds.airbnb.com/weve-open-sourced-rendr

======
pbiggar
I'm not sure I fully understand this, is this just for SEO? Why not run the
page in phantomJS, which is what we do at <https://circleci.com>, and what
meteor apps do, and any others?

~~~
frontendbeauty
SEO was our first concern, but then we realized performance was the big win.
Serving the user a full page of HTML rather than waiting for JS to download
before rendering HTML makes a big difference, especially on high-latency or
low-bandwidth connections (mobile).

EDIT: We decided against using something like PhantomJS or node-chimera
because why deal with a DOM if you don't have to? DOM is complicated and slow,
compared to string-based templating. Plus, it's another moving part, another
process to keep up and running. The Meteor guys aren't too excited about the
PhantomJS approach either, and IIRC they'd like to be able to serve HTML
without firing up a DOM.

~~~
msoad
Does this mean Rendrjs applications will run in a JavaScript disabled browser?
That would be a big win!

~~~
frontendbeauty
Yep! Because links use full URLs which get intercepted by JavaScript, if JS is
disabled, you can still navigate around the app, getting full HTML from the
server. Of course, any client-specific code wouldn't run (slideshows, etc).

~~~
jonny_eh
So far, this is the most convincing argument I've heard for Rendr.

~~~
bilalq
I'm a little confused here. Maybe I'm just not seeing it, but how does that
make Rendr any different from any other server-side framework that responds
with HTML?

~~~
WickyNilliams
Because you're using the same JavaScript code for rendering on either the
client or the server.

------
wsc981
Posts like this makes me think Airbnb is a awesome place to work. Sharing is
caring!

~~~
malandrew
I want to see them start open sourcing more of their i18n and translation
tools. Most people aren't aware of this, but one of the coolest problems you
can work on at AirBnB is building out tools and features that let two people,
who don't speak a common language between them, transact with one another.
There is no other startup I know of as vested in solving this problem.

~~~
ajacksified
Indeed! We've started with polyglot.js[0], an i18n helper for Node.js and
client-side javascript, but there's definitely a lot going on besides this.

[0] <https://github.com/airbnb/polyglot.js>

------
bru
Fourth link on the page links to
<http://nerds.airbnb.com/github.com/airbnb/rendr-app-template> (which
obviously does not work) instead of <http://github.com/airbnb/rendr-app-
template>

~~~
ssorallen
Indeed it does. Thanks for the heads up, we'll change that.

------
j_s
Previewed and discussed back in January:

[http://nerds.airbnb.com/weve-launched-our-first-nodejs-
app-t...](http://nerds.airbnb.com/weve-launched-our-first-nodejs-app-to-
product)

<https://news.ycombinator.com/item?id=5137859>

------
seanconaty
Anyone interested in something like this should also check out PJAX. Push
State and AJAX. <https://github.com/defunkt/jquery-pjax>

This is what GitHub uses between tabs on its Pull Requests page. I love how
simple the implementation is.

Your app still needs to follow the convention of having links going to
different pages with URLs. I know it's not "single page" and the interaction
is not that "rich." But it's nice because all your logic is still on the
server, all rendering and templates are on the server and the server responds
with either a full page of HTML or a partial page of HTML depending on an HTTP
header you set.

Oh yeah, it also works without Javascript, crazy!

~~~
ricardobeat
That is how Backbone and all other current frameworks work.

~~~
superfreek
No it isn't.

~~~
ricardobeat
Care to explain? They use pushState or hashes for routing, and load data via
XHR. If you are using pushState it is assumed that the URL must exist on the
server.

~~~
cheapsteak
Having the URL exist on the server isn't the same as serving a rendered page
from the URL, which is what most SPAs do. You could just rewrite all URLs in a
website to point back to your index.html, then have the client side router
initialize the app from the URL parameters. If you don't have javascript
turned on (e.g. googlebot) then all you'll see is a blank page

~~~
ricardobeat
Googlebot interprets javascript. In that case you shouldn't use pushState but
fragment URLs[1].

I should have said it is assumed that the URL exists on the server _and points
to the same resource/content_ ; otherwise setting URLs using pushState makes
no sense. GitHub is a good example of how it should be done, not an exception.

[1] [https://developers.google.com/webmasters/ajax-
crawling/docs/...](https://developers.google.com/webmasters/ajax-
crawling/docs/getting-started)

------
d0m
Just wondering what's the difference between this post and the last one where
Rendr was already open-sourced? I mean, it was already open sourced for a
while. Is there a change log or an adapter to better integrate with other
systems? Thanks!

~~~
frontendbeauty
At the time of the previous post, Rendr was not yet open-sourced.

------
csulmone
Wow, looks very impressive from my quick look over it.

These days, there are so many JavaScript frameworks for web development, it's
starting to make my head spin a little bit.

Does anyone have a link to a good rundown of where everyone stands?

~~~
liveaxle
Being a JS developer must be the pits - you need to run really fast just to
keep up.

~~~
wilmoore
_...you need to run really fast just to keep up._

This is exactly the part of being a JS developer that is appealing :)

------
jedschmidt
This is an awesome solution for folks using Backbone and who don't mind a
tight framework coupling.

But if you're not on Backbone, or don't want to add another constraint to how
your app is built, it's pretty easy to set up your own PhantomJS server; I
presented on this very topic at TXJS this week[1], and created a library[2]
that makes it a snap to set up.

[1]
[http://www.flickr.com/photos/tr4nslator/sets/721576332659462...](http://www.flickr.com/photos/tr4nslator/sets/72157633265946285/show/)

[2] <https://github.com/jed/rndr.me>

------
don_draper
Are there any similar efforts to tie the server with the client, reducing
duplication, for Angular?

~~~
davej
Angular uses DOM templating instead of string-based templating (most current
JS templating engines are string-based), so you would definitely need to fire
up a headless browser (PhantomJS) or DOM (JSDOM) of some sort to get it
working.

It would be very slow if you were doing this dynamically so you would probably
want to regularly compile and cache your pages.

Some links on this topic: <https://github.com/steeve/angular-seo>
<http://www.yearofmoo.com/2012/11/angularjs-and-seo.html>

~~~
jameswyse
Yeah this is the best way to serve rendered pages to search engines. I also
found this project: <https://github.com/ithkuil/angular-on-server> \- Which
might be worth looking at too.

------
ksec
so they have completely ditch Rails and Ruby?

~~~
apendleton
I don't work there, but I doubt it. With rendr, both the client- and server-
side portions of the Backbone stack still need to consume an upstream API. If
I had to guess, I'd say that for projects they're building that use this
stack, all the templating/rendering/presentation logic is in JS, but that the
database interaction stuff probably isn't; they probably have Rails apps that
expose a RESTful API that the rendr apps consume.

~~~
frontendbeauty
This is exactly right. We still have 5 years worth of business logic in Rails,
so we just expose a RESTful API as part of the Rails app. The same API is
consumed by our iOS, Android, Mobile Web, and Desktop clients.

~~~
fuddle
Cool stuff, very interesting concept, would love to see an example working
with a Rails RESTful API.

~~~
frontendbeauty
The app template is such an example, consuming the public GitHub API:
<https://github.com/airbnb/rendr-app-template>

In the future, we'd like to come up with some more in-depth tutorials.

~~~
fuddle
Great thanks I'll take a look at it again, I seen the "Interacting with a
RESTful API" section in the wiki left blank and assumed it was in the
pipeline.

------
ameyakarve
Could there be a feature to run the app logic on the client when a connection
is not available? Else, it can fallback to the server. This will help a lot
when it comes to offline support

------
msoad
IS IT FASTER?

I assume Node/JavaScript will render HTML faster than ruby/rails. Do you have
benchmarks?

~~~
tracker1
Node/JS won't necessarily render HTML faster. There are libraries to bring DOM
interaction into NodeJS, there's also PhantomJS, and previous attempts like
Aptana's server. All of these have been very heavy, and didn't scale well.
PhantomJS is probably the best current option, but doesn't tie directly to
Node, and still not as fast as string based templating.

Regarding string based templates, they are really implementation dependant,
and there are tons of options available. Right now some common ones for NodeJS
are probably Bliss (Razor inspired), Nunjucks (jinja2 inspired),
Mustache/Handlebars and Jade (Haml inspired), and EJS (similar to PHP, or
classic ASP).

Probably the most broadly available is Mustache, which has implementations in
about every language under the sun, and probably could make a decent benchmark
to compare string processing in different languages.

All of the above simply bring me, to use what you feel comfortable with and
what feels right.

------
JPKab
Awesome. Looking forward to checking this out.

