Careful when casting large number to integer in php
You probably used to do this $val = (int)$val;
in php as a way to be sure that $val is an integer.
Some people do this for added security, since integers cannot contain any type of
script or html tags, so it's an easy way to sort-of sanitize the string.
But.. but... but ..... but....
Php like a child that can only count to 10, can only count to 2147483647
That's right, I did not expect this either.
Any number larger than 2147483647 php just does not know!
This means when you try to case any number larger than 2147483647 to integer using (int)$val, php will just return 2147483647
This is terribly wrong, certainly should be considered a bug!
If php does not know any integers larger than 2147483647, then it should raise error when you try to convert a larger number, not return the largest number it knows!
This can cause some weird problems in your code.
In my case I discovered this bug when working with Twitter API
The Twitter has billions of status messages, so all the latest status_ids are larger than 2147483647, so I was doing what I thought was a good practice and casting these status ids to integer with (int), but php was quietly replacing all the actual values with the 2147483647
By the way, it was php version 5.2.9, which is fairly new version. I mean, I would not be surprised to see this bug in php prior to 5, but in 5.2.9?!
That's crazy.
Wednesday, March 10, 2010
Monday, March 8, 2010
Some near-term todos for qod site
Some feature to add to qod soon:
use javascript api to see if logged in user is following question owner and if not, then add "Follow " button which will point to user server and we can follow the user of behalf of the logged in user.
Add 'Other questions by this member'
Add 'Invite friends to join' but not sure how this will work - show a list of friends or just tweet about the link?
use javascript api to see if logged in user is following question owner and if not, then add "Follow " button which will point to user server and we can follow the user of behalf of the logged in user.
Add 'Other questions by this member'
Add 'Invite friends to join' but not sure how this will work - show a list of friends or just tweet about the link?
Sunday, March 7, 2010
Normalizing utf-8 string for Twitter API
In order to send Unicode (utf-8 to be exact) text to Twitter via Twitter app, you must first run the string through the php Normalizer class
This class comes with php 5.3 but before the 5.3 you need to build the lib yourself and then install extension from pecl
Then, once you have the Normalizer class, just do this:
Normalize::normalize($string,Normalizer::FORM_C)
This is not always necessary as most utf-8 strings and chars are already "just fine", it's just that some fairly rare chars can be considered 'not normalized'.
This means that Twitter will still accept them, they will even be rendered by the end user browser in most cases, it's just that Twitter may count such chars as 2 chars instead of just one, and you know in Twitter every char counts.
Basically you really want to make sure that utf-8 strings are normalized before you send then to Twitter from your API because otherwise you may run into situation that your message unexpectedely exceeds 140 chars and will be rejected by Twitter API.
Normalize::normalize($string,Normalizer::FORM_C)
And here is the info from php
http://www.php.net/manual/en/book.intl.php
http://php.net/manual/en/class.normalizer.php
This class comes with php 5.3 but before the 5.3 you need to build the lib yourself and then install extension from pecl
Then, once you have the Normalizer class, just do this:
Normalize::normalize($string,Normalizer::FORM_C)
This is not always necessary as most utf-8 strings and chars are already "just fine", it's just that some fairly rare chars can be considered 'not normalized'.
This means that Twitter will still accept them, they will even be rendered by the end user browser in most cases, it's just that Twitter may count such chars as 2 chars instead of just one, and you know in Twitter every char counts.
Basically you really want to make sure that utf-8 strings are normalized before you send then to Twitter from your API because otherwise you may run into situation that your message unexpectedely exceeds 140 chars and will be rejected by Twitter API.
Normalize::normalize($string,Normalizer::FORM_C)
And here is the info from php
http://www.php.net/manual/en/book.intl.php
http://php.net/manual/en/class.normalizer.php
Saturday, February 20, 2010
changing value of meta tag with javascript
Interesting:
if you assign value of meta tag element in javascript
using the
eMeta.setAttribute('content', somenewvalue);
it will not be found if looking for for it this way:
eMeta.content but the attribute value of 'content' will actually
be set and could be seen in Firebug right away.
But it will work if just setting value by assignment, like this
eMeta.content = 'somenewval';
This is in Firefox, not sure how it will work in other browsers
if you assign value of meta tag element in javascript
using the
eMeta.setAttribute('content', somenewvalue);
it will not be found if looking for for it this way:
eMeta.content but the attribute value of 'content' will actually
be set and could be seen in Firebug right away.
But it will work if just setting value by assignment, like this
eMeta.content = 'somenewval';
This is in Firefox, not sure how it will work in other browsers
Tuesday, February 16, 2010
oAuth Signin with Twitter via popup window design pattern
It looks like couple of well made sites use the same pattern for logging in with twitter via the popup window:
The DISCUSS widgets have this pattern:
Dsq.Twitter = new function() {
var that = this;
this.startTwitterConnect = function() {
var popupParams = 'location=0,status=0,width=800,height=400';
that._twitterWindow = window.open(Dsq.jsonData.settings.disqus_url + '/_ax/twitter/begin/', 'twitterWindow', popupParams);
that._twitterInterval = window.setInterval(that.completeTwitterConnect, 1000);
};
this.completeTwitterConnect = function() {
if (that._twitterWindow.closed) {
window.clearInterval(that._twitterInterval);
window.location.reload();
}
};
};
and the twitgoo.com also have very similar pattern:
TG.util.oauth = {
win: null,
timer: null,
loginUpdate: function() {
$.getJSON('/-login/check?format=json', TG.util.oauth.loginCallback);
},
loginCallback: function(data) {
if (data && data.loggedin) {
TG.util.login.update(data);
}
},
winCheck: function() {
if (!TG.util.oauth.win || TG.util.oauth.win.closed) {
window.clearInterval(TG.util.oauth.timer);
return TG.util.oauth.loginUpdate();
}
},
loginClick: function() {
TG.util.oauth.win = window.open('/-oauth-twitter/request?gotoafter=1&gotor=oauthtwitter&gotop=action%3Dwindowend',
'OAuthTwitterRequest',
'width=800,height=450,modal=yes,alwaysRaised=yes');
if (!TG.util.oauth.win) return true;
TG.util.oauth.timer = window.setInterval(TG.util.oauth.winCheck, 300);
return false;
}
};
This means that the callback url - the one that Twitter redirects to after the oAuth dance is complete contains ONLY the window.close() javascript and basically does nothing else at the browser. It's main job is do populate the oViewer object on the server so that when the main window is reloaded it will determine that user is now logged in. OK, one more thing that callback window can do is to set some sort of cookie.
I can see a legitimate reason to do this because what if user closes the browser popup window manually? Then we will never get to the part where the JS in the popup window calls the window.opener
So there is a very small chance that user will be successfully logged in but because he closed what window manually, the main window will never know.
I guess I'll go with that pattern now, after all, I've seen in on 2 well built sites and also the same pattern is recommended on Google OpenSocial developers page.
This is actually very easy to code because you don't need anything special as far as in php of the callback url, only static HTML and OK, possibly setting of cookie, but I'm not even sure that it's even necessary to set this cookie.
The DISCUSS widgets have this pattern:
Dsq.Twitter = new function() {
var that = this;
this.startTwitterConnect = function() {
var popupParams = 'location=0,status=0,width=800,height=400';
that._twitterWindow = window.open(Dsq.jsonData.settings.disqus_url + '/_ax/twitter/begin/', 'twitterWindow', popupParams);
that._twitterInterval = window.setInterval(that.completeTwitterConnect, 1000);
};
this.completeTwitterConnect = function() {
if (that._twitterWindow.closed) {
window.clearInterval(that._twitterInterval);
window.location.reload();
}
};
};
and the twitgoo.com also have very similar pattern:
TG.util.oauth = {
win: null,
timer: null,
loginUpdate: function() {
$.getJSON('/-login/check?format=json', TG.util.oauth.loginCallback);
},
loginCallback: function(data) {
if (data && data.loggedin) {
TG.util.login.update(data);
}
},
winCheck: function() {
if (!TG.util.oauth.win || TG.util.oauth.win.closed) {
window.clearInterval(TG.util.oauth.timer);
return TG.util.oauth.loginUpdate();
}
},
loginClick: function() {
TG.util.oauth.win = window.open('/-oauth-twitter/request?gotoafter=1&gotor=oauthtwitter&gotop=action%3Dwindowend',
'OAuthTwitterRequest',
'width=800,height=450,modal=yes,alwaysRaised=yes');
if (!TG.util.oauth.win) return true;
TG.util.oauth.timer = window.setInterval(TG.util.oauth.winCheck, 300);
return false;
}
};
This means that the callback url - the one that Twitter redirects to after the oAuth dance is complete contains ONLY the window.close() javascript and basically does nothing else at the browser. It's main job is do populate the oViewer object on the server so that when the main window is reloaded it will determine that user is now logged in. OK, one more thing that callback window can do is to set some sort of cookie.
I can see a legitimate reason to do this because what if user closes the browser popup window manually? Then we will never get to the part where the JS in the popup window calls the window.opener
So there is a very small chance that user will be successfully logged in but because he closed what window manually, the main window will never know.
I guess I'll go with that pattern now, after all, I've seen in on 2 well built sites and also the same pattern is recommended on Google OpenSocial developers page.
This is actually very easy to code because you don't need anything special as far as in php of the callback url, only static HTML and OK, possibly setting of cookie, but I'm not even sure that it's even necessary to set this cookie.
Monday, February 15, 2010
CakePHP pages shows ads for wedding cakes
Google shows ads for wedding cakes, birthday cakes,
even geo-targeted bakeries based on my IP address when I view the page about CakePHP
Another proof that Google is not very smart when it comes to parsing words that have more than one meaning.
Tuesday, February 9, 2010
Firefox consumes too much memory
Firefox is a memory-hungry cunt. I have to restart it every couple hours otherwise it keeps consuming up to 800Megs of RAM
Subscribe to:
Posts (Atom)