

{"id":12257,"date":"2019-06-02T11:35:55","date_gmt":"2019-06-02T16:35:55","guid":{"rendered":"https:\/\/rud.is\/b\/?p=12257"},"modified":"2019-06-02T20:12:44","modified_gmt":"2019-06-03T01:12:44","slug":"trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r","status":"publish","type":"post","link":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/","title":{"rendered":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R"},"content":{"rendered":"<p>In a recent <a href=\"https:\/\/rud.is\/b\/2019\/06\/01\/quick-hit-handling-cocoa-core-data-timestamps-in-r\/\">previous post<\/a> I brazenly talked over the &#8220;hard parts&#8221; of how I got to the target SQLite file that houses &#8220;mowing history&#8221; for what has become my weekend obsession. So, we&#8217;ll cover just how to do that (find things in iOS backups) in this post along with how to deal with some &#8220;gotchas&#8221; if you&#8217;re doing this from macOS.<\/p>\n<h3>macOS (the Knife)<\/h3>\n<p>Kurt Weill, Bertolt Brecht, and Marc Blitzstein created some amazing lyrics that Bobby Darin did some <a href=\"https:\/\/www.youtube.com\/watch?v=SEllHMWkXEU\">sweet, sweet justice to<\/a>:<\/p>\n<p><iframe loading=\"lazy\" width=\"560\" height=\"315\" src=\"https:\/\/www.youtube-nocookie.com\/embed\/SEllHMWkXEU\" frameborder=\"0\" allow=\"accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen><\/iframe><\/p>\n<p>I bring that up to talk about the cutting, biting, dangerous edge of macOS that is Apple&#8217;s somewhat mixed attempt at protecting your privacy and keeping out of sight sensitive files and directories from the the sharp teeth of malware (and to re-pimp my <a href=\"https:\/\/git.sr.ht\/~hrbrmstr\/mactheknife\"><code>{mactheknife}<\/code> package<\/a>) . You can read up on Apple&#8217;s new protections more thoroughly over at <a href=\"https:\/\/eclecticlight.co\/?s=sandbox\">The Eclectic Light Company<\/a>. For the purposes of this blog post, Apple&#8217;s macOS Sandbox policies means you have to do some extra steps to gain access to the folder and files associated with iOS backups (which is <code>~\/Library\/Application Support\/MobileSync\/Backup\/<\/code>).<\/p>\n<p>If you want RStudio, R, and anything run with Rscript to access these sandboxed areas you&#8217;ll need to enable &#8220;Full Disk Access&#8221; for those apps and executables. First you&#8217;ll need to open <code>System Preferences &gt; Security &amp; Privacy<\/code> and then make the <code>Privacy<\/code> tab active. Keep that window open and tap the lock to unlock the settings.<\/p>\n<div id=\"attachment_12259\" style=\"width: 540px\" class=\"wp-caption aligncenter\"><a href=\"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?ssl=1\"><img data-recalc-dims=\"1\" loading=\"lazy\" decoding=\"async\" aria-describedby=\"caption-attachment-12259\" data-attachment-id=\"12259\" data-permalink=\"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/full-disk-access\/\" data-orig-file=\"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?fit=1560%2C1370&amp;ssl=1\" data-orig-size=\"1560,1370\" data-comments-opened=\"1\" data-image-meta=\"{&quot;aperture&quot;:&quot;0&quot;,&quot;credit&quot;:&quot;&quot;,&quot;camera&quot;:&quot;&quot;,&quot;caption&quot;:&quot;&quot;,&quot;created_timestamp&quot;:&quot;0&quot;,&quot;copyright&quot;:&quot;&quot;,&quot;focal_length&quot;:&quot;0&quot;,&quot;iso&quot;:&quot;0&quot;,&quot;shutter_speed&quot;:&quot;0&quot;,&quot;title&quot;:&quot;&quot;,&quot;orientation&quot;:&quot;0&quot;}\" data-image-title=\"full-disk-access\" data-image-description=\"&lt;p&gt;Full Disk Access settings panel in macOS&lt;\/p&gt;\n\" data-image-caption=\"&lt;p&gt;Full Disk Access settings panel in macOS&lt;\/p&gt;\n\" data-large-file=\"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?fit=510%2C447&amp;ssl=1\" src=\"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=510%2C447&#038;ssl=1\" alt=\"Full Disk Access settings panel in macOS\" width=\"510\" height=\"447\" class=\"size-large wp-image-12259\" srcset=\"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=530%2C465&amp;ssl=1 530w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=150%2C132&amp;ssl=1 150w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=300%2C263&amp;ssl=1 300w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=768%2C674&amp;ssl=1 768w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=500%2C439&amp;ssl=1 500w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=1200%2C1054&amp;ssl=1 1200w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=400%2C351&amp;ssl=1 400w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=800%2C703&amp;ssl=1 800w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?resize=200%2C176&amp;ssl=1 200w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?w=1560&amp;ssl=1 1560w, https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?w=1020&amp;ssl=1 1020w\" sizes=\"auto, (max-width: 510px) 100vw, 510px\" \/><\/a><p id=\"caption-attachment-12259\" class=\"wp-caption-text\">Full Disk Access settings panel in macOS<\/p><\/div>\n<p>Adding RStudio is easy. Just make Finder active and hit <kbd>Cmd<\/kbd> <kbd>Shift<\/kbd> <kbd>A<\/kbd> and then find and drag the &#8220;RStudio&#8221; application into the pane+tab you opened in the previous step. Back in the Finder, hit <kbd>Cmd<\/kbd> <kbd>Shift<\/kbd> <kbd>G<\/kbd> and paste in: <code>\/Library\/Frameworks\/R.framework\/Resources\/bin<\/code> and go to that folder. Drag in <code>R<\/code> and <code>Rscript<\/code> each into the pane+tab from the aforementioned step. Finally (and this got me for a minute) you <em>also<\/em> need to (again, in Finder) hit <kbd>Cmd<\/kbd> <kbd>Shift<\/kbd> <kbd>G<\/kbd> and paste in <code>\/Library\/Frameworks\/R.framework\/Versions\/3.6\/Resources\/bin\/exec<\/code> and drag <em>that R executable<\/em> into the Security &amp; Privacy Privacy\/Full Disk Access pane+tab as well. When you&#8217;ve done all that, lock the System Preferences pane and close it.<\/p>\n<p>It is important to note that you just gave &#8220;R&#8221; and anything that calls R from your user space complete (well, <em>almost<\/em>) access to every sandboxed area on your system. R is a general purpose programming and scripting language which means any bit of malicious code that knows you have added those executables can use R to read from and write to any area on your system.<\/p>\n<p>It is also important to note that I had to use <code>3.6<\/code> vs the <code>Current<\/code> symlink for the last entry so that means you need to do this for each new R version you install.<\/p>\n<p>I hope folks on legacy Windows OS installs didn&#8217;t skip over this part as you&#8217;ll need to go <a href=\"http:\/\/bfy.tw\/Nvfc\">here<\/a> to figure out where your iOS backups folder is to go through the rest of the post.<\/p>\n<h3>Sneakin&#8217; Round The Corner<\/h3>\n<p>Windows folks hopefully read at least the last bit of the previous section to figure out where their iOS backups are. On macOS that&#8217;s <code>~\/Library\/Application Support\/MobileSync\/Backup\/<\/code>. You need a local backup there (most folks just use iCloud backups these days) and <a href=\"https:\/\/support.apple.com\/en-us\/HT203977\">Apple tells you how to do this<\/a>.<\/p>\n<p>Once you know you&#8217;ve got an (<strong>unencrypted<\/strong>) backup just go to your iOS backups directory and list the files by date and note the name\/path of the most recent backup. Now we can have some fun.<\/p>\n<pre><code class=\"language-r\">library(XML) # to read plist (property list) files\nlibrary(tidyverse) # for printing and access to sqlite dbs\n\n# replace this with the relative path to your most recent backup dir\nmb &lt;- \"~\/Library\/Application Support\/MobileSync\/Backup\/28500cd31b9580aaf5815c695ebd3ea5f7455628-20190601-165737\"\n\nlist.files(mb, pattern = \".*\\\\.(db|plist)$\")\n## [1] \"Info.plist\"      \"Manifest.db\"      \"Manifest.plist\"      \"Status.plist\"\n<\/code><\/pre>\n<p>The above code looks for some key metadata files for iOS backups.<\/p>\n<ul>\n<li><code>Info.plist<\/code> has info on your device<\/li>\n<li><code>Manifest.db<\/code> has tons of info on all the files in the backup in a SQLite database<\/li>\n<li><code>Manifest.plist<\/code> has some additional metadata on the backup including applications included in the backup<\/li>\n<li><code>Status.plist<\/code> contains info on the status of the backup<\/li>\n<\/ul>\n<p>Let&#8217;s take a look at the plists:<\/p>\n<pre><code class=\"language-r\">info_p &lt;- file.path(mb, \"Info.plist\")\nfile.copy(info_p, \"\/tmp\", overwrite = TRUE)\nsystem2(\"plutil\", args=c(\"-convert\", \"xml1\", \"-o\", \"\/tmp\/Info.plist\", \"\/tmp\/Info.plist\"))\n\ninfo &lt;- XML::readKeyValueDB(\"\/tmp\/Info.plist\")\n\nstr(info)\n## List of 11\n##  $ Device Name        : chr REDACTED\n##  $ Display Name       : chr REDACTED\n##  $ ICCID              : chr REDACTED\n##  $ IMEI               : chr REDACTED\n##  $ IPBE Backup Version: int 1\n##  $ Last Backup Date   : POSIXct[1:1], format: \"2019-06-01 21:23:02\"\n##  $ Phone Number       : chr REDACTED\n##  $ Product Type       : chr REDACTED\n##  $ Product Version    : chr REDACTED\n##  $ Serial Number      : chr REDACTED\n##  $ Unique Identifier  : chr REDACTED\n\nstatus_p &lt;- file.path(mb, \"Status.plist\")\nfile.copy(status_p, \"\/tmp\", overwrite = TRUE)\nsystem2(\"plutil\", args=c(\"-convert\", \"xml1\", \"-o\", \"\/tmp\/Status.plist\", \"\/tmp\/Status.plist\"))\n\nstatus &lt;- XML::readKeyValueDB(\"\/tmp\/Status.plist\")\n\nstr(status)\n## List of 6\n##  $ BackupState  : chr \"new\"\n##  $ Date         : POSIXct[1:1], format: \"2019-06-01 21:22:53\"\n##  $ IsFullBackup : logi FALSE\n##  $ SnapshotState: chr \"finished\"\n##  $ UUID         : chr REDACTED\n##  $ Version      : chr \"3.3\"\n\nmainf_p &lt;- file.path(mb, \"Manifest.plist\")\nfile.copy(mainf_p, \"\/tmp\", overwrite = TRUE)\nsystem2(\"plutil\", args=c(\"-convert\", \"xml1\", \"-o\", \"\/tmp\/Manifest.plist\", \"\/tmp\/Manifest.plist\"))\n\nmanifest &lt;- XML::readKeyValueDB(\"\/tmp\/Manifest.plist\")\n\nstr(manifest, 1)\n## List of 8\n##  $ Applications        :List of 745\n##  $ BackupKeyBag        : chr __truncated__\n##  $ Date                : POSIXct[1:1], format: \"2019-06-01 20:57:40\"\n##  $ IsEncrypted         : logi FALSE\n##  $ Lockdown            :List of 12\n##  $ SystemDomainsVersion: chr \"24.0\"\n##  $ Version             : chr \"10.0\"\n##  $ WasPasscodeSet      : logi TRUE\n<\/code><\/pre>\n<p>You&#8217;ll note we&#8217;re making copies of these files (never play with system-managed files directly unless you know what you&#8217;re doing) and turning binary property lists into plain text XML property lists as well so we can read them with the <code>XML::readKeyValueDB()<\/code> function.<\/p>\n<p>Most of that information is fairly useless for this blog post but I figured you might like to see the hidden things the system knows about your devices. What we do want to check is to see if the John Deere application and data made it into the backup. The <code>Applications<\/code> slot is a named list of application metadata. Let&#8217;s see if there&#8217;s anything Deere-ish in it:<\/p>\n<pre><code class=\"language-r\">grep(\"deere\", names(manifest$Applications), ignore.case = TRUE, value = TRUE)\n##                   key \n## \"com.deere.mowerplus\"\n\nstr(manifest$Applications$com.deere.mowerplus, 1)\n## List of 4\n##  $ CFBundleIdentifier   : chr \"com.deere.mowerplus\"\n##  $ CFBundleVersion      : chr \"180\"\n##  $ ContainerContentClass: chr \"Data\/Application\"\n##  $ Path                 : chr \"\/var\/containers\/Bundle\/Application\/30DF2640-A9AA-43A0-AD87-932CA513D75A\/MowerPlus.app\"\n<\/code><\/pre>\n<p>Aye! This means we should have some luck finding &#8220;mower&#8221; data in the Manifest SQLite database.<\/p>\n<p>Now, we <em>could<\/em> try to follow UUIDs around but we can also take a stab at a less cumbersome approach. Let&#8217;s make a copy of the Manifest database and see what it holds:<\/p>\n<pre><code class=\"language-r\">mainf_d &lt;- file.path(mb, \"Manifest.db\")\nfile.copy(mainf_d, \"\/tmp\", overwrite = TRUE)\n## [1] TRUE\n\n(manifest_db &lt;- src_sqlite(\"\/tmp\/Manifest.db\"))\n## src:  sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n## tbls: Files, Properties\n<\/code><\/pre>\n<p>We want to get to (hopefully) a SQLite file with the mowing data so we likely care about the <code>Files<\/code> table. Let&#8217;s take a look at the structure of that table:<\/p>\n<pre><code class=\"language-r\">(fils &lt;- tbl(manifest_db, \"Files\"))\n## # Source:   table&lt;Files&gt; [?? x 5]\n## # Database: sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n##    fileID           domain         relativePath           flags        file\n##    &lt;chr&gt;            &lt;chr&gt;          &lt;chr&gt;                  &lt;int&gt;      &lt;blob&gt;\n##  1 c1da4199a18d0b5\u2026 AppDomain-com\u2026 \"\"                         2 &lt;raw 437 B&gt;\n##  2 7426ac0386e2887\u2026 AppDomain-com\u2026 Library                    2 &lt;raw 444 B&gt;\n##  3 a6393e739e1ad37\u2026 AppDomain-com\u2026 Library\/WebKit             2 &lt;raw 444 B&gt;\n##  4 c54f5c77a5e970b\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 458 B&gt;\n##  5 578f2c96f219e95\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 465 B&gt;\n##  6 c8833032ce7c9e9\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 481 B&gt;\n##  7 6af21902e595f7c\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 468 B&gt;\n##  8 4c1c49324646af0\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 471 B&gt;\n##  9 d0636bf9b5ba2ae\u2026 AppDomain-com\u2026 Library\/WebKit\/Websit\u2026     2 &lt;raw 468 B&gt;\n## 10 0b6bb30c8abaa4e\u2026 AppDomain-com\u2026 Library\/Preferences        2 &lt;raw 458 B&gt;\n## # \u2026 with more rows\n<\/code><\/pre>\n<p>If you have a ton of apps, this is a pretty big haystack to comb through. We may be able to narrow things down a bit, though, and we&#8217;ll start by seeing what that <code>domain<\/code> column holds:<\/p>\n<pre><code class=\"language-r\">distinct(fils, domain)\n## # Source:   lazy query [?? x 1]\n## # Database: sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n##    domain                                 \n##    &lt;chr&gt;                                  \n##  1 AppDomain-Outils-OBD-Facile.EOBD-Facile\n##  2 AppDomain-ch.threema.iapp              \n##  3 AppDomain-co.humanco.Human             \n##  4 AppDomain-co.ortatech.colr-app         \n##  5 AppDomain-co.vero.app                  \n##  6 AppDomain-com.7thg.Tides               \n##  7 AppDomain-com.AerLingus                \n##  8 AppDomain-com.BloomSky.BloomSky        \n##  9 AppDomain-com.PunchThrough.LightBlue   \n## 10 AppDomain-com.agilebits.onepassword-ios\n## # \u2026 with more rows\n<\/code><\/pre>\n<p>So, these are app-specific and the bits after the <code>-<\/code> in each one look like the <code>CFBundleIdentifier<\/code>s from above. Let&#8217;s make sure:<\/p>\n<pre><code class=\"language-r\">filter(fils, lower(domain) %like% \"%com.deere.mowerplus%\") %&gt;% \n  distinct(domain)\n## # Source:   lazy query [?? x 1]\n## # Database: sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n##   domain                       \n##   &lt;chr&gt;                        \n## 1 AppDomain-com.deere.mowerplus\n<\/code><\/pre>\n<p>Aye! Let&#8217;s check to see what files are in there (and hope for a nice SQLite database):<\/p>\n<pre><code class=\"language-r\">filter(fils, domain == \"AppDomain-com.deere.mowerplus\") %&gt;%\n  select(relativePath) %&gt;% \n  collect() \n## # A tibble: 14 x 1\n##    relativePath                                                     \n##    &lt;chr&gt;                                                            \n##  1 \"\"                                                               \n##  2 Library                                                          \n##  3 Library\/Preferences                                              \n##  4 Library\/Application Support                                      \n##  5 Library\/Application Support\/com.crashlytics                      \n##  6 Documents                                                        \n##  7 Library\/GoAppPersistentStore-GoMow.sqlite                        \n##  8 Library\/googleanalytics-aux-v4.sql                               \n##  9 Library\/googleanalytics-v3.sql                                   \n## 10 Library\/Preferences\/com.deere.mowerplus.plist                    \n## 11 Library\/Application Support\/ActivityCards.sqlite                 \n## 12 Library\/Application Support\/com.crashlytics\/CLSUserDefaults.plist\n## 13 Library\/googleanalytics-v2.sql                                   \n## 14 Library\/Application Support\/MowTracking.sqlite\n<\/code><\/pre>\n<p>It turns out that last one is what we&#8217;re looking for. Now we just need a bit of crucial metadata to get to it:<\/p>\n<pre><code class=\"language-r\">filter(fils, relativePath == \"Library\/Application Support\/MowTracking.sqlite\") %&gt;% \n  select(fileID, relativePath)\n## # Source:   lazy query [?? x 2]\n## # Database: sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n##   fileID                            relativePath                           \n##   &lt;chr&gt;                             &lt;chr&gt;                                  \n## 1 ad0009ec04c44b544d37bfc7ab343869\u2026 Library\/Application Support\/MowTrackin\u2026\n<\/code><\/pre>\n<p>That <code>fileID<\/code> maps to the seriously ugly directory tree that is the rest of the iOS backups folder (you likely looked into it and wondered &#8220;What the heck?!&#8221;). The top level is a 2-digit hex prefix with files underneath it (likely for performance reasons but a bit of obfuscation never hurts, too). We&#8217;ll get the whole string:<\/p>\n<pre><code class=\"language-r\">filter(fils, relativePath == \"Library\/Application Support\/MowTracking.sqlite\") %&gt;% \n  select(fileID)\n## # Source:   lazy query [?? x 1]\n## # Database: sqlite 3.22.0 [\/private\/tmp\/Manifest.db]\n##   fileID                                  \n##   &lt;chr&gt;                                   \n## 1 ad0009ec04c44b544d37bfc7ab3438697d23d618\n<\/code><\/pre>\n<p>and, then copy over the mowing database somewhere safe to work on:<\/p>\n<pre><code class=\"language-r\">file.copy(\n  file.path(mb, \"ad\/ad0009ec04c44b544d37bfc7ab3438697d23d618\"),\n  \"\/tmp\/mowtrack.sqlite\",\n  overwrite = TRUE\n)\n## [1] TRUE\n\nmow &lt;- src_sqlite(\"\/tmp\/mowtrack.sqlite\")\n\nmow\n## src:  sqlite 3.22.0 [\/private\/tmp\/mowtrack.sqlite]\n## tbls: Z_METADATA, Z_MODELCACHE, Z_PRIMARYKEY, ZACTIVITY, ZDEALER,\n##   ZMOWALERT, ZMOWER, ZMOWLOCATION, ZSMARTCONNECTOR, ZUSER\n\ntbl(mow, \"ZMOWLOCATION\") %&gt;% \n  glimpse()\n## Observations: ??\n## Variables: 16\n## Database: sqlite 3.22.0 [\/private\/tmp\/mowtrack.sqlite]\n## $ Z_PK                &lt;int&gt; 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 1\u2026\n## $ Z_ENT               &lt;int&gt; 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,\u2026\n## $ Z_OPT               &lt;int&gt; 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,\u2026\n## $ ZISPAUSEDPOINT      &lt;int&gt; NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, \u2026\n## $ ZORDER              &lt;int&gt; 1, 2, 0, 11, 20, 58, 38, 43, 30, 25, 21, 10,\u2026\n## $ ZSESSION            &lt;int&gt; 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,\u2026\n## $ ZSESSION2           &lt;int&gt; NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, \u2026\n## $ ZALTITUDE           &lt;dbl&gt; 42.64804, 42.70590, 40.99661, 39.54770, 38.2\u2026\n## $ ZCOURSE             &lt;dbl&gt; 358.242188, 332.226562, 18.281250, 260.85937\u2026\n## $ ZHORIZONTALACCURACY &lt;dbl&gt; 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,\u2026\n## $ ZLATITUDE           &lt;dbl&gt; 43.25913, 43.25914, 43.25913, 43.25915, 43.2\u2026\n## $ ZLONGITUDE          &lt;dbl&gt; -70.80069, -70.80069, -70.80069, -70.80067, \u2026\n## $ ZSPEED              &lt;dbl&gt; 0.0000000, 0.4250179, 0.5592341, 0.3802792, \u2026\n## $ ZTIMESTAMP          &lt;dbl&gt; 581100271, 581100272, 581100270, 581100281, \u2026\n## $ ZVERTICALACCURACY   &lt;dbl&gt; 6, 6, 8, 6, 4, 4, 4, 3, 4, 4, 4, 6, 4, 4, 4,\u2026\n## $ ZKLVDATA            &lt;blob&gt; &lt;NA&gt;, &lt;NA&gt;, &lt;NA&gt;, &lt;NA&gt;, &lt;NA&gt;, &lt;NA&gt;, &lt;NA&gt;, &lt;\u2026\n<\/code><\/pre>\n<h3>(Shark) FIN<\/h3>\n<p>Even if you don&#8217;t have this mower app that I&#8217;m currently obsessed with, you now have a primer on how to get to SQLite databases stored by any application on your iOS device. That alone may unearth some fun projects for you to hack on. Plus, you  also learned a bit on how to do some light forensics on iOS backups with R\/RStudio.<\/p>\n<p>If you did your own trawling and found something interesting definitely blog or tweet about it and drop a link in the comments.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In a recent previous post I brazenly talked over the &#8220;hard parts&#8221; of how I got to the target SQLite file that houses &#8220;mowing history&#8221; for what has become my weekend obsession. So, we&#8217;ll cover just how to do that (find things in iOS backups) in this post along with how to deal with some [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"jetpack_post_was_ever_published":false,"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_memberships_contains_paid_content":false,"activitypub_content_warning":"","activitypub_content_visibility":"","activitypub_max_image_attachments":3,"activitypub_interaction_policy_quote":"anyone","activitypub_status":"","footnotes":""},"categories":[10,780,91],"tags":[],"class_list":["post-12257","post","type-post","status-publish","format-standard","hentry","category-ios","category-macos","category-r"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.3 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is\" \/>\n<meta property=\"og:description\" content=\"In a recent previous post I brazenly talked over the &#8220;hard parts&#8221; of how I got to the target SQLite file that houses &#8220;mowing history&#8221; for what has become my weekend obsession. So, we&#8217;ll cover just how to do that (find things in iOS backups) in this post along with how to deal with some [&hellip;]\" \/>\n<meta property=\"og:url\" content=\"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/\" \/>\n<meta property=\"og:site_name\" content=\"rud.is\" \/>\n<meta property=\"article:published_time\" content=\"2019-06-02T16:35:55+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2019-06-03T01:12:44+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access-530x465.png\" \/>\n<meta name=\"author\" content=\"hrbrmstr\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"hrbrmstr\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"10 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/\"},\"author\":{\"name\":\"hrbrmstr\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#\\\/schema\\\/person\\\/d7cb7487ab0527447f7fda5c423ff886\"},\"headline\":\"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R\",\"datePublished\":\"2019-06-02T16:35:55+00:00\",\"dateModified\":\"2019-06-03T01:12:44+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/\"},\"wordCount\":1126,\"commentCount\":2,\"publisher\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#\\\/schema\\\/person\\\/d7cb7487ab0527447f7fda5c423ff886\"},\"image\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2019\\\/06\\\/full-disk-access-530x465.png\",\"articleSection\":[\"iOS\",\"macOS\",\"R\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/\",\"url\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/\",\"name\":\"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#primaryimage\"},\"image\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2019\\\/06\\\/full-disk-access-530x465.png\",\"datePublished\":\"2019-06-02T16:35:55+00:00\",\"dateModified\":\"2019-06-03T01:12:44+00:00\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#primaryimage\",\"url\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2019\\\/06\\\/full-disk-access.png?fit=1560%2C1370&ssl=1\",\"contentUrl\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2019\\\/06\\\/full-disk-access.png?fit=1560%2C1370&ssl=1\",\"width\":1560,\"height\":1370,\"caption\":\"Full Disk Access settings panel in macOS\"},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/2019\\\/06\\\/02\\\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\\\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/rud.is\\\/b\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#website\",\"url\":\"https:\\\/\\\/rud.is\\\/b\\\/\",\"name\":\"rud.is\",\"description\":\"&quot;In God we trust. All others must bring data&quot;\",\"publisher\":{\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#\\\/schema\\\/person\\\/d7cb7487ab0527447f7fda5c423ff886\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/rud.is\\\/b\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":[\"Person\",\"Organization\"],\"@id\":\"https:\\\/\\\/rud.is\\\/b\\\/#\\\/schema\\\/person\\\/d7cb7487ab0527447f7fda5c423ff886\",\"name\":\"hrbrmstr\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2023\\\/10\\\/ukr-shield.png?fit=460%2C460&ssl=1\",\"url\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2023\\\/10\\\/ukr-shield.png?fit=460%2C460&ssl=1\",\"contentUrl\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2023\\\/10\\\/ukr-shield.png?fit=460%2C460&ssl=1\",\"width\":460,\"height\":460,\"caption\":\"hrbrmstr\"},\"logo\":{\"@id\":\"https:\\\/\\\/i0.wp.com\\\/rud.is\\\/b\\\/wp-content\\\/uploads\\\/2023\\\/10\\\/ukr-shield.png?fit=460%2C460&ssl=1\"},\"description\":\"Don't look at me\u2026I do what he does \u2014 just slower. #rstats avuncular \u2022 ?Resistance Fighter \u2022 Cook \u2022 Christian \u2022 [Master] Chef des Donn\u00e9es de S\u00e9curit\u00e9 @ @rapid7\",\"sameAs\":[\"http:\\\/\\\/rud.is\"],\"url\":\"https:\\\/\\\/rud.is\\\/b\\\/author\\\/hrbrmstr\\\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/","og_locale":"en_US","og_type":"article","og_title":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is","og_description":"In a recent previous post I brazenly talked over the &#8220;hard parts&#8221; of how I got to the target SQLite file that houses &#8220;mowing history&#8221; for what has become my weekend obsession. So, we&#8217;ll cover just how to do that (find things in iOS backups) in this post along with how to deal with some [&hellip;]","og_url":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/","og_site_name":"rud.is","article_published_time":"2019-06-02T16:35:55+00:00","article_modified_time":"2019-06-03T01:12:44+00:00","og_image":[{"url":"https:\/\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access-530x465.png","type":"","width":"","height":""}],"author":"hrbrmstr","twitter_card":"summary_large_image","twitter_misc":{"Written by":"hrbrmstr","Est. reading time":"10 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#article","isPartOf":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/"},"author":{"name":"hrbrmstr","@id":"https:\/\/rud.is\/b\/#\/schema\/person\/d7cb7487ab0527447f7fda5c423ff886"},"headline":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R","datePublished":"2019-06-02T16:35:55+00:00","dateModified":"2019-06-03T01:12:44+00:00","mainEntityOfPage":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/"},"wordCount":1126,"commentCount":2,"publisher":{"@id":"https:\/\/rud.is\/b\/#\/schema\/person\/d7cb7487ab0527447f7fda5c423ff886"},"image":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#primaryimage"},"thumbnailUrl":"https:\/\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access-530x465.png","articleSection":["iOS","macOS","R"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/","url":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/","name":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R - rud.is","isPartOf":{"@id":"https:\/\/rud.is\/b\/#website"},"primaryImageOfPage":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#primaryimage"},"image":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#primaryimage"},"thumbnailUrl":"https:\/\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access-530x465.png","datePublished":"2019-06-02T16:35:55+00:00","dateModified":"2019-06-03T01:12:44+00:00","breadcrumb":{"@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#primaryimage","url":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?fit=1560%2C1370&ssl=1","contentUrl":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2019\/06\/full-disk-access.png?fit=1560%2C1370&ssl=1","width":1560,"height":1370,"caption":"Full Disk Access settings panel in macOS"},{"@type":"BreadcrumbList","@id":"https:\/\/rud.is\/b\/2019\/06\/02\/trawling-through-ios-backups-for-treasure-a-k-a-how-to-fish-for-target-files-in-ios-backups-with-r\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/rud.is\/b\/"},{"@type":"ListItem","position":2,"name":"Trawling Through iOS Backups For Treasure (a.k.a. How to fish for target files in iOS backups) with R"}]},{"@type":"WebSite","@id":"https:\/\/rud.is\/b\/#website","url":"https:\/\/rud.is\/b\/","name":"rud.is","description":"&quot;In God we trust. All others must bring data&quot;","publisher":{"@id":"https:\/\/rud.is\/b\/#\/schema\/person\/d7cb7487ab0527447f7fda5c423ff886"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/rud.is\/b\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":["Person","Organization"],"@id":"https:\/\/rud.is\/b\/#\/schema\/person\/d7cb7487ab0527447f7fda5c423ff886","name":"hrbrmstr","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2023\/10\/ukr-shield.png?fit=460%2C460&ssl=1","url":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2023\/10\/ukr-shield.png?fit=460%2C460&ssl=1","contentUrl":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2023\/10\/ukr-shield.png?fit=460%2C460&ssl=1","width":460,"height":460,"caption":"hrbrmstr"},"logo":{"@id":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2023\/10\/ukr-shield.png?fit=460%2C460&ssl=1"},"description":"Don't look at me\u2026I do what he does \u2014 just slower. #rstats avuncular \u2022 ?Resistance Fighter \u2022 Cook \u2022 Christian \u2022 [Master] Chef des Donn\u00e9es de S\u00e9curit\u00e9 @ @rapid7","sameAs":["http:\/\/rud.is"],"url":"https:\/\/rud.is\/b\/author\/hrbrmstr\/"}]}},"jetpack_featured_media_url":"","jetpack_shortlink":"https:\/\/wp.me\/p23idr-3bH","jetpack_likes_enabled":true,"jetpack-related-posts":[{"id":12645,"url":"https:\/\/rud.is\/b\/2020\/02\/06\/prying-r-script-files-away-from-xcode-et-al-on-macos\/","url_meta":{"origin":12257,"position":0},"title":"Prying &#8220;.R&#8221; Script Files Away from Xcode (et al) on macOS","author":"hrbrmstr","date":"2020-02-06","format":false,"excerpt":"As the maintainer of RSwitch --- and developer of my own (for personal use) macOS, iOS, watchOS, iPadOS and tvOS apps --- I need the full Apple Xcode install around (more R-focused macOS folk can get away with just the command-line tools being installed). As an Apple Developer who insanely\u2026","rel":"","context":"In &quot;macOS&quot;","block_context":{"text":"macOS","link":"https:\/\/rud.is\/b\/category\/macos\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":13042,"url":"https:\/\/rud.is\/b\/2021\/04\/25\/a-small-macos-big-sur-to-extract-indicators-of-compromise\/","url_meta":{"origin":12257,"position":1},"title":"A Small macOS (Big Sur+) App to Extract Indicators of Compromise","author":"hrbrmstr","date":"2021-04-25","format":false,"excerpt":"There's a semi-infrequent-but-frequent-enough-to-be-annoying manual task at $DAYJOB that involves extracting a particular set of strings (identifiable by a fairly benign set of regular expressions) from various interactive text sources (so, not static documents or documents easily scrape-able). Rather than hack something onto Sublime Text or VS Code I made a\u2026","rel":"","context":"In &quot;Information Security&quot;","block_context":{"text":"Information Security","link":"https:\/\/rud.is\/b\/category\/information-security\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":12537,"url":"https:\/\/rud.is\/b\/2019\/10\/28\/spelunking-macos-screentime-app-usage-with-r\/","url_meta":{"origin":12257,"position":2},"title":"Spelunking macOS &#8216;ScreenTime&#8217; App Usage with R","author":"hrbrmstr","date":"2019-10-28","format":false,"excerpt":"Apple has brought Screen Time to macOS for some time now and that means it has to store this data somewhere. Thankfully, Sarah Edwards has foraged through the macOS filesystem for us and explained where these bits of knowledge are in her post, Knowledge is Power! Using the macOS\/iOS knowledgeC.db\u2026","rel":"","context":"In &quot;macOS&quot;","block_context":{"text":"macOS","link":"https:\/\/rud.is\/b\/category\/macos\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":12185,"url":"https:\/\/rud.is\/b\/2019\/05\/12\/quick-hit-updates-to-quicklookr-and-rdatainfo\/","url_meta":{"origin":12257,"position":3},"title":"Quick Hit: Updates to QuickLookR and {rdatainfo}","author":"hrbrmstr","date":"2019-05-12","format":false,"excerpt":"I'm using GitUgh links here b\/c the issue was submitted there. Those not wishing to be surveilled by Microsoft can find the macOS QuickLook plugin project and {rdatainfo} project in SourceHut and GitLab (~hrbrmstr and hrbrmstr accounts respectively). I hadn't touched QuickLookR? or {rdatainfo}? at all since 2016 since it\u2026","rel":"","context":"In &quot;macOS&quot;","block_context":{"text":"macOS","link":"https:\/\/rud.is\/b\/category\/macos\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":12763,"url":"https:\/\/rud.is\/b\/2020\/05\/25\/rswitch-1-7-0-has-been-released\/","url_meta":{"origin":12257,"position":4},"title":"RSwitch 1.7.0 Has Been Released","author":"hrbrmstr","date":"2020-05-25","format":false,"excerpt":"I (and, apparently, Gandalf O_o) are pleased to announce that RSwitch version 1.7.0 has been released. (Direct Download) RSwitch is a macOS menubar utility that: makes it dead simple to manage multiple macOS R versions use the latest RStudio daily builds access remote RStudio Server sessions using in a purpose-built\u2026","rel":"","context":"In &quot;Apple&quot;","block_context":{"text":"Apple","link":"https:\/\/rud.is\/b\/category\/apple\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/rud.is\/b\/wp-content\/uploads\/2020\/05\/gandalf-rswitch.png?fit=480%2C280&ssl=1&resize=350%2C200","width":350,"height":200},"classes":[]},{"id":4611,"url":"https:\/\/rud.is\/b\/2016\/08\/06\/quicklookr-a-macos-quicklook-plugin-for-r-data-files\/","url_meta":{"origin":12257,"position":5},"title":"QuickLookR &#8211; A macOS QuickLook plugin for R Data files","author":"hrbrmstr","date":"2016-08-06","format":false,"excerpt":"I had tried to convert my data-saving workflows to [`feather`](https:\/\/github.com\/wesm\/feather\/tree\/master\/R) but there have been [issues](https:\/\/github.com\/wesm\/feather\/issues\/155) with it supporting large files (that seem to be near resolution), so I've been continuing to use R Data files for local saving of processed\/cleaned data. I make _many_ of these files and sometimes I\u2026","rel":"","context":"In &quot;Objective-C&quot;","block_context":{"text":"Objective-C","link":"https:\/\/rud.is\/b\/category\/objective-c\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]}],"jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/posts\/12257","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/comments?post=12257"}],"version-history":[{"count":0,"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/posts\/12257\/revisions"}],"wp:attachment":[{"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/media?parent=12257"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/categories?post=12257"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/rud.is\/b\/wp-json\/wp\/v2\/tags?post=12257"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}