benefits of clientside templating for red dot ruby
DESCRIPTION
Explore the implications & philosophy of client-side rendering & templating.TRANSCRIPT
RenderingClient-side
Implications & philosophy of client-side rendering.
Sunday, 20 May 12
Me
• Tim Oxley
• @secoif
• Freelance Node.js Consultant
• blog.timoxley.com
Sunday, 20 May 12
Who should be listening?
Sunday, 20 May 12
Anyone who calls themselves a “web master”
Sunday, 20 May 12
“Javascript is just for validations & animations.”
Sunday, 20 May 12
“My site is living in 2001, I have a pantry full of ajax powered spaghetti, and
basically everything is a new page refresh. How can I make
it slick?”
Sunday, 20 May 12
What is Clientside
Templating?Sunday, 20 May 12
What is Clientside Templating?
1. Server sends Client templates + ‘application code’.
2. Application code initialises the View
3. As user interacts with view, JSON data is transferred between client and server.
4. Application code applies templates to the data to update the view.
Sunday, 20 May 12
Downsides of Server-side
Architecture
Sunday, 20 May 12
Coupling
Sunday, 20 May 12
Server-side Load
• Infrastructure
• Dynamic pages can be expensive.
• Caching
Sunday, 20 May 12
<li class="uiUnifiedStory uiStreamStory genericStreamStory uiStreamBoulderHighlight aid_100000938073354 uiListItem uiListLight uiListVerticalItemBorder" data-ft="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}" id="stream_story_4fae38784e6a97a91051591"><div class="storyHighlightIndicatorWrapper"></div><div class="storyContent"><div class="UIImageBlock clearfix"><a class="actorPhoto UIImageBlock_Image UIImageBlock_MED_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" aria-hidden="true" data-ft="{"type":60,"tn":"\u003C"}" data-hovercard="/ajax/hovercard/hovercard.php?id=100000938073354"><img class="uiProfilePhoto profilePic uiProfilePhotoLarge img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><div class="storyInnerContent UIImageBlock_Content UIImageBlock_MED_Content"><div class="uiInlineBlock mlm uiPopover highlightSelector uiStreamHide" data-ft="{"type":55,"tn":"V"}" id="uisj4x_119"><a class="highlightSelectorButton uiStreamContextButton uiPopoverTriggerElem" href="#" aria-haspopup="true" role="menu" rel="toggle" id="uisj4x_120">Options</a></div><div class="mainWrapper"><h6 class="uiStreamMessage uiStreamHeadline" data-ft="{"tn":":"}"><div class="actorDescription actorName" data-ft="{"type":2,"tn":":"}"><a href="http://www.facebook.com/bonnie.felice" data-ft="{"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a></div></h6><h6 class="uiStreamMessage" data-ft="{"type":1,"tn":"K"}"> <span class="messageBody" data-ft="{"type":3}">Faces with beards > faces without beards</span></h6><form rel="async" class="live_393867123987887_131325686911214 commentable_item autoexpand_mode" method="post" action="/ajax/ufi/modify.php" data-live="{"seq":76754027}" onsubmit="return Event.__inlineSubmit(this,event)" id="uisj4x_153"><input type="hidden" name="charset_test" value="€,´,€,´,水,Д,Є"><input type="hidden"
name="fb_dtsg" value="AQB5BhPE" autocomplete="off"><input type="hidden" autocomplete="off" name="feedback_params" value="{"actor":"100000938073354","target_fbid":"393867123987887","target_profile_id":"100000938073354","type_id":"22","assoc_obj_id":"","source_app_id":"0","extra_story_params":[],"content_timestamp":"1336804069","check_hash":"AQCF-FbqG1g6gOoP","source":"1"}"><span class="uiStreamFooter"><span class="UIActionLinks UIActionLinks_bottom" data-ft="{"tn":"=","type":20}"><button class="like_link stat_elem as_link" title="Like this item" type="submit" name="like" onclick="fc_click(this, false); return true;" data-ft="{"tn":">","type":22}"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button> · <label class="uiLinkButton comment_link" title="Leave a comment"><input data-ft="{"type":24,"tn":"S"}" type="button" value="Comment" onclick="return fc_click(this);"></label> · </span><span class="uiStreamSource" data-ft="{"type":26,"tn":"N"}"><a href="/bonnie.felice/posts/393867123987887"><abbr title="Saturday, 12 May 2012 at 16:27" data-utime="1336804069" class="timestamp livetimestamp">3 hours ago</abbr></a></span> · <a data-hover="tooltip" title="Shared with: Bonnie's friends of friends" class="uiStreamPrivacy inlineBlock fbStreamPrivacy fbPrivacyAudienceIndicator" href="#"><i class="lock img sp_66rfdh sx_eda74d"></i></a></span><div><ul class="uiList uiUfi focus_target fbUfi" data-ft="{"type":30,"tn":"]"}"><li class="ufiNub uiListItem uiListVerticalItemBorder"><i></i></li><li class="hidden_elem uiUfiLike uiListItem uiListVerticalItemBorder" data-ft="{"type":31}"></li><li class="translateable_info hidden_elem uiListItem uiListVerticalItemBorder"><input type="hidden" autocomplete="off" name="translate_on_load" value=""></li><li class="uiUfiComments uiListItem uiListVerticalItemBorder" data-ft="{"type":32}"><ul class="commentList"><li class="uiUfiComment comment_76754027 ufiItem ufiItem" data-ft="{"tn":"R"}"><div class="UIImageBlock clearfix uiUfiActorBlock"><a class="actorPic UIImageBlock_Image UIImageBlock_SMALL_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" data-ft="{"type":34,"tn":"T"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354"><img class="uiProfilePhoto uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><a data-hover="tooltip" title="Hide as Spam" class="commentRemoverButton UIImageBlock_Ext uiCloseButton" href="#" role="button" rel="async-post" ajaxify="/ajax/ufi/one_click_remove?comment_id=76754027&commenter_id=100000938073354&profile_id=100000938073354&post_fbid=393867517321181&can_remove=0&can_report=1&can_edit=0&is_spam=0&report_link=%2Fajax%2Freport.php%3Fcontent_type%3D74%26cid%3D393867517321181%26rid%3D100000938073354%26cid2%3D0%26profile%3D100000938073354%26h%3DAfgqqM70GpkG7LcJ&feedback_params=%7B%22actor%22%3A%22100000938073354%22%2C%22target_fbid%22%3A%22393867123987887%22%2C%22target_profile_id%22%3A%22100000938073354%22%2C%22type_id%22%3A%2222%22%2C%22assoc_obj_id%22%3A%22%22%2C%22source_app_id%22%3A%220%22%2C%22extra_story_params%22%3A%5B%5D%2C%22content_timestamp%22%3A%221336804069%22%2C%22check_hash%22%3A%22AQCF-FbqG1g6gOoP%22%2C%22source%22%3A%221%22%7D"></a><div class="commentContent UIImageBlock_Content UIImageBlock_SMALL_Content" data-ft="{"type":33,"tn":"K"}"><a class="actorName" href="http://www.facebook.com/bonnie.felice" data-ft="{"type":35,"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a> <span data-jsid="text" class="commentBody">Provided the faces are male, I suppose.</span><span></span><div class="commentActions fsm fwn fcg"><a class="uiLinkSubtle" href="/bonnie.felice/posts/393867123987887?comment_id=76754027&offset=0&total_comments=1" data-ft="{"tn":"N"}"><abbr title="Saturday, 12 May 2012 at 16:29" data-utime="1336804155" class="timestamp livetimestamp">3 hours ago</abbr></a> · <span class="comment_like_76754027 fsm fwn fcg" data-ft="{"type":36,"tn":">"}"><button class="stat_elem as_link cmnt_like_link" type="submit" name="like_comment_id[76754027]" value="76754027" title="Like this comment"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button></span></div></div></div></li></ul></li><li class="uiUfiAddComment clearfix uiUfiSmall ufiItem ufiItem uiListItem uiListVerticalItemBorder uiUfiAddCommentCollapsed" data-ft="{"tn":"["}"><div class="UIImageBlock clearfix mentionsAddComment"><img class="uiProfilePhoto actorPic UIImageBlock_Image UIImageBlock_ICON_Image uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/41628_1245243750_9374_q.jpg" alt=""><div class="commentArea UIImageBlock_Content UIImageBlock_ICON_Content"><div class="commentBox"><div class="uiMentionsInput textBoxContainer" id="uisj4x_147"><div class="highlighter"><div><span class="highlighterContent"></span></div></div><div class="uiTypeahead mentionsTypeahead" id="uisj4x_149"><div class="wrap"><input type="hidden" autocomplete="off" class="hiddenInput"><div class="innerWrap"><textarea class="enter_submit DOMControl_placeholder uiTextareaNoResize uiTextareaAutogrow textBox mentionsTextarea textInput" title="Write a comment..." placeholder="Write a comment..." name="add_comment_text" onfocus="return wait_for_load(this, event, function() {JSCC.get('j5reBLCqEq0jyN8rnQ17').init(JSCC.get('j5reBLCqEq0jyN8rnQ18'));;JSCC.get('j5reBLCqEq0jyN8rnQ18').init(["buildBestAvailableNames","hoistFriends"]);JSCC.get('j5reBLCqEq0jyN8rnQ16').init({"max":10}, null, JSCC.get('j5reBLCqEq0jyN8rnQ17'));;;});" id="uisj4x_148" autocomplete="off" aria-autocomplete="list" aria-expanded="false" aria-invalid="false" aria-owns="typeahead_list_uisj4x_149" role="textbox" onkeydown="Bootloader.loadComponents(["control-textarea"], function() { TextAreaControl.getInstance(this) }.bind(this)); ">Write a comment...</textarea></div></div></div><input type="hidden" autocomplete="off" class="mentionsHidden"></div></div><label class="mts commentBtn stat_elem hidden_elem optimistic_submit uiButton uiButtonConfirm" for="uisj4x_150"><input value="Comment" class="enter_submit_target" name="comment" type="submit" id="uisj4x_150"></label></div></div></li></ul></div><input type="hidden" name="link_data" value="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}"></form></div></div></div></div></li>
Sunday, 20 May 12
<li class="uiUnifiedStory uiStreamStory genericStreamStory uiStreamBoulderHighlight aid_100000938073354 uiListItem uiListLight uiListVerticalItemBorder" data-ft="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}" id="stream_story_4fae38784e6a97a91051591"><div class="storyHighlightIndicatorWrapper"></div><div class="storyContent"><div class="UIImageBlock clearfix"><a class="actorPhoto UIImageBlock_Image UIImageBlock_MED_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" aria-hidden="true" data-ft="{"type":60,"tn":"\u003C"}" data-hovercard="/ajax/hovercard/hovercard.php?id=100000938073354"><img class="uiProfilePhoto profilePic uiProfilePhotoLarge img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><div class="storyInnerContent UIImageBlock_Content UIImageBlock_MED_Content"><div class="uiInlineBlock mlm uiPopover highlightSelector uiStreamHide" data-ft="{"type":55,"tn":"V"}" id="uisj4x_119"><a class="highlightSelectorButton uiStreamContextButton uiPopoverTriggerElem" href="#" aria-haspopup="true" role="menu" rel="toggle" id="uisj4x_120">Options</a></div><div class="mainWrapper"><h6 class="uiStreamMessage uiStreamHeadline" data-ft="{"tn":":"}"><div class="actorDescription actorName" data-ft="{"type":2,"tn":":"}"><a href="http://www.facebook.com/bonnie.felice" data-ft="{"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a></div></h6><h6 class="uiStreamMessage" data-ft="{"type":1,"tn":"K"}"> <span class="messageBody" data-ft="{"type":3}">Faces with beards > faces without beards</span></h6><form rel="async" class="live_393867123987887_131325686911214 commentable_item autoexpand_mode" method="post" action="/ajax/ufi/modify.php" data-live="{"seq":76754027}" onsubmit="return Event.__inlineSubmit(this,event)" id="uisj4x_153"><input type="hidden" name="charset_test" value="€,´,€,´,水,Д,Є"><input type="hidden"
name="fb_dtsg" value="AQB5BhPE" autocomplete="off"><input type="hidden" autocomplete="off" name="feedback_params" value="{"actor":"100000938073354","target_fbid":"393867123987887","target_profile_id":"100000938073354","type_id":"22","assoc_obj_id":"","source_app_id":"0","extra_story_params":[],"content_timestamp":"1336804069","check_hash":"AQCF-FbqG1g6gOoP","source":"1"}"><span class="uiStreamFooter"><span class="UIActionLinks UIActionLinks_bottom" data-ft="{"tn":"=","type":20}"><button class="like_link stat_elem as_link" title="Like this item" type="submit" name="like" onclick="fc_click(this, false); return true;" data-ft="{"tn":">","type":22}"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button> · <label class="uiLinkButton comment_link" title="Leave a comment"><input data-ft="{"type":24,"tn":"S"}" type="button" value="Comment" onclick="return fc_click(this);"></label> · </span><span class="uiStreamSource" data-ft="{"type":26,"tn":"N"}"><a href="/bonnie.felice/posts/393867123987887"><abbr title="Saturday, 12 May 2012 at 16:27" data-utime="1336804069" class="timestamp livetimestamp">3 hours ago</abbr></a></span> · <a data-hover="tooltip" title="Shared with: Bonnie's friends of friends" class="uiStreamPrivacy inlineBlock fbStreamPrivacy fbPrivacyAudienceIndicator" href="#"><i class="lock img sp_66rfdh sx_eda74d"></i></a></span><div><ul class="uiList uiUfi focus_target fbUfi" data-ft="{"type":30,"tn":"]"}"><li class="ufiNub uiListItem uiListVerticalItemBorder"><i></i></li><li class="hidden_elem uiUfiLike uiListItem uiListVerticalItemBorder" data-ft="{"type":31}"></li><li class="translateable_info hidden_elem uiListItem uiListVerticalItemBorder"><input type="hidden" autocomplete="off" name="translate_on_load" value=""></li><li class="uiUfiComments uiListItem uiListVerticalItemBorder" data-ft="{"type":32}"><ul class="commentList"><li class="uiUfiComment comment_76754027 ufiItem ufiItem" data-ft="{"tn":"R"}"><div class="UIImageBlock clearfix uiUfiActorBlock"><a class="actorPic UIImageBlock_Image UIImageBlock_SMALL_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" data-ft="{"type":34,"tn":"T"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354"><img class="uiProfilePhoto uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><a data-hover="tooltip" title="Hide as Spam" class="commentRemoverButton UIImageBlock_Ext uiCloseButton" href="#" role="button" rel="async-post" ajaxify="/ajax/ufi/one_click_remove?comment_id=76754027&commenter_id=100000938073354&profile_id=100000938073354&post_fbid=393867517321181&can_remove=0&can_report=1&can_edit=0&is_spam=0&report_link=%2Fajax%2Freport.php%3Fcontent_type%3D74%26cid%3D393867517321181%26rid%3D100000938073354%26cid2%3D0%26profile%3D100000938073354%26h%3DAfgqqM70GpkG7LcJ&feedback_params=%7B%22actor%22%3A%22100000938073354%22%2C%22target_fbid%22%3A%22393867123987887%22%2C%22target_profile_id%22%3A%22100000938073354%22%2C%22type_id%22%3A%2222%22%2C%22assoc_obj_id%22%3A%22%22%2C%22source_app_id%22%3A%220%22%2C%22extra_story_params%22%3A%5B%5D%2C%22content_timestamp%22%3A%221336804069%22%2C%22check_hash%22%3A%22AQCF-FbqG1g6gOoP%22%2C%22source%22%3A%221%22%7D"></a><div class="commentContent UIImageBlock_Content UIImageBlock_SMALL_Content" data-ft="{"type":33,"tn":"K"}"><a class="actorName" href="http://www.facebook.com/bonnie.felice" data-ft="{"type":35,"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a> <span data-jsid="text" class="commentBody">Provided the faces are male, I suppose.</span><span></span><div class="commentActions fsm fwn fcg"><a class="uiLinkSubtle" href="/bonnie.felice/posts/393867123987887?comment_id=76754027&offset=0&total_comments=1" data-ft="{"tn":"N"}"><abbr title="Saturday, 12 May 2012 at 16:29" data-utime="1336804155" class="timestamp livetimestamp">3 hours ago</abbr></a> · <span class="comment_like_76754027 fsm fwn fcg" data-ft="{"type":36,"tn":">"}"><button class="stat_elem as_link cmnt_like_link" type="submit" name="like_comment_id[76754027]" value="76754027" title="Like this comment"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button></span></div></div></div></li></ul></li><li class="uiUfiAddComment clearfix uiUfiSmall ufiItem ufiItem uiListItem uiListVerticalItemBorder uiUfiAddCommentCollapsed" data-ft="{"tn":"["}"><div class="UIImageBlock clearfix mentionsAddComment"><img class="uiProfilePhoto actorPic UIImageBlock_Image UIImageBlock_ICON_Image uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/41628_1245243750_9374_q.jpg" alt=""><div class="commentArea UIImageBlock_Content UIImageBlock_ICON_Content"><div class="commentBox"><div class="uiMentionsInput textBoxContainer" id="uisj4x_147"><div class="highlighter"><div><span class="highlighterContent"></span></div></div><div class="uiTypeahead mentionsTypeahead" id="uisj4x_149"><div class="wrap"><input type="hidden" autocomplete="off" class="hiddenInput"><div class="innerWrap"><textarea class="enter_submit DOMControl_placeholder uiTextareaNoResize uiTextareaAutogrow textBox mentionsTextarea textInput" title="Write a comment..." placeholder="Write a comment..." name="add_comment_text" onfocus="return wait_for_load(this, event, function() {JSCC.get('j5reBLCqEq0jyN8rnQ17').init(JSCC.get('j5reBLCqEq0jyN8rnQ18'));;JSCC.get('j5reBLCqEq0jyN8rnQ18').init(["buildBestAvailableNames","hoistFriends"]);JSCC.get('j5reBLCqEq0jyN8rnQ16').init({"max":10}, null, JSCC.get('j5reBLCqEq0jyN8rnQ17'));;;});" id="uisj4x_148" autocomplete="off" aria-autocomplete="list" aria-expanded="false" aria-invalid="false" aria-owns="typeahead_list_uisj4x_149" role="textbox" onkeydown="Bootloader.loadComponents(["control-textarea"], function() { TextAreaControl.getInstance(this) }.bind(this)); ">Write a comment...</textarea></div></div></div><input type="hidden" autocomplete="off" class="mentionsHidden"></div></div><label class="mts commentBtn stat_elem hidden_elem optimistic_submit uiButton uiButtonConfirm" for="uisj4x_150"><input value="Comment" class="enter_submit_target" name="comment" type="submit" id="uisj4x_150"></label></div></div></li></ul></div><input type="hidden" name="link_data" value="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}"></form></div></div></div></div></li>
Facebook Post + Comment =
9.1K of Markup
Sunday, 20 May 12
Sunday, 20 May 12
<li class="uiUnifiedStory uiStreamStory genericStreamStory uiStreamBoulderHighlight aid_100000938073354 uiListItem uiListLight uiListVerticalItemBorder" data-ft="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}" id="stream_story_4fae38784e6a97a91051591"><div class="storyHighlightIndicatorWrapper"></div><div class="storyContent"><div class="UIImageBlock clearfix"><a class="actorPhoto UIImageBlock_Image UIImageBlock_MED_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" aria-hidden="true" data-ft="{"type":60,"tn":"\u003C"}" data-hovercard="/ajax/hovercard/hovercard.php?id=100000938073354"><img class="uiProfilePhoto profilePic uiProfilePhotoLarge img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><div class="storyInnerContent UIImageBlock_Content UIImageBlock_MED_Content"><div class="uiInlineBlock mlm uiPopover highlightSelector uiStreamHide" data-ft="{"type":55,"tn":"V"}" id="uisj4x_119"><a class="highlightSelectorButton uiStreamContextButton uiPopoverTriggerElem" href="#" aria-haspopup="true" role="menu" rel="toggle" id="uisj4x_120">Options</a></div><div class="mainWrapper"><h6 class="uiStreamMessage uiStreamHeadline" data-ft="{"tn":":"}"><div class="actorDescription actorName" data-ft="{"type":2,"tn":":"}"><a href="http://www.facebook.com/bonnie.felice" data-ft="{"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a></div></h6><h6 class="uiStreamMessage" data-ft="{"type":1,"tn":"K"}"> <span class="messageBody" data-ft="{"type":3}">Faces with beards > faces without beards</span></h6><form rel="async" class="live_393867123987887_131325686911214 commentable_item autoexpand_mode" method="post" action="/ajax/ufi/modify.php" data-live="{"seq":76754027}" onsubmit="return Event.__inlineSubmit(this,event)" id="uisj4x_153"><input type="hidden" name="charset_test" value="€,´,€,´,水,Д,Є"><input type="hidden" name="fb_dtsg" value="AQB5BhPE" autocomplete="off"><input type="hidden" autocomplete="off" name="feedback_params" value="{"actor":"
100000938073354","target_fbid":"393867123987887","target_profile_id":"100000938073354","type_id":"22","assoc_obj_id":"","source_app_id":"0","extra_story_params":[],"content_timestamp":"1336804069","check_hash":"AQCF-FbqG1g6gOoP","ot;source":"1"}"><span class="uiStreamFooter"><span class="UIActionLinks UIActionLinks_bottom" data-ft="{"tn":"=","type":20}"><button class="like_link stat_elem as_link" title="Like this item" type="submit" name="like" onclick="fc_click(this, false); return true;" data-ft="{"tn":">","type":22}"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button> · <label class="uiLinkButton comment_link" title="Leave a comment"><input data-ft="{"type":24,"tn":"S"}" type="button" value="Comment" onclick="return fc_click(this);"></label> · </span><span class="uiStreamSource" data-ft="{"type":26,"tn":"N"}"><a href="/bonnie.felice/posts/393867123987887"><abbr title="Saturday, 12 May 2012 at 16:27" data-utime="1336804069" class="timestamp livetimestamp">3 hours ago</abbr></a></span> · <a data-hover="tooltip" title="Shared with: Bonnie's friends of friends" class="uiStreamPrivacy inlineBlock fbStreamPrivacy fbPrivacyAudienceIndicator" href="#"><i class="lock img sp_66rfdh sx_eda74d"></i></a></span><div><ul class="uiList uiUfi focus_target fbUfi" data-ft="{"type":30,"tn":"]"}"><li class="ufiNub uiListItem uiListVerticalItemBorder"><i></i></li><li class="hidden_elem uiUfiLike uiListItem uiListVerticalItemBorder" data-ft="{"type":31}"></li><li class="translateable_info hidden_elem uiListItem uiListVerticalItemBorder"><input type="hidden" autocomplete="off" name="translate_on_load" value=""></li><li class="uiUfiComments uiListItem uiListVerticalItemBorder" data-ft="{"type":32}"><ul class="commentList"><li class="uiUfiComment comment_76754027 ufiItem ufiItem" data-ft="{"tn":"R"}"><div class="UIImageBlock clearfix uiUfiActorBlock"><a class="actorPic UIImageBlock_Image UIImageBlock_SMALL_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" data-ft="{"type":34,"tn":"T"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354"><img class="uiProfilePhoto uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><a data-hover="tooltip" title="Hide as Spam" class="commentRemoverButton UIImageBlock_Ext uiCloseButton" href="#" role="button" rel="async-post" ajaxify="/ajax/ufi/one_click_remove?comment_id=76754027&commenter_id=100000938073354&profile_id=100000938073354&post_fbid=393867517321181&can_remove=0&can_report=1&can_edit=0&is_spam=0&report_link=%2Fajax%2Freport.php%3Fcontent_type%3D74%26cid%3D393867517321181%26rid%3D100000938073354%26cid2%3D0%26profile%3D100000938073354%26h%3DAfgqqM70GpkG7LcJ&feedback_params=%7B%22actor%22%3A%22100000938073354%22%2C%22target_fbid%22%3A%22393867123987887%22%2C%22target_profile_id%22%3A%22100000938073354%22%2C%22type_id%22%3A%2222%22%2C%22assoc_obj_id%22%3A%22%22%2C%22source_app_id%22%3A%220%22%2C%22extra_story_params%22%3A%5B%5D%2C%22content_timestamp%22%3A%221336804069%22%2C%22check_hash%22%3A%22AQCF-FbqG1g6gOoP%22%2C%22source%22%3A%221%22%7D"></a><div class="commentContent UIImageBlock_Content UIImageBlock_SMALL_Content" data-ft="{"type":33,"tn":"K"}"><a class="actorName" href="http://www.facebook.com/bonnie.felice" data-ft="{"type":35,"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a> <span data-jsid="text" class="commentBody">Provided the faces are male, I suppose.</span><span></span><div class="commentActions fsm fwn fcg"><a class="uiLinkSubtle" href="/bonnie.felice/posts/393867123987887?comment_id=76754027&offset=0&total_comments=1" data-ft="{"tn":"N"}"><abbr title="Saturday, 12 May 2012 at 16:29" data-utime="1336804155" class="timestamp livetimestamp">3 hours ago</abbr></a> · <span class="comment_like_76754027 fsm fwn fcg" data-ft="{"type":36,"tn":">"}"><button class="stat_elem as_link cmnt_like_link" type="submit" name="like_comment_id[76754027]" value="76754027" title="Like this comment"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button></span></div></div></div></li></ul></li><li class="uiUfiAddComment clearfix uiUfiSmall ufiItem ufiItem uiListItem uiListVerticalItemBorder uiUfiAddCommentCollapsed" data-ft="{"tn":"["}"><div class="UIImageBlock clearfix mentionsAddComment"><img class="uiProfilePhoto actorPic UIImageBlock_Image UIImageBlock_ICON_Image uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/41628_1245243750_9374_q.jpg" alt=""><div class="commentArea UIImageBlock_Content UIImageBlock_ICON_Content"><div class="commentBox"><div class="uiMentionsInput textBoxContainer" id="uisj4x_147"><div class="highlighter"><div><span class="highlighterContent"></span></div></div><div class="uiTypeahead mentionsTypeahead" id="uisj4x_149"><div class="wrap"><input type="hidden" autocomplete="off" class="hiddenInput"><div class="innerWrap"><textarea class="enter_submit DOMControl_placeholder uiTextareaNoResize uiTextareaAutogrow textBox mentionsTextarea textInput" title="Write a comment..." placeholder="Write a comment..." name="add_comment_text" onfocus="return wait_for_load(this, event, function() {JSCC.get('j5reBLCqEq0jyN8rnQ17').init(JSCC.get('j5reBLCqEq0jyN8rnQ18'));;JSCC.get('j5reBLCqEq0jyN8rnQ18').init(["buildBestAvailableNames","hoistFriends"]);JSCC.get('j5reBLCqEq0jyN8rnQ16').init({"max":10}, null, JSCC.get('j5reBLCqEq0jyN8rnQ17'));;;});" id="uisj4x_148" autocomplete="off" aria-autocomplete="list" aria-expanded="false" aria-invalid="false" aria-owns="typeahead_list_uisj4x_149" role="textbox" onkeydown="Bootloader.loadComponents(["control-textarea"], function() { TextAreaControl.getInstance(this) }.bind(this)); ">Write a comment...</textarea></div></div></div><input type="hidden" autocomplete="off" class="mentionsHidden"></div></div><label class="mts commentBtn stat_elem hidden_elem optimistic_submit uiButton uiButtonConfirm" for="uisj4x_150"><input value="Comment" class="enter_submit_target" name="comment" type="submit" id="uisj4x_150"></label></div></div></li></ul></div><input type="hidden" name="link_data" value="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}"></form></div></div></div></div></li>
Sunday, 20 May 12
<li class="uiUnifiedStory uiStreamStory genericStreamStory uiStreamBoulderHighlight aid_100000938073354 uiListItem uiListLight uiListVerticalItemBorder" data-ft="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}" id="stream_story_4fae38784e6a97a91051591"><div class="storyHighlightIndicatorWrapper"></div><div class="storyContent"><div class="UIImageBlock clearfix"><a class="actorPhoto UIImageBlock_Image UIImageBlock_MED_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" aria-hidden="true" data-ft="{"type":60,"tn":"\u003C"}" data-hovercard="/ajax/hovercard/hovercard.php?id=100000938073354"><img class="uiProfilePhoto profilePic uiProfilePhotoLarge img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><div class="storyInnerContent UIImageBlock_Content UIImageBlock_MED_Content"><div class="uiInlineBlock mlm uiPopover highlightSelector uiStreamHide" data-ft="{"type":55,"tn":"V"}" id="uisj4x_119"><a class="highlightSelectorButton uiStreamContextButton uiPopoverTriggerElem" href="#" aria-haspopup="true" role="menu" rel="toggle" id="uisj4x_120">Options</a></div><div class="mainWrapper"><h6 class="uiStreamMessage uiStreamHeadline" data-ft="{"tn":":"}"><div class="actorDescription actorName" data-ft="{"type":2,"tn":":"}"><a href="http://www.facebook.com/bonnie.felice" data-ft="{"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a></div></h6><h6 class="uiStreamMessage" data-ft="{"type":1,"tn":"K"}"> <span class="messageBody" data-ft="{"type":3}">Faces with beards > faces without beards</span></h6><form rel="async" class="live_393867123987887_131325686911214 commentable_item autoexpand_mode" method="post" action="/ajax/ufi/modify.php" data-live="{"seq":76754027}" onsubmit="return Event.__inlineSubmit(this,event)" id="uisj4x_153"><input type="hidden" name="charset_test" value="€,´,€,´,水,Д,Є"><input type="hidden" name="fb_dtsg" value="AQB5BhPE" autocomplete="off"><input type="hidden" autocomplete="off" name="feedback_params" value="{"actor":"
100000938073354","target_fbid":"393867123987887","target_profile_id":"100000938073354","type_id":"22","assoc_obj_id":"","source_app_id":"0","extra_story_params":[],"content_timestamp":"1336804069","check_hash":"AQCF-FbqG1g6gOoP","ot;source":"1"}"><span class="uiStreamFooter"><span class="UIActionLinks UIActionLinks_bottom" data-ft="{"tn":"=","type":20}"><button class="like_link stat_elem as_link" title="Like this item" type="submit" name="like" onclick="fc_click(this, false); return true;" data-ft="{"tn":">","type":22}"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button> · <label class="uiLinkButton comment_link" title="Leave a comment"><input data-ft="{"type":24,"tn":"S"}" type="button" value="Comment" onclick="return fc_click(this);"></label> · </span><span class="uiStreamSource" data-ft="{"type":26,"tn":"N"}"><a href="/bonnie.felice/posts/393867123987887"><abbr title="Saturday, 12 May 2012 at 16:27" data-utime="1336804069" class="timestamp livetimestamp">3 hours ago</abbr></a></span> · <a data-hover="tooltip" title="Shared with: Bonnie's friends of friends" class="uiStreamPrivacy inlineBlock fbStreamPrivacy fbPrivacyAudienceIndicator" href="#"><i class="lock img sp_66rfdh sx_eda74d"></i></a></span><div><ul class="uiList uiUfi focus_target fbUfi" data-ft="{"type":30,"tn":"]"}"><li class="ufiNub uiListItem uiListVerticalItemBorder"><i></i></li><li class="hidden_elem uiUfiLike uiListItem uiListVerticalItemBorder" data-ft="{"type":31}"></li><li class="translateable_info hidden_elem uiListItem uiListVerticalItemBorder"><input type="hidden" autocomplete="off" name="translate_on_load" value=""></li><li class="uiUfiComments uiListItem uiListVerticalItemBorder" data-ft="{"type":32}"><ul class="commentList"><li class="uiUfiComment comment_76754027 ufiItem ufiItem" data-ft="{"tn":"R"}"><div class="UIImageBlock clearfix uiUfiActorBlock"><a class="actorPic UIImageBlock_Image UIImageBlock_SMALL_Image" href="http://www.facebook.com/bonnie.felice" tabindex="-1" data-ft="{"type":34,"tn":"T"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354"><img class="uiProfilePhoto uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/573465_100000938073354_159540580_q.jpg" alt=""></a><a data-hover="tooltip" title="Hide as Spam" class="commentRemoverButton UIImageBlock_Ext uiCloseButton" href="#" role="button" rel="async-post" ajaxify="/ajax/ufi/one_click_remove?comment_id=76754027&commenter_id=100000938073354&profile_id=100000938073354&post_fbid=393867517321181&can_remove=0&can_report=1&can_edit=0&is_spam=0&report_link=%2Fajax%2Freport.php%3Fcontent_type%3D74%26cid%3D393867517321181%26rid%3D100000938073354%26cid2%3D0%26profile%3D100000938073354%26h%3DAfgqqM70GpkG7LcJ&feedback_params=%7B%22actor%22%3A%22100000938073354%22%2C%22target_fbid%22%3A%22393867123987887%22%2C%22target_profile_id%22%3A%22100000938073354%22%2C%22type_id%22%3A%2222%22%2C%22assoc_obj_id%22%3A%22%22%2C%22source_app_id%22%3A%220%22%2C%22extra_story_params%22%3A%5B%5D%2C%22content_timestamp%22%3A%221336804069%22%2C%22check_hash%22%3A%22AQCF-FbqG1g6gOoP%22%2C%22source%22%3A%221%22%7D"></a><div class="commentContent UIImageBlock_Content UIImageBlock_SMALL_Content" data-ft="{"type":33,"tn":"K"}"><a class="actorName" href="http://www.facebook.com/bonnie.felice" data-ft="{"type":35,"tn":";"}" data-hovercard="/ajax/hovercard/user.php?id=100000938073354">Bonnie Felice Newman</a> <span data-jsid="text" class="commentBody">Provided the faces are male, I suppose.</span><span></span><div class="commentActions fsm fwn fcg"><a class="uiLinkSubtle" href="/bonnie.felice/posts/393867123987887?comment_id=76754027&offset=0&total_comments=1" data-ft="{"tn":"N"}"><abbr title="Saturday, 12 May 2012 at 16:29" data-utime="1336804155" class="timestamp livetimestamp">3 hours ago</abbr></a> · <span class="comment_like_76754027 fsm fwn fcg" data-ft="{"type":36,"tn":">"}"><button class="stat_elem as_link cmnt_like_link" type="submit" name="like_comment_id[76754027]" value="76754027" title="Like this comment"><span class="default_message">Like</span><span class="saving_message">Unlike</span></button></span></div></div></div></li></ul></li><li class="uiUfiAddComment clearfix uiUfiSmall ufiItem ufiItem uiListItem uiListVerticalItemBorder uiUfiAddCommentCollapsed" data-ft="{"tn":"["}"><div class="UIImageBlock clearfix mentionsAddComment"><img class="uiProfilePhoto actorPic UIImageBlock_Image UIImageBlock_ICON_Image uiProfilePhotoMedium img" src="http://profile.ak.fbcdn.net/hprofile-ak-snc4/41628_1245243750_9374_q.jpg" alt=""><div class="commentArea UIImageBlock_Content UIImageBlock_ICON_Content"><div class="commentBox"><div class="uiMentionsInput textBoxContainer" id="uisj4x_147"><div class="highlighter"><div><span class="highlighterContent"></span></div></div><div class="uiTypeahead mentionsTypeahead" id="uisj4x_149"><div class="wrap"><input type="hidden" autocomplete="off" class="hiddenInput"><div class="innerWrap"><textarea class="enter_submit DOMControl_placeholder uiTextareaNoResize uiTextareaAutogrow textBox mentionsTextarea textInput" title="Write a comment..." placeholder="Write a comment..." name="add_comment_text" onfocus="return wait_for_load(this, event, function() {JSCC.get('j5reBLCqEq0jyN8rnQ17').init(JSCC.get('j5reBLCqEq0jyN8rnQ18'));;JSCC.get('j5reBLCqEq0jyN8rnQ18').init(["buildBestAvailableNames","hoistFriends"]);JSCC.get('j5reBLCqEq0jyN8rnQ16').init({"max":10}, null, JSCC.get('j5reBLCqEq0jyN8rnQ17'));;;});" id="uisj4x_148" autocomplete="off" aria-autocomplete="list" aria-expanded="false" aria-invalid="false" aria-owns="typeahead_list_uisj4x_149" role="textbox" onkeydown="Bootloader.loadComponents(["control-textarea"], function() { TextAreaControl.getInstance(this) }.bind(this)); ">Write a comment...</textarea></div></div></div><input type="hidden" autocomplete="off" class="mentionsHidden"></div></div><label class="mts commentBtn stat_elem hidden_elem optimistic_submit uiButton uiButtonConfirm" for="uisj4x_150"><input value="Comment" class="enter_submit_target" name="comment" type="submit" id="uisj4x_150"></label></div></div></li></ul></div><input type="hidden" name="link_data" value="{"qid":"5741588654933905232","mf_story_key":"6185231577928856054"}"></form></div></div></div></div></li>
16bytes
Sunday, 20 May 12
Not DRY• Transfer of Data + Markup for every
request
Sunday, 20 May 12
Not Efficient• Transfer of Data + Markup for every
request
Sunday, 20 May 12
Dumb Clients
Sunday, 20 May 12
Lag
Sunday, 20 May 12
Unoptimal UX
Sunday, 20 May 12
Ugly Clientside Code
Sunday, 20 May 12
Upsides of aThick Client
Sunday, 20 May 12
Free Stuff
Sunday, 20 May 12
Good Architecturefor Free
Sunday, 20 May 12
Decoupled Designfor Free
Sunday, 20 May 12
“Good Architecture Allows Future
Features”- Yehuda Katz
Sunday, 20 May 12
API For Free
Sunday, 20 May 12
MOBILE
API
WEB MOBILE WEB ???
Multiplatform for Free
Sunday, 20 May 12
Structure for Free
Sunday, 20 May 12
Separation of Responsibilities for
Free
Sunday, 20 May 12
Modular Caching for Free
Sunday, 20 May 12
More Static Assets for Free
Sunday, 20 May 12
Simplicity for Free
Sunday, 20 May 12
Power for Free
Sunday, 20 May 12
Benefits of Templating
Sunday, 20 May 12
Why not just template with straight JS?
• Get a smaller stack
• Simpler
• You enjoy typing
• Need it to be a little bit faster
Sunday, 20 May 12
Sunday, 20 May 12
Why not just use JS?
• String concatenation and array.push + join() is unwieldy.
• Multi-line strings are a pain in JS
• Double vs. single quotes
Uglies:
Sunday, 20 May 12
displaySessions: function(sessions, domSelector) { var li,html; if (sessions.length === 0) { $(domSelector).html('<li class="info">No sessions available</li>'); return; } html = sessions.map(function(s) { li = []; li.push('<li class="catalogCourse"><a href="#sessionDetails" data-id="'); li.push(s.guid); li.push('"></div><div class="coverArt"><img alt="" height="50" width="50" src="'); li.push(s.cover_art_url); li.push('" /></div><div class="details">'); li.push(s.html_description); li.push('</div><div class="rating"></div><div class="title">'); li.push(s.title); li.push('</div><div class="summary">'); li.push(s.start_on_in_words); li.push(' -- '); li.push(s.end_on_in_words); li.push('</div></a></li>'); return li.join(''); }).join(''); $(domSelector).html(html); },
Sunday, 20 May 12
{{#if sessions.length}} <li class="info">No sessions available</li>{{else}} {{each sessions}} {{with this}} <li class="catalogCourse"><a href="#sessionDetails" data-id="{{guid}}"> <div class="coverArt"> <img alt="" height="50" width="50" src="{{cover_art_url}}" /> </div> <div class="details"> {{s.html_description}} </div> <div class="rating"></div> <div class="title">{{title}}</div> <div class="summary"> {{start_on_in_words}} -- {{end_on_in_words}} </div> </a></li> {{/with}} {{/each}}{{/if}}
Sunday, 20 May 12
Template Engine Benefits
• Readable
• Maintainable
• Usable
Sunday, 20 May 12
Downsides of Thick Client
Sunday, 20 May 12
Complexity
Sunday, 20 May 12
•I don’t like things that are different
•A build process is usually required
•Performance varies per device
•More state managementSunday, 20 May 12
Finding the Sweet Spot
Sunday, 20 May 12
The Sweet Spot
100% Serverside 100% Clientside
Serverside Rendering + Ajax
HTML
Mostly Serverside rendering + JSON
via Ajax with clientside templates
Only Render Layout with ClientEverything else
rendered with JS
Sunday, 20 May 12
Hybrid Model• Twitter/Facebook/Google all render
HTML serverside for initial page load.
• UX: “Loading…” vs Content
Sunday, 20 May 12
Hybrid Model• Reduces the number of requests
• Shares rendering load between client/serverside
Sunday, 20 May 12
The Future
Sunday, 20 May 12
The Future• Rails: the next 5 years
@wycatshttp://lanyrd.com/2012/railsconf/srhtg/
• Rails is just an API & that’s OK@maccmanhttp://blog.alexmaccaw.com/rails-is-just-and-api-and-that-s-ok
Sunday, 20 May 12
Source: http://www.youtube.com/watch?v=cGdCI2HhfAU&feature=player_profilepage#start=44:20
DHH, RailsConf 2011 @ 44:20
Sunday, 20 May 12
Meteor is Coming
Sunday, 20 May 12
What To Use?
Sunday, 20 May 12
Spoilt for Choice
• JQuery
• HAML
• Mustache
• Underscore
• EJS
• Hogan
• DustJS
• Handlebars
• DoT
Sunday, 20 May 12
Spoilt for Choice
• JQuery
• HAML
• Mustache
• Underscore
• EJS
• Hogan
• DustJS
• Handlebars
• DoT
Sunday, 20 May 12
Stop Building Big Apps
Sunday, 20 May 12
More Smaller Components
Sunday, 20 May 12
Constant Greenfield
Sunday, 20 May 12
Damage Control
Sunday, 20 May 12
Isolate Complexity
Sunday, 20 May 12
How to get started
Sunday, 20 May 12
Don’t rewrite your app!
• Rewriting is (almost) never a good idea.
Sunday, 20 May 12
Incremental Enhancement.
• Use client side templating for the most used parts of the app, where it makes the biggest difference.
Sunday, 20 May 12
• Per User Role
• Per Device
Incremental Enhancement.
Sunday, 20 May 12
Build the UI first
• Only add API features as required
• Mock your server
Sunday, 20 May 12
Ember Rails• Clientside Framework
• Handlebars
• Rails integration
Sunday, 20 May 12
Thanks• @secoif
• blog.timoxley.com
• Come talk to me about Node & JS
• Interested in new opportunities
Sunday, 20 May 12
campjs.com
Sunday, 20 May 12