• BNRPersistence

    Friday, July 16, 2010

    One of the things that's bugged me about Pear Note for a long time is that search took way too long. Search is one of those things that should be instant while you're typing. The reason it was slower was that it was querying Spotlight as you type. Spotlight has gotten faster through the years, but it's still not in the league I wanted for speed. So, I started trying out ways to speed this up. Soon, it became apparent that the way to go was to keep my own database of Pear Note documents to search, rather than rely on Spotlight on the fly.

    The obvious choice for a local database on the Mac would be to use Core Data. I've never used it before, but it's supported by Apple and would likely suffice. However, a few months ago, I attended NSConference in Atlanta, and heard Aaron Hillegass talk about his new project, BNRPersistence. I'd previously heard Aaron talk about some of the issues with Core Data on a podcast, and at NSConference Aaron unveiled this project to do something about it.

    BNRPersistence is a set of local persistence classes built on top of Tokyo Cabinet and Tokyo Dystopia. Tokyo Cabinet is one of the no-SQL databases that are gaining popularity these days. Aaron demoed BNRPersistence at NSConference and I took one thing away from his demo - it's crazy fast. Orders of magnitude faster than Core Data.

    So, I set out to try both BNRPersistence and Core Data out. That's when I discovered BNRPersistence's next major advantage - it's really simple. By the time I had started wrapping my head around managed object contexts and data models in Core Data, I had everything working in BNRPersistence. Objects being stored just need a pair of methods (very similar to complying with NSCoding), and almost the entire API for interacting with the object store is described in the short README. Once I had things working, I confirmed that indeed, BNRPersistence is crazy fast. So, I stopped delving into Core Data and started integrating BNRPersistence into Pear Note.

    It definitely does show its immaturity at times, so there are some drawbacks:

    • It's not thread safe at all, so you have to make sure you lock appropriately or stick to a single thread for store access.
    • There aren't many convenience methods, but that contributes to the simplicity of the API.
    • Getting Tokyo Cabinet and Tokyo Dystopia installed and usable for multiple architectures was a bit of a pain, but I'll take a bit of administrative pain if it makes the code simpler and easier to write.
    • Tokyo Cabinet stores have a very large disk footprint for what they store. For me, this wasn't a big deal as I'm only storing a search cache in it, but I'd have to do some testing before using it for a document format.

    All that said, I think BNRPersistence is a great project and am happy I chose to use it. Once Pear Note 2 comes out in a couple weeks, you can all see it in action and judge for yourself.

  • Premium computers are not dying off

    Saturday, May 1, 2010

    This post is a response to this post by Charlie Stross and the discussion that it has prompted across the Internet. I don't entirely understand why people across the web are nodding their heads in agreement with this. I presume that most people are struggling to understand some of Apple's recent moves, and any explanation will do. That said, this line of thinking should be strangely familiar to all of us from a few years ago.

    Charlie's basic points seem to be:

    1. The future of computing is Software as a Service (SaaS), content on the Internet, and data in the Cloud
    2. Because of this, desktop computers will become a commodity market, margins will disappear, and hardware will become much less profitable
    3. Desktop computer makers (e.g. HP, Dell, etc.) are doomed
    4. Apple is in even worse shape since they make premium computers and no one will want to pay for premium hardware to access the same Internet services
    5. Apple has decided the way forward is to stop focusing on hardware sales and instead create an ecosystem where they control access to content, since that's where the money is

    Anyone else feel like it's 10 years ago? All the money is going to be in SaaS, and hardware will be a commodity market like electricity. Everyone will only care about getting the cheapest computer possible to access all the wonderful content and services. This shift keeps getting predicted, despite the fact that the real world seems to indicate the opposite shift.

    You need look no further than Apple's latest quarterly results to see that Apple's focus is on making money on hardware. Mac and iPhone sales are way up, and that's been the story for some time. These premium computing devices that are theoretically dying off are becoming more and more popular.

    You can see this around you as well. More and more people are paying attention to what devices they purchase and choosing to spend more money to get something they deem better. Sure, there will always be a market segment that just wants whatever is on sale at Best Buy, but the segment that is willing to pay for something nicer is the one that is growing. That's why Apple has been so successful over the past decade. More people are choosing to pay for a premium product.

    Apple knows this, and that is why they are moving into more and more hardware segments (phones, tablets). They want to be the premium brand in all these segments that discerning customers choose. Content and software are mostly important because they help drive hardware sales (though they're happy to take money there as well).

    Apple doesn't want Flash or other cross-platform tools used with the iPhone because their worst nightmare is a world where the user experience on an iPhone is no different from an Android phone. That would take away their ability to charge a premium for their hardware. It really is that simple. Imagining that this is part of a larger shift in Apple from making money selling their hardware to making money on content/software distribution is just an effort to rehash failed predictions from 10 years ago.

  • A bit of style

    Saturday, February 13, 2010

    I finally got around to adding a bit more design to this blog (but only a bit). So, instead of the boring grey of before, there's a bit of color and even a bit of a picture I took. If you're looking at the site right now, you already know this, but I wanted to post for those just reading the feed. Let me know what you think and anything that's broken.

  • Scripting QuickTime's web plugin

    Sunday, February 7, 2010

    I'm not much of a web programmer. I can usually hack things together, but I've never done anything serious. What I have done has largely been server-side, so I'm basically a noob when it comes to JavaScript. That said, I really want to get Pear Note to the point where users can share their notes with others that don't use Pear Note. The best possibility for that is obviously the web, so I've been digging into JavaScript.

    Pear Note records to QuickTime movies, and QuickTime is commonly found in users' web browsers. So, I started looking into scripting QuickTime to link its playback with some text (like Pear Note does). I of course stumbled a bit due to my lack of experience, but things went fairly smoothly. I followed some of the examples in Apple's documentation, used their AC_QuickTime.js script to embed the movie in a cross-browser way, and things eventually started working. I'd been testing in Safari (my standard browser), so I then tested in Firefox. There were a couple of little things that Safari had been forgiving on, but after a quick fix it worked in Firefox as well.

    Then I tested in IE...

    Neither IE7 nor IE8 worked at all (I didn't even try IE6). Per the Apple example, if the movie was named aMovie, I addressed it as document.aMovie. IE said that document had no such property, despite Apple's documentation saying this would work. I walked through the DOM tree and found the <object> for the movie, and things started working when I used that instead. The code I used to search for the movie is essentially:

    var movie = false;
    
    function searchForMovie(node) {
    	if (node && node.childNodes) {
    		for (var i=0;i<node.childNodes.length;i++) {
    			var el = node.childNodes[i];
    			if ((typeof el === "object") && el.tagName && /^object$/i.test(el.tagName)) {
    				if (el.GetMovieName() === "aMovie") {
    					return el;
    				}
    			}
    			var childResult = searchForMovie(el);
    			if (childResult !== false) {
    				return childResult;
    			}
    		}
    	}
    	return false;
    };
    
    function getMovie() {
    	if (movie === false) {
    		if (document.aMovie) {
    			movie = document.aMovie;
    		}
    		else {
    			var searchResults = searchForMovie(document.body);
    			if (searchResults !== false) {
    				movie = searchResults;
    			}
    		}
    	}
    };
    

    getMovie() first checks to see if there is a document.aMovie. If not, it will call searchForMovie() on the <body> element, which calls itself recursively until it finds an <object> with a movie name of aMovie. If it finds anything, it sets a variable (movie) to save the node for use by other functions later.

    It's obviously a complete hack. It assumes that the only <object> tags will be QuickTime movies. I could not find a useful way to test if an <object> was actually a QuickTime movie or something else. So, if you're struggling with this as I was, know that there is hope and this is one way to script QuickTime in IE. If you're an experienced web developer and shaking your head at how badly I did this, please leave a comment or shoot me an email to tell me how I should have done this.

  • Indie+Relief

    Wednesday, January 20, 2010

    Unless you've been disconnected for the past week, you've likely heard about the destruction in Haiti. A bunch of us Mac developers have gotten together and decided to give all of our income from sales today to relief efforts. So, if you're a Mac user, please check out Indie+Relief and consider buying some great software and supporting a great cause. You can read more about what my personal side of this at my company blog.

  • A new compiler

    Saturday, January 16, 2010

    I know many of you switched to Clang/LLVM the second it shipped with Snow Leopard, but I've been a bit timid with regard to that switch. So, I've been merrily compiling Pear Note with gcc 4.2 until very recently. A few weeks ago, after listening to the MDN Show episode 15 in which Danny Greg praises it and Kevin Hoctor gives John Fox a hard time about not switching to it, I decided to give it a go.

    I had actually tested Clang/LLVM out a few months ago just to see what problems it would find with my code. It found around 80 issues, which I fixed, but I kept building with gcc, fearing the unknown of a new compiler.

    After hearing that other devs had made the switch long ago in their production code, I decided to give it a go. To be clear, I switched to using what Apple is shipping with the Snow Leopard developer tools. Apple calls this Clang LLVM 1.0 (I'm not sure where that version number came from). So, I made the switch for Pear Note 1.4 (the current 1.4 beta is built using Clang/LLVM).

    Since the switch, I have not hit any problems. I was worried that given how new the tools were there might be little bugs. Working around compiler problems is a pain, but I have not found any problems with using Clang/LLVM.

    Is it faster?

    There are two sides to performance improvements - faster code produced by the compiler and faster compilation. I really can't tell if the code produced is any faster. Given that Pear Note is a user application and most of the computationally intensive operations (encoding video, etc.) occur in shared libraries rather than Pear Note itself, it's not immediately apparent whether the code is faster. I could have written a test application that used some of the model code from Pear Note and tested it with both compilers, but I wasn't that motivated.

    Compilation speed is a different story. It was immediately obvious that Clang/LLVM was much faster building Pear Note than gcc was. Doing some tests, build time dropped from an average of 60 seconds with gcc to an average of 32 seconds with Clang/LLVM. That's especially impressive when you consider that much of the build involves many pieces that will not change with this switch (building nibs, python and shell scripts, the preprocessor). Given that, it appears that Clang/LLVM is much more than twice as fast as gcc. And remember that this is Clang/LLVM 1.0. My understanding is that Clang/LLVM tip-of-trunk is much faster than this, so more improvements are on the way.

    The moral of the story here is Clang/LLVM is good stuff. It gives you much more useful and more plentiful warnings/errors and it builds much faster than gcc. If you're a Mac developer and you're building on Snow Leopard (though you can still target earlier OS releases, as I'm targeting 10.5), you should at least try it out.

  • A blog app in Django

    Sunday, January 3, 2010

    As I said in the previous post, this blog is not using Wordpress. In fact, it's not using any commonly available blog application. Instead, I wrote my own blog app for it in Django. Yes, it is generally a stupid idea to rework the wheel when there are other more capable apps with fewer bugs out there, but I did have a couple of good reasons:

    • I have very little experience in web development. I have some upcoming projects planned, but I'd really rather get my feet wet in something less critical. A simple blog application seemed perfect.
    • I've had my eye on Django for some time and wanted to try it out, but never had a good reason to do so. This seemed like a good reason.
    • I was tired of having to upgrade Wordpress constantly.

    My opinion of Django so far

    I chose to use Django because I've come to like a lot of the ideas behind Rails, but I just can't seem to become a fan of ruby. Perhaps I've been using python for too long, but ruby just doesn't feel right to me. Django seems to be the leading competitor to Rails, and uses python, so it seemed like a great choice.

    So far, I very much like Django. It seems to be a very well designed framework and makes many things easy without making anything impossible. The model layer abstracts database access very well, and URLConf makes laying out where things are very easy. Deploying apps, while not as easy as a php app, is not bad at all with mod_wsgi. There are a couple of things I'm not a fan of, but I can certainly live with them. For instance, I wish I could put python code in templates the way you can put ruby code into Rails templates. I get that this was done intentionally to ensure that I don't break MVC separation (which it did ensure as I was developing this blog), but sometimes I'd prefer to have a little more rope to hang myself with.

    That said, I've very much enjoyed using Django and look forward to continuing to use it in the future. It's integration with Google's App Engine is especially appealing, so hopefully it will become a more comfortable tool in my tool belt soon.

    Practical tips

    For anyone getting started with Django, here are a few practical tips that I discovered during this project:

    • Django, CentOS 5, and MySQL don't play nicely together by default. CentOS includes MySQL-python 1.2.1, which is too old to use with current versions of Django (I'm using 1.1.1). I could have tried to build a newer version of MySQL-python (though I'd need to make sure it would work with the python 2.4 that comes with CentOS 5), but instead I just switched to using PostgreSQL, which I already had set up and works just fine. Since the model layer abstracts the database so well, I just had to change a couple of lines in the settings file to switch to PostgreSQL.
    • The Big Nerd Ranch has some very nice Coda modes for Django. I've specifically liked the template mode.
    • If you use the django.contrib.syndication app to create RSS feeds (which works quite well), make sure you change the name of the default site in the Sites app. By default, it will be example.com, and this will be used in your RSS feed links if you don't change it to the appropriate domain name.

    It took me about a day (spread over a 3 day weekend) to write this blog app, and I'm pleased with the results. I'm sure I'll keep hacking on it for some time, but Django will hopefully make that pretty easy.

  • A blog

    Sunday, January 3, 2010

    I've been putting off creating a blog for all of my tech thoughts for some time. There always seemed to be more important things to do. As is evidenced by this blog, I've finally given up. As time has gone on, I've found I've had more and more to say, as well as fewer and fewer people who are willing to put up with me babbling on about the problem I just solved in the QTKitCapture frameworks or how cool Django is. So, I've given in and joined the masses that have been blogging for years. I guess I technically have been blogging for years (I'm certainly still managing several Wordpress installs, though this site is not running on Wordpress), but I've never had a place to voice my tech thoughts. As of right now, that's no longer true.

    I'm looking forward to seeing where this site goes. I'm guessing it will mostly be Cocoa/Mac development focused, but I don't want to contain myself. Hopefully you mythical future readers find it helpful.

Post 1-8 of 8

My links: Useful Fruit Software | c_had at Twitter

Contact
About

Copyright Chad Sellers 2010