Sabtu, 31 Desember 2011

ubuntu 11.10 rails 3 passenger


Senin, 03 Oktober 2011

install mysql2 > 0.3.6 for mysql 64bit in windows

gem install mysql2 --platform=ruby -- '--with-mysql-lib="C:\Program Files\MySQL\MySQL Server 5.5\lib" --with-mysql-include="C:\Program Files\MySQL\MySQL Server 5.5\include"'


copy  C:\mysql-connector-c-noinstall-6.0.2-win32\lib\libmysql.dll to ruby\bin

original source: http://blog.mmediasys.com/2011/07/07/installing-mysql-on-windows-7-x64-and-using-ruby-with-it/

Senin, 04 Juli 2011

fixing option tag display none bug in webkit

The Problem

option tag using style display:none isn't hidden in browser using webkit engine (chrome, safari)

The workaround

using jQuery js framework with one simple function taken from jquery.extended_helper_2.6:
(function($) {
    /* hide select's specified option by removing the option and storing it in variable
     * this function is a workaround to fix webkit bug when hiding select's option:
     * https://bugs.webkit.org/show_bug.cgi?id=8351
     * hideSelectOptions(selector, options)
     * selector:
     * - string selector of options to hide
     * - null or undefined will not hide any options
     * - empty string will hide all options
     * - function will be ran for all options, return true to hide the options
     * options:
     * - toggleHide: true/false, activate/deactive toggle hide/show select if all options is hidden
     * - placeholder: string, add placeholder option if all options is hidden
     * usage:
     *  - $('select.certain_class').hideSelectOptions('.another_class'); // -> show previously hidden options and hide all options with 'another_class' class
     *  - $('select.certain_class').hideSelectOptions(''); // -> hide all options
     *  - $('select.certain_class').hideSelectOptions(); // -> show previously hidden options without hiding any options
    hideSelectOptions: function(selector, options){
      if(!options) options = {};
        var $this = $(this);
        // restore previously hidden options and remove any placeholder option

        // return if no selector specified
        if(!selector) return;
        // find, detach and store specified hidden options
        var hidden_options = $this.find('option');
          hidden_options = hidden_options.deleteIf(function(){return !selector.call(this);});
          hidden_options = hidden_options.filter(selector);

        // find visible options
        var visible_options = $this.find('option');

        // toggle hide/show select depend on visible option found
        if(options.placeholder && !visible_options.length)

        // select first option if no other visible option selected and trigger select change
          visible_options.filter(':first').attr('selected', 'selected');
      return this;

The Demonstration

Kamis, 30 Juni 2011

Additional Range method

class Range
  # return true if 2 range overlapped
  def overlap? other_range
    include?(other_range.begin) || other_range.include?(self.begin)

  # return a new intersection range between two ranges
  def & other_range
    raise TypeError, "exclusive range can't be intersected with non-exclusive one" unless self.exclude_end? == other_range.exclude_end?
    new_begin = [self.begin, other_range.begin].max
    new_end = [self.end, other_range.end].min
    new_begin <= new_end ? Range.new(new_begin, new_end, self.exclude_end?) : nil

  # return true if other_range is a subset in self
  def contains? other_range
    if !exclude_end?
      include?(other_range.begin) && include?(other_range.end)
    elsif self.begin.respond_to?('>=')
      self.begin <= other_range.begin && self.end.send(other_range.exclude_end? ? '>=' : '>', other_range.end)
      raise TypeError, "can't determine inclusion of range with this type of members"

  # return true if self is a subset of other_range
  def within? other_range
    other_range.contains? self

  # return length of the range (only for subtract-able range)
  def length
    self.end.respond_to?('-') ? self.end - self.begin : nil

  # return next range with same span (only for subtract-able and add-able range)
  def succ allow_touch=false
    return nil unless self.end.respond_to?('-') && self.end.respond_to?('+')
    new_begin = allow_touch || exclude_end? || !self.end.respond_to?(:succ) ? self.end : self.end.succ
    new_end = new_begin + length
    Range.new(new_begin, new_end, exclude_end?)

  # return previous range with same span (only for subtract-able and add-able range)
  def pred allow_touch=false
    return nil unless self.end.respond_to?('-') && self.begin.respond_to?('+')
    new_end = allow_touch || exclude_end? || !self.begin.respond_to?(:pred) ? self.begin : self.begin.pred
    new_begin = new_end - length
    Range.new(new_begin, new_end, exclude_end?)

Selasa, 28 Juni 2011

array flatten with level for ruby 1.8.7

straight to the code:
class Array
  alias_method :orig_flatten, :flatten
  def flatten level=nil
    if level.is_a?(Integer)
      temp_arr = clone
      level.times{ |i| temp_arr = temp_arr.inject([]){|s,v| v.is_a?(Array) ? s.concat(v) : s << v} }

of course although untested i'm sure it will have worse performance than the original flatten in ruby 1.9.2, but better than nothing right? ;)

ruby array to hash method

update 2012-12-21:
you should use flat_map instead of flatten, i'm too lazy to update the code though.. :P

we can convert hash to array easily using .to_a method for example:
hsh = {:a => 1, :b => 2, :c => 3}
arr = hsh.to_a # -> [[:a, 1], [:b, 2], [:c, 3]]

but there's no built in method to reverse that, there's no .to_hash instance method for array.

to solve that i added a simple instance method for array:
class Array
  def to_hash values=nil
    Hash[*(values.is_a?(Array) ? self.zip(values) : self).flatten(1)]

hsh = {:a => 1, :b => 2, :c => 3}
arr = hsh.to_a # -> [[:a, 1], [:b, 2], [:c, 3]]
arr.to_hash == hsh # -> true
[:a,:b,:c].to_hash [1,2,3] # -> {:a => 1, :b => 2, :c => 3}

a little precaution, flatten(1) will not work properly in ruby 1.8.7 or older, therefore it won't be possible to create hash with array as key or value. but there's a simple workaround for that by overriding array flatten method to behave like ruby 1.9.2 in my next post :)

useful online tools for web programming

  • Regex for ruby: http://www.rubular.com/
  • strftime: http://strfti.me/
  • css gradient generator: http://www.colorzilla.com/gradient-editor/
  • css validator: http://jigsaw.w3.org/css-validator/
  • css rounder corner generator: http://a.deveria.com/roundgen/
  • 7 great js resources (not really a tool but useful): http://mashable.com/2011/07/03/7-great-javascript-resources

will be updated as i found another tools

Sabtu, 11 Juni 2011

Rails general coding style


# somethings_controller.rb
def create
  @something = Something.new params[:something]
  if @something.some_state?
  redirect_to success_url
  render :action => "failed"


  1. should avoid rescue without specifying the exception, in above code, use
    rescue ActiveRecord::RecordInvalid
  2. better yet, don't use any rescue at all, use save instead of save! with some if
  3. post processing should be done in callback.
    after_create {|something| something.initialize_for_some_state if something.some_state}

Better Code:

# somethings_controller.rb
def create
  @something = Something.new params[:something]
  if @something.save
    redirect_to success_url
    render :action => "failed"


# somethings_controller.rb
def show
  @something = Something.find(:first, :conditions => "user_id = #{current_user.id} AND id = #{params[:id]} AND name = #{params[:name]}")
  respond_to do |format|
    format.js do
      render :js => "$('#container').html('#{escape_javascript(render :partial => "something", :object => @something)}');"
    format.json do
      render :json => @something.to_json


  1. SQL injection warning! never use data from params or from user input directly in sql code. use something like this instead:
    :conditions => ["user_id = #{current_user.id} AND id = ? AND name = ?", params[:id], params[:name]]
  2. using model relation and dynamic finder you can avoid the conditions entirely
    @something = current_user.somethings.find_by_id_and_name params[:id], params[:name]
  3. you should check if nothing found (@something is nil)
  4. this is just my opinion, but in most case i'll avoid using respond_to, instead i'll use 3 different view files: show.html.erb, show.js.erb, show.json.erb. rails will automatically use the correct view.

Better Code:

# somethings_controller.rb
def show
  @something = current_user.somethings.find_by_id_and_name params[:id], params[:name]
  render_invalid "not found" if @something.nil? # read about render_invalid in http://tech.maysora.com/2010/12/rails-renderinvalid-method.html

to be continued about model

Rabu, 01 Juni 2011

Counting sub-string occurrence in a string

Once upon a time.. I need a way to count number of occurrence of certain sub-string (not exclusively words) inside a string.

For example, string "Aya Hirano is the best seiyuu in the world! She was mostly known as her role as Haruhi." I wanted to know how many times string "he" occurred in there.
The result should be 4, 2 in the, 1 in She and 1 in her.

By using scan method we can do that easily:
class String
  def substr_count(pattern)

"Aya Hirano is the best seiyuu in the world! She was mostly known as her role as Haruhi.".substr_count("he") # -> 4
"Aya Hirano is the best seiyuu in the world! She was mostly known as her role as Haruhi.".substr_count(/(!|\.|\?)/) # -> 2 -> counting sentences? :D

Too simple to become share-worthy article I guess.. :P

Selasa, 03 Mei 2011

Aborting AJAX Request

For some functions like autocomplete, usually we send ajax request whenever user stop typing (by using timeout), but if the request takes a long time to finish, user might sending another request while the previous one isn't done yet, in worst case scenario this might cause the requests complete order messed up therefore the result will be invalid.

We can prevent this by aborting previous ajax request before sending a new one.
XMLHttpRequest object have abort() function we can use for that purpose, documented here:

in the following jquery script, i have a 2 text fields sending ajax request onkeyup that always completed in 2 seconds and adding the inputted text in the result div, the first one will have stackable ajax request, and the other one will prevent ajax request stacking by using abort

Senin, 14 Maret 2011

cookie operation functions

function setCookie(c_name,value,exdays){
  var exdate=new Date();
  exdate.setDate(exdate.getDate() + exdays);
  var c_value=escape(value) + ((exdays==null) ? "" : "; expires="+exdate.toUTCString());
  document.cookie=c_name + "=" + c_value;

function getCookie(c_name){
  var i,x,y,ARRcookies=document.cookie.split(";");

  for (i=0;i<ARRcookies.length;i++){
    if (x==c_name){
      return unescape(y);

function removeCookie(c_name){
  setCookie(c_name, '', -1);

Senin, 07 Maret 2011

international saimoe league voting

my voting result: