Monday, December 15, 2008

Try Wine

Wine is a very nice thing, it is a program you can use in order to run applications dedicated for certain platforms on any other one

for example i use it to run some windows application i get to use them on my linux machine, although Wine isn't fully mature yet but a large number of applications run nice on it

Friday, December 12, 2008

Personal Area Network (PAN)

Personal Area Network or shortly (PAN) is a communication network between a group of bluetooth-enabled devices (supporting PAN)

this network can be used between these devices in the same manner as local area connection i.e you can use it to transfer files between two devices or even more you can use it in a twisted way to enable one device to use other device internet connection after configuring a bridge between it and WLAN network

anyway it is a nice technique of communication, i liked it so much and tried to use it but i couldn't because my N80 doesn't support it. i suggest everyone to make use of this powerful facility

Sunday, October 5, 2008

How to name your command line windows??

if you are one of the people that use to open so many command line windows while working then you may have faced the problem knowing which one is opened on which task

for example, suppose you have a windows doing task X and another doing Y and another doing Z and so on. all have same default name added by windows when you open a command line window. Due to these similarities you always get lost getting to the window you want in one step

to get rid of this problem, use this small tip and name them with significant names using 'TITLE' command as follows

TITLE {{desired-name}}


that's it, now you can know which windows you have and select the one you desire in a fast way

Tuesday, September 23, 2008

Rails Console Tips & Tricks II

This is my second rails console tips & tricks. if you interested in reading previous tips and tricks read my first blog post regarding that matter.

This second part is about one command called "load" that is available in your Rails console. you can use this command to do many things as

1. to reload any file that was loaded when starting console and don't get reloaded when using "reload!" command such as files in your lib folder. to reload any file just write

load "#{RAILS_ROOT}/lib/{{file_name}}"


2. if you faced a problem such as "MySQL has gone away" just reload environment.rb once again as follows

load "#{RAILS_ROOT}/config/environment.rb"


3. also if you want to test a bunch of code in your console not just a single line of code, and want to be able to change part in it and rerun it once again then doing so in console is very time consuming and annoying so rather than doing so, you can write this code in a file and then

load "{{your-ruby-file}}"

Monday, September 8, 2008

Ruby Make Problem

Still in my early days using Linux and trying to compile ruby 1.9 on my machine in order to move my working environment to Linux

I downloaded ruby 1.9 source from ftp.ruby-lang.org and as stated in readMe file, i ran

./configure --prefix={{any-desired-path}}

successfully then ran

make

it took some time then i was faced with that error

executable host ruby is required. use --with-baseruby option.

What is that error? and what ruby?? i am compiling ruby how come i need it.


Anyway, i began searching for an explanation. i reached to a comment in one of the forums stating that this error can occur in these two cases

1. ruby isn't in the default path
2. ruby isn't installed

More investigation showed that i should have any previous version of ruby installed in order to use it with that make file as follows

./configure --prefix={{any-desired-path}} --with_baseruby={{full-path-to-ruby-executable}}

then run make command once again. And it worked finally

What a nice recursive world, "ruby is needed to compile ruby"

Thursday, September 4, 2008

configure: error: C compiler cannot create executables

In my first start to use ubuntu, i wanted to compile ruby on my machine

i downloaded ruby source and executed configure file to generate make file

./configure

i got this error

C compiler cannot create executables

although i have gcc latest version installed



after investigating this error i found that the solution was

sudo apt-get install build-essential


after doing so, everything worked fine

Tuesday, August 19, 2008

SVN Branches do HELP


Q: Have you heard about SVN branches ?
A: yes i have

Q: Have you used it before ?
A: no i didn't


if this scenario applies on you, then let me tell you why you should deal with SVN branches. I will try to prove my concept through a small scenario introducing 3 problems you might face while using SVN and how they can be solved with or without branches

Scenario


suppose you are working on a project and after a while you reached a stable state at which you decided to go live. after going live, you decided to move ahead and work on the next version of your project. while working on this version, a sudden problem occurred on your server and your online version was lost.


HOW WILL YOU RETURN IT BACK LIVE AFTER YOU STARTED DEVELOPMENT ON A NEW UNSTABLE VERSION?? This is problem 1.

hopefully you succeeded to do so, but later on, you found a bug and started fixing it but you can't leave your online version containing this bug until you finish development of the new version.


HOW CAN YOU COPY THIS BUG FIX TO THE ONLINE VERSION?? This is problem 2.

you also succeeded doing so, now suppose that problem 1 happened once more but this time after fixing problem 2.


HOW WILL YOU GET BACK ONLINE WHILE NO REVISION CONTAINS BUG FIXES MADE?? This is problem 3.

Without using SVN Branches


In problem 1, you will start looking at the repository revisions searching for the revision number at which you decided to go live in order to check it out again on your server and return online
accepted solution but considering the time and effort you took to do so i consider this solution a difficult one

In problem 2, you will fix the bug then select from your project the altered files and copy them one by one to your server without selecting any other files related to the new version you are working on. this solution will take a lot of time and effort and some errors might be expected while selecting files

In problem 3, i think you will have to work in your weekend in order to find the stable version and add it to bugs fixes that you have made

After SVN Branches


In problem 1, since you have created a new branch for the new version leaving your stable version as it is. all you need is to check it out again.


In problem 2, when you find a bug you will just commit all files you changed to your branch then start fixing that bug and commit the changed files then finally merge the difference between the last two revisions on branch with trunk


In problem 3, take what is in the trunk directly


I think it is now clear how helpful branches can be especially in a project that is expected to change from time to time which is actually common in a large of projects

Monday, August 18, 2008

Different encoding error

if you found yourself suffering with this error

ActiveRecord::StatementInvalid: Mysql::Error: #HY000Incorrect string value

don't cry or check your code looking at the data you save thinking that you might have left some bad characters around causing you this misery

all you need to do is to check the used database connection encoding against your db tables encoding, most probably you will find them different

if so then the solution is one of these two options
1) remove encoding field from specification and use default db encoding
2) change the encoding of your db tables to this encoding

once you do so, you will have a good life

Tuesday, July 22, 2008

acts_as_modified plugin

is it changed? which attributes? what are the old values? in some cases you may be asking yourself these questions when dealing with some models

When should you care about these questions?

suppose you have a model doing an expensive operation on save. this operation is useful only if one specific attribute changed. so doing it on every save neglecting which attributes changed will degrades performance significantly

So what can you do?

you can load model old data from database and check if that attribute has changed or not and if so do your action

or

you can use acts_as_modified plugin, it helps keeping modified attributes with their old values within model in order to be capable of answering your questions without doing any extra database trips

I am exited, from where can i get it?

it depends on your rails version

1. ((rails 2.1)) do nothing, dirty objects already embedded in this version
2. ((rails r7315 and above)) install from http://svn.viney.net.nz/things/branches/acts_as_modified_edge
3. ((ELSE)) install from http://svn.viney.net.nz/things/rails/plugins/acts_as_modified

That's it, Enjoy the fun

Sunday, July 20, 2008

Rails Console Tips & Tricks

Rails console have many useful tips that you may exploit as

Getting out of a block of code


If you're in an indented block of code (e.g., something that should be terminated with end) and want to escape without finishing, you can use ctrl + c to get back to the top level. The current expression will be ignored and not run.



Accessing the last return value


you can use the magic variable (_) for accessing last value
and you can then assign this value to a variable as x = _



Rollback all database changes on exit


script/console --sandbox

Sunday, June 22, 2008

Rails Validations & Unit Tests

I was doing a new feature in an existing rails project, and after finishing that feature, i ran all tests to check that everything is fine and no failures or errors occurred after my change

i ran the tests and found a failure in one of the unit tests, i opened it to see what is the problem. at this point i found in that file a function that gained my attention.

before stating what is inside this function, lets have a look at the part of the model that is being tested by this function

class Feed < ActiveRecord::Base
validates_presence_of :name

...
end

we can see in this part that name field should be present for the model to be valid, now lets look at the testing function

f = Feed.new
assert !f.valid?
assert f.errors.invalid?(:action)


So, what is the point in this code? the point is that at my first look at this function, i considered it a redundant test function because it checks an already tested rails function which is the validation function.

so i asked a friend of mine about his opinion, and he agreed with me that it is redundant and useless

later on, i asked someone with greater experience about his opinion also in this function as it represents a class of functions found in many models checking such validations.

But his opinion was different. he considered it useful and justified that by stating that this function tests the contract (which is that no feed is accepted if no name is stated) with the client, so that if someone later on changed this part in a wrong way, this test will alert us that the contract has changed. so that we reconsider our action to see if it has been really changed by the contract or by mistake

i found that answer reasonable and added to me a new way of thinking towards tests which is testing the agreements rather than checking whether our code is working or not

Rails: Modules & Routes

I used to make a module for every set of controllers which are doing certain task or feature because this way, things become organized in a better way

but something weird happened to me while trying to test a controller inside one of the modules, to see what happened i represent my case here by an example

i added in routes file this snippet of code

map.resources :items do |item|
item.resource :rate, :controller => 'ItemActions::Rate'
end

and in my controllers folder, made a folder called 'item_actions' and added inside it a file called 'rate_controller.rb', inside this file i wrote

module ItemActions
class RateController < ApplicationController
...
end
end

restarted the server and run my work, everything fine and i can call the controller actions as any other controller

then i opened the controller test file and inside one of its test functions, i added this code

post :create, {:item_id => 1, :rating => 50}


i got that error

No route to match {:controller => 'item_actions/rate', :action => 'create', :item_id => 1}


i changed the controller to be

class ItemActions::RateController < ApplicationController
...
end

but nothing changed, i am still getting that error once again, searching for a long time, i reached to a working solution which was to open routes file and change it to

map.resources :items do |item|
item.resource :rate, :controller => 'item_actions/rate'
end


That's it, it worked and i didn't get the error once again

Wednesday, June 18, 2008

Remember User Login Via Cookies

How to persist user login via cookies if session has expired?, this is a question almost answered in most of nowadays web applications, So how can this be done?

The idea is simple, and can be summarized in these simple steps

1. add a new column in your users table called login_key or remember_token or any name you prefer of type string

2. whenever user tries to login and his login is successful, add in his cookies a cookie called anything ex: remember_token and let its value be a generated random string of length around 40 characters for better security which is our token, and save this token in the db with that user

3. now add, in any action you need to check in it whether this user already in system or guest, a snippet of code that checks if the person isn't logged in whether the request has a cookie with the name choosed before and if so, check the db looking for a user having that token, if found then this user is logged in as if he did that in the normal ordinary way

That's it, now you can use cookie to log user in if his session has expired. There are also some points you may need to take care of when using this technique

1. Make cookie expires after some time so that it gets created once again with new token

2. In order to provide extra security, add with that token another info about the user

Monday, June 16, 2008

ActiveRecord Association Weird Length Method

The method 'length' defined for ActiveRecord associations works in a very weird manner.

consider this example


class User < ActiveRecord::Base
has_many :feeds
end


i was using the class and writing this snippet of code to get the count of feeds in the db


@user = User.find :first




puts @user.feeds.length


looking at the log, i found that the added query was


SELECT * FROM `feeds` WHERE (feeds.user_id = 1)


and not


SELECT count(*) AS count_all FROM `feeds` WHERE (feeds.user_id = 1)


so in order to get away from such weird sql statement which will exhaust a very large bandwidth getting all records to count them, use this instead


puts @user.feeds.count


or


puts @user.feeds.size


but don't use 'length' method

Thursday, May 15, 2008

SVN Branches

Imagine working on a deployed project, and you want to add some new features and changes on the running copy.

Since making new features may cause problems in the deployed project, you need to have another copy from the application and work on it freely then merge it with the running copy to apply your changes.

Subversion makes this very easy, all you need to do is to create a new branch.

So, what is a branch?

in order to understand that, lets look at the repository location hierarichy, you will find that it is as follows
--
-- trunk
-- branches
  • trunk is the folder containing the version of the website currently deployed

  • branches is another folder containing some other versions, as a new edition of the application
Now, in order to do that, just run this command

svn copy ((repository-path))/((project-name))/trunk ((repository-path))/((project-name))/branches/((branch-name)) -m "Creating a private branch in order to ... bla bla bla"


now you are done with your branch, checkout the project from that new path, and do any changes you want freely then at the end merge with your trunk to apply your changes

Monday, May 5, 2008

acts_as_changed plugin farewell

i used acts_as_changed plugin since a while and i have been enjoying the idea of being capable to know which attributes has been changed in my model and to take action upon certain attributes changes

and today i only tried to look at it again to know if there are any changes made in it or not but, i was shocked when i read a comment from the owner stating that it isn't plugin anymore

it is now an alternative base.rb file that you can update your activerecord with if you want to enjoy the plugin functionality once again

and he stated that he did so because he was facing problem in callbacks that he couldn't solve till now except through this way

anyway, i hope he finds a solution for it so that we all benefit from this plugin functionality

Wednesday, April 23, 2008

Memcache Trick

i was faced with a very weird behaviour while working with memcache-client with two memcache servers

first lets look of my configuration to the client in order to explain on it
On my first server

memcache_options = {
((some options)
}
CACHE = MemCache.new memcache_options
CACHE.servers = [((SERVER1)), ((SERVER2))]


On my second server

memcache_options = {
((some options)
}
CACHE = MemCache.new memcache_options
CACHE.servers = [((SERVER2)), ((SERVER1))]


after running both servers, i noticed that what i enter in memcache on that server isn't available to the other server

Where is the problem??

here it is, a very strange reason

CACHE.servers = [((SERVER2)), ((SERVER1))]
CACHE.servers = [((SERVER1)), ((SERVER2))]


this is the problem, one uses SERVER1 then SERVER2
other uses SERVER2 then SERVER1

i thought that memcache client when checking for a key, he looks at the first, if not found then looks at the second then say it is a miss
but i realized that if it isn't on the first then it doesn't look at the second

That's it, just take care, cuz small things can waste your time and energy looking after their reasons

Adding Data Through Migrations

one of the points i am always faced with while adding some migrations, is my need to add some system data as a static group for Administrators or any other.

so simply i create a new migration and add the following
ex:
Group.create((some_attributes>))

and it simply works fine, until someone later one adds a new column
in another new migration and adds validation on that column in the Model

and here the problem occurs
my old migration throws exception because of validation added on a new column added later in another migration but Model carries code validating it

how to solve these problems?

i suggest not using create at all
but rather use new and set our attributes
then save without validations

Thursday, April 3, 2008

Thick Models Thin Controllers

i have worked for about six months with Rails and through this time i was coding a lot in my controller which has shown to me lots of problem later on

for example,

i was having a Topic model and Post model, where every topic has many posts
and in each of these two models there is a field called archive

i was having a controller that changes the archive field to a certain value then pass on every post it owns and change its attribute also

later on, i made another controller and in it i also changed that field in it and passed on all posts to do the same change in it

this led to redundancy and duplication of code

but the problem became more complicated when i wanted to change the logic of this topic and its posts replication to a new way

here i have to move on my controllers and change this code in them

but i have added the code that observe this change in topic attribute and apply it on all its posts inside the model, i would haven't faced this problem anymore
and this will give me flexibility to do changes easily also

so this led to the idea of having my controller thin containing the least amount of code and my model thick containing large amount of code

Wednesday, March 26, 2008

script/console reload models

if you are one of the Rails applications developer, then you would have used this command before
ruby script/console

it is very nice and gives you the ability to load your environment and try it as you wish, but what if you changed anything in the application models, you will find that the console isn't aware of these changes at all

so what can you do to make him aware of your changes?

here it is, just run this command in your console
Dispatcher.reset_application!


Now you can try the new changes you made in your models

Wednesday, February 27, 2008

Unobtrusive JavaScript

While serving the internet looking for something, i found someone talking about something called 'Unobtrusive JavaScript', it was the first time for me to hear that expression so i looked for it and found that

Unobtrusive JavaScript is one of the emerged paradigms in JavaScript, its main idea is to achieve more separation while working on web applications

Since now, we almost reached to an agreement to separate presentation from content/structure through separation of CSS from HTML, this paradigm is greedy and wants extra separation of behaviour from structure

lets look at this example to clarify things out
<#input type="text" id="date" onchange="validateDate(this);" />


here we can see that our structure is that simple input field but it is mixed by this onchange function which shows to us what this input does on change

Now, look at that one
<#input type="text" id="date" />


here we have only structure and no behaviour, so WHERE SHOULD WE ADD OUR BEHAVIOUR?, we should do that with javascript away from our presentation as follows

window.onload = function(){ //Wait for the page to load.
var input = document.getElementById('input');
input.onchange = function(){
//Do something changed.
}
};


This is the simplest illustration that i can give to this paradigm, it makes you live in a world of layers (structure, presentation, behaviour)

actually, i am admired with this paradigm so much because it layered our application and thus allowed for better separation but i think one of its problems is that looking at structure won't give you a quick idea about what elements behave until you visit the behaviour layer

finally, i would like to end with this nice quote from one of the articles i read about this topic
The first rule of the unobtrusive Javascript club is don't talk about the unobtrusive Javascript club.


this post isn't done yet until i hear from you what do you think about this emerged paradigm and whether it should be the dominant in the following years or not

Ip2Country Mapping

I was working on a web application that required mapping every request to its corresponding country in order to use this data later in site statistics

i searched over the internet for a solution that can do this mapping for me, i found a lot of solutions that are great to the extent that they can also get the ISP and geographical location of the request but MOST OF THEM WERE NOT FREE

Since i was only looking for a simple solution that simply maps ip to corresponding country, i searched for free versions of these solutions which are limited but free

i found this Website that offered a nice & easy solution for this issue. Although, this website has a very nice tutorial but i will explain what i did because i modified the steps provided by the website somehow

Just do as follows

1. Download the CSV file that contain all mapping details

2. Create a new table in your database that should carries all data needed to do
this mapping, you will needs these columns
* begin_num - FLOAT
* end_num - FLOAT
These are two magical numbers that will be used later in
our mapping

* ISO - VARCHAR(2)
* Name - VARCHAR(255)

2. Import CSV file into that table but, remember to choose only 3rd, 4th, 5th, and 6th values while importing - neglect 1st and 2nd one because they are useless in our mapping

3. On every request, apply this formula on the IP as follows

ipnum = 16777216*w + 65536*x + 256*y + z

where

IP Address = w.x.y.z


4. Use ipnum to retrieve corresponding ISO or name of country through this simple query

SELECT ((required-columns)) FROM ((table-name)) WHERE ((ipnum)) BETWEEN begin_num AND end_num


That's it, you can now map any request to the corresponding country with an accuracy reaching 98% as stated by this website

Note:
1. This query may return nothing if the IP can't be mapped and this will happen especially when using localhost
2. Always index begin_num and end_num for better performance
3. Always update your CSV file because it is updated every now and then on the website so keep an eye on the website to get updates