Fluidinfo

May 24, 2010

Anatomy of a funding

Filed under: Essence,Happiness — Terry Jones @ 11:43 am

Yes!! Fluidinfo is finally funded. Getting there took a while, and wasn’t easy. In fact, it was the most difficult thing I’ve ever done. Below are a few loosely related comments on how it all went down. I hope this will be of interest to people who are specifically interested in the progress of Fluidinfo, and also to other entrepreneurs. I’ve been waiting years to write it. Predictably, now that I’m in a position to do so, I don’t really have time to do a decent job.

There was a lot of rejection along the way. I blogged about expecting and embracing startup rejection in Nov 2008. We had to ignore all that, and take heart from the strong support of a few people. More on them later.

We were even called "unfundable" (and “world-changing”) in a generous article by Robert Scoble, who is a very careful listener and much smarter than people seem to realize. I was of course determined to change that.

Tim O’Reilly uttered the most memorable fund-raising related sentence along the way: “This could take over the world…. but I don’t see how we could fund you.” Argh! Best, clearest, and most useful advice came from Jeff Bezos who simply said “Never give up”. Most haunting startup article: Avoiding the Cargo Cult by Roman Stanek. Most inspiring and favorite other entrepreneur met along the way: Jason Calacanis.

Several times we could have been funded if I’d accepted very low valuations. I said no to deals that didn’t feel right. I said no, and we pushed on to a release living on fumes, when people told me Fluidinfo was just ideas – as if the years of coding counted for nothing. I even said no to a couple of informal offers to acquire Fluidinfo.

Several times we could have been funded if we’d agreed to just build some kind of application, instead of insisting on working on Fluidinfo as a general storage architecture. I was never willing to give up or even relegate the importance and value of getting the right architecture in place. I think many startups have powerful general ideas but get diverted along the way into building something more specific. They have the intention of getting back to the more general and broadly applicable vision, but they never do. There are many reasons why that happens, among them the fact that once low-level engineering (programming) decisions are baked in, they are very hard to revisit.

So you could say I wasn’t willing to compromise on the vision – to get funded earlier in order to do less. And I felt compelled to push back on the elevator pitch, a posting through which I met Andy Weissman. I don’t think entrepreneurs should obediently infantilize their grand visions just so someone who’s probably not going to fund you can perhaps understand what you’re doing. Sure, if you have a compact idea that you can package up into a tiny pitch, go for it. If after trying to do that, you don’t, go find some potential investors with the patience to listen to you. The Betaworks guys told me after we’d first met that they’d blocked off 3 hours to talk to me – they knew it might take some time to see the scope of what we were attempting, to ask about it and consider it, to let it sink in, to hear why it might work, etc. (It didn’t take 3 hours, BTW, but they were prepared.)

I spent a lot of time pondering the link between obviousness, the creation of value, and passion. I often try to get people to read that article.

I’ve been introduced to many people along the way. A couple of years ago, in order to avoid real work, I started drawing a graph of the introductions I could remember. I filled my entire 3 meter whiteboard. So I wrote a small program to generate input for Graphviz and fed it all the information. You can see the result here. The colors are for people I’ve only talked to on the phone (light green), only emailed (orange), or was introduced to but never got a reply back from (yellow). All the rest (darker green) I met in person. I had to force myself to meet people, at first just telling myself it was part of my job and that if I didn’t do it Fluidinfo would simply cease to exist at some point, and in the end actually coming to enjoy it.

If you know your way around the seed and venture world, you’ll recognize many names in that graph. You can infer that they all – one way or another – found a way to say no, with the exception of Esther Dyson (who is a saint) and the investors who have just funded us. Many never actually bothered to say no, and several simply stopped replying to email. (See also: Pond Scum.) As an entrepreneur without a lot of outside support, it’s good to have things to keep you going. Planning to have the last laugh is sometimes all it takes. πŸ™‚

Quality I most enjoyed running into while meeting all those people: intellectual generosity. One thing I learned to stop doing: taking other people’s time and attention for granted.

The total money we spent on hardware over the last 4 years is $2000. That was one laptop, a couple of sticks of RAM, a USB memory, a couple of external hard drives, and a printer. The whole of Fluidinfo was written on two 15″ laptops, with no external monitors.

I can’t stand entrepreneurial cliches. They drive me nuts. There are so many people out there pontificating about startups, funding, VCs and entrepreneurs. If you spend any amount of time in that world you’re going to hear the same old tired cliches over and over and over. Standout exceptions: Chris Dixon, Scott Rafer, Nivi and Naval at Venture Hacks, and Paul Graham. Yes, there’s a bunch of other good stuff out there too.

I made the mistake of talking to VCs too early (see the post on rejection mentioned above). I should have been talking to earlier stage funders, but I was so sure the VCs would find Fluidinfo irresistible, and I wanted a bigger amount of money, that I neglected to talk to the only people (with money) who could really appreciate what we were trying to build.

John Borthwick and Andy Weissman, the founders of Betaworks, are fantastic. Betaworks are changing early-stage financing in New York (and beyond). Look at the intro graph: John is very easy to find. Those are almost all introductions he was making long before they funded us. They invited me to speak at their monthly brown bag lunch. They’ve had us in their office for a couple of months this year, given us keys, let us come to their weekly company-wide meetings, taken me into confidence multiple times, let me be present when sensitive things were discussed, created opportunities, pulled the funding round together, been generous and accommodating on the terms of the deal, and more. Spending time with the other small startups in and around the Betaworks office has been great – there’s a lot of very smart people there, and they’re working hard (while having fun) building all sorts of things. John is very good at his job. Keep your eye on Betaworks.

And never give up πŸ™‚

FluidDB enters alpha

Filed under: Programming,Progress — Terry Jones @ 11:38 am

We’re using the Techcrunch Disrupt event to launch FluidDB into a real alpha. Until today we’ve only let a small number of people in to play with the API, and we’ve been giving away API passwords by hand. As of today, we’re taking the brakes off a little, allowing anyone to sign up and begin using the FluidDB API. Of course to do that it will help enormously if you’re a programmer πŸ™‚

Although FluidDB has been up and running for 9 months, we’re being careful not to raise expectations too quickly. So for now we’re still labeling it an “alpha”. We have concrete plans for what will constitute a beta—these are mainly to do with speed and with adding flexibility to the API to reduce the number of calls apps have to make—and plan to be in beta by the end of 2010. Now that we have our funding cleared up, and can hire more developers, you can expect FluidDB development to ramp up quickly.

Please feel free to comment below. We’re listening!

Fluidinfo is funded!

Filed under: Happiness — Terry Jones @ 11:34 am

We’re thrilled to announce that Fluidinfo have just closed a small Series A round ($800K) led by Betaworks, with participation from IA Ventures, RRE Ventures, Lerer Ventures, Chris Dixon and the Founder Collective, Joshua Schacter, Andrew Rasiej, Ross Williams, Esther Speight, and Ed Carroll. They’ll be joined by early Fluidinfo seed funder Esther Dyson. We’ve been talking on and off to Betaworks for two years, and we couldn’t be more pleased with the close relationship we’ve developed with them over that time, and with the fit of our collective visions and aims.

We’d never have gotten this far without the support of several early “sweat equity” contributors and 17 friends and family seed investors – our huge thanks to that group too.

Fluidinfo is now a US (Delaware) corporation, thanks to the efforts of Gunderson Dettmer, and for the time being we’ll be based out of the dynamic Betaworks offices in New York. As you’d expect, we’re looking for a few passionate programmers to join the team.

In other news, we’ve been selected as a finalist in TechCrunch Disrupt Startup Battlefield, and we’re most of the way through a major overhaul to the Fluidinfo web site, with more good stuff to come.

I’ll stop now, to try to keep this short. Watch this space for some upcoming posts.

Fluidinfo is a TechCrunch Disrupt finalist

Filed under: Events,Progress — Terry Jones @ 10:15 am

Fluidinfo has been selected as a finalist in the TechCrunch Disrupt Startup Battlefield taking place today in New York.

Over 500 companies from around the world applied to present at TechCrunch Disrupt, and only 20 were accepted. We’ll be on stage fighting for the right to call ourselves the most disruptive start-up on the planet πŸ™‚

It’s quite an accomplishment and an honor to be selected as a finalist. The entry process wasn’t simple: a written application, a 5-minute video, a phone interview with TC CEO Heather Harde, a couple of hours talking and demoing to Erick Schonfeld, a written script of a presentation (with lots of suggestions from Erick), and several live rehearsals. Ben Siscovick of IA Ventures is kindly helping with the live presentation. And along the way I had to reluctantly pull out of giving a presentation at the NY Tech Meetup. Thanks to John Borthwick of Betaworks and to Todd Levy of bit.ly for helping cover for me, and especially to Nate Westheimer the NYTM organizer for his understanding and support.

I’ve never really liked these startup competitions. They amount of time allotted to present always seems too little, and the audience too general. But more importantly, they’ve always seemed biased towards startups working on much simpler things, with snazzy UIs and demos – exactly the kind of thing we never had. But the theme of TechCrunch Disrupt was too irresistible to ignore. In the demo video I submitted, I told them I had no demo and that real disruption will not necessarily arrive with a UI. To their credit, TC bought it and were courageous enough to consider Fluidinfo further, and to finally accept us. Erick Schonfeld was very thoughtful, supportive, and encouraging in this.

Hopefully the presentation will be available online – if so I’ll post a link here. I’ve been thinking about it and working on it for some time. I’m on stage sometime after 2:15pm (EST) today.

I think it’s going to go well. Hopefully by the time you read this we wont have already been voted off the TC Disrupt island!

May 6, 2010

TunkRank scores added to Fluidinfo

Filed under: Essence — Terry Jones @ 12:34 am

TunkRank is an influence measure for Twitter users. It was originally proposed by Daniel Tunkelang, and an online implementation was written and is maintained at tunkrank.com by Jason Adams. Given a Twitter user name, TunkRank computes a measure of that user’s influence based on followers of the user, how many people the user’s followers follow, etc. As well as a web interface, TunkRank scores can be obtained through their HTTP API.

Today we’re excited to announce that TunkRank scores can now also be accessed through Fluidinfo. This gives us a great way to concretely illustrate some of the unique properties of Fluidinfo. I’m going to give some examples that use Tickery, so you might want to go play with that a little first, or read our earlier postings, Meet Tickery and Tickery, for programmers.

  1. But wait, TunkRank already has an API
    That’s true, but why stop at one? The TunkRank API provides TunkRank scores in isolation. So a 3rd party application can fetch a score and use it in some way. By also putting TunkRank scores into Fluidinfo though, they become searchable and can be combined with other data in Fluidinfo. For example, here’s a Tickery query showing people I follow who have a TunkRank of over 30. Look at the Fluidinfo query: has twitter.com/friends/terrycojones and tunkrank.com/score > 30. In English: "Hey Fluidinfo, get me all objects that have a twitter.com/friends/terrycojones tag on them and that also have a TunkRank score greater than 30." That’s pretty interesting: a data mashup of Twitter friend information with TunkRank scores. You can’t (easily) do that when the two sources of data are held in isolation, each behind their own API, but it’s trivial if the information is in the same place.
  2. TunkRank’s domain name is on their data in Fluidinfo
    In the query above, the tag name for the TunkRank score is tunkrank.com/score. The tunkrank.com domain is part of the name of the data. With that name comes reputation and trust: if you see a tunkrank.com/score on a Fluidinfo object, you know it came from TunkRank. Want to put your domain name on individual pieces of data? Send us an email and if you can show us you own the domain, we’ll give you the Fluidinfo namespace with that name.
  3. TunkRank continue to control their own data
    The permissions system of Fluidinfo allows TunkRank to control their own data. If Jason Adams wants, he can take permission away from Tickery to read the TunkRank scores. Because Fluidinfo’s permission system works at the level of the tag, not at the level of the Fluidinfo object, you get fine-grained control over the pieces of information that comprise objects.
  4. Tickery was conceived independently of the idea of TunkRank scores
    Tickery doesn’t know anything about TunkRank. It happens to have an advanced tab that allows arbitrary Fluidinfo queries because that’s part of why we built it – to illustrate how other data added to Fluidinfo objects could easily be queried. Think about it – here we have two applications that were built independently of one another able to enhance each other because their information is in the same place.
  5. TunkRank did not ask for permission to add their scores
    Because Fluidinfo objects do not have owners, there was no need for TunkRank to ask for permission to put their scores onto the same Fluidinfo objects that Tickery is using. They just did it. You can too, all you need is a Fluidinfo user name (you can get one here) and then send mail to api@fluidinfo.com requesting an API password. (Fluidinfo is still in private alpha.)
  6. TunkRank and Tickery can move at different speeds
    As described in the Tickery for programmers posting, Tickery is using the Fluidinfo about tag, putting its information onto objects with a fluiddb/about whose values have the form twitter.com:uid:XXXX, where XXXX is a numeric Twitter user id. In Fluidinfo, anyone can create an object that’s "about" something. The upshot of that is that TunkRank does not have to wait until Tickery adds a user, it can just go ahead and put a tunkrank.com/score onto an object with the appropriate about tag – no questions asked. TunkRank doesn’t care or need to know if the object already existed, or whether Tickery had already put its tags there. Think about this too: here we have two (or more!) applications that are following the same convention, putting their own data into the same database, and each can move at its own speed without regard for the other. There’s no coordination beyond the about tag convention, when new data shows up from an application, it naturally goes to the place it belongs.
  7. Anyone can play – that’s the point
    Other tags can be added to the same Fluidinfo objects, and can be queried on using the Fluidinfo query language in Tickery’s advanced tab (or by using the Fluidinfo API directly). To illustrate, Esteve Fernández and I put esteve/met and terrycojones/met tags onto objects to indicate people we’ve physically met. That data can be instantly (and interestingly!) mashed up with other data. For example, here are the people Esteve is following that he has not met, but who I have met, via the query (has twitter.com/friends/esteve and has terrycojones/met) except has esteve/met. And to show Twitter friends info, TunkRank scores, and our met tags in a single query, here are the people I follow who have a high TunkRank but who I’ve not actually met.

If you’ve read all the way down to here, thanks.

If you were having trouble grasping the point of Fluidinfo before, I hope these concrete examples have helped (if not, please let us know in the comments). Considering just Twitter, TunkRank, and Tickery as three related web applications, it’s clear that when their data is in the same place – via something like a Wikipedia for data – that it becomes more valuable.

But Fluidinfo is not about Twitter – the above is just an example of three applications (four, if you count the informal esteve/met and terrycojones/met tags) that are related and which all benefit from having their data co-located. People (and applications) can do more with it – they can search it more easily, they can add to it, they can do things that the original application designers did not and could not have anticipated. This applies to any data anyone cares to add to Fluidinfo.

Finally, Fluidinfo does not have the disconcerting (to some) free-wheeling anarchy property of a wiki. While preserving the essential character of wikis: it is always writable and it has an object for everything, it has three important things that a wiki does not have and which make it suitable for use by applications: 1) a strong permissions system (e.g., only TunkRank can add tunkrank.com/score tags to objects, unless they allow others to too), 2) a query language, and 3) typed data.

January 21, 2010

Tickery, for programmers

Filed under: Essence,Programming — Terry Jones @ 5:21 pm

Where's the beef?If you’re a programmer and you’ve played around with Tickery, it should be clear that Tickery is functionally very simple when looked at from a traditional database perspective. Tickery looks like an application in its own right. It tries to offer something so simple that anyone (at least any Twitter user) can understand and use the Simple “Enter two Twitter usernames” functionality. But we actually designed and built Tickery mainly as a demo of what’s possible with Fluidinfo (description, API). So here are some first details on how Tickery uses Fluidinfo, and how you can use it too.

Fluidinfo objects

The most important thing to understand about Fluidinfo initially is that it maintains a collection of tagged objects that are not owned. Tags have permissions and a tag on an object can optionally have a value associated with it. Here’s a conceptual view of an object that has two tags on it that were added by Tickery.

The long identifier is the object’s unique id in Fluidinfo. The left column shows tag names, such as twitter.com/users/screen_name, and the right column shows the value (if any) of the tag on the object. Because objects in Fluidinfo are not owned, anyone (which is to say any application) can put additional tags onto this object. I’m going to ignore permissions in what follows – that’s a subject for a separate posting.

Any application can find this object in Fluidinfo, using a simple query, like twitter.com/users/id = 42983 or twitter.com/users/screen_name = "terrycojones".

Now let’s suppose Tickery adds @esteve to Fluidinfo, and wants to indicate that Esteve currently follows terrycojones. Tickery creates a new tag, twitter.com/friends/esteve in Fluidinfo, and adds it to the above object. The object then looks like this:

Similarly, Tickery adds a twitter.com/friends/esteve to the objects representing all the Twitter users Esteve follows. At this point it is easy to retrieve all those users via the Fluidinfo query has twitter.com/friends/esteve (i.e., get me all the objects that have a twitter.com/friends/esteve tag, irrespective of the tag’s value, if any).

Suppose Tickery now adds another Twitter user, @fergusstothart who currently follows me. It adds another tag to the object, resulting in

and also puts a twitter.com/friends/fergusstothart tag onto the objects for the other users that Fergus follows. It finds these objects via a Fluidinfo query (using the Twitter id of Fergus, obtained from the Twitter API). If Tickery needs to tag an object for a user that it hasn’t created yet, it simply creates a new object for that user, and tags it.

Given the above, we’ve seen enough to know how Tickery does most of its work. For example, getting things like the set of people Esteve and Fergus follow in common is just an and query has twitter.com/friends/esteve and has twitter.com/friends/fergusstothart, or the set of people Esteve follows but Fergus does not has twitter.com/friends/esteve except has twitter.com/friends/fergusstothart, etc.

Where we come in

That’s all well and good, but it’s all about Tickery. What if other programmers, who perhaps don’t care or even know about Tickery want to add data and search on it too? In a normal database or with a normal application, you’d probably expect to have to ask permission. Then, supposing it was granted, you could only do the kinds of things that had been anticipated and provided for.

But in Fluidinfo it’s completely different. Any application can come along and put whatever it likes onto the above object, or any other object (that it can find). As a trivial example, Esteve and I have also added tags to the Fluidinfo objects to indicate which of the people we follow we have also met in person. Esteve has an esteve/met tag, and because we’ve met (in fact we built Fluidinfo together), he has put that tag onto the above object:

Think about what just happened. An unknown 3rd party (well, let’s pretend Esteve was unknown) just came along, sometime after the Tickery data already existed in Fluidinfo, and added something completely new and unanticipated to an existing object, without asking for permission, and without in any way disturbing the original content. Esteve, or anyone else who can read his tag, can now do interesting searches, like has twitter.com/friends/esteve except has esteve/met, which shows the people he follows but has not yet met. Further, his searches seamlessly combine the existing Tickery data with his own data, and could also include other tags that other applications add.

That kind of unanticipated use of information, flexibility in representation and search, and change of control is what’s at the heart of Fluidinfo.

Twitter lists

If you think about it, Esteve adding esteve/met tags to the objects for Twitter users is exactly like making a list in Twitter using their new lists function. But it’s more useful for two main reasons.

Firstly, you can query across lists, e.g., has terrycojones/met and has esteve/met will find people we have both met in person, and (has twitter.com/friends/esteve and has terrycojones/met) except has esteve/met will find people Esteve follows that I have met in person but whom he has not. As you can see, querying on lists makes them much more useful.

Secondly, you can use the Fluidinfo permissions system to control who can see or read your tags. So it’s not only possible to have a completely private list, a public one, but you can also have a list that’s visible just to some friends, or one that you let certain other people add to (by giving them write permission on the tag involved).

Permissions in Fluidinfo are very simple and very flexible, and because they apply at the level of the tag (not the object), you can control who can do what to individual pieces (tags) of an object. That’s a subject for another post, as I mentioned. You might like to have a read of the Fluidinfo permissions docs and/or check out Nicholas Radcliffe‘s post Permissions Worth Getting Excited About, plus see the comment by Nicholas Tollervey, who writes Fluidinfo’s "killer feature" is actually its permissions system and the implications thereof. It is so important that I’ll save that topic for its own blog post later.

More Tickery tags

Tickery also saves a few more Twitter user details onto objects in Fluidinfo. The object above has some additional tags:

You can put these into queries too, of course. The Tickery Advanced tab lets you type them in, e.g., I can see which of the people that Jack follows are very popular has twitter.com/friends/jack and twitter.com/users/followers_count > 100000.

Running on ahead of Tickery

Finally, here’s a subtle but very important point. What if you write an application that uses Fluidinfo to store data, and you want it to interact fully with Tickery, but you want to store information about a user that Tickery doesn’t know about yet?

This is crucially important because it’s about information control, and if control is completely in the hands of Tickery, other developers will be less likely to want to add information. Exactly this scenario plays out in many domains: e.g., suppose Amazon released something that let you indicate which books you own, but that you own things that are not in the Amazon database. How can you run on ahead of Amazon to insert your data before they create an object for the book, if ever? How can you do it in a way so that when they finally do create the book your data and theirs are seamlessly joined without anyone having to lift a finger or even be aware of the other party?

This is one area in which the special Fluidinfo “about” tag (full name fluiddb/about) makes all the difference. You can read about it here, and be sure to check out Nicholas Radcliffe‘s blog which is titled, not coincidentally, About Tag.

Tickery uses the Fluidinfo about tag to hold a Twitter user id, like this:

There’s a ton that could be written about this. Very briefly, the about tag is immutable and can only be set on an object when it’s created (in fact the about tag shown above was put there when the object was made). So, if you want to add data to Twitter user that Tickery hasn’t gotten to, just look up the user’s Twitter id (say XXXX) with the Twitter API, create the object in Fluidinfo with about tag twitter.com:uid:XXXX, and put your tags onto that object. If Fluidinfo doesn’t have an object with that about tag, it will make one for you. When/if Tickery gets around to adding its information for that user, it will put it in the same place. Magic.

Convenience API

As a convenience, though note that it’s optional and it’s use is up to you, Tickery provides a small API that you can use to have it put its twitter.com/users/screen_name and twitter.com/users/id tags onto objects for you and give you the Fluidinfo object id its using for a user.

E.g., if you do an HTTP GET on http://tickery.net/api/screennames/terrycojones you’ll see the object id from our examples above. Or if you happened to know my Twitter user id (42983) via the Twitter API, you could do a GET on http://tickery.net/api/uids/42983 and receive the same thing.

Truly social data

This API is just for convenience. Tickery uses the about tag in order to be able to share Fluidinfo objects with other apps – including apps that want to add information about a user that Tickery has not gotten to yet. Just like Fluidinfo, Tickery wants to encourage what we call Truly Social Data. Tickery doesn’t place itself in the center, doesn’t make its data more important than anyone else’s, and doesn’t act as a gatekeeper.

In fact, it gets even better: a normal user can turn around and stop Tickery from reading the data that Tickery stored on the user’s behalf. That’s as it should be. Users should have control over their data, and a choice of application shouldn’t result in lock in.

Getting access

Fluidinfo is still very new, and we’re in a private alpha phase. If you’d like to use the API, there are two steps: 1) reserve a username, and 2) send us email mentioning the name you reserved and a line or two about what you’d like to do. We apologize for this early restriction – please rest assured that we’re planning to open Fluidinfo up to everyone before too long. That’s the whole point.

More soon. Thanks very much for reading!

Meet Tickery

Filed under: Essence,Happiness,Progress — Terry Jones @ 5:20 pm

TickeryWe’re very excited to present Tickery: a fun tool for exploring sets of Twitter friends and finding new people to follow.

Tickery starts off very simply, letting you see who pairs of Twitter users follow in common. For example, who do Tim O’Reilly and Tim Bray follow in common? Even simple queries like this are interesting, because they’re a great way to find interesting Twitter users you may want to follow too. In addition, on the Tickery page just below where you enter the two user names, you’ll get to see whether the two users follow each other. So if you find yourself asking “I wonder if X follows Y?” you can use Tickery to find out immediately, which beats scrolling through multiple pages on twitter.com.

Please be patient with Tickery if you do a query on a user we haven’t added yet. Tickery uses the Twitter API to get information about users, and there are restrictions on how fast we can make those API calls.

Tickery lets you sign in via Twitter – see the button on the top right of the tab bar. If you sign in you can filter results to show just the people you’re following (or not), you can click to follow new people, and you can send out tweets with links to Tickery results of interest.

Tickery’s Intermediate tab offers a big jump in power. Enter simple queries using Twitter user names, and simple terms like and, or and except. For example, the query (jack and ev and biz) except terrycojones shows me Twitter users that all the three Twitter founders follow, but who I do not. Or get possible hints on which entrepreneurs are being followed by one firm and missed by another: for example who does everyone at Union Square Ventures follow that no-one at Betaworks does?

Tickery also has an Advanced tab, which gives you another big jump in power. I’ll save a description of that for another post, but to whet your appetite, here are users Tickery knows about with a Twitter id less than 1000 and people I follow on Twitter that I have also met in person. Or see the description and examples in the "huh?" button on the Advanced tab.

Powered by FluidDB

The most important and interesting thing about Tickery is that it’s built on top of FluidDB (description, API). Tickery is great fun all by itself, but it was built to show what we at Fluidinfo think the relationship between applications, their users, and their data will come to look like. That’s also the subject of an upcoming post, but here are a few bullet points to give you an idea of why applications like Tickery, written on top of FluidDB, may look normal but are in fact very different. Such applications, in combination with an information architecture like FluidDB will:

  • Leave users in control of their data, which includes letting them use other applications to work on it and, if you’re really serious, being able to turn off access to the application that stored it for you.
  • Make the world writable by default, by allowing anyone to add anything to the underlying data in any way they like.
  • Selectively protect individual aspects of data objects on a user-by-user and application-by-application basis.
  • Allow users and applications to put their name (like an internet domain name) on pieces of data, thereby stamping that data with trust and reputation.
  • Let you combine and organize your data, in isolation or with anyone else’s, via search and tagging.
  • Let other applications add more data, in a compatible and integrated way, without needing the permission or advance knowledge of the original application.
  • Explicitly allow for, and encourage, the flexible evolution of data structure conventions, similar to the way that we see evolution of tagging and hashtags.

You can read about this in the context of Tickery on the About tab.

These are the kinds of ideas that people have recently been writing about as the future of data. For example, see some of these articles: The Future: Operating System And Application-Neutral Data, We need a Wikipedia for data, Can Twitter Survive What is About to Happen to It?, Shared data services – the next frontier?, and Robert Scoble’s Twitter to turn on advertising β€œyou will love” (here’s how: SuperTweet). While you’re at it, you might enjoy Scoble’s article The unfundable world-changing startup, which he wrote about Fluidinfo a year ago.

Stay tuned, there’s much more to come. If you’d like to find out how to write programs that can augment and use the data Tickery has stored in FluidDB, have a read of Tickery, for programmers.

Meanwhile, have fun with Tickery! Check back here, or follow me on Twitter for more news on Tickery, FluidDB, and Fluidinfo.

December 1, 2009

Putting metadata onto tweets with Fluidinfo

Filed under: Essence,Programming — Terry Jones @ 3:37 pm

novaVarious articles have recently discussed adding metadata to Twitter tweets – see the posts by Nova Spivack, Robert Scoble, and Dave Winer (who also suggests we need a programming language built into a Twitter client).

These are the sorts of things that Fluidinfo was designed to support, and you can do them today. If you want a password to start playing with the Fluidinfo API, send email to api at fluidinfo dot com and we’ll set you up.

In the meantime, here are some examples. I’m doing this at the iPython command line, using the Fluid Object Mapper (FOM) library, written by Ali Afshar. FOM provides a natural way to work with Fluidinfo objects, namespaces, tags, etc. But you could use any client-side software you like. The Fluidinfo API is just HTTP.

First, let’s get a connection to Fluidinfo:

from fom.session import Fluid

fdb = Fluid()
fdb.db.client.login('terrycojones', 'PASSWORD')
fdb.bind()

That last line is a bit of internal FOM magic that makes interactive use simpler in what follows. Ignore it for now.

To put metadata onto a tweet, we’ll first ask Fluidinfo for the object that’s about a particular tweet. Let’s take the one in the image above by @novaspivack. That tweet has a URL of http://twitter.com/novaspivack/status/4999653280. We ask Fluidinfo to give us the object “about” that URL:

from fom.mapping import Object

o = Object()
o.create('http://twitter.com/novaspivack/status/4999653280')
o.uid
>>> u'ab7fa032-06df-45be-9bb2-859c18c4d342'

The argument in the o.create call is the value of the Fluidinfo about tag. If an object with that about tag already exists, Fluidinfo gives it to us. Otherwise, a new object with that about tag is created. As you can see, the object also has an identifier (o.uid). In case you’re not familiar with Python, the “u” printed in front of the id indicates that the value is a unicode string.

This is a first point of interest. We’ve just created a Fluidinfo object corresponding to an arbitrary tweet. We didn’t ask for permission, we just did it. It’s a bit like a wiki: you can ask a wiki for its page on anything, and if no such page exists, the wiki just makes you a new one. Fluidinfo does the same thing with its objects and about tag. If you want to think about Fluidinfo in all its generality, you should now consider that the about tag above could have been for any tweet, including tweets that don’t exist (or don’t yet exist), for any URL, in fact for any string. We also could have followed Nova’s suggestion and used an about value like "twitter.com/id=4999653280". But we’re getting ahead of ourselves.

Fluidinfo has a simple query language, so let’s quickly confirm that we can find this object with a search:

fdb.objects.get('fluiddb/about = "http://twitter.com/novaspivack/status/4999653280"')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

The 200 is an HTTP OK status telling us the call succeeded, and you can see one object matched the search and that its id is as expected.

So how about some metadata? Let’s say I want to add a rating to the object. Here’s a bit of one-time setup. First I get my top-level namespace (which corresponds to my Fluidinfo user name). Then I create a new tag called rating in that namespace:

from fom.mapping import Namespace

ns = Namespace('terrycojones')
ns.create_tag("rating", "A tag for Terry's ratings.", False)

The False argument is telling Fluidinfo that I don’t want the tag to be indexed. Ignore that for now.

The magic of FOM lets us directly examine the tag using Python attributes. So you can get the tag and see its description like so:

rating = ns.tag('rating')
rating.description
>>> u"A tag for Terry's ratings."

At this point we have a new tag, or an abstract tag if you prefer, but we haven’t actually tagged any objects with it. So let’s tag the object we created above for Nova’s tweet:

o.set('terrycojones/rating', 6)

That was pretty easy! The Fluidinfo object that’s about Nova’s tweet now has some metadata on it, a ‘terrycojones/rating’ tag, with a value of 6. Let’s make sure we can get that value back:

o.get('terrycojones/rating')
>>> (6, None)

We get a 2-tuple whose second value is None when the tag’s value is a primitive Python type (in this case an integer).

Let’s do a couple of quick searches for objects with terrycojones/rating tags:

fdb.objects.get('terrycojones/rating = 6')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

fdb.objects.get('terrycojones/rating > 4')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

fdb.objects.get('has terrycojones/rating')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

In each case just that one object is returned, as expected. Note that the last query just tests for the presence of the tag, irrespective of the tag’s value (if any).

So there you have it: arbitrary metadata on tweets, and with a query language to help find things.

But let’s press on and see how things get more interesting.

First of all, you may have noticed that I didn’t have to deal with permissions at all in the above. I was able to create the Fluidinfo object about Nova’s tweet and to tag it without asking permission. In Fluidinfo that’s always the case.

But there is a permissions system. Let’s log in as a different user and try a few things to see how it works. First, I’ll log in as njr another user whose password I happen to know:

fdb.db.client.login('njr', 'PASSWORD')

The njr user is actually Nicholas Radcliffe who has written several great introductory articles about Fluidinfo over at About Tag.

Let’s try (as Nick) getting the terrycojones/rating tag from the object for Nova’s tweet:

o.get('terrycojones/rating')
>>> (6, None)

That still works, so we can infer that the terrycojones/rating tag is readable by the njr user. Let’s log in as terrycojones again and have a look at the permissions:

fdb.db.client.login('terrycojones', 'PASSWORD')
fdb.permissions.tag_values['terrycojones/rating'].get('read')
>>> (200, {u'exceptions': [], u'policy': u'open'}

We’ve asked Fluidinfo for read permissions on tag values for the tag terrycojones/rating. The result is a general policy (open), with exceptions (currently empty). Now I’ll put the njr user into the exceptions list, and confirm the result:

fdb.permissions.tag_values['terrycojones/rating'].put('read', 'open', ['njr'])
>>> (204, None)
fdb.permissions.tag_values['terrycojones/rating'].get('read')
>>> (200, {u'exceptions': [u'njr'], u'policy': u'open'}

The 204 status above is just the HTTP way of telling us that the call succeeded and that the reply has no content (as expected).

Now let’s reconnect as njr and try getting the terrycojones/rating tag again:

fdb.db.client.login('njr', 'PASSWORD')
o.get('terrycojones/rating')
>>>

You can see we got nothing back. If FOM handled non-OK HTTP responses a little more carefully, you’d see that this request actually got a 401 (Permission Denied) status. Fluidinfo is now refusing to let njr read the tag.

Nick already has a rating tag, called njr/rating, so let’s go get it, make sure there’s not one already on our object, and then tag our object with it:

ns = Namespace('njr')
rating = ns.tag('rating')
o.get('njr/rating')
o.set('njr/rating', 4)
o.get('njr/rating')
>>> (4, None)

Now things are getting interesting. We have tags from different users on the same object. That’s part of the point of Fluidinfo and its where the value comes from: putting information together allows you to do nice things, like query on it. After re-connecting as terrycojones, I can now do queries like this:

fdb.objects.get('terrycojones/rating > 5 and njr/rating > 3')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

fdb.objects.get('terrycojones/rating > 5 and njr/rating < 3')
>>> (200, {u'ids': []})

fdb.objects.get('has terrycojones/rating and njr/rating >= 4')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

fdb.objects.get('has terrycojones/rating and has njr/rating')
>>> (200, {u'ids': [u'ab7fa032-06df-45be-9bb2-859c18c4d342']})

fdb.objects.get('has terrycojones/rating except has njr/rating')
>> (200, {u'ids': []})

There’s a lot more I could do too, like giving Nick permission to add terrycojones/rating tag to objects. By the way, Nick has written some nice articles about the Fluidinfo permissions model. See Permissions Worth Getting Excited About and The Permissions Sketch.

For a final look at metadata, let’s put something totally different onto our object:

ns = Namespace('terrycojones')
page = ns.create_tag("page", "Terry's page tag.", False)
o.set('terrycojones/page', 'hiHello there!', 'text/html')

I’ve just made a new tag called terrycojones/page and tagged our object with it. What’s different here is that the value is a string, and I’m passing a MIME type with it. If I retrieve the value of the tag on the object, you’ll see the MIME type comes back too:

o.get('terrycojones/page')
>>> ('hiHello there!',
 'text/html')

and as you might hope, if you go get that tag from that object using a browser, the MIME type is returned in the HTTP Content-type header, so you end up with a real web page, with a predictable URL. Try clicking: http://fluiddb.fluidinfo.com/objects/ab7fa032-06df-45be-9bb2-859c18c4d342/terrycojones/page. We can do the same for any MIME type at all – including ones you invent for your own convenience.

So there you go. That’s metadata on tweets. With a permissions model, with a query language, with user identity, with the freedom to add anything you want, and with typed data. We don’t need a new programming language for doing this sort of thing. What we need is a better data architecture.

Fluidinfo was designed with exactly this kind of use in mind. And it’s not specific to Twitter or tweets, or anything in fact. So you can put metadata onto anything you like, search on it, continue to own/control your own data, combine it as you like, and get data in and out using a simple HTTP API.

This is all live. It’s up and running, you can do this today. I should also add that Fluidinfo is still an early alpha, and is not yet particularly fast. For more information on Fluidinfo, start with the high-level description and if you’re a programmer, read the API docs.

Next time I’ll show you how we’re putting metadata onto Twitter users, and how you can too, of course! I might also start to talk about Tickery, our upcoming Twitter query application.

If you like all this, please pass on this article. We’d love to get the word out about Fluidinfo. It’s a little difficult from Barcelona.

November 12, 2009

Why are Post-it notes sticky?

Filed under: Essence — Terry Jones @ 1:26 am
Image: PabloBM

Image: PabloBM

[Update: it has been politely pointed out (in the comments following this post) by David Semeria that the Post-it note analogy to FluidDB came from him, not me!]

It’s a pretty simple question, but you may have never thought about it directly. It’s the stickiness of Post-it notes that makes them so extraordinarily useful. The stickiness allows us to put a note in the place that makes the most sense, in the place where its information will be in context, and where it will have the greatest utility.

That’s trivial, agreed, but I nevertheless find it interesting and instructive.


Image: someToast

Image: someToast

Using Post-it notes we can add information to things in a very wide range of ways. The information might be about the thing to which it’s attached, or the object might just be something we anticipate being encountered at a relevant future moment.

How often do people ask for permission to attach a Post-it note to an object? Probably not very often. I’ve certainly never done it.

Image: someToast

Image: someToast

The information on the Post-it note can’t be presented by the object the note is on. If the object had been designed to carry that information, there’d be no need for a Post-it note. So Post-it notes are almost by definition for adding information to things in unanticipated ways.

And as for the content of Post-it notes – that’s clearly highly unpredictable. I’ve illustrated this posting with some fun examples.

Image: _nickd

Image: _nickd

It’s very useful to be able to put information in its most natural or useful place. We do it all the time. The other day I returned to my apartment and taped to the inside wall of the elevator was a form for the neighbors of my building to enter their gas meter readings. The elevator was the perfect place for the notice. But it certainly wasn’t designed for that purpose. The representative of the gas company didn’t ask permission, they just taped up the form.

Image: Iain Farrell

Image: Iain Farrell

I love thinking about how we work with information in the real world – especially the kinds of things we do so frequently or naturally that we barely notice them.

Image: wrestlingentropy

Image: wrestlingentropy

All of which brings me, inevitably, to FluidDB. As I’ve mentioned before several times, FluidDB objects have no owner. That means that anyone can put the digital equivalent of a Post-it onto anything they like, for whatever purpose, without asking for permission, and without anyone having to anticipate that they would want to do so.

Image: mulmatsherm

Image: mulmatsherm

That’s all I’ll say for now, as I’m trying to keep this short. I hope it will be thought provoking. Think about how tightly controlled, how unspontaneous, and how awkward our typical computational experiences are. There’s a reason for that, and it’s rooted in information architecture. Think about how Post-it notes, in a simplistic but important way, make the world writable. And then, for extra points, think about FluidDB πŸ™‚


I can’t resist one final image.

Image: Mr.Thomas

Image: Mr.Thomas

October 4, 2009

Digital hobgoblins

Filed under: Essence — Terry Jones @ 4:02 am

hobgoblin-hallMuch of the thinking behind FluidDB comes from thinking how we work with information in the real world, and comparing that to how we do so in the computational world (aka Hobgoblin Hall). The differences are striking.

Over the years, I’ve often asked myself why things are so bizarre in the computational world and why we don’t do something about it. Without going into the answers to those questions, I’ll just say that I think we’ve all grown up in Hobgoblin Hall and despite the fact that we’re all perfectly familiar with the freedoms of the outside world, we take it for granted that things are deeply weird in our computational homes.

Here I’ll quickly outline a few of the more glaring oddities. (BTW, I’d be remiss not to point out that FluidDB has none of the following restrictions.)

Things must be named, and have one name. In the real world we have plenty of things that don’t have names. As I look around my desk right now, I can see dozens of things that don’t have names. We also often give things many names – first names, surnames, nicknames, abbreviated names, English/Spanish/Chinese/etc names. Flexibility in naming (no names, one name, multiple names, private names, etc) is obviously of great utility. Yet in computational systems we’re usually compelled to name things, and we’re restricted to a single name. These are just a couple of the problems I have with file systems – I have about 10 others, but will spare you.

Inconsistency and ambiguity are common in the real world. While they’re obviously often not helpful, there are times when it is very useful to have both. Things may become clearer over time. Systems evolve. In the natural world we use representations that allow high degrees of inconsistency and ambiguity, and it’s very useful to be able to do so – how else would we learn or get anything accomplished if not? Yet if you suggest a computational system that explicitly allows for any level of inconsistency and ambiguity in information, people start to get nervous or even upset. They’ll begin to argue with you, and suggest ways to “fix” the system to get rid of the undesirable qualities. Why is that?

Multiple organizations of the same information are very common in the natural world. We do it all the time. Computationally it’s rare that systems allow us to multiply organize things. That’s changing, thankfully, with the rise of tagging and with music collection software that allows multiple simultaneous playlists (or “smart” dynamic playlists) of the same underlying sound files. But those systems are the exception rather than the rule.

There’s an obsession with “meaning” and pinning down what things are “about” in the computational world. In the real world we don’t seem to care that much – we’re more concerned with utility. What’s a book for? Something to read? Something to stop other objects from blowing away? Something to be hollowed out to hold a gun? Something to create an intellectual impression? A decoration? Something to hold up other books? A hiding place? A book can be all these things, and we can move seamlessly between them. What’s a glass for? Is it a weapon? Something we can hold to the wall to hear a conversation? Something to use as an insect trap? A fingerprint capturing device? A musical instrument? Maybe even something to drink out of? We don’t really know, and it’s not important to know. We don’t obsess over the “meaning” of a glass or try to determine what single thing it might be “about” etc. We just use it as we see fit. Similarly we can’t anticipate how people will want to use information – and our storage architecture shouldn’t try. (You could counter by pointing out the FluidDB about tag. But usage of the about tag is entirely optional. It’s a convenience. You can make your own, or use none at all. And a FluidDB object can be about whatever you think it’s about and used for whatever you want to use it for – even if others have completely different interpretations of and uses for the same object. No problem.)

Later (meta?) data is often most usefully put with the original data. That’s what we commonly do in the real world. It’s convenient, easy, useful, and natural. For example, when you’re reading a book and you want to remember what page you’re up to, you can simpy dog-ear the page or insert a bookmark. The extra information travels with the book. In the computational world you can’t do things like that unless a programmer has anticipated that you might want to and made provision for the extra information in the underlying data structure (or database). So we’re very often forced to put extra unanticipated information elsewhere – e.g., in a file, in our heads. Unfortunately, that later information is often the most important – because it’s generated by individuals who are trying to customize or personalize their computational world. I’ll have much more to say about that another time. For now: a writable architecture like FluidDB does not have this limitation because you can always put the new (meta?) information with the old (content?). And search on it, etc. That offers a fundamental change in how we work with information. I’ll blog about it at length one of these days. You get to think about it in the meantime πŸ™‚

« Newer PostsOlder Posts »

Powered by WordPress