Streamlining Git Workflows with Shell Scripts and AppleScript

Enhancing development workflow through automation

Posted by Michael S on September 22, 2024

Woke up at 8:30 a.m. today after a late night of coding where I was trying to build an iPhone app to generate audio from text. Spent the morning catching up on emails and planning out my tasks for the day. Didn't get much coding done before lunch, but that's alright. The afternoon is when the real fun begins.

Around midday, I headed down to Stonestown for a change of scenery. I listened to MrBeast's book, the inspiration for my app, while I was there. How to Succeed in MrBeast Production [sic]. While I was there, I couldn't help but notice the prices at Shake Shack. Can you believe they charge $10 for a burger with "black truffle sauce" made with "real black truffle oil"? For comparison, their regular hamburger goes for $7.50. Quite the markup for a bit of truffle oil, if you ask me. And their regular burger is super expensive, too. I'm not sure I'd pay $7.50 for a burger unless I had to. But I was raised to be cheap, so can't base any assumptions of other people on my own price. Once I have enough, I'll start paying more for food. And maybe not food that was picked out of the ground by a pig or a dog.

After my Stonestown excursion, where I didn't even work out at the Y, I came back home for lunch. Had a nice big bowl of vegetable soup and some carrots. Simple, but satisfying. Then it was back to work on the iPhone app. Managed to get a nice frontend put together for the free version. Still need to figure out how to save the files, but it's coming along.

2:15 PM: Automating Git Commit Messages

I've been meaning to streamline my git workflow for a while now. Today, I finally got around to it. I created a shell script that generates concise git commit messages using OpenAI's API. It takes the git diff of the staged changes and sends it off to the API and handles the API key securely, which then returns a nicely formatted commit message. Here's the script I came up with:


curl -X POST "https://api.openai.com/v1/chat/completions" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $(defaults read ~/Library/Preferences/(my_file_location_-_use_your_own).plist openaiApiKey)" \
-d @- <(): "
    },
    {
      "role": "user", 
      "content": "Generate a concise git commit message based on the following changes (if no changes are provided, return the following message: 'No staged changes. Stage your changes and try again.'):"
    },
    {
      "role": "user",
      "content": "$(git diff --cached | sed 's/&/\&/g' | sed 's//\>/g' | sed 's/\"/\"/g' | sed 's/'"'"'/\'/g' | sed 's/\//\//g' | sed 's/\\/\\\\/g')"  
    }
  ],
  "temperature": 0,
  "max_tokens": 300
}
EOF
                    

It took a bit (okay, a lot) of trial and error to get the API calls working just right, especially when it came to handling the git diff output. But once I got it figured out, it was smooth sailing (ha! had to edit it again just now at 10:15 p.m. to work for HTML files and the

\ No newline at end of file
that shows up (...if there's no newline at the end of a committed file) when publishing this blog post). Now I can stage my changes, run the script, and boom - a nice, tidy commit message ready to go. No more staring at the terminal for 15 min trying to come up with something clever to say.

A few hours of work to save 10 seconds every time I commit! Okay, it'll actually save anywhere from 10 seconds to 15 minutes and potentially lost focus every time I commit. But because it prevents losing focus when I switch contexts and look over what I've done, it's worth it.

Make a plist file to store the API key in ~/Library/Preferences/ (use your own file name). Then, to use the script, run the following command in the terminal:


sh '/path/to/script/generate-git-commit-message-from-staged-changes.sh'
                    

In case you want an example PLIST file to store the API key, here's one. Replace the API key with your own. Doesn't have to be fancy, just needs to store the key.


<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>openaiApiKey</key>
    <string>sk-proj-...</string>
</dict>
</plist>
                    

4:45 PM: Troubleshooting AppleScript

In addition to the shell scripts, I've also been working on an AppleScript to automate updating my git repository. The idea is to have it run on a schedule, pulling down the latest changes and keeping everything in sync. Unfortunately, it's been throwing some errors that I haven't quite been able to track down.

I spent a good chunk of the afternoon digging through the script, trying to pinpoint where things are going wrong. No luck so far, but I'll keep at it. Worst case, I can always fall back to good old-fashioned manual updates. But where's the fun in that?

6:00 PM: Dinner Time

Called it a day around 6:00 p.m. and whipped up some dinner. Started with a nice fresh salad, then was still hungry, so moved on to the main course: fish (salmon) with buckwheat. Simple, healthy, and delicious. Oh, and I couldn't resist ending the meal with a few chocolate truffles. Which, come to think of it, reminds me of that "black truffle sauce" at Shake Shack. I wonder how their truffles compare to the real deal?

6:30 PM: Wrapping Up

All in all, a pretty productive day on the git automation front. The commit message script is already saving me time, and once I get the AppleScript sorted out, if I bother to do it, my workflow will be even smoother. As of right now, it's not harming me enough to make me make fixing it a priority. It's always satisfying to take a process that used to be tedious and error-prone and turn it into something that just works.

Of course, there's always more to be done. I've got a few ideas for additional features to add to the script, and I'm sure I'll think of other ways to optimize my development process as I go. But for now, I'm calling it a day. Time to push these changes and kick back with some well-earned rest and relaxation.

P.S.: By the way, if you ever wonder why I write AM and PM in the headings and a.m. and p.m. in the text, it's because the Chicago Manual of Style says to use a.m. and p.m. for times, so I include them when writing, and Apple, the new authority on style followed by everyone, uses AM and PM for the times, so I follow Apple for SEO.

Enjoyed this post?

Get notified when I publish something new. No spam, unsubscribe anytime.