<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Keepers of the Lazy Guns</title>
	<atom:link href="http://www.thelostsouls.org.uk/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.thelostsouls.org.uk</link>
	<description>Programming, Computing, Life, Photographs and more..</description>
	<lastBuildDate>Sat, 15 Oct 2011 23:00:57 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
		<item>
		<title>Progress with adding iCloud to Chef&#8217;s Book.</title>
		<link>http://www.thelostsouls.org.uk/2011/10/progress-with-adding-icloud-to-chefs-book/</link>
		<comments>http://www.thelostsouls.org.uk/2011/10/progress-with-adding-icloud-to-chefs-book/#comments</comments>
		<pubDate>Sat, 15 Oct 2011 16:56:00 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Chef's Book]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Core-Data]]></category>
		<category><![CDATA[icloud]]></category>
		<category><![CDATA[iOS]]></category>
		<category><![CDATA[migrations]]></category>
		<category><![CDATA[news]]></category>
		<category><![CDATA[objective-c]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=478</guid>
		<description><![CDATA[There are some interesting challenges with incorporating iCloud support, especially into an existing application. One, which I&#8217;ve been working through, is that you can no longer copy in a pre-existing store for the purposes of loading data. Such a move appears to work but does not upload anything to the cloud, the cloud store will [...]]]></description>
			<content:encoded><![CDATA[<p>There are some interesting challenges with incorporating iCloud support, especially into an existing application. One, which I&#8217;ve been working through, is that you can no longer copy in a pre-existing store for the purposes of loading data. Such a move appears to work but does not upload anything to the cloud, the cloud store will only see future changes and not have the initial data set.<br />
The solution to this is to use NSPersistentStoreCordinator&#8217;s <a href="http://developer.apple.com/library/mac/documentation/cocoa/reference/CoreDataFramework/Classes/NSPersistentStoreCoordinator_Class/NSPersistentStoreCoordinator.html#//apple_ref/occ/instm/NSPersistentStoreCoordinator/migratePersistentStore:toURL:options:withType:error:">migratePersistentStore:toURL:options:withType:error</a> method. However I found the documentation somewhat lacking in clarity so here is the solution that now appears to be working for me.</p>
<p>There are some things I wanted to guarantee, which are probably not applicable to many so I&#8217;ll document them here:</p>
<p>- The application has gone through a few object model changes and I wanted to support people that may have skipped versions.<br />
- The application&#8217;s data store location has changed on one occasion, when I moved the store out of Documents and into the Library directory due to adding iTunes document sharing.</p>
<p>Before we look at the code we&#8217;ll have a look at a rough outline of the procedure, in handy bullet points, step is 4 is the one that took some figuring out:</p>
<ol>
<li>Run everything following this asynchronously.</li>
<li>Determine location of any existing stores, if not default to initial data set.</li>
<li>Check to see if application supports iCloud, e.g. is running iOS 5.</li>
<li>Configure store options if it does support iCloud.</li>
<li>Lock the persistent store coordinator.</li>
<li>If there is a cloud data set already, simply add it.</li>
<li>If there isn&#8217;t DON&#8217;T add it, the migrate function adds it.</li>
<li>Unlock persistent store coordinator.</li>
<li>Send messages out so that view controllers that need to can redo their fetches.</li>
</ol>
<p>A few caveats about the following, it&#8217;s not tested aside from ensuring it does migrate data into the store.  I&#8217;ve not yet verified that the data then careers across the cloud to another device but I&#8217;ll update the post as soon as I do.</p>
<p>The code isn&#8217;t optimal, but that should be obvious! <img src='http://www.thelostsouls.org.uk/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' />   The method should be called where in your code you&#8217;d normally add the store.  A lot of the framework, minus the migrations stuff, is based on some example iCloud code.<br />
Also note that the if block with the &#8220;//Migrate old store to new AND migrate into cloud&#8221; comment is devoid of code.  In that block I would need to update the old store to match the new one and THEN migrate the store as I&#8217;m using my own migrations code which also allows importing of new data and a few other tweaks, which I think I&#8217;ve previously blogged.</p>
<p>CLOUD_NAME,STORE_NAME are #defines.  DLog is a #define macro to NSLog that is blank in production environments.</p>
<pre>
- (void)aSynchronouslyAddPersistentStore {
  NSString *cloudPath = [[self applicationLibraryDirectory] stringByAppendingPathComponent:CLOUD_NAME];
  NSString *preCloudPath = [[self applicationLibraryDirectory] stringByAppendingPathComponent:STORE_NAME];
  NSString *defaultStorePath = [[NSBundle mainBundle]
                                pathForResource:@"InitialData" ofType:@"sqlite"];
  NSString *oldStorePath = [[self applicationDocumentsDirectory] stringByAppendingPathComponent:STORE_NAME];

  // do this asynchronously since if this is the first time this particular device is syncing with preexisting
  // iCloud content it may take a long long time to download
  dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSURL *storeUrl = [NSURL fileURLWithPath:cloudPath];
    NSURL *migrateUrl = nil;

    /**
     Find out which store has the data we need to migrate,
     if any.
     */
    if (![fileManager fileExistsAtPath:cloudPath]) {
      if ([fileManager fileExistsAtPath:preCloudPath]) {
        // Migrate old application data.
        migrateUrl = [NSURL fileURLWithPath:preCloudPath];
      } else if ([fileManager fileExistsAtPath:oldStorePath]) {
        // Migrate old store to new AND migrate into cloud.
      } else if ([fileManager fileExistsAtPath:defaultStorePath]) {
        // Migrate (copy) in initial recipe data set.
        migrateUrl = [NSURL fileURLWithPath:defaultStorePath];
      }
    }

    // this needs to match the entitlements and provisioning profile
    NSURL *cloudURL = nil;
    if([fileManager respondsToSelector:@selector(URLForUbiquityContainerIdentifier:)])
    {
      cloudURL = [fileManager URLForUbiquityContainerIdentifier:nil];
      NSString* coreDataCloudContent = [[cloudURL path] stringByAppendingPathComponent:@"chefsbook_v14b3"];
      cloudURL = [NSURL fileURLWithPath:coreDataCloudContent];
      DLog(@"cloudURL : %@", cloudURL);
    }

    //  The API to turn on Core Data iCloud support here.
    NSDictionary *options = nil;
    if (cloudURL) {
      options = [NSDictionary dictionaryWithObjectsAndKeys:
                 @"com.thelostsouls.chefsbook", NSPersistentStoreUbiquitousContentNameKey,
                 cloudURL, NSPersistentStoreUbiquitousContentURLKey,
                 [NSNumber numberWithBool:YES], NSMigratePersistentStoresAutomaticallyOption,
                 [NSNumber numberWithBool:YES], NSInferMappingModelAutomaticallyOption
                 ,nil];
    } 

    NSError *error = nil;
    [persistentStoreCoordinator_ lock];
    DLog(@"Persistent Store ****LOCKED****");

    /**
     If I migrate url is set don't just add, migrate!
     Otherwise proceed as planned.
     */
    if (migrateUrl) {
      NSPersistentStore *srcPS = [persistentStoreCoordinator_ addPersistentStoreWithType:NSSQLiteStoreType
                                                configuration:nil
                                                          URL:migrateUrl
                                                      options:nil
                                                        error:&#038;error];
      if (![persistentStoreCoordinator_ migratePersistentStore:srcPS
                                                         toURL:storeUrl
                                                       options:options
                                                      withType:NSSQLiteStoreType
                                                         error:&#038;error]) {
        DLog(@"Error migrating data: %@, %@", error, [error userInfo]);
        abort();
      }
    }
    else
    {
      if (![persistentStoreCoordinator_ addPersistentStoreWithType:NSSQLiteStoreType
                                                     configuration:nil
                                                               URL:storeUrl
                                                           options:options
                                                             error:&#038;error]) {
        DLog(@"Error adding persistent store: %@, %@", error, [error userInfo]);
        abort();
      }
    }
    [persistentStoreCoordinator_ unlock];
    DLog(@"Persistent Store ****UNLOCKED****");

    // tell the UI on the main thread we finally added the store and then
    // post a custom notification to make your views do whatever they need to such as tell their
    // NSFetchedResultsController to -performFetch again now there is a real store
    dispatch_async(dispatch_get_main_queue(), ^{
      DLog(@"asynchronously added persistent store!");
      [[NSNotificationCenter defaultCenter]
       postNotificationName:AppDelegateSharedPSCAddedStore
       object:self userInfo:nil];
    });
  });

}
</pre>
<p>So there you go.</p>
<p>Still a worry are scenarios where iCloud support is enabled/disabled and/or the data deleted from the cloud via the settings menu.  Hopefully nobody would do that and leave iCloud enabled or they&#8217;d end up with an empty application and no recovery.  That&#8217;s also the reason I&#8217;m still supporting and improving the code that saves the docs out to iTunes.</p>
<p>Another thought just occurred to me.  The following scenario needs serious consideration:</p>
<ol>
<li>User starts app with iCloud support, initial data set loaded.</li>
<li>User proceeds to add a handful of data.</li>
<li>User installs Chef&#8217;s Book on second device with iCloud enabled for app.</li>
<li>App starts and copies in default data PLUS receiving iCloud data.</li>
</ol>
<p>Will it fail, magically know it&#8217;s the same (eminently probable), or duplicate data?</p>
<p>Time to find out!</p>
<p>-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=</p>
<p>Well I found out, it hangs permanently.  Thanks to some helpful people on the apple forums I know why.  So the above code is only partially correct.  What needs to be done is to also query data on the cloud using NSMetadataQuery and examine the results, if there is cloud data you should use that and not add a persistent store in the normal way (I guess?).  What I now need to find out, having successfully been able to query the cloud and find LOTS of data on there from my previous tests, is how you should add that data.  </p>
<p>Then I&#8217;m going to rewrite the entire core data start up code from the bottom up.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/10/progress-with-adding-icloud-to-chefs-book/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
		</item>
		<item>
		<title>Fun with bash and old photo libraries.</title>
		<link>http://www.thelostsouls.org.uk/2011/08/fun-with-bash-and-old-photo-libraries/</link>
		<comments>http://www.thelostsouls.org.uk/2011/08/fun-with-bash-and-old-photo-libraries/#comments</comments>
		<pubDate>Mon, 15 Aug 2011 09:17:51 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Computer]]></category>
		<category><![CDATA[Photography]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[aperture]]></category>
		<category><![CDATA[backups]]></category>
		<category><![CDATA[bash]]></category>
		<category><![CDATA[photos]]></category>
		<category><![CDATA[recovery]]></category>
		<category><![CDATA[script]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=474</guid>
		<description><![CDATA[It recently dawned on me I had huge swathes of my photo collection entirely gone. Something like 3 years that were nowhere to be found on flickr or my main PC or Mac. I&#8217;m not sure how this gap appeared but I eventually found the files in a backup of my Mac from quite some [...]]]></description>
			<content:encoded><![CDATA[<p>It recently dawned on me I had huge swathes of my photo collection entirely gone.  Something like 3 years that were nowhere to be found on flickr or my main PC or Mac.  I&#8217;m not sure how this gap appeared but I eventually found the files in a backup of my Mac from quite some time ago (I keep everything until I really need the space).  Problem was it was in an old Aperture directory structure and I really just wanted to get the pictures out and sort through them from scratch.  I&#8217;d used different cameras, some of the pictures weren&#8217;t mine etc. etc.</p>
<p>So to sort through it all I wrote a small bash script.  First argument in quotes is the backup/source and the second argument in quotes is the destination.  It uses imagemagicks identify command and will copy the files to:</p>
<p>destination/camera model/date taken/name.count.jpg</p>
<p>count will iterate up if the file exists, if something goes wrong it will not copy the file but will print an F instead of a dot and write a log to extractPhotos.err.</p>
<pre>

#!/bin/bash
SOURCE="$1"
DEST="$2"
cd "$SOURCE"

function getSafeFilename {
    local SAFE="$1"
    local COUNT=1
    while [ -e "$SAFE" ]
    do
        local DIR=$(dirname "$1")
        local BASE=$(basename "$1")
        local NAME=${BASE%.*}
        SAFE="$DIR/$NAME.$COUNT.JPG"
        ((COUNT++))
    done

    echo $SAFE
}

# Identify all JPG images that are not thumbnails.
find . -iname *.jpg | grep -iv thumb | while read -r jpeg
do
    # Identify Model of Camera
    MODEL=$(identify -format "%[EXIF:Model]" "$jpeg" | sed 's/ *$//g')
    # Identify Date taken YYYY-MM-DD
    DATETAKEN=$(identify -format "%[EXIF:DateTime]" "$jpeg")
    DATEDAY=$(echo "$DATETAKEN" | cut -d' ' -f1)
    # Get base photo name
    PHOTO=$(basename "$jpeg")

    # Set camera model if undefined
    len=${#MODEL}
    if [[ "$len" -lt "1" ]]; then
        MODEL="Unknown"
    fi

    # Make destination directory
    DESTDIR="$DEST/$MODEL/$DATEDAY"
    if [ ! -d "$DESTDIR" ]; then
        mkdir -p "$DESTDIR"
    fi

    # Check for existing picture in that directory, if so, modify destination name, iterate if nec. (move to function)
    SAFEFILE=$(getSafeFilename "$DEST/$MODEL/$DATEDAY/$PHOTO")

    # Copy file!
    cp -n "$jpeg" "$SAFEFILE" &#038;&#038; echo -n "." || (echo -n "F"; echo "Failed: $jpeg to $SAFEFILE" >> extractPhotos.err)

    # End
    unset MODEL
    unset DATETAKEN
    unset DATEDAY
    unset DESTDIR
    unset SAFEFILE
    unset len
# End
done
</pre>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/08/fun-with-bash-and-old-photo-libraries/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Has it been nearly a month?</title>
		<link>http://www.thelostsouls.org.uk/2011/06/has-it-been-nearly-a-month/</link>
		<comments>http://www.thelostsouls.org.uk/2011/06/has-it-been-nearly-a-month/#comments</comments>
		<pubDate>Sat, 11 Jun 2011 21:50:05 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Miscellany]]></category>
		<category><![CDATA[games]]></category>
		<category><![CDATA[JA2]]></category>
		<category><![CDATA[Jagged Alliance]]></category>
		<category><![CDATA[Jagged Alliance 2]]></category>
		<category><![CDATA[Witcher]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=458</guid>
		<description><![CDATA[It&#8217;s odd, I can&#8217;t believe it&#8217;s been that long since the last post. There hasn&#8217;t really been anything to write about, no trials with code, no revelations, just fairly steady progress. In other news I&#8217;ve finished one playthrough of The Witcher 2, which is absolutely blinding. A more recent discovery is the ancient but still [...]]]></description>
			<content:encoded><![CDATA[<p>It&#8217;s odd, I can&#8217;t believe it&#8217;s been that long since the last post.  There hasn&#8217;t really been anything to write about, no trials with code, no revelations, just fairly steady progress.  In other news I&#8217;ve finished one playthrough of The Witcher 2, which is absolutely blinding.  A more recent discovery is the ancient but still utterly amazing Jagged Alliance 2.  Go buy, gog have it on sale this weekend!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/06/has-it-been-nearly-a-month/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Jagged Alliance 2 &#8211; the static universal binary.</title>
		<link>http://www.thelostsouls.org.uk/2011/06/jagged-alliance-2-the-static-universal-binary/</link>
		<comments>http://www.thelostsouls.org.uk/2011/06/jagged-alliance-2-the-static-universal-binary/#comments</comments>
		<pubDate>Sat, 11 Jun 2011 21:41:05 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Miscellany]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=454</guid>
		<description><![CDATA[Using a lot of cues from elsewhere I&#8217;ve put together a DMG containing JA2 statically linked to the necessary SDL library. It contains the data for the 800&#215;600 mod my Mythrell and still requires the game data files. More information inside: Jagged Alliance 2 &#8211; Mac Static The binary is i386 &#038; X86_64 but not [...]]]></description>
			<content:encoded><![CDATA[<p>Using a lot of cues from elsewhere I&#8217;ve put together a DMG containing JA2 statically linked to the necessary SDL library.  It contains the data for the 800&#215;600 mod my Mythrell and still requires the game data files.  More information inside:</p>
<p><a href="http://www.thelostsouls.org.uk/ja2/">Jagged Alliance 2 &#8211; Mac Static</a></p>
<p>The binary is i386 &#038; X86_64 but not PowerPC at the moment.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/06/jagged-alliance-2-the-static-universal-binary/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>The MD5 checksum bug identified.</title>
		<link>http://www.thelostsouls.org.uk/2011/05/the-md5-checksum-bug-identified/</link>
		<comments>http://www.thelostsouls.org.uk/2011/05/the-md5-checksum-bug-identified/#comments</comments>
		<pubDate>Fri, 13 May 2011 12:34:46 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Chef's Book]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[nil]]></category>
		<category><![CDATA[nsdictionary]]></category>
		<category><![CDATA[NSManagedObject]]></category>
		<category><![CDATA[nsnull]]></category>
		<category><![CDATA[null]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=442</guid>
		<description><![CDATA[Happily it&#8217;s easy to fix and exactly what I thought it was. When retrieving values from an NSManaged object like so: NSString *foo = recipe.value; or NSString *foo = [recipe valueForKey:@"value"]; If the value is not present you get a nil. Messages to nil go nowhere but do not crash, so if value should have [...]]]></description>
			<content:encoded><![CDATA[<p>Happily it&#8217;s easy to fix and exactly what I thought it was.  When retrieving values from an NSManaged object like so:<br />
<code><br />
NSString *foo = recipe.value;<br />
</code><br />
or<br />
<code><br />
NSString *foo = [recipe valueForKey:@"value"];<br />
</code><br />
If the value is not present you get a nil.  Messages to nil go nowhere but do not crash, so if value should have been an NSString the following is OK:<br />
<code><br />
[foo isEqualToString:@"bar"]<br />
</code><br />
However if the object you are retrieving from is an NSDictionary you will get an NSNull.  NSNull is a class and a valid object so sending it messages it does not understand will fail:<br />
<code><br />
NSString *foo = [dictionary valueForKey:@"value"];<br />
[foo isEqualToString:@"bar"]; // CRASH<br />
</code><br />
Seeing as I need to compute the md5 sum for a dictionary based recipe and an managed object based one and the sums need to be the same the code that produces the string to hash must produce identical results.  In the case of a null value the code to produce the key to hash from the recipe managed object inserted this:<br />
<code><br />
(null)<br />
</code><br />
The code to produce it from the dictionary simply crashed.  So I changed it in both the dictionary and the managed object routines to check:<br />
<code><br />
if ([object isEqualToClass:[NSNull class]]) {<br />
object = @"";<br />
}<br />
</code><br />
Which meant the keys changed and I didn&#8217;t update the initial data set to reflect that as I didn&#8217;t run OCUnit and thus didn&#8217;t get bashed upside the head that something had changed.</p>
<p>Always run your unit tests folks.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/05/the-md5-checksum-bug-identified/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Implementing iTunes syncing and a lesson to always run unit tests.</title>
		<link>http://www.thelostsouls.org.uk/2011/05/implementing-itunes-syncing-and-a-lesson-to-always-run-unit-tests/</link>
		<comments>http://www.thelostsouls.org.uk/2011/05/implementing-itunes-syncing-and-a-lesson-to-always-run-unit-tests/#comments</comments>
		<pubDate>Thu, 12 May 2011 23:00:16 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[App Store]]></category>
		<category><![CDATA[Chef's Book]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[document support]]></category>
		<category><![CDATA[iphone]]></category>
		<category><![CDATA[itunes]]></category>
		<category><![CDATA[synchronising]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=440</guid>
		<description><![CDATA[So the latest version of my main app is in the app store and&#8230;. it has a minor minor bug.  In a rush to eliminate a highly unlikely, in fact to pre-empt, a bug I updated some code to check for the possibility of NSNull being assigned to an NSString.  For some reason this changed [...]]]></description>
			<content:encoded><![CDATA[<p>So the latest version of my main app is in the app store and&#8230;. it has a minor minor bug.  In a rush to eliminate a highly unlikely, in fact to pre-empt, a bug I updated some code to check for the possibility of NSNull being assigned to an NSString.  For some reason this changed the md5 sum assigned to two recipes (Shepherd&#8217;s Pie and Seafood Linguine Carbonara) which means they will be duplicated for every user I expect.  Shame.  Not life ending but annoying.  I submitted the update metadata around 21:20 on Friday, the app at around 21:57.  I fixed the bug at 21:45.  I didn&#8217;t run the OCUnit tests which would have spotted the md5 checksum changing when it should not have.</p>
<p>Easy to fix though and on the upside all of this code and unit tests means development is much faster now.  So I&#8217;m well on the way to iTunes document synchronisation support.  I&#8217;ve had to relocate a plist file and the sqlite database out of documents and into library otherwise they show up in iTunes.  So all you people that write core data tutorials putting sqlite in the documents folder&#8230; stop it!  It&#8217;s not a good idea use NSLibraryDirectory instead of NSDocumentDirectory when calling NSSearchPathForDirectoriesInDomains.</p>
<p>On another note, to determine what files were new in the documents folder I thought I&#8217;d use file info, like dates etc.  Figuring that when the file is written to the iPhone by iTunes it would write a new file but it doesn&#8217;t&#8230; it preserves the host machines modified and creation dates:</p>
<pre>
      NSDictionary *fileInfo = [[NSFileManager defaultManager] attributesOfItemAtPath:filePath
                                                                                error:nil];
      NSDate *lastModified = [fileInfo valueForKey:NSFileModificationDate];

(gdb) po fileInfo
{
    NSFileCreationDate = "2011-05-09 11:30:53 +0000";
    NSFileExtensionHidden = 0;
    NSFileGroupOwnerAccountID = 501;
    NSFileGroupOwnerAccountName = mobile;
    NSFileModificationDate = "2011-05-09 11:30:53 +0000";
    NSFileOwnerAccountID = 501;
    NSFileOwnerAccountName = mobile;
    NSFilePosixPermissions = 420;
    NSFileProtectionKey = NSFileProtectionNone;
    NSFileReferenceCount = 1;
    NSFileSize = 1788192;
    NSFileSystemFileNumber = 2608135;
    NSFileSystemNumber = 234881027;
    NSFileType = NSFileTypeRegular;
}
</pre>
<p>A shame but totally understandable as the file is not being modified or created as such.  Looks like I&#8217;ll need to track a bit more metadata myself or waste time import/exporting everything every time.  Err&#8230; no.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/05/implementing-itunes-syncing-and-a-lesson-to-always-run-unit-tests/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Roger Hargreaves 76th Birthday &#8211; Google Logos</title>
		<link>http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/</link>
		<comments>http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/#comments</comments>
		<pubDate>Mon, 09 May 2011 23:18:53 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Art]]></category>
		<category><![CDATA[Miscellany]]></category>
		<category><![CDATA[Birthday]]></category>
		<category><![CDATA[Google]]></category>
		<category><![CDATA[Logos]]></category>
		<category><![CDATA[Mr. Men]]></category>
		<category><![CDATA[Roger Hargreaves]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=416</guid>
		<description><![CDATA[Google have celebrated Roger Hargreaves 76th birthday with a whole stack of Mr. Men logos. As far as I can discern from the javascript there are 16 of them, after the cut.]]></description>
			<content:encoded><![CDATA[<p>Google have celebrated Roger Hargreaves 76th birthday with a whole stack of Mr. Men logos.  As far as I can discern from the javascript there are 16 of them, after the cut.<span id="more-416"></span></p>

<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-chatterbox/' title='Little Miss Chatterbox'><img width="360" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Chatterbox.jpg" class="attachment-full" alt="Little Miss Chatterbox" title="Little Miss Chatterbox" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-curious/' title='Little Miss Curious'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Curious.jpg" class="attachment-full" alt="Little Miss Curious" title="Little Miss Curious" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-magic/' title='Little Miss Magic'><img width="368" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Magic.jpg" class="attachment-full" alt="Little Miss Magic" title="Little Miss Magic" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-naughty/' title='Little Miss Naughty'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Naughty.jpg" class="attachment-full" alt="Little Miss Naughty" title="Little Miss Naughty" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-shy/' title='Little Miss Shy'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Shy.jpg" class="attachment-full" alt="Little Miss Shy" title="Little Miss Shy" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-sunshine/' title='Little Miss Sunshine'><img width="396" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Sunshine.jpg" class="attachment-full" alt="Little Miss Sunshine" title="Little Miss Sunshine" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-little-miss-tiny/' title='Little Miss Tiny'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Little-Miss-Tiny.jpg" class="attachment-full" alt="Little Miss Tiny" title="Little Miss Tiny" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-bump/' title='Mr Bump'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Bump.jpg" class="attachment-full" alt="Mr Bump" title="Mr Bump" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-dizzy/' title='Mr Dizzy'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Dizzy.jpg" class="attachment-full" alt="Mr Dizzy" title="Mr Dizzy" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-forgetful/' title='Mr Forgetful'><img width="680" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Forgetful.jpg" class="attachment-full" alt="Mr Forgetful" title="Mr Forgetful" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-funny/' title='Mr Funny'><img width="393" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Funny.jpg" class="attachment-full" alt="Mr Funny" title="Mr Funny" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-happy/' title='Mr Happy'><img width="381" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Happy.jpg" class="attachment-full" alt="Mr Happy" title="Mr Happy" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-messy/' title='Mr Messy'><img width="370" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Messy.jpg" class="attachment-full" alt="Mr Messy" title="Mr Messy" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-rush/' title='Mr Rush'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Rush.jpg" class="attachment-full" alt="Mr Rush" title="Mr Rush" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-slow/' title='Mr Slow'><img width="432" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Slow.jpg" class="attachment-full" alt="Mr Slow" title="Mr Slow" /></a>
<a href='http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/76th-birthday-of-roger-hargreaves-mr-tickle/' title='Mr Tickle'><img width="416" height="161" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/76th-Birthday-of-Roger-Hargreaves-Mr-Tickle.jpg" class="attachment-full" alt="Mr Tickle" title="Mr Tickle" /></a>

]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/05/roger-hargreaves-76th-birthday-google-logos/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Recipe for Tunnock Cakes (Marshmallow Teacakes)</title>
		<link>http://www.thelostsouls.org.uk/2011/05/recipe-for-tunnock-cakes-marshmallow-teacakes/</link>
		<comments>http://www.thelostsouls.org.uk/2011/05/recipe-for-tunnock-cakes-marshmallow-teacakes/#comments</comments>
		<pubDate>Mon, 09 May 2011 11:37:16 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Cooking]]></category>
		<category><![CDATA[Marshmallow]]></category>
		<category><![CDATA[Teacakes]]></category>
		<category><![CDATA[Tunnocks]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=410</guid>
		<description><![CDATA[I cooked this yesterday, just a little to late to make it into the current build of the app. Either way no photos here just the basic ingredients and steps, after entering everything into the app the easiest way to just post the recipe here was to cut and paste from an app generated PDF: [...]]]></description>
			<content:encoded><![CDATA[<p>I cooked this yesterday, just a little to late to make it into the current build of the app.  Either way <del>no photos here</del> just the basic ingredients and steps, after entering everything into the app the easiest way to just post the recipe here was to cut and paste from an app generated PDF:</p>
<div id="attachment_411" class="wp-caption aligncenter" style="width: 650px"><a href="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/Finished-Tunnock.jpg"><img class="size-large wp-image-411" title="Finished Tunnock" src="http://www.thelostsouls.org.uk/wp-content/uploads/2011/05/Finished-Tunnock-1024x768.jpg" alt="Finished Tunnock" width="640" height="480" /></a><p class="wp-caption-text">Nom nom nom</p></div>
<p>Recipe Below<span id="more-410"></span></p>
<p><strong>Marshmallow Teacakes</strong></p>
<p>Servings : 10</p>
<p>Preparation Time : 45 mins</p>
<p>Cooking Time : 10 mins</p>
<p><strong>Ingredients</strong></p>
<p><strong>For The Biscuit Base </strong></p>
<p>110g PlainFlour<br />
1tsp. BakingPowder<br />
1tsp. Bicarbonate Of Soda<br />
Pinch Salt<br />
60g	Unsalted Butter (softened)<br />
60g	Caster Sugar<br />
2	Egg Yolks<br />
1/2tsp.	Pure Vanilla Extract<br />
1tbsp.Double Cream</p>
<p><strong>For The Marshmallow Filling </strong></p>
<p>2	Egg Whites<br />
100g Caster Sugar<br />
1/2tsp.	Pure Vanilla Extract<br />
Pinch Salt<br />
1tbsp. Plus 1tsp.	Golden Syrup</p>
<p><strong>For The Topping</strong></p>
<p>250g Good Quality Milk Chocolate</p>
<p>&nbsp;</p>
<p><strong>Method</strong></p>
<p>1.	To start set your oven to 180c/350f/gas mark 4 then grease and line two large baking trays. Separate your eggs into small bowls or cups, keeping the White for marshmallow and the yolk for the biscuit base. Due to the number of bowls you use along the way in this recipe I would recommended washing up as you go.<br />
2.	Sift the flour, salt, baking powder and bicarbonate of soda into a small bowl.<br />
3.	Place the softened butter, softening in the microwave for 10 seconds is acceptable, and caster sugar into a large bowl and cream together until it&#8217;s pale. Add the egg yolks and vanilla extract to the mix<br />
4.	Mix well then beat in the tablespoon of double cream. 5.	Add the sifted flour mixture to the bowl.<br />
6.	Mix together until just combined, I used a palette knife for this stage scraping along the bottom to unstick any buttery bits. Be careful not to over handle the dough.<br />
7.	Placetablespoonsizeddollopsofdoughontoyour bakingtraysabout2&#8243;/5cmapartfromeachotherandany edge then bake for 10 minutes or until the edges of the biscuits brown.<br />
8.	When you remove the biscuits from the oven place them on a rack to let them cool.<br />
9.	Whilst the biscuits are baking start to prepare the marshmallow filling. Put all the ingredients in a heatproof glass or metal bowl onto a pan of boiling water.<br />
10.	Whisk by hand until the mixture becomes slightly frothy, opaque and the sugar has dissolved. Remove the bowl from the heat and whisk with the electric whisk until it will hold a peak like meringue and has turned White.<br />
11.	Now spoon or pipe this mixture onto your now cooled biscuit bases. I did this by hand, if you have a piping bag with a large plain tip you will find that preferable I expect.<br />
12.	Now in a heatproof bowl again over boiling water add half of the chocolate stirring constantly until it has melted then remove from the heat.<br />
13.	Chop the remainder of the chocolate into small pieces and add to the melted chocolate but don&#8217;t stir. After 5-10 minutes you should find it has melted after a quick stir together. This lets the chocolate cool down to a reasonable but still molten temperature.<br />
14.	Now the messy bit. Arrange your biscuits on one wire rack with one of the lined baking trays underneath and start to spoon the chocolate over the biscuits. You&#8217;ll want to ration the chocolate carefully here to ensure you cover all of them. I lifted the rack onto the other baking tray and recovered the lost chocolate with a palette knife using the baking sheet as a chocolate funnel.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/05/recipe-for-tunnock-cakes-marshmallow-teacakes/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Viewing the MySQL dump import progress</title>
		<link>http://www.thelostsouls.org.uk/2011/05/viewing-the-mysql-dump-import-progress/</link>
		<comments>http://www.thelostsouls.org.uk/2011/05/viewing-the-mysql-dump-import-progress/#comments</comments>
		<pubDate>Sat, 07 May 2011 22:10:21 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Computer]]></category>
		<category><![CDATA[geekery]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[progress bars]]></category>
		<category><![CDATA[utility]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=407</guid>
		<description><![CDATA[A really useful linux shell hint from someone elses blog&#8230; stumbled across browsing recommended in google reader: Viewing the MySQL dump import progress. Small linux utility called &#8216;bar&#8217; which provides a progress bar for any program that can use a pipe for input&#8230;. e.g.: bar if=foo.sql &#124; mysql -u user -p database Nice&#8230; dd esq [...]]]></description>
			<content:encoded><![CDATA[<p>A really useful linux shell hint from someone elses blog&#8230; stumbled across browsing recommended in google reader:</p>
<p><a href="http://www.linuxjedi.co.uk/?p=213">Viewing the MySQL dump import progress</a>.</p>
<p>Small linux utility called &#8216;bar&#8217; which provides a progress bar for any program that can use a pipe for input&#8230;. e.g.:</p>
<p>bar if=foo.sql | mysql -u user -p database</p>
<p>Nice&#8230; dd esq CLI by the look of it.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/05/viewing-the-mysql-dump-import-progress/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>I lied, I love databases too much and core data is a weird one.</title>
		<link>http://www.thelostsouls.org.uk/2011/04/i-lied-i-love-databases-too-much-and-core-data-is-a-weird-one/</link>
		<comments>http://www.thelostsouls.org.uk/2011/04/i-lied-i-love-databases-too-much-and-core-data-is-a-weird-one/#comments</comments>
		<pubDate>Wed, 13 Apr 2011 18:16:57 +0000</pubDate>
		<dc:creator>Diziet</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Core-Data]]></category>
		<category><![CDATA[upgrades]]></category>
		<category><![CDATA[versioning]]></category>

		<guid isPermaLink="false">http://www.thelostsouls.org.uk/?p=403</guid>
		<description><![CDATA[Strictly speaking this isn&#8217;t a post about core data, honest. It&#8217;s ACTUALLY a post about how iPhone applications are deployed and updated. My shipped application contained two data models, my new application also contains two data models. One of the new versions data models is an old one renamed and another is entirely new. For [...]]]></description>
			<content:encoded><![CDATA[<p>Strictly speaking this isn&#8217;t a post about core data, honest.  It&#8217;s ACTUALLY a post about how iPhone applications are deployed and updated.  My shipped application contained two data models, my new application also contains two data models.  One of the new versions data models is an old one renamed and another is entirely new.  <del datetime="2011-04-13T21:18:23+00:00">For some ridiculous reason I thought if I deleted something from my applications bundle it would be similarly deleted on the iPhone.  That&#8217;s not the case.  Thus the application ends up with 4 data models.  This causes problems as the code I previously posted, cribbed from elsewhere in part, will happily migrate backwards if it finds a suitable model.  I&#8217;d not thought of this as a strict problem if I was in control of what models were present, it seems I am not though.</del></p>
<p><strong>UPDATE</strong>: After seeing some discussions about this issue and people saying it&#8217;s how XCode pushes out the updates I tested a bit more. XCode only pushes out files that have changed to ensure a quick testing cycle, it does not currently delete files.  To confirm this I built an ad-hoc ipa file and installed that on my phone with iTunes.  The files are indeed deleted.  Therefore this is potentially a bug with XCode, it should delete files that are no longer in the bundle even if it isn&#8217;t pushing out a full update like iTunes does.  It can take shortcuts, sure it has to I mean imagine testing something like Inifinity Blade any other way?, but should really ape the real world as much as possible and therefore should delete files.<br />
End of</p>
<p>Of course you shouldn&#8217;t delete data models from your application after it&#8217;s deployed as you cannot dictate that somebody will upgrade to each release of your app.  If the data model really was deleted from your bundle the user would be stuck as the software could not open the database to migrate.</p>
<p>There&#8217;s an argument to be made there, I am sure, for not using Core Data on simple or incredibly dynamic projects but that could be one for another day.</p>
<p>I do like the code I have got though and will not be abandoning it as it&#8217;s lightweight in terms of memory.  Much more so than the other options.  The use of NSOperations pushed into a queue as the migrations procede gives it remarkable power and flexibility too.  There is plenty that can be done inside the migration loop to ensure it proceeds forwards and not backwards.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.thelostsouls.org.uk/2011/04/i-lied-i-love-databases-too-much-and-core-data-is-a-weird-one/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

