Skip to main content

Mobomo webinars-now on demand! | learn more.

Michael Bleigh and Chris Selmer gave a talk at RailsConf Europe 2008 entitled “Hacking the Mid-End: Advanced Rails UI Techniques.” If you had a chance to attend, please take a moment to evaluate the session. If not, hopefully this post will help you understand a bit of what you missed!

This talk was aimed at being an introduction to the role of a mid-end developer; someone who facilitates the back-end and front-end developers and also writes the javascript interaction layer using Unobtrusive Scripting. You can view the slides embedded below, or you can download the slide deck directly.

The Rails app that we developed during the talk is available on GitHub with all of the completed code. If you have any questions or comments, we’d love to hear from you. Thanks to everyone who came and saw the talk!

Categories
Author

Greetings from still sunny Berlin, where Michael & I wrapped up our Hacking Rails Internals talk yesterday. We would love to hear comments from those who attended — we are actively working on getting the slides and demo code to you as soon as possible. Please rate our session if you did attend, so that we can get some constructive feedback.

Today, Chris & Michael will be presenting Hacking the Mid-End : Unobtrusive Scripting & Advanced UI Techniques in Rails. This 45-minute talk will be a discussion of the “Mid-End” — advanced user interface problems that don’t fit the traditional ‘back-end’ and ‘front-end’ categorization. You can find more details on the RailsConf site.

Chris & I will also be flying out today from Berlin to Austin, TX for the Lonestar RubyConf. Along with Adam Bair, we’re giving a 6-hour mid-level training session on refactoring Rails apps. We will be talking about how to effectively rescue horrid codebases, prevent your codebase from turning into a monster and performance issues — we’re quite excited.

While we’re sad to leave Berlin so quickly — we got the chance to checkout some excellent street food in the city. Next time you’re in Berlin, give yourself a break for one night from expensive restaurants and indulge in Doner Kababs and Bratwurst (usually found with a few blocks of your hotel). Highly recommended. We also saw some yellow watermelon, but that’s not much of a story.

Michael will be here in Berlin till the end of the conference on Thursday — please come say hello if you can at either conference!

Categories
Author

Chris, Michael & I are at sunny/rainy Berlin, Germany at Railsconf Europe 2008. This year, the conference is being held at the Maritim proArte Hotel right in the middle of Downtown Berlin. Great food and interesting people around — we’re looking forward to speaking at the conference tomorrow and the day after.

If you’re attending the RailsConf tutorials, come see Michael & I speak tomorrow (Sept. 2, 2008) about hacking and tweaking the Rails internals for your project’s benefits. We have a nice mixup of slides and livecoding sessions ready, and will be running through some hardcore Rails internals material including the Rails class loader and the ever-confusing Routes implementation.

Chris & I will be attending Bratwurst on Rails, so if you would like to meetup, find us there. Bratwurst On Rails

Stay tuned for more coverage of Railsconf Europe and Lonestar RubyConf!

Categories
Author

Intridea will be speaking at two Ruby/Rails conferences this week. If you're attending either conference, make sure you come by and say hi!

RailsConf Europe

Pradeep Elankumaran and Michael Bleigh will be presenting their RailsConf Europe tutorial: The Renegade's Guide to Hacking Rails Internals, on September 2nd.

This far-reaching tutorial will give Intermediate and Advanced Rails developers a crash course in hacking and extending Rails internals. The topics covered will include: Ruby Meta-programming Techniques; Rails Abstractions, Idioms & Mixins; Rails Structure & Initialization; A Tour of the Rails Class Loader; Plugin Locators and Loaders; Codebase Modularization using Rails Plugins; Extending ActionView Form Builders; Site-wide Settings; and much more¦

Michael Bleigh and Chris Selmer will be presenting a RailsConf Europe talk: Hacking the Mid-End: Unobtrusive Scripting and Advanced UI Techniques in Rails, on September 3rd. Here's the talk overview:

As web application development advances beyond the static page, a whole new field of development is emerging. In the Javascript behavior layer and markup abstracting helpers lie the 'Mid-End': advanced user interface problems that don't fit traditional ˜back-end' and ˜front-end' models. Explore this new field with case studies and real code such as usage of Lowpro Javascript behaviors to keep the behavior separate from the markup. Learn how to give back-end developers the tools to create simple, repeatable, quality markup through block-accepting helpers. Discuss the methods that allow for rapid development of complex interactions in new and exciting ways and see real examples. Finally, look into the future of the Mid-End and what lies ahead for user interface development.

The Lone Star Ruby Conference

Adam Bair, Pradeep Elankumaran, and Chris Selmer will be leading a training on the first day of the LSRC. The training is titled: Rails Refactoring: Triage, Prevention, and Performance. And the overview:

Maybe you inherited a mess of a Rails project “ or perhaps your own codebase is poorly-tested, not very DRY, or just generally confusing. Worse yet, maybe your Rails site has slowed down to a crawl or even stopped working entirely. Whatever the reason, it's time to consider refactoring these rough spots and boosting your site's performance.

In the first half of the day we'll go through real-life examples of (shameful) code we've written and refactored, give tips on how and when to start, and show you how to avoid the need for a future refactor. In the second half, we'll introduce common Rails performance pitfalls, how to diagnose them, and how to solve them. We'll also talk about other ways to speed up your app.

Categories
Author

While writing color customization code for a recent project, I once again ran into the fact that the existing color gems for Ruby seem to be built for vastly different purposes. To that end, I decided to write a new library for dead-simple manipulation of colors with an emphasis on ease-of-use and being useful for web developers.

Installation

gem install colorist

The Basics

To instantiate a color in Colorist, you use a number of methods:

require 'colorist' include Colorist  red = Color.new(0xff0000) red = 0xff0000.to_color red = "red".to_color red = "#f00".to_color red = Color.from_rgb(255,0,0)

Note: I include Colorist in these examples, but there’s no reason you can’t leave it namespaced i.e. Colorist::Color instead.

The idea is to give maximum flexibility without making it complicated. Once you’ve instantiated a color, you can figure out a few tidbits about it and perform some basic operations:

red.brightness # => 0.299 red.r # => 255 red.invert # => #<Color #00ffff> red.text_color # => #<Color #ffffff> red.to_s # => "#ff0000" red.to_s(:rgb) # => "1.000, 0.000, 0.000"

Operations

The real value of Colorist comes in comparison and addition. You can use normal operators with the colors to add them together, subtract them, and compare them based on brightness. You can also do this with the string or numeric representations of colors:

red = 0xff0000.to_color green = 0x00ff00.to_color yellow = red + green yellow = "red".to_color + "green" yellow.to_s # => "#ffff00" red - 0.2 # => #<Color #cc0000>

Comparisons work off of the brightness of a given color. You can also calculate the contrast between two colors using the W3C’s formula:

red = "red".to_color red > "black".to_color # => true red > "white".to_color # => false red.contrast_with("green".to_color) # => 0.500653594771242

Get Coloring!

That’s most of the basic functionality, for all of the details you can view the RDoc on RubyForge. The source is available on GitHub and there is a Lighthouse project for any bugs or feature requests. Enjoy!

Categories
Author

There is a piece of code that shows up more than 80% of the controllers that I write, and it goes a little something like this:

class UsersController < ApplicationController   def user     @user ||= User.find(params[:id])   end   helper_method :user end

A simple memoization method to allow me to easily grab the parameter-referred user in all of my actions. If I’m using nested routes, that means I can write two, maybe three of these methods into a controller. I’m basically using slight variations on the same code 20 different times in an application. Since we live in a world that loves to be DRY, I thought, “I can do better.”

Fetches: Memoizing Your Parameter Record Retrieval

Fetches is a simple extension to ActionController that lets you simply define those kinds of fetch methods on a one-line command. For the example above, I can rewrite it like so:

class UsersController < ApplicationController   fetches :user end

That’s pretty useful! Not only can I call the “user” method from the controller, but it’s automatically helperized so that I can use the same call in my views. Of course, there are times when more advanced fetching is called for, say using a method other than find or storing to a different variable name. Let’s take a look at a slightly more complex example:

# assuming a route like /users/:user_id/articles/:id class ArticlesController < ApplicationController   fetches :user, :as => :author, :from => :user_id, :using => :find_by_login   fetches :article end

Now if I were to call “author” in any of my controller actions, it would be equivalent to User.find_by_login(params[:user_id]). Similarly, calling “article” is equivalent to Article.find(params[:id]). The “from” option can also take a Proc in case your fetching is not simply a parameter key:

class UsersController < ApplicationController   fetches :user, :from => Proc.new{ |c| c.params[:user_id] || c.params[:id] } end

The main advantages to fetches are brevity, clarity and DRYness. I’ve found that this method covers every use case for parameter-based fetching that I’ve needed, and as such provides a much simpler, more readable, and shorter way to fetch models for use in your controller and views.

Installation

Fetches is available as a gem as well as in traditional plugin format. To install
as a gem, add this to your environment.rb:

config.gem 'mbleigh-fetches', :source => 'http://gems.github.com', :lib => "fetches"

To install it as a traditional plugin:

script/plugin install git://github.com/mbleigh/fetches.git

Resources

The source is available on GitHub, the Acts As Community project is there for general discussion, and the Lighthouse is there for bugs and feature suggestions.

UPDATE: A commenter requested that the plugin be able to handle creation of new records in addition to fetching existing records. I have added in the :initialize option to do just this. Examples:

fetches :user, :initialize => true # initialize from params[:user] fetches :user, :initialize => :author # initialize from params[:author] fetches :user, :initialize => Proc.new{ |c| {:login => c.params[:login], :email => c.params[:email]} }
Categories
Author

A problem that often arises in AJAX-based web applications is how to handle it when things go wrong. The user should be informed of the problem in a descriptive manner, but obviously the internal workings of the application should not be revealed. A generic and useful way to handle this problem is to use HTTP Status Codes to indicate the type of failure, and use the javascript to cope appropriately.

In this example I will be using jQuery, but the principles behind are just as applicable to Prototype or any other Javascript library.

Your Friends 403 and 500

Anyone who’s built a Rails site is familiar with the 500 error. That’s the generic exception code thrown whenever something goes wrong in your application. Users should, hopefully, never ever see this when they’re using the site. However, oftentimes there are exceptions or errors that users should experience just as result of improperly filling out fields, permissioning, etc. So how do we differentiate?

The Rails render method has the ability to render out an arbitrary HTTP Status Code (i.e. 500 for error, 404 for not found, and many more). The “403 Forbidden” code means that the server understood the request made of it, but is refusing to complete it. This sounds like an apt description for typically “caught” exceptions. So let’s use the 403 code to intelligently handle the exceptions that we want to be seen by the user.

In the controller

Let’s take the simplest example, an invalid record. If you are creating a record via AJAX, a flash[:error] with a render :action => "new" is not going to suffice. Let’s try something like this instead:

class ItemsController < ApplicationController   def create     Item.create!(params[:item])     # continue on your merry way if it works   rescue ActiveRecord::RecordInvalid => e     respond_to do |format|       format.html {          flash.now[:error] = "There was a problem creating the item."         render :action => "new"       }       # Render out the validation failed message with a       # 403 status code.       format.js { render :text => e.message, :status => 403 }     end   end end

All right, now that we’ve got it handled on the controller side, it’s time to work some Javascript magic on our AJAX call.

 $('a#ajax_link').click(function() {   $.ajax({     url: '/items',      success:function(data, textStatus) {       // do success things     },     error:function(request, textStatus, errorThrown) {       // Use the specific message for a 403, but       // a generic failure message for a 500       var message = (request.status == 403) ?          request.responseText : "An unknown error occurred. Support has been contacted.";       // Simple alert for example, but you can handle       // however you want, such as populating an error message       // div and making it appear.       alert(message);     }     return false;   }); }); 

Now when your AJAX request fails, it will render a user-friendly error message if it’s an ‘expected’ error or a generic message if the request fails with an unexpected exception.

This is a simple example, but by building a general framework for error expectations you can make it much easier to provide user-friendly error handling that gives them all of the information they need without revealing any of your internal processes.

Categories
Author

Let's face it, iPhone interfaces are awesome, but they can only cater to a fraction of the mobile market. What are you to do if you want to satisfy the rest of the mobile world? Mobile Fu helps to make this job much easier by automatically detecting mobile devices that access your Rails application. People can access your site from a Palm, Blackberry, iPhone, Nokia, etc. and it will automatically adjust the format of the request from :html to :mobile.

Learn Mobile Fu

First off, just install the Mobile Fu plugin into your Rails application.

script/plugin install git://github.com/brendanlim/mobile-fu.git

Start by adding this one line to your ApplicationController.

class ApplicationController < ActionController::Base    has_mobile_fu  end

Once this is in place, any request that comes from a mobile device will be be set as :mobile format. It is up to you to determine how you want to handle these requests by creating the .mobile.erb versions of your views that are to be requested. Also, I recommend that you setup a before_filter that will redirect to a specific page depending on whether or not it is a mobile request. How can you check this?

is_mobile_device? # => Returns true or false depending on the device

You can also determine which format is currently set in by calling the method below.

in_mobile_view? # => Returns true or false depending on current req. format

If you want the ability to allow a user to switch between ˜mobile' and ˜standard' format (:html), you can just adjust the mobile_view session variable in a custom controller action.

session[:mobile_view] # => Set to true if request format is :mobile and false                             if set to :html

 

What About Custom Mobile Styling?

Different devices need different styling. Don't worry though, we've got this baked in to Mobile Fu (thanks to Intridea's own Michael Bleigh, who created Browserized Styles for letting me modify his code). If you are including a css or sass file via stylesheet_link_tag, all you have to do is add _device to the name of one of your files to override your styling for a certain device. The stylesheet that is loaded is dependant on which device is making the request.

Supported stylesheet override device extensions at the moment are: blackberry, iphone, mobileexplorer, nokia, palm

e.g., Accessing a page from a Blackberry.          Ends up loading mobile.css, and mobile_blackberry.css if the file exists.

 

Feature Requests

You can check out Mobile Fu's very own project page at Acts As Community. If you have any problems or would like me to add a certain feature, please create a ticket at http://blim.lighthouseapp.com/projects/14490-mobile-fu/. Also, feel free to fork Mobile Fu and make any enhancements you please from its GitHub location at: http://github.com/brendanlim/mobile-fu/tree/master

Categories
Author

Last week the Uberkit kicked off with some helpers to make your menu-building much easier. This week we’re following it up with UberForms, a Form Builder that DRYs up your repetitive form stresses. Let’s see how it works!

Building an Uber-er Form

UberForms automatically generate all of the standard boilerplate HTML that goes around your forms. By wrapping everything up in an easily style-able package, it becomes a much easier business to make new forms as well as re-use form styling across projects. With the form markup taken care of, you can focus on the more important aspects of your UI building and keep your views deadly clean.

While UberForms are available as a standard form builder (Uberkit::Forms::Builder), you may find it more useful in its helper form (automatically available when the UberKit plugin is loaded:

<% uberform_for :user do |f| %>   <%= f.text_field :login %>   <%= f.password_field :password %>   <%= f.submit "Submit"%> <% end %>

This will automatically be translated into some nice, CSS-ready HTML:

<form method="post" class="uberform" action="/users">   <div class="field_row">     <label for="user_login">Login:</label>     <input type="text" size="30" name="user[login]" id="user_login" class="text_field"/>     <br/>   </div>   <div class="field_row">     <label for="user_password">Password:</label>     <input type="password" size="30" name="user[password]" id="user_password" class="password_field"/>     <br/>   </div>   <button type="submit">Submit</button> </form>

You can also change the label, add a description or help text to a field by adding the relevant options:

<%= f.text_field :login, :label => "Username",                           :help => "Only a-z and underscores.",                           :description => "The name you will use to log in." %>

Becomes…

<div class="field_row">   <label for="user_login">Username:</label>   <input type="text" size="30" name="user[login]" label="Username" id="user_login" help="Only a-z and underscores." description="The name you will use to log in." class="text_field"/>   <span class="help">Only a-z and underscores.</span>   <span class="description">The name you will use to log in.</span>   <br/> </div>

Finally, you can create custom HTML inside an UberForm field by passing a block:

<% f.custom :label => "State", :for => "user_state" do |f| %>   <%= state_select :user, :state %> <% end %>

Becomes…

<div class="field_row">   <label for="user_state">State:</label>   <div class="pseudo_field">     <select id="user_state">...</select>   </div>    <br/> </div>

Easy, right? That’s all there is to it, now you can be UberForming to your heart’s content

Installation

To install the UberKit (which includes more than just forms) you can do so either as a gem or a traditional plugin. As a gem, just add this to your environment.rb:

config.gem 'mbleigh-uberkit', :lib => 'uberkit', :source => 'http://gems.github.com'

As a traditional Rails plugin:

script/plugin install git://github.com/mbleigh/uberkit.git

The Future of the UberKit

These two pieces are pretty helpful, but there’s more coming for the UberKit. Stay tuned for more updates, including more hooks and ways to customize the UberKit to fit your needs as a developer.

Categories
Author

Ever since it's announcement at WWDC 2008, most of us have been waiting anxiously to get our hands on the new iPhone 3G. If you haven't been keeping up with the news or have just been in a coma for the past few weeks, you'd know that the second coming of the iPhone was to be released today at Apple and AT&T stores nationwide.

 

I arrived at the Apple Store at Lenox Mall in Atlanta, GA around five in the morning and ended up being the fifth person in line. Quite surprising, since the Apple Store in New York City had people lining up since last week. After purchasing and activating my new iPhone 3G, I had a chance to play with all of its great new features.

The first thing you'll notice is that the once silver backing has been replaced with a shiny, plastic back. The 8GB iPhone 3G ($199) only comes in black, whereas the 16GB iPhone 3G ($299) comes in either black or white. Surprisingly, the new plastic back, which has a nice curve to it, feels high quality and fits very nicely in your hand. My only gripe though, is that the black color is very prone to smudges and finger prints. Metal has replaced the old plastic volume, power, and silence switch, which also add to a sturdier feel. The recessed-headphone jack is also now no more, allowing you to ditch the clunky adapters that were needed for the first generation iPhone. Also, the chrome bezel around the edges has been pushed back, which gives off the impression that the face is larger, even though the front dimensions are exactly the same as the previous generation.

So, the iPhone 3G is named the way it is for a reason. Finally, you can get 3G speeds on AT&T's HSDPA network, which blows EDGE out of the water. I've gotten accustomed to EDGE speeds over the past year and having pages load up to 2.4x faster is a luxury I don't ever want to live without again. Now I can browse all of my favorite sites without spending so much time waiting for everything to load.

 

If you had a first generation iPhone, you probably didn't use the speakerphone that much because it was quite worthless. It's now quite loud. The much louder volume of the speakerphone is definitely something that I am very happy about. Now, I can hear my calls loud (very) and clear. Speaking of clarity, many have said that the incoming and outgoing voice quality has been vastly improved. I've noticed a much cleaner, crisper sound while on the phone, but nothing dramatic.

One of the coolest new features is the GPS capability. You now get 'real' GPS, unlike the cellphone tower triangulation that was used in the previous generation iPhone. You don't get voice guided, turn by turn directions out of the box, but it's really neat to see that blue, pulsating dot, smoothly move through the map, showing you exactly where you are. I had a fun time using it on the way back home from the Apple Store. It's also been confirmed that Navigon, will be producing a third-party app, available in the App Store sometime soon, that will provide real turn-by-turn navigation.

Speaking of third party applications, this is really where the new 2.0 firmware shines. The App Store allows you to purchase either paid-for or free applications, right from your new iPhone 3G. There are over 500 different applications already available during launch time. The majority of the applications now are not free, but the average price per application seems to fall between $5 and $10.

Also, anybody can develop these applications with the iPhone SDK. As the developer, you can take advantage of Multi-Touch interface, the accelerometer, GPS, real-time 3D graphics, and 3D positional audio to create some amazing applications. You can also choose to let your product be downloaded for free or you can charge a price. If you decide to charge a price, you agree to pay Apple 30% of the final purchase price. The App Store is proving itself to be a great place for developers to get their products directly to the consumer which an amazing amount of ease.

There are many other great features with the 2.0 firmware that I haven't mentioned, push integration with Exchange and MobileMe, bug fixes, and much more - to list them all, would take quite some time. The iPhone 3G is a nice upgrade from the original iPhone, and if you haven't gotten an iPhone yet, the lowered price and the great new features make it an amazing deal. Look out for some great iPhone applications from us in the future.

Categories
Author
Subscribe to