@simontatham Here's a possible alternative. At work we have a repo created with 'git clone --mirror' from upstream. When I clone that repo for development, 'git push -n' from my worktree is a local operation, and I do 'git push upstream my-branch:remote-branch' when everything looks ok (after setting up the 'upstream' remote).
(if the upstream updated in the meantime, I have to 'git fetch' in the mirror repo, and 'git pull --rebase' in my tree)