RSSAmplifier

Blog

Juri Pakaste: Blog

Personal blog of Juri Pakaste

juripakaste.fiRSS feed ↗130 posts

Latest posts

TIL: Typed do in Swift

TL;DR: Swift has do throws(MyError) . It's helpful. This is one of those "I can't believe I had missed that" things. I've been pretty enthusiastic about adopting typed throws in Swift. If you need to process certain kinds of errors, it just makes sense to me. However, it was always a bit painful. You have this: do { // throwing code here } catch { // error is…

Updating multiple rows with SQL and avoiding collisions

I ran into an interesting problem with SQL the other day: how do you update multiple rows while maintaining an uniqueness constraint? I have a table where each row describes an item in an ordered list. Each row has a position value. They are integers, not necessarily contiguous but each unique. A larger position means the row is further down the list. For reordering the rows, I sometimes need to…

New Swift Package: tui-fuzzy-finder

Speaking of new Swift libraries , I released another one: tui-fuzzy-finder is a terminal UI library for Swift that provides an incremental search and selection UI that imitates the core functionality of fzf very closely. I have a ton of scripts that wrap fzf. Some of them try to provide some kind of command line interface with options. Most of them work with pipes where I fetch data from…

New Swift Package: provision-info

I released a new Swift library! provision-info is a Swift package for macOS. Its purpose is to parse and show information about provisioning profile files. There's a command line tool and Swift library. The library part might work on iOS, too, but I have not tried. It relies on Apple's Security framework so no Linux. It's not actually that new, but it's been sitting in a GitHub…

DotEnvy

I released a new Swift library, DotEnvy . It's a parser and loader for dotenv files. Dotenv is a vaguely specified format that is supported by libraries found for most languages used in server-side development. The idea is that a twelve-factor app is supposed to read its configuration from environment variables, which can be a hassle to maintain during development. So you store them in a…

Git history search with fzf

fzf is one of my favorite shell tools. I have a ton of scripts where I use it for selection. Here's one for searching git history. git log -Gpattern allows you to search for commits that contain pattern in the patch text. Combine it with fzf and you get a pretty decent history search tool. I have this saved as ~/bin/git-search-log , so I can invoke it as git search-log pattern or…

Splitting a Xcode project with SPM

I was talking on Mastodon about splitting an Xcode project into smaller pieces. Here's an elaboration. Background: With SwiftUI previews you want small focused Xcode schemes. The larger your scheme, the less likely the preview is to succeed. You also get faster compilation if you don't always build the whole app. You can get smaller schemes with framework build targets or with Swift…

A fast timestamp parser in Swift

I wrote a timestamp parser in Swift. It's called Parse3339 . It's well known that DateFormatter , the main timestamp formatter and parser Apple ships in Foundation, is not particularly fast. It's flexible and it's correct, but it takes its time. The newer ISO8601DateFormatter has similar performance. I haven't much worried about that in the recent years. A while ago I had…

Git worktrees helper

I recently became an avid user of Git worktrees. However, the command line interface to them is about as great as Git command line interfaces always are. Just git worktree add is a confusing maze of options. I wrote a shell script to help myself and then I wanted to check parameters and then I decided that was a bridge too far with shell today and went for Swift instead. My Worktrees tool has just…

Better diff hunk headers with Swift

When you run git diff — or look at diffs in at least Fork — on a modified Swift project you see things like this: @@ -251,7 +251,7 @@ extension AppUITests { let container = app.scrollViews["scroll"] XCTAssertTrue(container.waitForExistence(timeout: 2)) - XCTAssertTrue(container.buttons["Restore"].exists) + XCTAssertTrue(container.buttons["Restore Purchases"].exists)…

Creating icons in Xcode playgrounds

I'm no good at drawing. I have Affinity Designer and I like it well enough, but it requires more expertise than I have, really. Usually when I want to draw things, I prefer to retreat back to code. Xcode playgrounds are pretty OK for writing your graphics code. Select your drawing technology of choice to create an image, create a view that displays it, make it the live view with…

Date component ranges in Swift

Ever needed to iterate over a list of days or months in Swift? Ever needed to have a random-access collection of those? The first thing they teach you in the How to not Operate on Dates Horribly Wrong class (aka Calendrical Fallacies ) is to forget about using seconds for calendar correct calculations. On the Apple platforms you should be using Foundation's Calendar type instead. You will…

Async Swift and ArgumentParser

Swift 5.5 brought us async functions. ArgumentParser is the most popular way to write command line interfaces with Swift. Swift 5.5 supports an asynchronous main function, but ArgumentParser does not, as of version 1.0.2. To bridge this gap, you can call ArgumentParser manually from your asynchronous main function, like this: import ArgumentParser struct MyCommand : ParsableCommand { @Argument var…

Converting between NSBezierPath and CGPath

The macOS SDK ships with at least two graphics path types: NSBezierPath and CGPath . They are mostly used in different contexts but sometimes it would be useful to convert between them. On iOS UIBezierPath has tools for the conversion, but on macOS we have to do it manually. Here are the two conversions, based on Stack Overflow answers ( NSBezierPath to CGPath , CGPath to NSBezierPath ), converted…

Swift networking with AsyncHTTPClient

When you need to access resources over HTTP in Swift, in most cases the answer is URLSession from Foundation. On server side that's most probably not the right choice; there you are most likely running on SwiftNIO and you'll want something that integrates with it. On command line it's a toss up; on macOS URLSession is great, on other platforms… well, hope you don't run into any…

Database connections in Vapor 4

Version 4 of the Swift web framework Vapor was released a while ago. Vapor emphasizes their ORM, Fluent, and it seems that version 4 has changed how a database connection can be acquired if you prefer to write the SQL yourself. They've also skipped documenting it, so getting things working requires some digging. In this post I'll explain how to do it. I'm using PostgreSQL. You need…

Alfred Script Filter with find and jq

Looks like this is a jq blog now, so here's another one. I work on an iOS repository that's used to create a large number of apps and a few frameworks. Each app has a directory with configuration and a script that regenerates the associated Xcode project with XcodeGen . You can run the script from the shell, or from Finder. Both of these require that you navigate to the appropriate…

Diff two modified JSON files in fish

Another interesting command line JSON exercise: you have two JSON files, you want to diff a modified version of one to the other, and your shell is fish . For making JSON diffable, gron is a great choice: it transforms a JSON file into a list of assignment lines. Like this: $ echo '{"a": ["b", "c"]}' | gron json = {} ; json.a = []; json.a[0] = "b" ; json.a[1] = "c" ; gron doesn't help us with…

Copy value with jq

I use jq heavily in my day to day work. It's a powerful tool but not always easy, so I have piles of notes about how to do things with it. I had to do a few iterations of copying a value from one JSON file to another the other day, and the files are large, and copying and pasting and launching editors was getting old, so I reached for jq. And after digging for a while and reading Stack…

Parsing and evaluating mathematical expressions in Swift / Part 3: Interpreter

Ever needed to interpret mathematical expressions with variables, like a.field1 + (a.field2 - b.field1) * 2 , in Swift? I did. This series of blog posts will walk you through my solution. This is part 3 of the series: Tokenization Building a syntax tree Evaluating the syntax tree Evaluating the syntax tree To recap, we started with the string a.field1 + (a.field2 - b.field1) * 2 and ended up with…

Parsing and evaluating mathematical expressions in Swift / Part 2: Building a syntax tree

Ever needed to interpret mathematical expressions with variables, like a.field1 + (a.field2 - b.field1) * 2 , in Swift? I did. This series of blog posts will walk you through my solution. This is part 2 of the series: Tokenization Building a syntax tree Evaluating the syntax tree Parsing a list into a syntax tree A refresher: we're looking at this expression: a.field1 + (a.field2 - b.field1)…

Parsing and evaluating mathematical expressions in Swift / Part 1: Tokenization

Ever needed to interpret mathematical expressions with variables, like a.field1 + (a.field2 - b.field1) * 2 , in Swift? I did. This series of blog posts will walk you through my solution. This is part 1 of the series: Tokenization Building a syntax tree Evaluating the syntax tree Background I needed to handle math expressions with a solution that would allow me to parse them in one place and later…

Looser dependencies with Swift

What kind of types do you use to manage dependencies between objects in Swift? How do you keep your objects that depend on others testable? How do you prevent an addition of a method from causing changes to test code? Couplings should be loose, but how to achieve that? Assumptions I’m making a few assumptions in this article: Your software has semi-permanent pieces — let’s call them services —…

GraphQL with Swift

Know that thing where you start writing a tool for something, discover it needs (for some values of “need”) something slightly complicated, you decide to write a library for said complicated thing, then discover you don’t need the tool you were working on in the first place but decide to write the library anyway? So I wrote GraphQLer (pronounced “graph quiller”), a library for generating GraphQL…

annotate-git-commit

I got into the feature branch workflow back when I was using Mercurial. I’ve since discovered that Mercurial’s branches aren’t really suitable for short-lived branches and switched to Git for a variety of reasons, but I still wish my commits carried with them metadata about what they were related to. I also still wish my VCS had a sane UI, but that’s an unrelated topic. Anyway, my Git branches,…

TODO.swift

I saw this Swift trick a few years ago on Twitter. I can’t recall who it was, sorry. It sounded way too clever at first, but after a while I tried and decided I love it. Now it’s one of those things I add to every project. Sometimes you just want to get on with declaring your functions without worrying about the actual implementations. A small enough function with good enough name and types is…

Converting UNIX dates to a readable format on Mac

I tend to run into UNIX dates — large numbers representing points in time as seconds since the first second of 1970, something like 1500000000 for 2017-07-14 05:40:00 — all the time in my work, dealing with servers, web APIs, etc. Here's how to make them readable on a Mac. All text below assumes macOS 10.13. Terminal The most straightforward solution is probably to open Terminal.app and run…

Netstrings for Swift

I published another small Swift library: swift-netstring implements reader and writer for D. J. Bernstein's Netstrings format in Swift. Netstrings is a specification for length-prefixed and delimited byte strings, useful mostly as a low-level building block for network protocols. With swift-netsring you can parse incoming data from a socket or some other stream by wrapping the stream in a…

Flue: Fluent API for value extraction and conversion for Swift

Flue is a Swift (3.0, as of this writing) library for extracting, validating and converting values from user input. It tries to do this with a fluent interface: vp. extract ( "100" ). maxLength ( 6 ). regexp ( "1.*" ) ! . asInt (). required () It can output readable help and error messages from your conversions. See the README for details. Enjoy.

Talking to servers: WebSockets

This is a sort of follow-up post to ZeroMQ, iOS and Python from a year ago. I again wrote a test app and server. Of the earlier components, iOS stayed, but ZeroMQ I replaced with WebSockets and the server is this time written in Clojure. Idea of the exercise is the same as last time: two-way communication between an iOS client and server over a persistent connection. WebSockets is a more…

NSStringinfying enums from AppCode

I added a --text option to nsstringfromenumgen so it can be used with JetBrains' excellent Objective-C IDE, AppCode . AppCode doesn't integrate with OS X services, but you can configure nsstringfromenumgen as an "External Tool" and provide the selected text as a parameter. There's still an extra copy & paste step not needed with Xcode and Services, but it's not too bad.

NSStringinfying enums

Making sense of enum values in C is too difficult. Usually sooner rather than later while debugging you need to see what's inside an enum value, but C provides no introspection tools. You just get an integer value, no mapping to the original symbolic name. That's why every enum should be accompanied by a stringifying function, but that requires manual labor. Few programmers are happy to…

ZeroMQ, iOS and Python

I wrote some example code for you. Background: last week a coworker asked me what's the flavor du jour in two-way communication between a network server and an iOS app, should he just go with BSD sockets or is there something better? I suggested he should take a look at ZeroMQ . Not that I actually knew very much at all about it, but I had heard the name and seen that some people were pretty…

Unit testing Cocoa code with MacRuby

Announcing RCRunner , a GUI test runner for MacRuby and Cocoa. Cocoa unit testing can be a pain. In addition to the usual difficulties of writing tests for user interface heavy code, the Apple sanctioned solution, SenTestingKit, can isn't the greatest testing framework around and the default way of using it rules out debugger. GHUnit helps somewhat. It's a GUI test runner with additional…

Using Firefox as Flash playing Safari fallback

If you want to go Flashless on Mac and Safari, it&#x27;s possible to use Firefox as a fallback, too, not just Chrome. While Firefox does load Plugins from &#x2F;Library&#x2F;Internet Plug-Ins and &#x2F;Library&#x2F;Internet Plug-Ins , it looks in other places too. I just tested and it seems to work fine from &#x2F;Library&#x2F;Application Support&#x2F;Firefox&#x2F;Profiles&#x2F;<profile…

xibgraph: Interface Builder overviews

When putting together user interfaces with Interface Builder, you connect things together with bindings, actions and outlets and it&#x27;s good. Understanding the result later on is a completely different matter. It can be time consuming and difficult to browse the objects inside one by one, trying to comprehend the whole. Even more so if you&#x27;re trying to read someone else&#x27;s work. Out of…

hg-status-sections

I usually use Murky , dvc or some other shell for Mercurial. Not always though, for various reasons, and when running hg status I&#x27;m always frustrated when copy and pasting file names. bzr provides neat, non-cluttered lines that can be copied whole to get a file name without a hassle, but hg takes the traditional one-character prefix approach to status display and as a result makes you…

A better @synthesize

The biggest problem with Objective-C&#x27;s @synthesize directive for properties is how difficult it&#x27;s to augment the synthesized code. You often need to add logic to a property setter, but while you&#x27;re adding it, you&#x27;re losing the probably correct implementation Apple&#x27;s code creates for property flags like atomic and retain . At the moment, when you synthesize a readwrite…

Block indentation in Emacs

There are several small things Emacs could be doing to make it nicer to write code. One I was missing was making it possible to go with one press of the return key between braces in a C derived language from this: if (test) { } to this: if (test) { <-- insertion point here } That is, pressing return before the closing parentheses, brace or bracket should move the closing character two lines down,…

Exporting geolocation data from iPhoto with AppleScript

I recently transferred all my photos to iPhoto. I share them on Flickr, but I&#x27;ve been unhappy with iPhoto&#x27;s built-in Flickr support — it has an arbitrary 500 photo limit on web album size, it&#x27;s crashy, it does weird synchronizations that take ages when combined with lots of large photos and a slow internet connection, it has multiple times failed to send all the full-resolution…

Announcing Chipmunk Backup

I put up on Launchpad a backup utility I wrote called Chipmunk Backup . It&#x27;s not extremely configurable nor does it have a huge set of features. It&#x27;s a simple tool for maintaining a number of GnuPG encrypted full backups of a directory in a remote, rsync-accessible location. There&#x27;s no ready to download archive, but checking out lp:chipmunk-backup with bzr should give you a working…

Emacs tips: Navigate CamelCase words

Emacs tip #0: Always search EmacsWiki when you think you might need something. Emacs tip #1: To navigate studlyCapped words, M-x c-subword-mode , as found on the CamelCase page . I had to add the following lines to my .emacs to get it work with C-left &#x2F; C-right , M-b &#x2F; M-f worked right out of the box: (define-key global-map [(control right)] 'forward-word) (define-key global-map…

Inline admin forms with admin site links in Django

I have a somewhat difficult relationship with Django &#x27;s admin site. It&#x27;s a very useful feature, but I haven&#x27;t really done enough with it to know when I&#x27;m going to hit a wall, if that wall&#x27;s in the code or in my understanding, and how hard it&#x27;s going to be to climb over the wall. This time I wanted to have inline admin forms , except that I didn&#x27;t actually want to…

iPhone shuffle

These days I use an iPhone as my mobile music device. I have a bit over 1800 songs on it. I usually use shuffle and had it stuck in a weird state a couple of weeks ago — it was constantly playing me just a few tracks . I usually listen for just half an hour to an hour at a time, so I don&#x27;t know if it would have started looping or what, but those were basically always there for a week&#x27;s…

Crashes with NSURLConnection

Speaking of Cocoa (and iPhone) programming, for a change. Having trouble with spurious EXC_BAD_ACCESS crashes when using NSURLConnection? NSZombie giving you not very clear messages about [Not A Type retain], pointing to an address that malloc_history says has been allocated somewhere with only framework code in the call stack? See Amro Mousa&#x27;s blog entry about the subject. In a nutshell,…

Various Python related things

Python Magazine published my article "Using Dependency Injection in Python" in their August issue . Doug Hellman saw my blog entry about DI when I was switching web hosting and managed to repost old stuff to Planet Python, contacted me to ask if I wanted to expand on it a bit, I said yes, and now I&#x27;ve been published. Which is nice. I basically argue in the article that dependency injection is…

Flow 08: Saturday and Sunday

On Saturday, it was raining cats and dogs. We were appropriately equipped and sniggered at the people in trainers etc trying to dodge the puddles. However, didn&#x27;t see too many acts — saw a bit of Sébastien Tellier , but decided the crowds were too much and went to find some food (which was excellent and at 25 € for a three course vegetarian menu pretty good value.) Next up on our schedule was…

Flow08, Day 1

Flow08 started off a whole lot better than last year . Everything worked smoothly despite the fact that there were twice as many people and twice as large an area as last year. In fact, the enlarged space felt better than the more constrained area of last year, maybe because we got to see more of the Suvilahti grounds. Artists we saw: Jamie Lidell was a positive surprise. I found a video I saw…

Using custom widgets with Django&#x27;s newforms-admin

The following isn&#x27;t magic but it was unclear to me and required reading both documentation and source code and some additional Googling to get right. Maybe that&#x27;s because I&#x27;m a Django newbie, but hey, I&#x27;m probably not the only one. By the way, the following applies to Django SVN revision 8068. That&#x27;s roughly Django 1.0 alpha. Anyway, I have in my model a field that&#x27;s…

A moment of C++ hate

Apologies, I&#x27;m going to indulge myself for a moment. If you aren&#x27;t interested in C++ ranting, skip this. I&#x27;m in the process of converting some C++ code to heap allocate objects instead of putting them in the stack, because I need to use them in Objective-C++ and stack-allocated objects aren&#x27;t the best idea there. Who in their right mind wants to spend programming time worrying…