Reading view

There are new articles available, click to refresh the page.

How to search document versions

Document versioning built into macOS is an unfinished masterpiece that promises much but never seems to have been developed as fully as it deserved. This article looks at how macOS can’t search saved versions, and how you can work around that.

In essence versioning is simple: apps that support it, and a great many do now, save a series of versions to the volume’s hidden and sealed database in the .DocummentRevisions-V100 folder at its top level. To access those versions you’d normally use the Time-Machine-like browser provided by the Browse All Versions command in the Revert To item in the app’s File menu. Whenever the app saves a document, the open document becomes the current version, and its saved state becomes the previous version. This works for manual saves, and for any automatic timed saves the app might make.

Unlike all other versioning systems, this is all handled automatically by macOS, and neither you the user nor the app developer has to make any effort to create or manage those versions. It really does come for free.

Unfortunately, all those saved versions in the version database fall outside the scope of Spotlight indexing, and Spotlight search can’t look inside any of the old versions saved in a volume’s version database. Surprisingly, the version browser doesn’t offer any search facilities either, as that’s presumably another feature intended for a future that never came.

This is a serious omission, as I access old versions not infrequently, and being able to search for them saves me laborious browsing. It might be a few hours or days after I removed a section from a document, that I realise I need it back. By that time it may well have vanished from Time Machine’s hourly backups, or the section may have been too transient to be retained there. But the chances are that the missing content will be safe inside a saved version, if only I can find it.

Pulling tricks with the hidden .DocumentRevisions-V100 folder isn’t a good approach to solve this. It’s clear from its contents that previous versions aren’t saved as discrete files, but it uses a chunking system to store what has changed between versions, for economy in space. Access supported by macOS is strictly limited to looking up saved versions for any given file in that volume, and there’s no way to search their contents like that.

One way around this is to save each document version as a separate file, allow Spotlight to extract their contents and add those to its indexes for that volume, then to search those files. This is quick and simple using my free utility Versatility. To demonstrate this, I picked two documents with a substantial number of versions:

  • a Swift source code file edited in Xcode with 112 versions, with just one of them containing a function named loadAppexIndexer;
  • a large Pages document with a mere 49 versions, where I was looking for the first containing the placename Hulverstone.

In both cases I started by dropping the current document onto Veratility’s window, and saving individual archived versions to a new folder alongside that original document. I then opened that archive folder in a Finder window, and converted that to a Find window with that command in the Finder’s File menu. I entered my term, loadAppexIndexer or Hulverstone, into the search box, and changed the search scope from This Mac to the open archive folder.

In the Swift code, Spotlight immediately found the term in the file numbered 033 by Versatility, and all versions from the file numbered 023 in the case of the Pages document.

With that Finder window still open I was then able to locate those versions in the original documents:

  • Using my free Revisionist, the version numbers start from 1, whereas Versatility starts them at 000. So I added 1 to the number in the filename, and previewed that version in Revisionist. In both cases that’s sufficient to copy content that had gone missing from the current version of the document, for example.
  • Using the version browser in XCode or Pages, I looked back for that version’s datestamp, given in the Finder window as its Date Created, and brought that old version up in the browser.

Once happy I had done what I wanted with that old version, I then trashed the archive folder created by Versatility.

To summarise the sequence:

  1. drop the versioned document on Versatility’s window;
  2. save the archive folder alongside the original document;
  3. open a Finder Find window on that archive folder;
  4. using the search box and find bars, locate the version(s) in the archive folder;
  5. to open the versioned document in Revisionist, add 1 to its file version number;
  6. to open in an app version browser, select the date of that version as shown in the Finder window;
  7. on completion delete the archive folder.

Happy finding!

How to preserve versions, and how to create versioned PDFs

Keeping previous versions of a document you’re working on can be a great timesaver. Although I seldom restore files from backups, it’s far more frequent that I look back in a file’s versions to recover changed or removed contents. In most cases, those had changed so rapidly that even hourly backups didn’t capture them. Had those versions not been saved automatically by macOS, I would have wasted time trying to recreate them from scratch.

Although a great many apps now come with built-in version support, macOS doesn’t preserve those versions as well as it could. Duplicate a document with versions, save it as another document, or move it to a different volume, and all its versions are blown away. As I explained yesterday, versions don’t transfer in iCloud Drive either. This article explains how you can work around all those, how to ensure versions get backed up, and how you can create PDF documents with versions.

How versions work

Opening the version browser from the File menu.

Many apps now have built-in support to automatically save versions of documents you edit with them. The tell-tale sign is when the app has a Revert To command in its File menu, which opens the current document in a version browser resembling the Time Machine app.

revisions1

Each time you save a document in those apps, the existing document is saved to a hidden and locked-down database at the root level of that volume, in the .DocumentRevisions-V100 folder. When you use the Revert To command to browse all versions, you can look back at all the versions of that document saved to that volume. You can then revert to an older version, or copy contents from an older version to the current one. As long as that document remains in its current volume, those versions will remain accessible. However, if that document is moved to a different volume, even on the same disk, those versions don’t move with it, but will be retained in the original volume until it’s deleted from there.

If you’ve been editing a document in your Documents folder and move it into iCloud Drive, which is actually a folder inside your Home Library folder, its versions will be preserved when you access it from the same Mac. However, other Macs connected to the same iCloud account won’t see those versions, as they remain on the original Mac and don’t get synced to iCloud Drive.

How to extend versions

Apps can’t access stored versions directly, but have to do that via macOS. The most compatible way for them to do that is to fetch previous versions from the volume version database. They can then save each version as a separate file, and reconstitute a document complete with its versions by adding those files back to a document’s versions in the volume’s database. That’s exactly what my free utilities Versatility and Revisionist do. Versatility is the simpler of the two to use here, while Revisionist adds more features including checking documents to see how many versions they already have stored in their volume database.

Archive versions

Simply drag and drop a file with saved versions onto Versatility’s window, and it will extract all its versions and save them as a series of numbered files in a folder. You can then copy or move that folder to any other location, where you can reconstitute the original document with all its versions intact.

Unarchive versions

Simply drag and drop a folder containing archived version files onto Versatility’s window, and it will reconstitute the original document with all its previous versions.

Versions in iCloud Drive

To preserve all versions in iCloud Drive and make them available to all that connect to that folder, move the document from its existing location in your Home folder, to the correct folder in iCloud Drive. Once it’s there:

  1. Perform any editing necessary.
  2. Archive. Drop the document onto Versatility’s window, and save that archive folder to the same location.
  3. Move the original document elsewhere.

When you want to edit that document, particularly on another Mac, on that Mac:

  1. Unarchive. Drop the archive folder onto Versatility’s window, and save the document to the same location.
  2. Edit the document, saving whenever you want to create a new version.
  3. When you’ve finished, save for the last time, and close the document.
  4. Archive. Drop the document onto Versatility’s window, and save that archive folder to the same location.
  5. Tidy up old archive folders and files.

That leaves the most recent archive folder, with composite versions written in the correct order, with the right timestamps, ready to be unarchived on the next Mac to edit that document. This may appear complicated, but once you have tried it out, it’s really a simple sequence to unarchive-edit-save-archive and hand over to the next editor.

Backing up versions

I’m not aware of any backup utility for macOS, including Time Machine, that backs up and preserves versions, although they are stored in local volume snapshots. However, all you have to do is archive the versions of important files into folders using Versatility, and back up those folders. When you want to restore the original document with all its versions, simply unarchive that folder using Versatility.

PDF versions

One of the lesser-known features of the PDF format are incremental updates, which can provide a primitive form of versioning within a single file. In practice it catches users out when they publish a PDF containing old edited content they thought had been removed.

Few PDF editors and viewers support the macOS version system, but Preview does, and Versatility can be used to assemble a PDF document with versions.

For my example, rather than edit a PDF, I generated a series from an archived RTF, converting each file into a consecutively numbered PDF, starting from 000.pdf and rising to 010.pdf. I then dropped that folder onto Versatility’s window and it unarchived those into a single PDF document with all those versions.

Key points

  • Archive a file with saved versions to a folder by dropping it onto Versatility’s window.
  • Unarchive a folder containing version files to a file with saved versions by dropping it onto Versatility’s window.
  • In iCloud Drive, unarchive-edit-save-archive to preserve versions for the next editor.
  • Wherever you want to preserve versions, archive the file using Versatility.

What gets synced in iCloud Drive?

Following yesterday’s surprise about syncing of extended attributes via iCloud Drive, this article summarises what does and does not get synced in iCloud Drive in macOS Tahoe.

Attributes and data

File attributes are generally synced correctly and retained locally through eviction and download of each file. As those are saved in the inode data that is stored locally even when a file is dataless, they should remain reliable.

File data, complete with any embedded metadata such as EXIF fields and the optional Info section in RTF files, is retained and kept in sync with the copy in iCloud Drive while that file is kept downloaded. That is the only option when Optimise Mac Storage is turned off, and iCloud Drive is operating in replicated mode. When in nonreplicated mode, data is removed if the file is evicted from local storage, and synced down from iCloud Drive when it’s downloaded or materialised.

Extended attributes

As demonstrated in yesterday’s article, only the following xattrs are expected to sync down from iCloud Drive:

  • com.apple.metadata:_kMDItemUserTags (Finder Tag)
  • com.apple.lastuseddate#PS
  • com.apple.quarantine
  • com.apple.TextEncoding
  • other xattrs explicitly assigned the S flag, with #S appended to their name.

Other xattrs including those with names starting with com.apple.metadata:kMDItem aren’t likely to sync down from iCloud Drive without explicit use of the S flag.

Versions

Document versions saved in that volume’s version database in the hidden .DocumentRevisions-V100 folder will normally only be saved locally, when the local copy of that file is saved, and aren’t synced up to iCloud Drive at all. This has complicated effects best illustrated in the example below.

In this example, two Macs, A and B, are connected to the same iCloud Drive. At the start, Mac A creates and saves a new file, locally Version 1, in an iCloud Drive folder. This is synced up to iCloud Drive, from where it syncs down to Mac B, as the first version of that file.

Mac A then edits that file, saving it in two further versions. Each of those is synced up to iCloud Drive, and synced down to Mac B. However, as none of those versions is saved locally on Mac B, each is shown as the current and only version until the next one arrives.

Mac A is shut down after it has saved its version 3 of the file, and that has been synced up to iCloud Drive. Once that has synced down to Mac B, the document is edited there, and two versions are added to the first. Mac B’s Version 3 of that file is synced up to iCloud Drive, Mac B is shut down, and the file is opened and saved on Mac A, where that becomes its local Version 4.

At that stage, Mac A’s version database contains 4 versions, but no copy of Mac B’s Version 2. Mac B has 3 saved versions, including its Version 2 that isn’t saved in Mac A. iCloud Drive only has a single version, its Version 5, the same as Mac A’s Version 4 and Mac B’s Version 3.

The rules are simple:

  • Each Mac only adds a version to its own local version database when that file is saved locally.
  • At any moment, only the latest version is stored in iCloud Drive.

However, the behaviour can appear baffling, particularly when a document is observed in its QuickLook thumbnail as it’s being edited and saved on another Mac. You can then see its contents evolving with each save, but none of those are added to that Mac’s version database unless that version is saved there.

The end result is an incomplete version history on each Mac. The only way to unify those is in a third-party utility such as Versatility or Revisionist to consolidate them. As this doesn’t require any intervention by the File Provider framework, this is likely to be similar in third-party cloud services using that framework, such as Dropbox and Microsoft OneDrive.

Spotlight index content

No indexes from Spotlight are synced across iCloud Drive, but once a file has been synced down from iCloud Drive, its contents should be indexed locally, on the Data volume. Those indexed contents should remain accessible to search even when the file has been evicted from local storage.

QuickLook previews

QuickLook thumbnails and previews are also generated and stored locally. Those that have been cached to local storage remain accessible even when the file has been evicted. When there’s no cached version available, a generic icon for that file type will be displayed until an evicted file has been downloaded again. At one time, selecting an evicted file and calling for its thumbnail or preview was a simple way to force the file to be downloaded, but that has now been fixed.

❌