Sunday, June 10, 2012

The difference between require, load, include and extend in ruby

Here are the differences between Include, Load,Require and Extend methods in Ruby :

Include:

When you Include a module into your class as shown below, it’s as if you took the code defined within the module and inserted it within the class, where you ‘include’ it. It allows the ‘mixin’ behavior. It’s used to DRY up your code to avoid duplication, for instance, if there were multiple classes that would need the same code within the module.

The following assumes that the module Log and class TestClass are defined in the same .rb file. If they were in separate files, then ‘load’ or ‘require’ must be used to let the class know about the module you’ve defined.


module Log
def class_type
"This class is of type: #{self.class}"
end
end

class TestClass
include Log
# ...
end

tc = TestClass.new.class_type

The above will print “This class is of type: TestClass”


Load :

The load method is almost like the require method except it doesn’t keep track of whether or not that library has been loaded. So it’s possible to load a library multiple times and also when using the load method you must specify the “.rb” extension of the library file name.

Most of the time, you’ll want to use require instead of load but load is there if you want a library to be loaded each time load is called. For example, if your module changes its state frequently, you may want to use load to pick up those changes within classes loaded from.

Here’s an example of how to use load. Place the load method at the very top of your “.rb” file. Also the load method takes a path to the file as an argument:


load 'test_library.rb'

So for example, if the module is defined in a separate .rb file than it’s used, then you can use the

File: log.rb


module Log
def class_type
"This class is of type: #{self.class}"
end
end

File: test.rb


load 'log.rb'

class TestClass
include Log
# ...
end

Require:

The require method allows you to load a library and prevents it from being loaded more than once. The require method will return ‘false’ if you try to load the same library after the first time. The require method only needs to be used if library you are loading is defined in a separate file, which is usually the case.

So it keeps track of whether that library was already loaded or not. You also don’t need to specify the “.rb” extension of the library file name.

Here’s an example of how to use require. Place the require method at the very top of your “.rb” file:


require 'test_library'

Extend:

When using the extend method instead of include, you are adding the module’s methods as class methods instead of as instance methods.

Here is an example of how to use the extend method:


module Log
def class_type
"This class is of type: #{self.class}"
end
end

class TestClass
extend Log
# ...
end

tc = TestClass.class_type

The above will print “This class is of type: TestClass”

When using extend instead of include within the class, if you try to instantiate TestClass and call method class_type on it, as you did in the Include example above, you’ll get a NoMethodError. So, again, the module’s methods become available as class methods.

Ruby Modules

Ruby Modules are similar to classes in that they hold a collection of methods, constants, and other module and class definitions. Modules are defined much like classes are, but the module keyword is used in place of the class keyword. Unlike classes, you cannot create objects based on modules nor can you subclass them; instead, you specify that you want the functionality of a particular module to be added to the functionality of a class, or of a specific object. Modules stand alone; there is no "module hierarchy" of inheritance. Modules is a good place to collect all your constants in a central location.

Modules are a way of grouping together methods, classes, and constants. Modules give you two major benefits:
  1. Modules provide a namespace and prevent name clashes.
  2. Modules implement the mixin facility. 
Modules define a namespace, a sandbox in which your methods and constants can play without having to worry about being stepped on by other methods and constants.

Syntax:

module Identifier
   statement1
   statement2
   ...........
end
Module constants are named just like class constants, with an initial uppercase letter. The method definitions look similar, too: module methods are defined just like class methods.
As with class methods, you call a module method by preceding its name with the module.s name and a period, and you reference a constant using the module name and two colons.

Example:

#!/usr/bin/ruby

# Module defined in trig.rb file

module Trig
   PI = 3.141592654
   def Trig.sin(x)
   # ..
   end
   def Trig.cos(x)
   # ..
   end
end
We can define one more module with same function name but different functionality:
#!/usr/bin/ruby

# Module defined in moral.rb file

module Moral
   VERY_BAD = 0
   BAD = 1
   def Moral.sin(badness)
   # ...
   end
end
Like class methods, whenever you define a method in a module, you specify the module name followed by a dot and then the method name.



Saturday, June 9, 2012

Ruby Public, Protected and Private Methods

Ruby gives three types of method visibility:
  1. Public methods can be called by everyone - no access control is enforced. A class's instance methods (these do not belong only to one object; instead, every instance of the class can call them) are public by default; anyone can call them. The initialize method is always private.
  2. Protected methods can be invoked only by objects of the defining class and its subclasses. Access is kept within the family. However, usage of protected is limited.
  3. Private methods cannot be called with an explicit receiver - the receiver is always self. This means that private methods can be called only in the context of the current object; you cannot invoke another object's private methods.
In Ruby, things are a bit different. Both private and protected methods can be called by any instance of the defining class and its subclasses. Inheritance plays absolutely no role in determining the visibility of a method. The difference instead is that private methods can never be called with an explicit receiver, even if the receiver is self. This means that it’s not possible to access another object’s private methods, even if the object is of the same type as the caller. A private method must be called from within the calling object.
Consider the following example:
class Person
  def public_method
    "public"
  end

  protected
  def protected_method
    "protected"
  end

  private
  def private_method
    "private"
  end
end

class SalesPerson < Person
  def check_protected_method_explicit_receiver
    "#{self.protected_method} method OK with explicit receiver"
  rescue
    "failure accessing protected method with explicit receiver"
  end

  def check_protected_method_implicit_receiver
    "#{protected_method} method OK with implicit receiver"
  rescue
    "failure accessing protected method with implicit receiver"
  end

  def check_private_method_explicit_receiver
    "#{self.private_method} method OK with explicit receiver"
  rescue
    "failure accessing private method with explicit receiver"
  end

  def check_private_method_implicit_receiver
    "#{private_method} method OK with implicit receiver"
  rescue
    "failure accessing private method with implicit receiver"
  end
end
The public method can of course be accessed from anywhere (in this case, outside the class with an explicit receiver) and both private and protected methods of Person will obviously raise a NoMethodError.
Person.new.public_method
=> "public"
Person.new.private_method
=> NoMethodError: private method `private_method' called for #
Person.new.protected_method
=> NoMethodError: protected method `protected_method' called for #
So the protected method cannot be accessed outside of the class or it’s subclass, but from within the subclass, using it with either an implicit or explicit receiver works fine:
SalesPerson.new.check_protected_method_explicit_receiver
=> "protected method OK with explicit receiver"
SalesPerson.new.check_protected_method_implicit_receiver
=> "protected method OK with implicit receiver"
The private method can also be called from the subclass, but note how it only works with an implicit receiver:
SalesPerson.new.check_private_method_explicit_receiver
=> "failure accessing private method with explicit receiver"
SalesPerson.new.check_private_method_implicit_receiver
=> "private method OK with implicit receiver"
This also means you can do stuff like:
class Person
  def ==(other)
    protected_method == other.protected_method
  end
end

x = SalesPerson.new
y = Person.new
x == y
=> true
We’re accessing the protected_method of another class instance that shares our type here, specifying an explicit receiver. If you were to try to use private_method instead, a NoMethodError would be raised. You could also just call other.send("private_method").

In summary, method visibility and access control can be a bit confusing at first, especially if you’re coming over to Ruby from some other OO language. If you’re still confused, there’s more information available here and here. Do yourself a favor and make sure you understand, cuz it’s important stuff!

Ruby Classes

Classes are the blue prints used to create objects in a running system.

In contrast to Java, Ruby’s building blocks are classes, modules and mixins.

A class is the blueprint from which individual objects are created.

Classes are the basic template from which object instances are created.

A class is made up of a collection of variables representing internal state and methods providing behaviors that operate on that state.

Classes are defined in Ruby using the class keyword followed by a name. The name must begin with a capital letter and by convention names that contain more than one word are run together with each word capitalized and no separating characters (CamelCase). The class definition may contain method, class variable, and instance variable declarations as well as calls to methods that execute in the class context at read time, such as attr_accessor. The class declaration is terminated by the end keyword.

Example:
  class MyClass
    def some_method
    end
  end


When a new class is created (typically using class Name ... end), an object of type Class is created and assigned to a global constant (Name in this case). When Name.new is called to create a new object, the new method in Class is run by default. This can be demonstrated by overriding new in Class:
class Class
   alias oldNew  new
   def new(*args)
     print "Creating a new ", self.name, "\n"
     oldNew(*args)
   end
 end

 class Name
 end

 n = Name.new
produces:
Creating a new Name
 

Variables in a Ruby Class:

Ruby provides four types of variables:
  • Local Variables: Local variables are the variables that are defined in a method. Local variables are not available outside the method. You will see more detail about method in subsequent chapter. Local variables begin with a lowercase letter or _.
  • Instance Variables: Instance variables are available across methods for any particular instance or object. That means that instance variables change from object to object. Instance variables are preceded by the at sign (@) followed by the variable name.
  • Class Variables: Class variables are available across different objects. A class variable belongs to the class and is a characteristic of a class. They are preceded by the sign @@ and are followed by the variable name.
  • Global Variables: Class variables are not available across classes. If you want to have a single variable, which is available across classes, you need to define a global variable. The global variables are always preceded by the dollar sign ($).
 
 

Instance Variables

Instance variables are created for each class instance and are accessible only within that instance. They are accessed using the @ operator. Outside of the class definition, the value of an instance variable can only be read or modified via that instance's public methods.
Example:
  class MyClass
    @one = 1
    def do_something
      @one = 2
    end
    def output
      puts @one
    end
  end
  instance = MyClass.new
  instance.output
  instance.do_something
  instance.output
Surprisingly, this outputs:
nil 2
This happens (nil in the first output line) because @one defined below class MyClass is an instance variable belonging to the class object (note this is not the same as a class variable and could not be referred to as @@one), whereas @one defined inside the do_something method is an instance variable belonging to instances of MyClass. They are two distinct variables and the first is accessible only in a class method.

Class Variables

Class variables are accessed using the @@ operator. These variables are associated with the class hierarchy rather than any object instance of the class and are the same across all object instances. (These are similar to class "static" variables in Java or C++).
Example:
  class MyClass
    @@value = 1
    def add_one
      @@value= @@value + 1
    end
 
    def value
      @@value
    end
  end
  instanceOne = MyClass.new
  instanceTwo = MyClass.new
  puts instanceOne.value
  instanceOne.add_one
  puts instanceOne.value
  puts instanceTwo.value
Outputs:
 1
 2
 2

Class Instance Variables

Classes can have instance variables. This gives each class a variable that is not shared by other classes in the inheritance chain.
  class Employee
    class << self; attr_accessor :instances; end
    def store
      self.class.instances ||= []
      self.class.instances << self
    end
    def initialize name
      @name = name
    end
  end
  class Overhead < Employee; end
  class Programmer < Employee; end
  Overhead.new('Martin').store
  Overhead.new('Roy').store
  Programmer.new('Erik').store
  puts Overhead.instances.size    # => 2
  puts Programmer.instances.size  # => 1
For more details, see MF Bliki: ClassInstanceVariables

Class Methods

Class methods are declared the same way as normal methods, except that they are prefixed by self, or the class name, followed by a period. These methods are executed at the Class level and may be called without an object instance. They cannot access instance variables but do have access to class variables.
Example:
  class MyClass
    def self.some_method
      puts 'something'
    end
  end
  MyClass.some_method
Outputs:
 something

Instantiation

An object instance is created from a class through the a process called instantiation. In Ruby this takes place through the Class method new.
Example:
  anObject = MyClass.new(parameters)
This function sets up the object in memory and then delegates control to the initialize function of the class if it is present. Parameters passed to the new function are passed into the initialize function.
  class MyClass
    def initialize(parameters)
    end
  end

Wednesday, March 10, 2010

Hadoop And Hive Configuration on Ubuntu kamic

1. To Install Hadoop
=================

Setting up your Apt Repository

1.

Add repository. Create a new file /etc/apt/sources.list.d/cloudera.list with the following contents, taking care to replace DISTRO with the name of your distribution (find out by running lsb_release -c)

For the stable repository, use…

deb http://archive.cloudera.com/debian karmic-stable contrib
deb-src http://archive.cloudera.com/debian karmic-stable contrib

For the testing repository use…

deb http://archive.cloudera.com/debian karmic-testing contrib
deb-src http://archive.cloudera.com/debian karmic-testing contrib

2.

Add repository key. (optional) Add the Cloudera Public GPG Key to your repository by executing the following command:

curl -s http://archive.cloudera.com/debian/archive.key | sudo apt-key add -

This allows you to verify that you are downloading genuine packages.
3.

Update APT package index. Simply run:

sudo apt-get update

4.

Find and install packages. You may now find and install packages from the Cloudera repository using your favorite APT package manager (e.g apt-get, aptitude, or dselect). For example:

apt-cache search hadoop
sudo apt-get install hadoop

2. To Install Hive
===============

Installing Hive is simple and only requires having Java 1.6 and Ant installed on your machine.

Hive is available via SVN at http://svn.apache.org/repos/asf/hadoop/hive/trunk. You can download it by running the following command.

$ svn co http://svn.apache.org/repos/asf/hadoop/hive/trunk hive

To build hive, execute the following command on the base directory:

$ ant package

It will create the subdirectory build/dist with the following contents:

* README.txt: readme file.
* bin/: directory containing all the shell scripts
* lib/: directory containing all required jar files)
* conf/: directory with configuration files
* examples/: directory with sample input and query files

Subdirectory build/dist should contain all the files necessary to run hive. You can run it from there or copy it to a different location, if you prefer.

In order to run Hive, you must have hadoop in your path or have defined the environment variable HADOOP_HOME with the hadoop installation directory.

Moreover, we strongly advise users to create the HDFS directories /tmp and /user/hive/warehouse (aka hive.metastore.warehouse.dir) and set them chmod g+w before tables are created in Hive.

To use hive command line interface (cli) go to the hive home directory (the one with the contents of build/dist) and execute the following command:

$ bin/hive

Metadata is stored in an embedded Derby database whose disk storage location is determined by the hive configuration variable named javax.jdo.option.ConnectionURL. By default (see conf/hive-default.xml), this location is ./metastore_db

Using Derby in embedded mode allows at most one user at a time. To configure Derby to run in server mode, look at HiveDerbyServerMode.

3. Setting up Hadoop/Hive to use MySQL as metastore
================================================

Many believe MySQL is a better choice for such purpose, so here I'm going to show how we can configure our cluster which we created previously to use a MySQL server as the metastore for Hive.

First we need to install MySQL. In this scenario, I'm going to install MySQL on our Master node, which is named centos1.



When logged in as root user:

yum install mysql-server

Now make sure MySQL server is started:

/etc/init.d/mysqld start

Next, I'm going to create a new MySQL user for hadoop/hive:

mysql
mysql> CREATE USER 'hadoop'@'centos1' IDENTIFIED BY 'hadoop';
mysql> GRANT ALL PRIVILEGES ON *.* TO 'hadoop'@'centos1' WITH GRANT OPTION;
mysql> exit
To make sure this new user can connect to MySQL server, switch to user hadoop:

We need to change the hive configuration so it can use MySQL:

nano /hadoop/hive/conf/hive-site.xml

and new configuration values are:


hive.metastore.local
true



javax.jdo.option.ConnectionURL
jdbc:mysql://centos1:3306/hive?createDatabaseIfNotExist=true



javax.jdo.option.ConnectionDriverName
com.mysql.jdbc.Driver



javax.jdo.option.ConnectionUserName
hadoop



javax.jdo.option.ConnectionPassword
hadoop



Some of the above parameters do not match what we did to setup derby server in previous post, so I decided to delete the jpox.properties file:

rm /hadoop/hive/conf/jpox.properties
hive needs to have the MySQL jdbc drivers, so we need to download and copy it to hive/lib folder:

cd /hadoop
wget http://dev.mysql.com/get/Downloads/Connector-J/mysql-connector-java-5.1.11.tar.gz/from/http://mysql.he.net/
tar -xvzf mysql-connector-java-5.1.11.tar.gz
cp mysql-connector-java-5.1.11/*.jar /hadoop/hive/lib

To make sure all settings are done correctly, we can do this:

cd /hadoop/hive
bin/hive
hive> show tables;

Thursday, January 7, 2010

Facebook integration in rails

People have found the integration of Facebook Connect tricky and while great libraries like facebooker handle the API part, actually getting the profile linking and integration flow is harder. So I’ve written this tutorial to integrate the most often starter plugin for authentication and registration in Ruby On Rails restful_authentication with Facebook Connect to allow your users to login and register through Connect.

First of all lets state what this integration is going to achieve.

* As a user I can register to the site through entering my details so I can access all that great functionality
* As a user I can login to the site through my entered username and password
* As a user I can register to the site through Facebook Connect so I don’t have to fill in that form
* As a user I can login to the site through Facebook Connect so I don’t have to remember two passwords
* As a user I can connect my existing site user with my Facebook Connect user so I can later login through Facebook Connect

We also have some constraints we need to consider

* As a user if I register a user through entering my details and later login through Facebook Connect I want to make sure I retain my old user account

So read on and i’ll have you Connected in 15 minutes.

We will first create a standard restful_authentication Rails application. I’m going to user mysql for this example


rails -d mysql connect_tutorial

Install restful authentication


git clone git://github.com/technoweenie/restful-authentication.git restful_authentication
cd ../..
./script/generate authenticated user sessions

Create our database


rake db:create
rake db:migrate

Move include AuthenticatedSystem from the Sessions Controller to the Application Controller

Start the server and browse to http://localhost:3000/signup. Bingo, Restful Authentication in 3 minutes. Don’t create any users yet we need to make to add some fields to connect up our accounts


script/generate migration add_users_fb


def self.up
add_column :users, :fb_user_id, :integer
add_column :users, :email_hash, :string
#if mysql
execute("alter table users modify fb_user_id bigint")
end

def self.down
remove_column :users, :fb_user_id
remove_column :users, :email_hash
end


rake db:migrate

We need two extra columns for our users. One to store the facebook user id in fb_user_id and another to store a special hash of our users email address which we can use to later match new Facebook users to existing accounts to take care of our constraint.

For the facebook connect we are going to use the facebooker plugin. This will handle the API level communication for us.


script/plugin install git://github.com/mmangino/facebooker.git
script/generate xd_receiver

The last line creates a cross-domain receiver file for Facebook Connect to callback on.

You are now going to have to create a Facebook Application on Facebook to get your API key and secret. Head over to http://www.facebook.com/developers/createapp.php



(Enter your own application name)



Take a note of the api_key, secret and callback url and add these to config/facebooker.yml


development:
api_key: {YOUR_KEY}
secret_key: {YOUR_SECRET}
canvas_page_name:
callback_url: http://localhost:3000/
pretty_errors: true
set_asset_host_to_callback_url: true
tunnel:
public_host_username:
public_host:
public_port: 4007
local_port: 3000

We need to initialise the Facebook Connect on every page. Basically this consists of 3 things. Adding a namespace decleration for FBML, adding the Facebook Connect Javascript and initialising the Javascript. Luckily rfacebooker can do this for us, so we create a generic layout index.html.erb

<%= javascript_include_tag :defaults%>


<%= fb_connect_javascript_tag %>
<%= init_fb_connect "XFBML"%>
<%=yield%>


And add the following to ApplicationController


layout 'index'
before_filter :set_facebook_session
helper_method :facebook_session

You are now ready to roll with some Facebook Connect tags. Add the following to the bottom of sessions/new.html.erb


or login with Facebook connect


<%= fb_login_button('window.location = "/users/link_user_accounts";')%>

And the following to users/new.html.erb


or register with Facebook connect


<%= fb_login_button('window.location = "/users/link_user_accounts";')%>

We also add another registration field for name


<%= label_tag 'name' %>

<%= f.text_field :name %>



These are going to create FBML tags which the Facebook connect Javascript will render as our Connect buttons

Start the server and go to http://localhost:3000/login. You should get this, if you don’t retrace your steps you have done something wrong.



Now it’s time to integrate. We need to do 3 main things

1. When you are logged in through a Facebook session then login through restful authentication
2. Link accounts between Facebook and Restful Authentication
3. Create accounts when someone login or register with facebook.

We need to add to lib/authenticated_system.rb. Change the current_user method to


def current_user
@current_user ||= (login_from_session || login_from_basic_auth || login_from_cookie || login_from_fb) unless @current_user == false
end

And add


def login_from_fb
if facebook_session
self.current_user = User.find_by_fb_user(facebook_session.user)
end
end

This will handle the seamless login for us. Now we need to add to our User model.


#find the user in the database, first by the facebook user id and if that fails through the email hash
def self.find_by_fb_user(fb_user)
User.find_by_fb_user_id(fb_user.uid) || User.find_by_email_hash(fb_user.email_hashes)
end
#Take the data returned from facebook and create a new user from it.
#We don't get the email from Facebook and because a facebooker can only login through Connect we just generate a unique login name for them.
#If you were using username to display to people you might want to get them to select one after registering through Facebook Connect
def self.create_from_fb_connect(fb_user)
new_facebooker = User.new(:name => fb_user.name, :login => "facebooker_#{fb_user.uid}", :password => "", :email => "")
new_facebooker.fb_user_id = fb_user.uid.to_i
#We need to save without validations
new_facebooker.save(false)
new_facebooker.register_user_to_fb
end

#We are going to connect this user object with a facebook id. But only ever one account.
def link_fb_connect(fb_user_id)
unless fb_user_id.nil?
#check for existing account
existing_fb_user = User.find_by_fb_user_id(fb_user_id)
#unlink the existing account
unless existing_fb_user.nil?
existing_fb_user.fb_user_id = nil
existing_fb_user.save(false)
end
#link the new one
self.fb_user_id = fb_user_id
save(false)
end
end

#The Facebook registers user method is going to send the users email hash and our account id to Facebook
#We need this so Facebook can find friends on our local application even if they have not connect through connect
#We hen use the email hash in the database to later identify a user from Facebook with a local user
def register_user_to_fb
users = {:email => email, :account_id => id}
Facebooker::User.register([users])
self.email_hash = Facebooker::User.hash_email(email)
save(false)
end
def facebook_user?
return !fb_user_id.nil? && fb_user_id > 0
end

This allows authentication to look up users either from their stored Facebook ID, or a hash of their email address. It also adds methods for our createing and linking. After any user is created we need to register them we Facebook Connect so add to the User model


after_create :register_user_to_fb

In the previous views Facebook Connect login button we added an after login javascript callback. This is to link our accounts after a user has gone through the callback process. We need to add this to the user controller


def link_user_accounts
if self.current_user.nil?
#register with fb
User.create_from_fb_connect(facebook_session.user)
else
#connect accounts
self.current_user.link_fb_connect(facebook_session.user.id) unless self.current_user.fb_user_id == facebook_session.user.id
end
redirect_to '/'
end

Don’t forget to add a route for this.


map.resources :users, :collection => {:link_user_accounts => :get}

Finally we need to have someone to go after login. Let’s create a home page under Users controller users/home.html.erb


<% if logged_in? %>
You are logged in as <%= current_user.name %>
<% if current_user.facebook_user? %>
"

Logout


<% else %>

why don't you connect with your facebook account


<%= fb_login_button('window.location = "/users/link_user_accounts";')%>

<%= link_to 'Logout', logout_path%>


<% end %>
<% else %>
You are not logged in!
<%= link_to 'Signup', signup_path%> or <%= link_to 'Login', login_path%>
<% end %>

And map it to root and delete public/index.html


map.root :controller => "users", :action => "home"

And its done. Stop the clock. Start the server and go to http://localhost:3000/login and press the big connect button



Login with your facebook account. Restful Authentication with Facebook Connect. Done!

Monday, June 15, 2009

rails plugin calendar_helper year added to helper

As I was working on one of the rails project which had calendar_helper plugin, which was not displaying year in the header of the calendar with month.

So I modified the calendar_helper.rb in the plugin lib directory.

Previously at line no.107 the code was
cal << %

("#{colspan}" class="#{options[:month_name_class]}">#{Date::MONTHNAMES[options[:month]]} )

just added #{options[:year]}

and modified it to

cal << %("#{colspan}" class="#{options[:month_name_class]}">#{Date::MONTHNAMES[options[:month]]} #{options[:year]})

Now month and year both displays perfectly in the calendar header