5 ms·
The Single Page Interface Manifesto
- swombat 17y agoGood luck with that. Pages are a good metaphor for many websites. Many RIAs are better suited to a single-screen metaphor (for example, my own business, Woobius, or GMail, or Google Maps), but to claim that, for example, a blog, or HN, should be single-page, is silly. Use multi-page metaphors where it makes sense. Use single-page metaphors where it makes sense. Don't go on crusades trying to force round pegs into square holes, or vice versa.
- hello_moto 17y agoOne of the projects I'm working right now is sort of a hybrid between multi-page and single-page in hindsight (even though the implementation is in single-page). This particular project chose to use GWT. While GWT provides a lot of good abstractions to build such application, I find the requirements for the project is disturbing: want to be like desktop, but looks like a web-app, but can do bookmarking, etc etc. It suffers a lot of issues from: 1) Having to re-implement how the history works 2) Having data freshness issue vs not re-fetching every visit 3) Huge DOM structure within the single page It's just too crazy. Luckily GWT ease the pain a little bit, but I wished we wouldn't go that far or at least cap the requirements with some limitations.
- ericd 17y agoThis is the model that padmapper.com follows, and it has worked fairly well. Users don't have to ever leave the tool's main interface (except that listings open a new tab/window), which has had a number of benefits. Making the possible states crawlable by search engines was a pain, but in the end I think the tradeoff was well worth it. EDIT: As swombat says below, though, this isn't a natural fit for all types of websites, and it's a bit hyperbolic/silly to call this the next model of web development. That time might come, but it's not nearly here for the vast majority of sites.
- emilis_info 17y agoA case when this will still break bookmarking: - user with JS enabled opens the website and navigates to some inner page - user with JS copies the url for the inner page (e.g. http://example.org/#foo/bar http://example.org/#foo/bar) - user with JS sends this url to a friend - a friend with JS disabled opens the url and does not get the inner page. Also -- what if a search engine "bookmarks" the page and a user with JS opens it? Do you: a) redirect him from example.org/foo/bar to exmple.org/#foo/bar or... b) do you leave the url untouched and wait until the user bookmarks another page as example.org/foo/bar#foo/baz ? a) -- you waste processing power on visitors from search engines. b) -- you waste processing power on the next opening of the bookmark. Also this looks like a bug waiting to happen. Disclosure: I browse with JS turned off (Firefox NoScript extension) and websites that rely on JavaScript when a static page would do annoy me.
- jasonkester 17y agoNot to defend the author's bad idea, but actually, the apps I've built with hash-based navigation would still work fine in the case you describe. The server needs to be smart enough to read that hashtag and display the initial page in the correct state. It's just laziness to always load the same app and then immediately swap everything out based on hashes.
- joshd 17y agoI prefer to send the page to the index before loading dynamic content. Imagine two scenarios: I send a link to a friend saying "check out the kittens": <example.com/product/pr0n#/product/kittens> My friend ends up on a completely different page and there is no explaination as to why the page is wrong. Secondly, the URL leaked information about my browsing history. Finally, Google page rank goes to /produces/pr0n rather than the cute kittens. If the URL is <example.com/#/product/kittens> then my friend sees the homepage rather than the correct product page. At least they'll know they're on the right site and can easily search for the correct page manually. Google page rank goes to the homepage rather than some arbitrary page.
- boucher 17y agoNot all browsers (in fact, maybe no browsers) send the hash tag to the server with the request.
- grannyg00se 17y agoSome people don't use javascript. Especially on mobile devices, I sometimes leave it off. Aside from specific application style pages, most should consider javascript an optional enhancement, not a requirement.
- joshd 17y agoI've implemented this before. The site was standard MVC, built in CodeIgniter. I then built a middleware layer that would either decorate the content with a layout template to generate the HTML version or create a JSON structure with linked elements (CSS and JS files) and page title. The JavaScript would parses the incoming JSON and attach listeners to all the elements. It had to do a few tricky things like tracking JS and CSS files and provide alternatives to dom:loaded so scripts could be rerun on dynamically loading content. Really Simple History was then used to track the state. I built and tested the functionality as a plain HTML site first then builf the dynamic loader afterward, which was relatively easy to implement. Some of the trickiest parts were gettingand the DOM to update in a timely fashion and to get the interface to "feel" right (when do you clear the old page, when do you scroll user back to top of page, etc.). Like emilis said, there are still a few small cases where the implemetation breaks down, mainly when sending or publishing links. I ended up enforcing clean links: if you hit a HTML page when you had JavaScript enabled it would take you to the homepage and reload your desired page from there. This was mainly because not doing so would make the copy-paste problems worst. E.g. If you expecting to see "bar" but had no JavaScript then example.com/foo#bar (showing foo rather than bar) would be more confusing seeing the homepage at example.com/#bar. The redirect logic was the first thing encountered on the page so was pretty quick. E.g. http://www.google.co.uk/search?q=http%3A%2F%2Fwww.thebeatles.com%2Fuser http://www.google.co.uk/search?q=http%3A%2F%2Fwww.thebeatles... I wouldn't recommend implementing this unless you absolutely had to. For me the requirement for a streaming music player was a "must-have" feature. Even the quickest page load would still lead to skipping music.
- voidpointer 17y ago"I then built a middleware layer that would either decorate the content with a layout template..." Methinks you might have a somewhat non-standard definition of the term middleware. Please have your buzzword generator re-calibrated ;)
- joshd 17y agoToo much time spent around Django :P
- jasonkester 17y agoGoogle did this for a few days not too long ago, and got a firestorm of bad press about it. Twitter Search is doing it now and annoying the crap out of me every time I use it. Unless it's done VERY right, it's a really bad user experience. GMail can get away with using hashtags for navigation because it's an application you're never going to search or bookmark externally. Most plain-old web apps don't have that advantage, and therefore are bad candidates for hash-based navigation. So yeah, this is tech that's been around for a while, and it's a convenient way to allow the browser back button to work in a single-page app. But I wouldn't recommend using it unless you have a good reason.
- petervandijck 17y agoFacebook does this now, so you can keep chatting while surfing through its pages. But used like that, it does feel like a bit of a hack somehow.
- jwecker 17y agoSome of this is fine, if a bit dogmatic (but what do you expect from a manifesto). However the section on SEO is a potentially bad idea. It seems borderline black-hat and very similar to cloaking.
- pixelcort 17y agoIn regards to "Goodbye to Back/Forward buttons", while the author is correct that browsers don't offer a good API to observe the back and forward buttons being invoked, there are at least two workarounds. One way is to poll window.location.hash via setInterval or whatnot. Another has something to do with a hidden iframe which can observe the back and forward buttons. For example, SproutCore's routing system uses the first technique: http://docs.sproutcore.com/symbols/SC.routes.html http://docs.sproutcore.com/symbols/SC.routes.html From the observer, the developer can then ensure the web app is in a state consistent with the hash part of the url, enabling the user to use the back and forward buttons within the app.
- toolate 17y agoReally Simple History packages this in a library, and it will be introduced natively in HTML5.
- simonw 17y agoDo not want. http://www.innowhere.com/ http://www.innowhere.com/ is cited as an example of this kind of interface, and is a total disaster - I'm browsing on a 3G modem on a train (tunnels etc mean my connection is a bit spotty) and clicking the links on that site offers me no feedback at all on whether or not a page is about to load - it either fails silently or eventually throws an alert() box with a weird type error. Call me old fashioned, but I like links that work. I can just about forgive Gmail for being a single page interface (though I'm frequently frustrated there as well), but for a content oriented site it remains a terrible idea.
- rantfoil 17y agoFacebook and Lala have done this. We added this to the Posterous Manage page, and it reduces page load times and makes that part of the site feel faster, especially when a user is exploring what's there and trying to find a particular setting or tool. The key is to use the URL hash to drive page changes in JS, so back button, browser history, and bookmarks all still work.
- hello_moto 17y agoI use Facebook everyday and they're quite slow and buggy. Sometime pressing back button doesn't work. Sometime even pressing the "previous" or "next" image icon takes a while or failed to load. Especially in their image section: press "next" and use the back button immediately (but not too fast), you'll see some "oops"
- Semiapies 17y agoFrameworks like Sammy take the approach of treating states as URIs. I'm not sure it's strictly necessary to abandon browser history functionality. http://code.quirkey.com/sammy/ http://code.quirkey.com/sammy/