Tuesday 29 November 2011

Password field shows password as default value in Mozilla in Cakephp

Here a peculiar problem i face while creating a user settings page in Cakephp , At FireFox browser, password field shows a default value as password after page got loaded or even if i click at that element.
$this->Form->password('User.password',array('id'=>'password','class'=>'pass'));
every time page gets loaded it shows ******* in password field , default is password text in password field, so to overcome this problem i used a Trick as follows..

echo $this->Form->input('users_check',array('id'=>'pass_input','label'=>false,'div'=>false));
echo $this->Form->password('users_passnew',array('id'=>'pass_password'));
i create a password element and a input element now, as there is an plain input field it will not show any default Asterisk. and when user click on to that input control the following Jquery will run and will hide the input field and show the actual password field.
<script>
$(document).ready(function(){

$('#pass_password').hide(); //hide the password element when page is ready
       $('#pass_input').focus(function(){ 
      $('#pass_input').hide(); //hide the input field
     $('#pass_password').show(); //show the password field
     $('#pass_password').focus();
      });
});

</script>

Thursday 24 November 2011

Send Mail in CakePHP

Following are the steps to send Email in CakePHP. we are using Email component of cake
The first thing you need to do is include the "EmailComponent".

class CommentsController extends AppController  
{  
    var $components = array('Email');  

Now, to send an email, you need two things: email templates (for content) and layouts. Basically, email layout has the same purpose as regular layout - to wrap your content. And templates are where your content will go. This example assumes you're sending an email in both HTML and plain text format.

Location of your layouts and templates are as follows:
/app/views/layouts/email/html/default.ctp
/app/views/layouts/email/text/default.ctp
/app/views/elements/email/html/my_template.ctp
/app/views/elements/email/text/my_template.ctp

..Layout
// /app/views/layouts/email/html/default.ctp
<div> 
<?php echo $content_for_layout; ?>  
<br />  
Thanks & regards
admin
</div>


..Template file
// /app/views/elements/email/html/my_template.ctp  

<p>Dear <?php echo $email_user; ?>,  
<br /><br />  
i will be there, this is my message.  
</p> 
Now, all that remains is to glue all that up with your controller, setting up EmailComponent properties and variables. Setting variables for email templates works the same as setting variables for your view.

$this->Email->reset();  
$this->Email->sendAs = 'both'; // both = html + plain text  
$this->Email->to = 'sam@yahoo.com';  
$this->Email->from = 'admin@example.com';  
$this->Email->replyTo = 'admin@example.com';  
$this->Email->subject = 'your amazing subject here';  
$this->Email->template = 'my_template';  
// of course, if you have multiple layouts, you can change that too  
//$this->Email->layout = 'my_second_layout';  
// this would require you to have my_second_layout  
// ~/app/views/layouts/email/html/my_second_layout.ctp  
// ~/app/views/layouts/email/text/my_second_layout.ctp  
// set some variables for your templates  
$this->set('email_user', $user);   
// uncomment this to debug EmailComponent instead of sending  
//$this->Email->_debug = true;  
$this->Email->send();  




Wednesday 16 November 2011

FaceBook f-connect in cakephp


<span class="facebook">
<a href="<?php echo $this->webroot.'users/facebook_login?first=1';?>">Facebook</a> 
<a href="<?php echo $this->webroot.'users/facebook_login?first=1';?>">
        <img src="<?php echo $this->webroot;?>img/fconnect.png" /></a>
</span>
now code at User controller

/* This function is used to handel fconnect code..when ever a user clicks on fconnect icon at example.com site
the link will redirct it to this function.. where 3 steps will performed
1) if url parameter had 'first' option then redirect to facebook for Authorization code with client_id passed in params
2) It will allow user to enter FaceBook username password and Allow button to click, if cliked it will send Auth Code back,
   redirect url which we collect in 'code' section..then again redirect to FB with Authcode,client_id,secret_key to get
Token_key.
3) on sucessfully getting Token Key again send a request to FB with TokenKey at (c)....
which will return the name,email and other info of that logged in user.
*/
//http://example.com/users/facebook_login
function facebook_login(){
$appId='191645377665635';
$app_secret='b13d9660bcaa0005624f18df4139820';
              //** above API you get after registering the example.com at Facebook to get API key
$cookie=true;
$query="";
if(isset($_SERVER['REQUEST_URI'])){
$str=$_SERVER['REQUEST_URI']; //** get browser URL
$output=parse_url($str);
if(isset($output['query']))
$query=$output['query']; //parameters at url
if(isset($output['first']))
$query=$output['first'];
if(!empty($query)){
$temp=explode("=",$query);
if($temp[0]=="first"){
//*** First Step ************* (a)
$url="http://example.com/users/facebook_login"; 
                                 //callback function should be same in any case,else will show Error in verifcation
$dialog_url="https://www.facebook.com/dialog/oauth?client_id=".$appId."&redirect_uri=".urlencode($url).
"&scope=email,read_stream,offline_access";
echo("<script> top.location.href='".$dialog_url."'</script>");
}
if($temp[0]=="code"){
//** Second Step ************ (b)
$code=$temp[1];
$url="http://example.com/users/facebook_login"; 
                                //callback function should be same in any case,else will show Error in verifcation
$token_url = "https://graph.facebook.com/oauth/access_token?client_id=".$appId.
"&client_secret=".$app_secret."&code=".$code."&redirect_uri=".urlencode($url);
$response = file_get_contents($token_url);
$params = null;
parse_str($response, $params);
$access_token=$params['access_token'];
if(isset($access_token)){
//*** Third Step  ********* (c)
$graph_url = "https://graph.facebook.com/me?access_token=".$access_token;
$user = json_decode(file_get_contents($graph_url));
//print_r($user);
$uname=$user->name; 
$email=$user->email; // ** dipankar@gmail.com - myfacebook mail-id
$gender=$user->gender;
//as we get $uname here now we can write DB quries and other code below.....
}

}
}
}
exit();
}

Friday 11 November 2011

Multi column index in MySQL

Multi column index is a useful feature to optimize searches. MySQL allows to create an index either on single column or on multi columns of the table however single column index and multi column(combination of columns) index behavior differs. To understand the behavior of single column index and multi column index, we will walk through the following examples. I assume after this we will be able to decide when to use multi column index. To continue, let's create a table named "buyers" to take it as an example.

CREATE TABLE buyers(
 buyer_id INT NOT NULL AUTO_INCREMENT,
 first_name CHAR(19) NOT NULL,
 last_name CHAR(19) NOT NULL,
 zip CHAR(5) NOT NULL,
 state_code CHAR(2) NOT NULL,
 PRIMARY KEY (buyer_id)
 );

Suppose, there are four Tariqs (three Iqbals, one Mehmood), three from 92082 zip, and one from another zip 99088 (Tariq Mehmood).
Now our requirement is to get the buyer_id for buyers with a specific first_name, last_name, and zip. For example, we want to find the buyer_id for Tariq Iqbal, zip 92082 so we write the following query to the desired record.

SELECT buyer_id FROM buyers WHERE first_name='Tariq'  AND last_name='Iqbal' AND zip=92082;

As per our above query and structure of examplory defined table "buyers", MySQL will scan all the table three times to find the requested record. Of course this may take considerable time to find out wanted record particularly when the table has records in millions in it.
Since we want to ask MySQL to avoid a full table scan, therefore we would like to take advantage of indexes to get them in use. First option is to create an index on each column (so called "single column index") viz first_name, last_name, or zip. Let's we put the index on each column like below so that MySQL should skip to scan all table three times.

ALTER TABLE buyers ADD INDEX idx_firstname (first_name);
ALTER TABLE buyers ADD INDEX idx_last_name (last_name);
ALTER TABLE buyers ADD INDEX idx_zip (zip);

In this case at the first instance MySQL will use the idx_firstname index to limit the records to those where first_name=’Tariq’. At the next step, using this "temporary result set" MySQL will apply other indexes conditions individually i.e. last_name='Iqbal' and zip=92082. First it eliminates those whose last_name is not Iqbal. And then it eliminates those who are not from zip 92082. MySQL has now applied all conditions and can return the results after more than one sorting.
Of course, the above is more efficient than forcing MySQL to do a full table scan, but we are still forcing MySQL to scan significantly more rows than it needs to.
Now here's where the multi column index comes into use. If we add a single index on the three columns, we can get the correct set in a single pass! However, here is the code we use to add multi column index (index on combination of columns.

ALTER TABLE buyers ADD INDEX idx_flname_zip(first_name,last_name,zip);

Since the MySQL keeps the index files in an organized versions, MySQL can jump directly to the correct first_name, then move to the correct last_name, and finally go directly to the correct zip. Therefore, MySQL has found the correct rows without having to scan a single row of the data file!
Thus creating three single-column indexes on (first_name), (last_name), and (zip) is completely different from one "multi column index" on (first_name, last_name, zip). While running a query, MySQL can only use one index. So, if we have three single column indexes instead of multi column index(first_name, last_name, zip), MySQL will attempt to pick the most restrictive one, but the most restrictive single column index will be significantly less restrictive than our multi column index.
Point to note about Multi Column Index.
With the multi column index (first_name, last_name, zip) then queries can only use the index if you have a WHERE clause that partially matches the index from left to right. Check below.
1. [SELECT * FROM buyers WHERE first_name=? AND last_name=? AND zip=?] will use the index. 
2. [SELECT * FROM buyers WHERE last_name=? AND first_name=? AND zip=?] can't use the index.