{"rowid": 105, "title": "Contract Killer", "contents": "When times get tough, it can often feel like there are no good people left in the world, only people who haven\u2019t yet turned bad. These bad people will go back on their word, welch on a deal, put themselves first. You owe it to yourself to stay on top. You owe it to yourself to ensure that no matter how bad things get, you\u2019ll come away clean. You owe it yourself and your business not to be the guy lying bleeding in an alley with a slug in your gut.\n\nBut you\u2019re a professional, right? Nothing bad is going to happen to you.\n\nYou\u2019re a good guy. You do good work for good people.\n\nThink again chump.\n\nMaybe you\u2019re a gun for hire, a one man army with your back to the wall and nothing standing between you and the line at a soup kitchen but your wits. Maybe you work for the agency, or like me you run one of your own. Either way, when times get tough and people get nasty, you\u2019ll need more than a killer smile to save you. You\u2019ll need a killer contract too.\n\nIt was exactly ten years ago today that I first opened my doors for business. In that time I\u2019ve thumbed through enough contracts to fill a filing cabinet. I\u2019ve signed more contracts than I can remember, many so complicated that I should have hired a lawyer (or detective) to make sense of their complicated jargon and solve their cross-reference puzzles. These documents had not been written to be understood on first reading but to spin me around enough times so as to give the other player the upper-hand.\n\n\nIf signing a contract I didn\u2019t fully understand made me a stupid son-of-a-bitch, not asking my customers to sign one just makes me plain dumb. I\u2019ve not always been so careful about asking my customers to sign contracts with me as I am now. Somehow in the past I felt that insisting on a contract went against the friendly, trusting relationship that I like to build with my customers. Most of the time the game went my way. On rare the occasions when a fight broke out, I ended up bruised and bloodied. I learned that asking my customers to sign a contract matters to both sides, but what also matters to me is that these contracts should be more meaningful, understandable and less complicated than any of those that I have ever autographed.\n\n\nWriting a killer contract\n\nIf you are writing a contract between you and your customers it doesn\u2019t have to conform to the seemingly standard format of jargon and complicated legalese. You can be creative. A killer contract will clarify what is expected of both sides and it can also help you to communicate your approach to doing business. It will back-up your brand values and help you to build a great relationship between you and your customers. In other words, a creative contract can be a killer contract.\n\n\nYour killer contract should cover:\n\n\n\tA simple overview of who is hiring who, what they are being hired to do, when and for how much\n\tWhat both parties agree to do and what their respective responsibilities are\n\tThe specifics of the deal and what is or isn\u2019t included in the scope\n\tWhat happens when people change their minds (as they almost always do)\n\tA simple overview of liabilities and other legal matters\n\tYou might even include a few jokes\n\n\nTo help you along, I will illustrate those bullet points by pointing both barrels at the contract that I wrote and have been using at Stiffs & Nonsense for the past year. My contract has been worth its weight in lead and you are welcome to take all or any part of it to use for yourself. It\u2019s packing a creative-commons attribution share-a-like license. That means you are free to re-distribute it, translate it and otherwise re-use it in ways I never considered. In return I only ask you mention my name and link back to this article. As I am only an amateur detective, you should have it examined thoroughly by your own, trusted legal people if you use it.\n\nNB: The specific details of this killer contract work for me and my customers. That doesn\u2019t mean that they will work for you and yours. The ways that I handle design revisions, testing, copyright ownership and other specifics are not the main focus of this article. That you handle each of them carefully when you write your own killer contract is.\n\nKiss Me, Deadly\n\nSetting a tone and laying foundations for agreement\n\nThe first few paragraphs of a killer contract are the most important. Just like a well thought-out web page, these first few words should be simple, concise and include the key points in your contract. As this is the part of the contract that people absorb most easily, it is important that you make it count. Start by setting the overall tone and explaining how your killer contract is structured and why it is different.\n\n\n\n\tWe will always do our best to fulfill your needs and meet your goals, but sometimes it is best to have a few simple things written down so that we both know what is what, who should do what and what happens if stuff goes wrong. In this contract you won\u2019t find complicated legal terms or large passages of unreadable text. We have no desire to trick you into signing something that you might later regret. We do want what\u2019s best for the safety of both parties, now and in the future.\n\n\tIn short\n\n\tYou ([customer name]) are hiring us ([company name]) located at [address] to [design and develop a web site] for the estimated total price of [total] as outlined in our previous correspondence. Of course it\u2019s a little more complicated, but we\u2019ll get to that.\n\n\nThe Big Kill\n\nWhat both parties agree to do\n\nHave you ever done work on a project in good faith for a junior member of a customer\u2019s team, only to find out later that their spending hadn\u2019t been authorized? To make damn sure that does not happen to you, you should ask your customer to confirm that not only are they authorized to enter into your contract but that they will fulfill all of their obligations to help you meet yours. This will help you to avoid any gunfire if, as deadline day approaches, you have fulfilled your side of the bargain but your customer has not come up with the goods.\n\n\n\n\tAs our customer, you have the power and ability to enter into this contract on behalf of your company or organization. You agree to provide us with everything that we need to complete the project including text, images and other information as and when we need it, and in the format that we ask for. You agree to review our work, provide feedback and sign-off approval in a timely manner too. Deadlines work two ways and you will also be bound by any dates that we set together. You also agree to stick to the payment schedule set out at the end of this contract.\n\n\tWe have the experience and ability to perform the services you need from us and we will carry them out in a professional and timely manner. Along the way we will endeavor to meet all the deadlines set but we can\u2019t be responsible for a missed launch date or a deadline if you have been late in supplying materials or have not approved or signed off our work on-time at any stage. On top of this we will also maintain the confidentiality of any information that you give us.\n\n\nMy Gun Is Quick\n\nGetting down to the nitty gritty\n\nWhat appear at first to be a straight-forward projects can sometimes turn long and complicated and unless you play it straight from the beginning your relationship with your customer can suffer under the strain. Customers do, and should have the opportunity to, change their minds and give you new assignments. After-all, projects should be flexible and few customers know from the get-go exactly what they want to see. If you handle this well from the beginning you will help to keep yourself and your customers from becoming frustrated. You will also help yourself to dodge bullets in the event of a fire-fight.\n\n\n\n\tWe will create designs for the look-and-feel, layout and functionality of your web site. This contract includes one main design plus the opportunity for you to make up to two rounds of revisions. If you\u2019re not happy with the designs at this stage, you will pay us in full for all of the work that we have produced until that point and you may either cancel this contract or continue to commission us to make further design revisions at the daily rate set out in our original estimate.\n\n\tWe know from plenty of experience that fixed-price contracts are rarely beneficial to you, as they often limit you to your first idea about how something should look, or how it might work. We don\u2019t want to limit either your options or your opportunities to change your mind.\n\n\tThe estimate/quotation prices at the beginning of this document are based on the number of days that we estimate we\u2019ll need to accomplish everything that you have told us you want to achieve. If you do want to change your mind, add extra pages or templates or even add new functionality, that won\u2019t be a problem. You will be charged the daily rate set out in the estimate we gave you. Along the way we might ask you to put requests in writing so we can keep track of changes.\n\n\nAs I like to push my luck when it comes to CSS, it never hurts to head off the potential issue of progressive enrichment right from the start. You should do this too. But don\u2019t forget that when it comes to technical matters your customers may have different expectations or understanding, so be clear about what you will and won\u2019t do.\n\n\n\n\tIf the project includes XHTML or HTML markup and CSS templates, we will develop these using valid XHTML 1.0 Strict markup and CSS2.1 + 3 for styling. We will test all our markup and CSS in current versions of all major browsers including those made by Apple, Microsoft, Mozilla and Opera. We will also test to ensure that pages will display visually in a \u2018similar\u2019, albeit not necessarily an identical way, in Microsoft Internet Explorer 6 for Windows as this browser is now past it\u2019s sell-by date.\n\n\tWe will not test these templates in old or abandoned browsers, for example Microsoft Internet Explorer 5 or 5.5 for Windows or Mac, previous versions of Apple\u2019s Safari, Mozilla Firefox or Opera unless otherwise specified. If you need to show the same or similar visual design to visitors using these older browsers, we will charge you at the daily rate set out in our original estimate for any necessary additional code and its testing.\n\n\nThe Twisted Thing\n\nIt is not unheard of for customers to pass off stolen goods as their own. If this happens, make sure that you are not the one left holding the baby. You should also make it clear who owns the work that you make as customers often believe that because they pay for your time, that they own everything that you produce.\n\n\nCopyrights\n\n\n\tYou guarantee to us that any elements of text, graphics, photos, designs, trademarks, or other artwork that you provide us for inclusion in the web site are either owned by your good selfs, or that you have permission to use them. When we receive your final payment, copyright is automatically assigned as follows:\n\n\tYou own the graphics and other visual elements that we create for you for this project. We will give you a copy of all files and you should store them really safely as we are not required to keep them or provide any native source files that we used in making them.\n\n\tYou also own text content, photographs and other data you provided, unless someone else owns them. We own the XHTML markup, CSS and other code and we license it to you for use on only this project.\n\n\nVengeance Is Mine!\n\nThe fine print\n\nUnless your work is pro-bono, you should make sure that your customers keep you in shoe leather. It is important that your customers know from the outset that they must pay you on time if they want to stay on good terms.\n\n\n\tWe are sure you understand how important it is as a small business that you pay the invoices that we send you promptly. As we\u2019re also sure you\u2019ll want to stay friends, you agree to stick tight to the following payment schedule.\n\n\t[Payment schedule]\n\n\nNo killer contract would be complete without you making sure that you are watching your own back. Before you ask your customers to sign, make it clear-cut what your obligations are and what will happen if any part of your killer contract finds itself laying face down in the dirt.\n\n\n\n\tWe can\u2019t guarantee that the functions contained in any web page templates or in a completed web site will always be error-free and so we can\u2019t be liable to you or any third party for damages, including lost profits, lost savings or other incidental, consequential or special damages arising out of the operation of or inability to operate this web site and any other web pages, even if you have advised us of the possibilities of such damages.\n\n\tJust like a parking ticket, you cannot transfer this contract to anyone else without our permission. This contract stays in place and need not be renewed. If any provision of this agreement shall be unlawful, void, or for any reason unenforceable, then that provision shall be deemed severable from this agreement and shall not affect the validity and enforceability of any remaining provisions.\n\n\tPhew.\n\n\tAlthough the language is simple, the intentions are serious and this contract is a legal document under exclusive jurisdiction of [English] courts. Oh and don\u2019t forget those men with big dogs.\n\n\nSurvival\u2026 Zero!\n\nTake it from me, packing a killer contract will help to keep you safe when times get tough, but you must still keep your wits about you and stay on the right side of the law.\n\nDon\u2019t be a turkey this Christmas.\n\nBe a contract killer.\n\nUpdate, May 2010: For a follow-on to this article see Contract Killer: The Next Hit", "year": "2008", "author": "Andy Clarke", "author_slug": "andyclarke", "published": "2008-12-23T00:00:00+00:00", "url": "https://24ways.org/2008/contract-killer/", "topic": "business"} {"rowid": 109, "title": "Geotag Everywhere with Fire Eagle", "contents": "A note from the editors: Since this article was written Yahoo! has retired the Fire Eagle service.\n \n \n \n Location, they say, is everywhere. Everyone has one, all of the time. But on the web, it\u2019s taken until this year to see the emergence of location in the applications we use and build.\n\nThe possibilities are broad. Increasingly, mobile phones provide SDKs to approximate your location wherever you are, browser extensions such as Loki and Mozilla\u2019s Geode provide browser-level APIs to establish your location from the proximity of wireless networks to your laptop. Yahoo\u2019s Brickhouse group launched Fire Eagle, an ambitious location broker enabling people to take their location from any of these devices or sources, and provide it to a plethora of web services. It enables you to take the location information that only your iPhone knows about and use it anywhere on the web.\n\nThat said, this is still a time of location as an emerging technology. Fire Eagle stores your location on the web (protected by application-specific access controls), but to try and give an idea of how useful and powerful your location can be \u2014 regardless of the services you use now \u2014 today\u2019s 24ways is going to build a bookmarklet to call up your location on demand, in any web application.\n\nLocation Support on the Web\n\nOver the past year, the number of applications implementing location features has increased dramatically. Plazes and Brightkite are both full featured social networks based around where you are, whilst Pownce rolled in Fire Eagle support to allow geotagging of all the content you post to their microblogging service. Dipity\u2019s beautiful timeline shows for you moving from place to place and Six Apart\u2019s activity stream for Movable Type started exposing your movements.\n\nThe number of services that hook into Fire Eagle will increase as location awareness spreads through the developer community, but you can use your location on other sites indirectly too.\n\nConsider Flickr. Now world renowned for their incredible mapping and places features, geotagging on Flickr started out as a grassroots extension of regular tagging. That same technique can be used to start rolling geotagging in any publishing platform you come across, for any kind of content. Machine-tags (geo:lat= and geo:lon=) and the adr and geo microformats can be used to enhance anything you write with location information.\n\nA crash course in avian inflammability\n\nFire Eagle is a location store. A broker between services and devices which provide location and those which consume it. It\u2019s a switchboard that controls which pieces of your location different applications can see and use, and keeps hidden anything you want kept private. A blog widget that displays your current location in public can be restricted to display just your current city, whilst a service that provides you with a list of the nearest ATMs will operate better with a precise street address. \n\nEven if your iPhone tells Fire Eagle exactly where you are, consuming applications only see what you want them to see. That\u2019s important for users to realise that they\u2019re in control, but also important for application developers to remember that you cannot rely on having super-accurate information available all the time. You need to build location aware applications which degrade gracefully, because users will provide fuzzier information \u2014 either through choice, or through less accurate sources.\n\nApplication specific permissions are controlled through an OAuth API. Each application has a unique key, used to request a second, user-specific key that permits access to that user\u2019s information. You store that user key and it remains valid until such a time as the user revokes your application\u2019s access. Unlike with passwords, these keys are unique per application, so revoking the access rights of one application doesn\u2019t break all the others.\n\nBuilding your first Fire Eagle app; Geomarklet\n\nFire Eagle\u2019s developer documentation can take you through examples of writing simple applications using server side technologies (PHP, Python). Here, we\u2019re going to write a client-side bookmarklet to make your location available in every site you use. It\u2019s designed to fast-track the experience of having location available everywhere on web, and show you how that can be really handy. Hopefully, this will set you thinking about how location can enhance the new applications you build in 2009.\n\nAn oddity of bookmarklets\n\nBookmarklets (or \u2018favlets\u2019, for those of an MSIE persuasion) are a strange environment to program in. Critically, you have no persistent storage available. As such, using token-auth APIs in a static environment requires you to build you application in a slightly strange way; authing yourself in advance and then hardcoding the keys into your script.\n\nGet started\n\nBefore you do anything else, go to http://fireeagle.com and log in, get set up if you need to and by all means take a look around. Take a look at the mobile updaters section of the application gallery and perhaps pick out an app that will update Fire Eagle from your phone or laptop.\n\nOnce that\u2019s done, you need to register for an application key in the developer section. Head straight to /developer/create and complete the form. Since you\u2019re building a standalone application, choose \u2018Auth for desktop applications\u2019 (rather than web applications), and select that you\u2019ll be \u2018accessing location\u2019, not updating.\n\nAt the end of this process, you\u2019ll have two application keys, a \u2018Consumer Key\u2019 and a \u2018Consumer Secret\u2019, which look like these:\n\n \n Consumer Key\n luKrM9U1pMnu\n Consumer Secret\n ZZl9YXXoJX5KLiKyVrMZffNEaBnxnd6M\n \n\nThese keys combined allow your application to make requests to Fire Eagle.\n\nNext up, you need to auth yourself; granting your new application permission to use your location. Because bookmarklets don\u2019t have local storage, you can\u2019t integrate the auth process into the bookmarklet itself \u2014 it would have no way of storing the returned key. Instead, I\u2019ve put together a simple web frontend through which you can auth with your application.\n\nHead to Auth me, Amadeus!, enter the application keys you just generated and hit \u2018Authorize with Fire Eagle\u2019. You\u2019ll be taken to the Fire Eagle website, just as in regular Fire Eagle applications, and after granting access to your app, be redirected back to Amadeus which will provide you your user tokens. These tokens are used in subsequent requests to read your location.\n\nAnd, skip to the end\u2026\n\nThe process of building the bookmarklet, making requests to Fire Eagle, rendering it to the page and so forth follows, but if you\u2019re the impatient type, you might like to try this out right now. Take your four API keys from above, and drag the following link to your Bookmarks Toolbar; it contains all the code described below. Before you can use it, you need to edit in your own API keys. Open your browser\u2019s bookmark editor and where you find text like \u2018YOUR_CONSUMER_KEY_HERE\u2019, swap in the corresponding key you just generated.\n\nGet Location\n\nBookmarklet Basics\n\nTo start on the bookmarklet code, set out a basic JavaScript module-pattern structure:\n\nvar Geomarklet = function() {\n\treturn ({\n\t\tcallback: function(json) {},\n\t\trun: function() {}\n\t});\n};\nGeomarklet.run();\n\nNext we\u2019ll add the keys obtained in the setup step, and also some basic Fire Eagle support objects:\n\nvar Geomarklet = function() {\n\tvar Keys = {\n\t\t\tconsumer_key: 'IuKrJUHU1pMnu',\n\t\t\tconsumer_secret: 'ZZl9YXXoJX5KLiKyVEERTfNEaBnxnd6M',\n\t\t\tuser_token: 'xxxxxxxxxxxx',\n\t\t\tuser_secret: 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx'\n\t};\n\tvar LocationDetail = {\n\t\t\tEXACT: 0,\n\t\t\tPOSTAL: 1,\n\t\t\tNEIGHBORHOOD: 2,\n\t\t\tCITY: 3,\n\t\t\tREGION: 4,\n\t\t\tSTATE: 5,\n\t\t\tCOUNTRY: 6\n\t};\n\tvar index_offset;\n\treturn ({\n\t\tcallback: function(json) {},\n\t\trun: function() {}\n\t});\n};\nGeomarklet.run();\n\nThe Location Hierarchy\n\nA successful Fire Eagle query returns an object called the \u2018location hierarchy\u2019. Depending on the level of detail shared, the index of a particular piece of information in the array will vary. The LocationDetail object maps the array indices of each level in the hierarchy to something comprehensible, whilst the index_offset variable is an adjustment based on the detail of the result returned.\n\nThe location hierarchy object looks like this, providing a granular breakdown of a location, in human consumable and machine-friendly forms.\n\n\"user\": {\n\t\t\"location_hierarchy\": [{\n\t\t\t\"level\": 0,\n\t\t\t\"level_name\": \"exact\",\n\t\t\t\"name\": \"707 19th St, San Francisco, CA\",\n\t\t\t\"normal_name\": \"94123\",\n\t\t\t\"geometry\": {\n\t\t\t\t\t\"type\": \"Point\",\n\t\t\t\t\t\"coordinates\": [ - 0.2347530752, 67.232323]\n\t\t\t},\n\t\t\t\"label\": null,\n\t\t\t\"best_guess\": true,\n\t\t\t\"id\": ,\n\t\t\t\"located_at\": \"2008-12-18T00:49:58-08:00\",\n\t\t\t\"query\": \"q=707%2019th%20Street,%20Sf\"\n\t\t},\n\t\t{\n\t\t\t\t\"level\": 1,\n\t\t\t\t\"level_name\": \"postal\",\n\t\t\t\t\"name\": \"San Francisco, CA 94114\",\n\t\t\t\t\"normal_name\": \"12345\",\n\t\t\t\t\"woeid\": ,\n\t\t\t\t\"place_id\": \"\",\n\t\t\t\t\"geometry\": {\n\t\t\t\t\t\t\"type\": \"Polygon\",\n\t\t\t\t\t\t\"coordinates\": [],\n\t\t\t\t\t\t\"bbox\": []\n\t\t\t\t},\n\t\t\t\t\"label\": null,\n\t\t\t\t\"best_guess\": false,\n\t\t\t\t\"id\": 59358791,\n\t\t\t\t\"located_at\": \"2008-12-18T00:49:58-08:00\"\n\t\t},\n\t\t{\n\t\t\t\t\"level\": 2,\n\t\t\t\t\"level_name\": \"neighborhood\",\n\t\t\t\t\"name\": \"The Mission, San Francisco, CA\",\n\t\t\t\t\"normal_name\": \"The Mission\",\n\t\t\t\t\"woeid\": 23512048,\n\t\t\t\t\"place_id\": \"Y12JWsKbApmnSQpbQg\",\n\t\t\t\t\"geometry\": {\n\t\t\t\t\t\t\"type\": \"Polygon\",\n\t\t\t\t\t\t\"coordinates\": [],\n\t\t\t\t\t\t\"bbox\": []\n\t\t\t\t},\n\t\t\t\t\"label\": null,\n\t\t\t\t\"best_guess\": false,\n\t\t\t\t\"id\": 59358801,\n\t\t\t\t\"located_at\": \"2008-12-18T00:49:58-08:00\"\n\t\t\t},\n\t\t}\n\nIn this case the first object has a level of 0, so the index_offset is also 0.\n\nPrerequisites\n\nTo query Fire Eagle we call in some existing libraries to handle the OAuth layer and the Fire Eagle API call. Your bookmarklet will need to add the following scripts into the page:\n\n\n\tThe SHA1 encryption algorithm\n\tThe OAuth wrapper\n\tAn extension for the OAuth wrapper\n\tThe Fire Eagle wrapper itself\n\n\nWhen the bookmarklet is first run, we\u2019ll insert these scripts into the document. We\u2019re also inserting a stylesheet to dress up the UI that will be generated.\n\nIf you want to follow along any of the more mundane parts of the bookmarklet, you can download the full source code.\n\nRendering\n\nThis bookmarklet can be extended to support any formatting of your location you like, but for sake of example I\u2019m going to build three common formatters that you\u2019ll find useful for common location scenarios: Sites which already ask for your location; and in publishing systems that accept tags or HTML mark-up.\n\nAll the rendering functions are items in a renderers object, so they can be iterated through easily, making it trivial to add new formatting functions as your find new use cases (just add another function to the object).\n\nvar renderers = {\ngeotag: function(user) {\n\tif(LocationDetail.EXACT !== index_offset) {\n\t\t\treturn false;\n\t}\n\telse {\n\t\tvar coords =\n\t\t\tuser.location_hierarchy[LocationDetail.EXACT].geometry.coordinates;\n\t\treturn \"geo:lat=\" + coords[0] + \", geo:lon=\" + coords[1];\n\t}\n},\ncity: function(user) {\n\tif(LocationDetail.CITY < index_offset) {\n\t\treturn false;\n\t}\n\telse {\n\t\treturn user.location_hierarchy[LocationDetail.CITY - index_offset].name; \n\t}\t\t\t\t\t\t \n}\n\nYou should always fail gracefully, and in line with catering to users who choose not to share their location precisely, always check that the location has been returned at the level you require. Geotags are expected to be precise, so if an exact location is unavailable, returning false will tell the rendering aspect of the bookmarklet to ignore the function altogether.\n\nThese first two are quite simple, geotag returns geo:lat=-0.2347530752, geo:lon=67.232323 and city returns San Francisco, CA.\n\nThis final renderer creates a chunk of HTML using the adr and geo microformats, using all available aspects of the location hierarchy, and can be used to geotag any content you write on your blog or in comments:\n\nhtml: function(user) {\n\tvar geostring = '';\n\tvar adrstring = '';\n\tvar adr = [];\t\t \n\tadr.push('
');\n\t// city\n\tif(LocationDetail.CITY >= index_offset) {\n\t\tadr.push(\n\t\t\t'\\n\t\t '\n\t\t+ user.location_hierarchy[LocationDetail.CITY-index_offset].normal_name\n\t\t+ ','\n\t\t);\n\t}\n\t// county\n\tif(LocationDetail.REGION >= index_offset) {\n\t\tadr.push(\n\t\t\t'\\n\t\t ' \n\t\t+ user.location_hierarchy[LocationDetail.REGION-index_offset].normal_name\n\t\t+ ','\n\t\t\t);\n\t}\n\t// locality\n\tif(LocationDetail.STATE >= index_offset) {\n\t\tadr.push(\n\t\t\t'\\n\t\t '\n\t\t+ user.location_hierarchy[LocationDetail.STATE-index_offset].normal_name\n\t\t+ ','\n\t\t);\n\t}\n\t// country\n\tif(LocationDetail.COUNTRY >= index_offset) {\n\t\tadr.push(\n\t\t\t'\\n\t\t '\n\t\t+ user.location_hierarchy[LocationDetail.COUNTRY-index_offset].normal_name\n\t\t+ ''\n\t\t);\n\t}\n\t// postal\n\tif(LocationDetail.POSTAL >= index_offset) {\n\t\tadr.push(\n\t\t\t'\\n\t\t '\n\t\t+ user.location_hierarchy[LocationDetail.POSTAL-index_offset].normal_name\n\t\t+ ','\n\t\t);\n\t}\n\tadr.push('\\n
\\n');\n\tadrstring = adr.join('');\n\tif(LocationDetail.EXACT === index_offset) {\n\t\tvar coords = \n\t\t\tuser.location_hierarchy[LocationDetail.EXACT].geometry.coordinates;\n\t\tgeostring = ''\n\t\t\t+'\\n\t\t'\n\t\t\t+ coords[0]\n\t\t\t+ ';'\n\t\t\t+ '\\n\t\t '\n\t\t\t+ coords[1]\n\t\t\t+ '\\n
\\n';\n\t}\n\treturn (adrstring + geostring);\n}\n\nHere we check the availability of every level of location and build it into the adr and geo patterns as appropriate. Just as for the geotag function, if there\u2019s no exact location the geo markup won\u2019t be returned.\n\nFinally, there\u2019s a rendering method which creates a container for all this data, renders all the applicable location formats and then displays them in the page for a user to copy and paste. You can throw this together with DOM methods and some simple styling, or roll in some components from YUI or JQuery to handle drawing full featured overlays.\n\nYou can see this simple implementation for rendering in the full source code.\n\nMake the call\n\nWith a framework in place to render Fire Eagle\u2019s location hierarchy, the only thing that remains is to actually request your location. Having already authed through Amadeus earlier, that\u2019s as simple as instantiating the Fire Eagle JavaScript wrapper and making a single function call. It\u2019s a big deal that whilst a lot of new technologies like OAuth add some complexity and require new knowledge to work with, APIs like Fire Eagle are really very simple indeed.\n\nreturn {\n\trun: function() {\n\t\tinsert_prerequisites();\n\t\tsetTimeout(\n\t\t\tfunction() {\n\t\t\t\tvar fe = new FireEagle(\n\t\t\t\t\tKeys.consumer_key,\n\t\t\t\t\tKeys.consumer_secret,\n\t\t\t\t\tKeys.user_token,\n\t\t\t\t\tKeys.user_secret\n\t\t\t\t);\n\t\t\t\tvar script = document.createElement('script');\n\t\t\t\tscript.type = 'text/javascript';\n\t\t\t\tscript.src = fe.getUserUrl(\n\t\t\t\t\tFireEagle.RESPONSE_FORMAT.json,\n\t\t\t\t\t'Geomarklet.callback'\n\t\t\t\t);\n\t\t\t\tdocument.body.appendChild(script);\n\t\t\t},\n\t\t\t2000\n\t\t);\n\t},\n\tcallback: function(json) {\n\t\tif(json.rsp && 'fail' == json.rsp.stat) {\n\t\t\talert('Error ' + json.rsp.code + \": \" + json.rsp.message);\n\t\t}\n\t\telse {\n\t\t\tindex_offset = json.user.location_hierarchy[0].level;\t\t\t\t\t\t \n\t\t\tdraw_selector(json);\n\t\t}\n\t}\n};\n\nWe first insert the prerequisite scripts required for the Fire Eagle request to function, and to prevent trying to instantiate the FireEagle object before it\u2019s been loaded over the wire, the remaining instantiation and request is wrapped inside a setTimeout delay.\n\nWe then create the request URL, referencing the Geomarklet.callback callback function and then append the script to the document body \u2014 allowing a cross-domain request.\n\nThe callback itself is quite simple. Check for the presence and value of rsp.status to test for errors, and display them as required. If the request is successful set the index_offset \u2014 to adjust for the granularity of the location hierarchy \u2014 and then pass the object to the renderer.\n\nThe result? When Geomarklet.run() is called, your location from Fire Eagle is read, and each renderer displayed on the page in an easily copy and pasteable form, ready to be used however you need.\n\nDeploy\n\nThe final step is to convert this code into a long string for use as a bookmarklet. Easiest for Mac users is the JavaScript bundle in TextMate \u2014 choose Bundles: JavaScript: Copy as Bookmarklet to Clipboard. Then create a new \u2018Get Location\u2019 bookmark in your browser of choice and paste in.\n\nThose without TextMate can shrink their code down into a single line by first running their code through the JSLint tool (to ensure the code is free from errors and has all the required semi-colons) and then use a find-and-replace tool to remove line breaks from your code (or even run your code through JSMin to shrink it down).\n\nWith the bookmarklet created and added to your bookmarks bar, you can now call up your location on any page at all. Get a feel for a web where your location is just another reliable part of the browsing experience.\n\nWhere next?\n\nSo, the Geomarklet you\u2019ve been guided through is a pretty simple premise and pretty simple output. But from this base you can start to extend: Add code that will insert each of the location renderings directly into form fields, perhaps, or how about site-specific handlers to add your location tags into the correct form field in Wordpress or Tumblr? Paste in your current location to Google Maps? Or Flickr?\n\nGeomarklet gives you a base to start experimenting with location on your own pages and the sites you browse daily.\n\nThe introduction of consumer accessible geo to the web is an adventure of discovery; not so much discovering new locations, but discovering location itself.", "year": "2008", "author": "Ben Ward", "author_slug": "benward", "published": "2008-12-21T00:00:00+00:00", "url": "https://24ways.org/2008/geotag-everywhere-with-fire-eagle/", "topic": "code"} {"rowid": 100, "title": "Moo'y Christmas", "contents": "A note from the editors: Moo has changed their API since this article was written.\n \n \n \n As the web matures, it is less and less just about the virtual world. It is becoming entangled with our world and it is harder to tell what is virtual and what is real. There are several companies who are blurring this line and make the virtual just an extension of the physical. Moo is one such company. \n\nMoo offers simple print on demand services. You can print business cards, moo mini cards, stickers, postcards and more. They give you the ability to upload your images, customize them, then have them sent to your door. Many companies allow this sort of digital to physical interaction, but Moo has taken it one step further and has built an API. \n\nPrintable stocking stuffers \n\nThe Moo API consists of a simple XML file that is sent to their servers. It describes all the information needed to dynamically assemble and print your object. This is very helpful, not just for when you want to print your own stickers, but when you want to offer them to your customers, friends, organization or community with no hassle. Moo handles the check-out and shipping, all you need to do is what you do best, create! \n\nNow using an API sounds complicated, but it is actually very easy. I am going to walk you through the options so you can easily be printing in no time. \n\nBefore you can begin sending data to the Moo API, you need to register and get an API key. This is important, because it allows Moo to track usage and to credit you. To register, visit http://www.moo.com/api/ and click \u201cRequest an API key\u201d. \n\nIn the following examples, I will use {YOUR API KEY HERE} as a place holder, replace that with your API key and everything will work fine. \n\nFirst thing you need to do is to create an XML file to describe the check-out basket. Open any text-editor and start with some XML basics. Don\u2019t worry, this is pretty simple and Moo gives you a few tools to check your XML for errors before you order. \n\n \nLorem ipsum dolor sit amet\u2026
\n\t\tThis hCard created with the hCard creator.
\n