Skip to content

Instantly share code, notes, and snippets.

View Thomascountz's full-sized avatar
💃
LGTM!

Thomas Countz Thomascountz

💃
LGTM!
View GitHub Profile
@Thomascountz
Thomascountz / extract_apple_memos_transcript.sh
Last active June 10, 2025 23:25
Extract transcript text from Apple Memos M4A file
#!/bin/bash
if ! command -v mp4extract >/dev/null 2>&1; then
echo "Error: mp4extract is not installed or not in your PATH." >&2
echo "Please install it and try again" >&2
exit 1
fi
if ! command -v jq >/dev/null 2>&1; then
echo "Error: jq is not installed or not in your PATH." >&2
@Thomascountz
Thomascountz / apple_memos_transcription_extractor.rb
Last active June 10, 2025 23:24
Extract transcript text from Apple Memos M4A file
require "json"
class AppleMemosTranscriptionExtractor
class TsrpAtomNotFoundError < StandardError; end
class TranscriptDataInvalidError < StandardError; end
class MalformedAtomError < StandardError; end
RECORDINGS_PATH = "#{Dir.home}/Library/Group Containers/group.com.apple.VoiceMemos.shared/Recordings".freeze
require "json"
require "open-uri"
require "date"
## DESCRIPTION:
# This script reads the Gemfile.lock of a Rails project and extracts the Rails
# version from each commit that updated the activerecord gem. It then uses the
# endoflife.date API to get the EOL date for each Rails version, and computes
# the number of days until EOL for each commit. Finally, it groups the results
# by year and prints the max, min, and avg "days until EOL" for each year.
@Thomascountz
Thomascountz / ijq.sh
Last active January 31, 2025 23:53
(Yet another) interactive jq, but it's a bash script using fzf
#!/usr/bin/env bash
set -euo pipefail
if [ "${1:-}" = "--help" ]; then
cat << EOF
Usage: ijq [filename]
A wrapper around jq that uses fzf to interactively build jq filters.
@Thomascountz
Thomascountz / progress.rb
Created January 2, 2025 19:30
Progress bar in Ruby
def print_progress(title, total, current_progress, bar_width: 50)
progress_pct = (current_progress.to_f / total) * bar_width
printf("\r#{title}: [%-#{bar_width}s ] -- %s", "▤" * progress_pct.round, "#{current_progress}/#{total} ")
end
# Usage
1.upto(10) do |i|
print_progress("Here we go!", 10, i)
sleep 0.2
end;print("\n")
@Thomascountz
Thomascountz / models_to_erd.rb
Last active July 30, 2024 14:42
Turn your ApplicationRecord models into a Mermaid ERD
Rails.application.eager_load!
# Instead of all ApplicationRecord descendants, you can
# make an Array of only the models you care about
data = ApplicationRecord.descendants.each_with_object({}) do |model, data|
model_name = model.name.upcase
data[model_name] = {
columns: model.columns.map { |column| [column.name, column.sql_type] },
associations: model.reflect_on_all_associations.each_with_object({}) do |reflection, assoc_data|
assoc_data[reflection.name] = {
@Thomascountz
Thomascountz / laser_cut_test_card.svg
Created December 5, 2023 19:06
Laser Cut Test Card
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
@Thomascountz
Thomascountz / async_http_client.py
Last active October 25, 2023 13:43
AsyncHttpClient is an asyncio-based MicroPython library, designed for asynchronous, concurrent HTTP/HTTPS requests to avoid blocking the execution of other coroutines.
# v0.1
import usocket as socket
import ussl
import uasyncio as asyncio
import ujson as json
from utime import ticks_ms, ticks_diff
class AsyncHttpClient:
"""
@Thomascountz
Thomascountz / closures.md
Created August 7, 2023 01:23
Closures in Ruby

🚀 Let's explore Closures in #Ruby with a space-themed example! 🌌 #ThomasTip

Closures are functions/methods that can be invoked from other functions or methods, while retaining access to variables from their original scope.

def launch_sequence(seconds)
  start = Time.now
  -> do
    elapsed = Time.now - start
 remaining = seconds - elapsed.round
@Thomascountz
Thomascountz / hash_struct_data_class_benchmark.rb
Created August 4, 2023 18:45
Ruby Hash v. Struct v. Data v. Class
require 'benchmark/ips'
PointStruct = Struct.new(:x, :y, :grayscale)
PointData = Data.define(:x, :y, :grayscale)
class PointClass
attr_accessor :x, :y, :grayscale
def initialize(x, y, grayscale)