Skip to content

Instantly share code, notes, and snippets.

View tomsaleeba's full-sized avatar

Tom Saleeba tomsaleeba

View GitHub Profile

Keybase proof

I hereby claim:

  • I am tomsaleeba on github.
  • I am tomsaleeba (https://keybase.io/tomsaleeba) on keybase.
  • I have a public key ASCQLgwf5nOen0sIm5tyL5yq_ZO2slYSfrfH69tm02Y91go

To claim this, I am signing this object:

@tomsaleeba
tomsaleeba / bash-wait-demo.sh
Created March 9, 2018 00:23
BASH wait command demo
#!/usr/bin/env bash
# short demo on how to wait for multiple jobs
echo 'start'
sleep 2 &
job1=$!
echo "do things that don't require job 1 output"
sleep 4 &
job2=$!
echo "do things that don't require job 2 output"
wait $job1
@tomsaleeba
tomsaleeba / README.md
Last active May 16, 2018 00:32
Concatenating RDF Turtle files

ttlcat

When you have a series of *.ttl files in a directory and you want to cat them all together, you need to make sure you strip out the @prefix and only prepend it once to the output.

Use the following commands

# run *in* the directory with the TTL files
head -n 50 -q *.ttl | grep '^@prefix' | sort -u > header
time cat *.ttl | grep -v '^@prefix' | cat header - | gzip > $(basename $(pwd)).ttl.gz
rm header
@tomsaleeba
tomsaleeba / README.md
Last active May 18, 2018 04:25
Bulk file rename

Assume have a directory of files in an Angular.io project. We need to clone them all but rename and do a find+replace in them to work with another model name. The old model is plot and the new model is photo.

  1. Clone the directory and contents
    cp -r plot photo
    cd photo
  2. create a script to receive the results from our find:

blah.sh

@tomsaleeba
tomsaleeba / async-await-error-handling.js
Created July 24, 2018 03:16
NodeJS async/await error propagation
// direct as promise
;(function () {
const prefix = '[direct-promise level]'
async function direct () {
throw new Error(`${prefix} explosion`)
}
direct().then(() => {
console.log(`${prefix} success`)
}).catch(err => {
@tomsaleeba
tomsaleeba / README.md
Last active February 20, 2019 04:06
FISH shell VI keybindings with ctrl-<arrow> word navigation
  1. enable VI mode
    fish_vi_key_bindings
    
  2. restore the word navigation keys I'm used to in insert mode
    cat << EOF > ~/.config/fish/functions/fish_user_key_bindings.fish
    function fish_user_key_bindings
      bind -M insert \e\[1\;5C nextd-or-forward-word   # ctrl-right
    

bind -M insert \e[1;5D prevd-or-backward-word # ctrl-left

@tomsaleeba
tomsaleeba / README.md
Last active December 11, 2019 07:09
iNat bulk upload instructions

Which method is for me?

If you have a bunch of photos to upload, and they have location information embedded in the photo, then you have a few options.

  1. If they're on your phone, you can use our app (at the time of writing our app doesn't yet support reading the location information from photos, but it will)
  2. Use the "regular" upload method for iNat via their website

If you have observations that do not have a photo, or do have a photo but the photo does not have location information embedded in it, then the CSV based bulk upload if the best choice.

@tomsaleeba
tomsaleeba / puzzle.jpg
Last active April 15, 2020 00:42
Kimmy's "dress the man" puzzle
puzzle.jpg
@tomsaleeba
tomsaleeba / imagemagick-watermark-readme.md
Created April 16, 2020 09:02
How to add watermarks with ImageMagick
$ magick --version
Version: ImageMagick 7.0.10-3 Q16 x86_64 2020-03-28 https://imagemagick.org
Copyright: © 1999-2020 ImageMagick Studio LLC
License: https://imagemagick.org/script/license.php
Features: Cipher DPC HDRI Modules OpenMP(4.5) 
Delegates (built-in): bzlib cairo fontconfig freetype heic jbig jng jp2 jpeg lcms lqr ltdl lzma openexr pangocairo png raqm raw rsvg tiff webp wmf x xml zlib

The command

@tomsaleeba
tomsaleeba / can-js-promises-be-cancelled.js
Created April 29, 2020 11:57
A test to see if you can truly cancel JS promises. Spoiler: you can't.
// Question: does calling reject on a running promise cut it short?
// Answer: sort of. It returns to the caller early but it keep running behind
// the scenes. So more of a short-circuit than really being cancelled.
const printFrequency = 500
const printRounds = 10
const cancelPoint = 7
let someOtherState = 'untouched'