About/Contact

Steve Trefethen

Steve Trefethen is CTO at Wanderful Media.
Contact me

View my LinkedIn profile



Calendar

<<  June 2013  >>
MoTuWeThFrSaSu
272829303112
3456789
10111213141516
17181920212223
24252627282930
1234567

View posts in large calendar

Disclaimer

The posts on this weblog are provided AS IS with no warranties, and confer no rights. The opinions expressed herein are my own personal opinions and do not represent my employer's view in any way.



A SQLObject case insensitive LIKE query

April 06 2011 8:12PM

SQLObject is:

…a popular Object Relational Manager for providing an object interface to your database, with tables as classes, rows as instances, and columns as attributes.

SQLObject includes a Python-object-based query language that makes SQL more abstract, and provides substantial database independence for applications.

 

I’ve been reading through the SQLObject documentation and it’s not always clear when it comes to executing a LIKE query and a bit of Googling turned up a number of related questions therefore I thought I’d contribute this tiny bit of knowledge to the Intertubes. In my case I want to perform a case insensitive LIKE query and here’s one means of performing this sort of query via SQLObject:

MyTable.select(sqlobject.LIKE(func.lower(MyTable.q.url), func.lower('http://www.stevetrefethen.com/%')))

That equates to this SQL:

SELECT MyTable.field1 FROM MyTable WHERE (lower(MyTable.url) LIKE (lower('http://www.stevetrefethen.com/blog/%')))

In the above example “func.lower” is SQLObject’s syntax for indicating the SQL server’s lowercase function should be used.

FacebookDel.icio.usDigg It!

Ubuntu in VirtualBox on OSX

March 29 2011 9:21PM

UbuntuI’ve been wanting a VM to mirror a production front end machine I’ve been working so I can more closely replicate the production setup as well as test configuration options and different software versions. I’ve installed Ubuntu 10.10 on VirtualBox (v4.04 r70112) and wanted to mention a few items for those who might run into similar issues.

Package Updates

The first item is updating ~300 packages immediately after the install which included numerous security updates etc. Trying to perform the update from the Update Manager window resulted in the error “Important security updates requires installation of untrusted packages” and wouldn’t proceed. Turns out the answer is to use System | Applications | Synaptic Package Manager and not the Update Manager which is what appeared by default.

 Synaptic Package Manager

Screen Resolution

After installing the default screen resolution on the VM was 800x600 which is just too small considering I have 1920x1200 pixels to work with. For this issue, Google yielded this fix which is to install build-essentials using the Synaptic Package Manager mentioned previously and restart the machine. Next, install the VM Guest Additions:

VM Additions

Then in the VM select Places | Home Folder, click on VBoxLinuxAdditions.run and click Open Autorun Prompt.

  Ubuntu Home Folder

At that point, the monitor was recognized correctly and screen resolution changes were enabled.

Ubuntu Monitor Preferences

Winning!

FacebookDel.icio.usDigg It!

Getting the Tornado Facebook demo working

March 26 2011 10:16PM

Recently, I downloaded Tornado:

Tornado is an open source version of the scalable, non-blocking web server and tools that power FriendFeed.

Included is a facebook demo that displays your feed though it didn’t work “out-of-the-box” raising the error:

File "modules/post.html", line 26, in _execute
KeyError: 'message'

modules/post.html is a snippet of html used to render each feed item. The snippet looks like this:

<div class="post">
  <div class="picture">
    {% set author_url="http://www.facebook.com/profile.php?id=" + escape(post["from"]["id"]) %}
    <a href="{{ author_url }}"><img src="//graph.facebook.com/{{ escape(post["from"]["id"]) }}/picture?type=square"/></a>
  </div>
  <div class="body">
    <a href="{{ author_url }}" class="actor">{{ escape(post["from"]["name"]) }}</a>
    {% if post["message"] %}
      <span class="message">{{ escape(post["message"]) }}</span>
    {% end %}
    <div class="meta">
      <a href="{{ escape(post["actions"][0]["link"]) }}" class="permalink">{{ locale.format_date(datetime.datetime.strptime(post["created_time"], "%Y-%m-%dT%H:%M:%S+0000")) }}</a>
    </div>
  </div>
</div>

The curly braces are python code snippets and the line reading if post[“message”] is causing the problem. In python referencing a non-existent dictionary key raises a KeyError exception thus changing the code to use:

{% if “message” in post %}

To debug this problem I simply removed the code referencing post[“message”] and replaced it with str(post) which simply dumped the JSON contents onto the page. From there I could see that not all entries had a message key thus the error.

One more note. Looking at the documentation Tornado uses a library call epoll which at first glance sounds familiar to I/O completion ports on Windows which is something I'm familiar with.

FacebookDel.icio.usDigg It!

My New Project DIY Bosch Dishwasher Repair Model SHX46A05UC

March 09 2011 4:41PM

We've recently had a problem with our Bosch dishwasher so this is looking for some advice for a DIY repair.

When we starting our dishwasher the other day there was an electrical smoke smell that seemed to be coming from the top right hand corner of the door on where the control panel buttons are located. The power button light no longer turns on and the machine is dead at this point.

Google led me to the need to check the wire nut for the power cord and make sure there wasn't some sort of short (haven't done this yet). My next thought is perhaps the control board for the machine which I understand is located in the door near the control panel buttons. Searching on the Bosch website I can see there is a recall for a different model (mine's not covered) for a problem that sounds exactly like what I've experience that related to a faulty control board thus my guess as what the issue is.

I checked locally and the repair is $216 + $109 for the control board if that's the problem so I want to do a bit of digging myself as that's an amount I don't want to part with right now.

The model is SHX46A05UC /30 and the serial number starts FD8604.

Do you have any advice?

[Update: March 13, 2011] After a bit of Googling I found the cause of the problem. When we purchased this dishwasher, much to my surprise it didn't come with a power cord. The manual specified the proper gauge and after a trip to the hardware store it was up and running. However, the cause of the failure was a wire nut:

burned out wire nut

On another note, one of the places my searching found was appliantology.org where it looked like they had a pretty helpful forum. I created an account, agreeing to the forum Terms & Rules:

Although we offer free repair help, this site is not free to operate! We are supported by your parts purchases. If we help you figure out what's wrong with your appliance, then help make sure that we're still gonna be here the next time you need us by purchasing your appliance parts through the parts links that we post. A small percentage of your purchase goes to supporting this website without costing you one penny more for the parts you order.

…and posted a near copy of what I wrote above. Someone from the site replied directing me to a link to purchase a control board for $180.10. Well prior to my web searching my wife had priced the board at a local place and found the cost as quoted above which is why we were looking online. At that point, not wanting to look like some sort of troll I carefully posted a replied asking for verification that the part was $72.10 more than what we’d been quoted and got a rude reply telling me they were saving me from spending over $300 by DIY’ing it implying that I just didn’t get it! After posting a brief follow-up comment the next day my account and the thread had been deleted. So much for “…help you figure out what’s wrong with your appliance” and instead just pushing to sell expensive parts. Interestingly while all this was going on and still thinking the issue was perhaps the control board I’d made a request to applicancepartspro.com who came back with $73.91 for the same part, over $100 cheaper.

After a new wire nut and resetting the dishwasher total cost of repair: $0.17. Though I’m considering a different gauge cord altogether.

FacebookDel.icio.usDigg It!

Chrysler's Super Bowl ad did it resonate with you?

February 07 2011 11:39PM

A friend on Facebook posed the question “I'm curious, what was the impression of this ad for people outside MI?”.

I thought it might be interesting to expand the discussion here.

Here's my West Coast :) angle. I’d guess it resonates much better there than here. For me it's very difficult to sell a surviving-the-hard-knocks storyline after the not-so-distant massive bailouts for a company that simply lost all sense of innovation let alone fiscal responsibility.

The ad has me admiring Ford's decision to pass on the Super Bowl even more. Yet for Chrysler quite the opposite, they’ve seemingly learned nothing. This two minute production costs $12 million in Super Bowl ad fees alone forgetting the $9 million production costs. That’s 262, $80K/year UAW jobs for a year. They just don't get it.

This line is revealing “Now it’s probably not the one you’ve been reading in papers.” clearly referring to the last few years of bad bailout press as though it’s all been a conspiracy! Amazing.

It’s hard to believe Chrysler feels ratcheting up the attitude to a fevered pitch is the best tact to sell this product. Admittedly, I’m not familiar with this model car but how about a bite of humble pie? Better yet, how about explaining why people should buy this car over an import beyond heaps of attitude.

Can you tell this touched a cord?  

What did you make of this ad?

[UPDATE] A few links/quotes:

Chrysler, which is 10 percent owned by the U.S. government because of a $12.5 billion bailout in 2009, had the lowest fleet gas mileage of any major automaker in 2009 at 19.2 mpg. -link

From Chrysler's home page flash rotator:

Chrysler Group LLC to Invest $179 Million in Jobs for Michigan, Fuel Efficient Engines for North America

That's dated December '09, after the bailout they commit to fuel efficient engines. -link
FacebookDel.icio.usDigg It!

Tags: Soapbox

Installing Google’s python client API and running samples on 2.4.6

January 22 2011 4:09PM

At work I’m using Python 2.4.6 and wanted to play around with some of the Google API’s like Buzz and Moderator. Things didn’t quite work out-of-the-box so I thought I’d document my steps here for future reference and in the event anyone else might find it useful.

First, I read over the Python Google API page and found that in order to grab the code I’d first need to install Mercurial.

SteveT:cc strefethen$ sudo port install mercurial
--->  Computing dependencies for mercurial
--->  Dependencies to be installed: curl-ca-bundle python26 db46 gdbm sqlite3
--->  Fetching curl-ca-bundle
--->  Attempting to fetch curl-7.21.2.tar.bz2 from http://distfiles.macports.org/curl
--->  Attempting to fetch certdata-1.70.txt from http://distfiles.macports.org/curl
--->  Verifying checksum(s) for curl-ca-bundle
--->  Extracting curl-ca-bundle
--->  Applying patches to curl-ca-bundle
--->  Configuring curl-ca-bundle
--->  Building curl-ca-bundle
--->  Staging curl-ca-bundle into destroot
--->  Installing curl-ca-bundle @7.21.2_4
--->  Activating curl-ca-bundle @7.21.2_4
--->  Cleaning curl-ca-bundle
--->  Fetching db46
--->  Attempting to fetch patch.4.6.21.1 from http://distfiles.macports.org/db4/4.6.21_6
--->  Attempting to fetch patch.4.6.21.2 from http://distfiles.macports.org/db4/4.6.21_6
--->  Attempting to fetch patch.4.6.21.3 from http://distfiles.macports.org/db4/4.6.21_6
--->  Attempting to fetch patch.4.6.21.4 from http://distfiles.macports.org/db4/4.6.21_6
--->  Attempting to fetch db-4.6.21.tar.gz from http://distfiles.macports.org/db4/4.6.21_6
--->  Verifying checksum(s) for db46
--->  Extracting db46
--->  Applying patches to db46
--->  Configuring db46
--->  Building db46
--->  Staging db46 into destroot
--->  Installing db46 @4.6.21_6
--->  Activating db46 @4.6.21_6
--->  Cleaning db46
--->  Fetching gdbm
--->  Attempting to fetch gdbm-1.8.3.tar.gz from http://mirrors.kernel.org/gnu/gdbm
--->  Verifying checksum(s) for gdbm
--->  Extracting gdbm
--->  Configuring gdbm
--->  Building gdbm
--->  Staging gdbm into destroot
--->  Installing gdbm @1.8.3_3
--->  Activating gdbm @1.8.3_3
--->  Cleaning gdbm
--->  Fetching sqlite3
--->  Attempting to fetch sqlite-autoconf-3070400.tar.gz from http://distfiles.macports.org/sqlite3
--->  Attempting to fetch sqlite-autoconf-3070400.tar.gz from http://www.sqlite.org/
--->  Verifying checksum(s) for sqlite3
--->  Extracting sqlite3
--->  Applying patches to sqlite3
--->  Configuring sqlite3
--->  Building sqlite3
--->  Staging sqlite3 into destroot
--->  Installing sqlite3 @3.7.4_0
--->  Activating sqlite3 @3.7.4_0
--->  Cleaning sqlite3
--->  Fetching python26
--->  Attempting to fetch Python-2.6.6.tar.bz2 from http://distfiles.macports.org/python26
--->  Verifying checksum(s) for python26
--->  Extracting python26
--->  Applying patches to python26
--->  Configuring python26
--->  Building python26
--->  Staging python26 into destroot
--->  Installing python26 @2.6.6_1
--->  Activating python26 @2.6.6_1

To fully complete your installation and make python 2.6 the default,  please run:
 	sudo port install python_select
 	sudo python_select python26

--->  Cleaning python26
--->  Fetching mercurial
--->  Attempting to fetch mercurial-1.7.3.tar.gz from http://distfiles.macports.org/python
--->  Attempting to fetch mercurial-1.7.3.tar.gz from http://mercurial.selenic.com/release/
--->  Verifying checksum(s) for mercurial
--->  Extracting mercurial
--->  Configuring mercurial
--->  Building mercurial
--->  Staging mercurial into destroot
--->  Installing mercurial @1.7.3_0
--->  Activating mercurial @1.7.3_0
--->  Cleaning mercurial

As you can see after a fairly lengthy install I was ready to grab the API sources:

SteveT:work strefethen$ hg clone https://google-api-python-client.googlecode.com/hg/ google-api-python-client
requesting all changes
adding changesets
adding manifests
adding file changes
added 153 changesets with 468 changes to 204 files
updating to branch default
172 files updated, 0 files merged, 0 files removed, 0 files unresolved

Next, was to setup the Google API python client

SteveT:work strefethen$ cd google-api-python-client/
SteveT:google-api-python-client strefethen$ sudo python setup.py install
Password:
Installing the following packages: 
'apiclient', 'apiclient.ext', 'uritemplate'
Loaded setuptools
running install
Checking .pth file support in /Users/strefethen/Library/Python2.4/site-packages/
/opt/local/bin/python -E -c pass
TEST PASSED: /Users/strefethen/Library/Python2.4/site-packages/ appears to support .pth files
running bdist_egg
running egg_info
creating google_api_python_client.egg-info
writing google_api_python_client.egg-info/PKG-INFO
writing top-level names to google_api_python_client.egg-info/top_level.txt
writing dependency_links to google_api_python_client.egg-info/dependency_links.txt
writing manifest file 'google_api_python_client.egg-info/SOURCES.txt'
reading manifest file 'google_api_python_client.egg-info/SOURCES.txt'
writing manifest file 'google_api_python_client.egg-info/SOURCES.txt'
installing library code to build/bdist.macosx-10.6-i386/egg
running install_lib
running build_py
creating build
creating build/lib
creating build/lib/apiclient
copying apiclient/__init__.py -> build/lib/apiclient
copying apiclient/anyjson.py -> build/lib/apiclient
copying apiclient/discovery.py -> build/lib/apiclient
copying apiclient/errors.py -> build/lib/apiclient
copying apiclient/http.py -> build/lib/apiclient
copying apiclient/model.py -> build/lib/apiclient
copying apiclient/oauth.py -> build/lib/apiclient
creating build/lib/apiclient/ext
copying apiclient/ext/__init__.py -> build/lib/apiclient/ext
copying apiclient/ext/appengine.py -> build/lib/apiclient/ext
copying apiclient/ext/authtools.py -> build/lib/apiclient/ext
copying apiclient/ext/django_orm.py -> build/lib/apiclient/ext
creating build/lib/uritemplate
copying uritemplate/__init__.py -> build/lib/uritemplate
creating build/lib/apiclient/contrib
creating build/lib/apiclient/contrib/buzz
copying apiclient/contrib/buzz/future.json -> build/lib/apiclient/contrib/buzz
creating build/lib/apiclient/contrib/latitude
copying apiclient/contrib/latitude/future.json -> build/lib/apiclient/contrib/latitude
creating build/lib/apiclient/contrib/moderator
copying apiclient/contrib/moderator/future.json -> build/lib/apiclient/contrib/moderator
creating build/bdist.macosx-10.6-i386
creating build/bdist.macosx-10.6-i386/egg
creating build/bdist.macosx-10.6-i386/egg/apiclient
copying build/lib/apiclient/__init__.py -> build/bdist.macosx-10.6-i386/egg/apiclient
copying build/lib/apiclient/anyjson.py -> build/bdist.macosx-10.6-i386/egg/apiclient
creating build/bdist.macosx-10.6-i386/egg/apiclient/contrib
creating build/bdist.macosx-10.6-i386/egg/apiclient/contrib/buzz
copying build/lib/apiclient/contrib/buzz/future.json -> build/bdist.macosx-10.6-i386/egg/apiclient/contrib/buzz
creating build/bdist.macosx-10.6-i386/egg/apiclient/contrib/latitude
copying build/lib/apiclient/contrib/latitude/future.json -> build/bdist.macosx-10.6-i386/egg/apiclient/contrib/latitude
creating build/bdist.macosx-10.6-i386/egg/apiclient/contrib/moderator
copying build/lib/apiclient/contrib/moderator/future.json -> build/bdist.macosx-10.6-i386/egg/apiclient/contrib/moderator
copying build/lib/apiclient/discovery.py -> build/bdist.macosx-10.6-i386/egg/apiclient
copying build/lib/apiclient/errors.py -> build/bdist.macosx-10.6-i386/egg/apiclient
creating build/bdist.macosx-10.6-i386/egg/apiclient/ext
copying build/lib/apiclient/ext/__init__.py -> build/bdist.macosx-10.6-i386/egg/apiclient/ext
copying build/lib/apiclient/ext/appengine.py -> build/bdist.macosx-10.6-i386/egg/apiclient/ext
copying build/lib/apiclient/ext/authtools.py -> build/bdist.macosx-10.6-i386/egg/apiclient/ext
copying build/lib/apiclient/ext/django_orm.py -> build/bdist.macosx-10.6-i386/egg/apiclient/ext
copying build/lib/apiclient/http.py -> build/bdist.macosx-10.6-i386/egg/apiclient
copying build/lib/apiclient/model.py -> build/bdist.macosx-10.6-i386/egg/apiclient
copying build/lib/apiclient/oauth.py -> build/bdist.macosx-10.6-i386/egg/apiclient
creating build/bdist.macosx-10.6-i386/egg/uritemplate
copying build/lib/uritemplate/__init__.py -> build/bdist.macosx-10.6-i386/egg/uritemplate
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/__init__.py to __init__.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/anyjson.py to anyjson.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/discovery.py to discovery.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/errors.py to errors.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/ext/__init__.py to __init__.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/ext/appengine.py to appengine.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/ext/authtools.py to authtools.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/ext/django_orm.py to django_orm.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/http.py to http.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/model.py to model.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/apiclient/oauth.py to oauth.pyc
byte-compiling build/bdist.macosx-10.6-i386/egg/uritemplate/__init__.py to __init__.pyc
creating build/bdist.macosx-10.6-i386/egg/EGG-INFO
copying google_api_python_client.egg-info/PKG-INFO -> build/bdist.macosx-10.6-i386/egg/EGG-INFO
copying google_api_python_client.egg-info/SOURCES.txt -> build/bdist.macosx-10.6-i386/egg/EGG-INFO
copying google_api_python_client.egg-info/dependency_links.txt -> build/bdist.macosx-10.6-i386/egg/EGG-INFO
copying google_api_python_client.egg-info/top_level.txt -> build/bdist.macosx-10.6-i386/egg/EGG-INFO
zip_safe flag not set; analyzing archive contents...
apiclient.discovery: module references __file__
creating dist
creating 'dist/google_api_python_client-0.1-py2.4.egg' and adding 'build/bdist.macosx-10.6-i386/egg' to it
removing 'build/bdist.macosx-10.6-i386/egg' (and everything under it)
Processing google_api_python_client-0.1-py2.4.egg
creating /Users/strefethen/Library/Python2.4/site-packages/google_api_python_client-0.1-py2.4.egg
Extracting google_api_python_client-0.1-py2.4.egg to /Users/strefethen/Library/Python2.4/site-packages
Adding google-api-python-client 0.1 to easy-install.pth file

Installed /Users/strefethen/Library/Python2.4/site-packages/google_api_python_client-0.1-py2.4.egg
Processing dependencies for google-api-python-client==0.1
Finished processing dependencies for google-api-python-client==0.1
Setup complete!

Finally, attempt to run the Buzz sample which caused the following error

SteveT:buzz strefethen$ python three_legged_dance.py 
Go to the following link in your browser:
https://www.google.com/buzz/api/auth/OAuthAuthorizeToken?scope=https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fbuzz&domain=anonymous&oauth_token=4%2FetZ5lubFdHfPmrqf0pg9IRR_Nury

    

^CTraceback (most recent call last):
  File "three_legged_dance.py", line 40, in ?
    run(flow, 'buzz.dat')
  File "/Users/strefethen/Library/Python2.4/site-packages/google_api_python_client-0.1-py2.4.egg/apiclient/ext/authtools.py", line 121, in run
    httpd.handle_request()
  File "/opt/local/lib/python2.4/SocketServer.py", line 217, in handle_request
    request, client_address = self.get_request()
  File "/opt/local/lib/python2.4/SocketServer.py", line 373, in get_request
    return self.socket.accept()
  File "/opt/local/lib/python2.4/socket.py", line 161, in accept
    sock, addr = self._sock.accept():

I hadn’t reviewed the code (yeah, not necessarily the brightest idea but hey, it’s Google right?). The above error occurred because I had an application running on port 8080 and didn’t realize the demo was going to require that. After shutting down Hudson I was able to authenticate and move forward.

SteveT:buzz strefethen$ python three_legged_dance.py 
Go to the following link in your browser:
https://www.google.com/buzz/api/auth/OAuthAuthorizeToken?scope=https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fbuzz&domain=anonymous&oauth_token=4%2FyDtHZJcU8xD_XP023fUiaKC93wyE

You have successfully authenticated.

However, I ran into another problem which is where the significance of python 2.4 comes in. Attempting to run the buzz.py example I got the following error:

SteveT:buzz strefethen$ python buzz.py 
Traceback (most recent call last):
  File "buzz.py", line 75, in ?
    main()
  File "buzz.py", line 37, in main
    activitylist = activities.list(
  File "/Users/strefethen/Library/Python2.4/site-packages/google_api_python_client-0.1-py2.4.egg/apiclient/discovery.py", line 243, in method
    new_base_url = url_result.scheme + '://' + url_result.netloc
AttributeError: 'tuple' object has no attribute 'scheme'

After a few minutes of tangling with Google I found this page which gave me a clue. Specifically, it was dag’s post from 2008/12/9 relating to urlparse and a difference between python 2.4 and 2.5. I opened the above discovery.py file and searched for ‘scheme’ in order to change the reference to something that would work in 2.4. I had to repeat this for ‘netloc’ and ‘path’ with url_result[0], [1], [2] respectively. After saving the file the sample worked as expected.

Granted I’ve probably included a lot more information with respect to the console output above but there are are few things I’m interested in keeping so this is a great place to do just that.

Now, time to go off and have some fun with these Google API’s.

I’m particularly interested in the Moderator API and I’m curious if anyone has written apps to completely replace the Google Moderator UI with a custom design?

FacebookDel.icio.usDigg It!

How to handle Facebook friend requests?

January 15 2011 12:32AM

photo_25250_20101224[1]If you use Facebook I’d guess you too probably have a backlog of friend requests. Having been on Facebook for several years and with 180 friends I’ve reached a point where I struggle to justify letting more people into my status stream. At 180 I already find myself looking back through older updates to find interesting things.

Most of my pending requests have been out-of-the-blue, old high school friends/acquaintances or people whom I’ve met online but never in person and the occasional complete stranger. In some instances I’ve probably been mistaken for one of my brother’s.

The whole notion of a “friend request” implies having to pass judgment on the relationship you have with the requestee which can feel awkward at times even though that awkwardness isn't really shared. What’s the proper “etiquette” when you’ve been mistaken for a sibling especially for distance relationships?

I’ve noticed my wife and I both let requests we can’t decided immediately on sit in the queue for months at a time with no clear resolution in sight. I haven’t looked but I wonder if there is a way to simply turn off friend requests or perhaps better yet inform the requestee they should contact you directly first?

Personally, I prefer my Facebook social graph be more personal nature and less work/professional using LinkedIn for the latter.

Do you have the same problem? How do you handle friend requests?

[UPDATE] Interesting related article.

Photo credit: FreeDigitalPhotos.net

FacebookDel.icio.usDigg It!