Monday, April 11, 2011

Poke tracking added

Good afternoon everyone!

I spent today adding the ability to track the number of pokes between the user and their target.  Of course, this count is completely localized, so if you use the script on multiple computers, it will keep different numbers on each computer.  Not sure if this value is carried over if you use Mozilla Firefox Sync and not going to test this.  Portability is not going to be a feature for the 4.0 release.  It may be in the future.

A couple of things worth noting about this feature:

There is always a trade-off between information and space.  While there is no limit imposed by Greasemonkey, the amount of data that can be stored within the browser should be minimized.  While developing the schema, I debated how much information should be tracked: last poke datetime, initial poke datetime, name, count.  Realizing that people prefer speed over information, I've decided to only keep the count.  This makes it very efficient.

I'm sure there are those of you that would like to know when your friend last poked you and when you last poked him.  The fact is that the more information you store, the slower your browser as a whole will be.  The information is stored in your RAM.  Firefox has a fairly large footprint as it is.  So if you want more of this information and are willing to sacrifice speed (and possibly a crash), you will have to edit the script.

I will not expand on the pokewar tracking feature beyond the number of pokes.  I believe the cost will not outweigh the benefits.  If you want me to code this specifically for you, you will have to purchase a license (which will not be cheap).

At this time, the number of pokes will only show for current wars.  If you want to see a list of everyone you've poked, you will have to open the about:config panel.  This feature may be added in the future, thus will not be in the 4.0 release.

Thursday, April 7, 2011

Major Milestone Achieved!

Quick stats:
  • 377 lines of code
  • 15 KB
  • About 50 total programming hours spanned over three weeks
I am pleased to announce that the autopoke script has reached an important milestone: it has completed it's first set of pokes!  Until now, the majority of the programming concentrated on how to actually detect pokes without loading the entire page.  Then, work began on detecting pokes across all languages, which meant hacking the code of Facebook.  Finally, the poke functions were re-written from the ground-up.

Here are the technical changes made thus far:
  • Uses XMLHttpRequest instead of GM_XMLHttpRequest: Makes use of the fast Javascript engine instead of passing to Greasemonkey.  This change should make it easier for non-Firefox users to install the script.  But remember that it is not officially supported.
  • Makes asynchronous requests: Fixes a bug that users of slow computers from properly auto-poking.  A copy of the front page is used instead of the DOM itself.  It allows for faster processing and allows users to be poked even before the page finishes loading.
  • New status/error messages: These messages are far more informative and allows the user to see why a poke failed.  Debug variable can still be set to see the "console".
  • Makes use of XML 1.0 standards: Facebook is XML 1.0 compliant. The script makes use of this to retrieve important information to pass to the poke function.  (If you want to see this in action, set debug to 3 or higher.)
 And here are a list of features that will be added over the next couple of weeks:
  • Tracking number of pokes in current war: Obviously, this won't include pokes that have already occurred
  • Check Facebook for pokes automatically
  • Prettify error messages so that they can be copied and pasted into bug reports
  • Comments within the code
And finally, I am working with The Last Well, a 501(c)(3) non-profit organization that building wells in Liberia, to receive donations for it's mission.

Monday, April 4, 2011

Facebook changes their poke engine...again

This seems to happen about 2-3 times a year.  Facebook will change the way that pokes are processed both via the browser and on the backend.  While there is no proof that Facebook is doing this purposefully to disable the autopoke script, it does break the script and produces error 1.1.  This error code means that the autopoke script received a response from Facebook that wasn't expected and could not process the poke any further.

As I've stated before, I do not plan on releasing fixes to autopoke 3.5.  I'm actively developing 4.0 to replace 3.5, which will include an adaptive regular expression to be able to execute the pokes without having a perfect match.  However, this is proving harder than I initially realized.

(Note, another user fixed 3.5 and has released it on userscripts.org.)

There are about eight different places that Facebook can change that could break the script.  I won't run through them all here, but needless to say, it is impossible to predict and anticipate these changes.  For example, prior to this last update, the ID that was assigned to the poke DIV element was named pagelet_netego_pokes.  Facebook has renamed the DIV element to pagelet_pokes.

Facebook uses ajaxify to load a large majority of it's modules (e.g. pokes, birthdays, stories, photos, etc).  This means most of these elements load in the background.  Instead of waiting for these elements to completely load, the 4.0 script now downloads a copy of your homepage to evaluate.  This fixes a HUGE bug where pokes were not being processed because the elements do not completely load.

Even though the script doesn't use the DIV element, it still relies on the ID, which is used within ajaxify to actually load the poke node.  Unfortunately, this is something that cannot be changed due to the mere fact that Facebook can change this div to something completely random.

Facebook has already done this to many of their elements.  If you view the source of the Facebook frontpage, you'll notice many of the linked script names are Df69GCI-zBW.js, 4gR9cTpQYHa.js, etc.  I assume this is done so that the files can only be used once can the source cannot be downloaded conveniently.  Those who know what they are doing (like yours truly) can download these files without much hassle.

The poke link detection is based on the fact that the poke engine (e.g. the actual webpage that processes all pokes) has the word "poke" in it.  Originally, the link detection was based on the link text having the word "poke" in it.  This was changed to allow non-English speakers to use the script.  If Facebook changes things again so that these IDs are randomized, the script will have to fail-back to searching for the work "poke" within the link text, breaking the script for non-English users.

Another change that Facebook has made is how pokes are processed.  This used to be a POST form, which meant encoding the form parameters.  But now, it looks like Facebook is changing this to GET.  (FWIW, this used to be how Facebook did things back in the day.)  Unfortunately, this is something that the script cannot anticipate and must be hard-coded.

As development on 4.0 continues, I will attempt to make the script as adaptive as possible.  But please understand that it is impossible to anticipate everything.  Hopefully, it will be more resilient than it's predecessors.