Code Snippets


Select IDs starting with a number

#12345       { /* Doesn't work!  */ }
[id="12345"] { /* Does work!     */ }
#\31 2345    { /* Works as well. */ }

Taken from this CSS-Tricks article.


Fix video thumbnails on iOS devices

In some cases, iOS devices will not display video thumbnails. To fix this, add #t=0.001 to src, for example:

<video src="video.mp4#t=0.001"></video>

Thanks to Stanko Tadić.

Theme-based stylesheets

<link rel="stylesheet" href="light.css" media="(prefers-color-scheme: light)">
<link rel="stylesheet" href="dark.css" media="(prefers-color-scheme: dark)">

This is not supported by IE and other lesser known browsers.


Asynchronous functions in loops

const start = 0;
const end = 5;

for (i = start; i < end; i++) {
    setTimeout(() => {
        console.log(i); // -> 5, 5, 5, 5, 5

function forSync(i) {
    setTimeout(() => {
        console.log(i); // -> 0, 1, 2, 3, 4
        if (i + 1 < end) forSync(i + 1);

This allows for asynchronous functions by placing the callback within that function.

Await a forEach function

Instead of:

await x.forEach(async y => y);


for (y of x) await y;

See joeytwiddle’s gist for more details.

Await a map function

Instead of:

await y => y);


await Promise.all( y => y));

Check if executable exists in PATH

const path = require("path");
const fs = require("fs");

process.env.PATH.split(path.delimiter).some(x => fs.existsSync(path.join(x, "node")));

Connection test (204) server

const http = require("http");

http.createServer((req, res) => {

Or, as a minified version:


Convert duration to seconds

input.split(":").reduce((p, c) => p * 60 + Number(c));

//       1 -> 1
//    1:00 -> 60
// 1:00:00 -> 3600

Don’t use replacement patterns

When using String.prototype.replace(), the dollar sign is used for special replacement patterns. If this is undesirable (for example, when handling user input), a custom replacement function can be used like so:

"€€".replace("€€",       "$$"); // -> $
"€€".replace("€€", () => "$$"); // -> $$

Axiom – the static site generator behind this website – uses this workaround as well.

Expand Bootstrap accordions via URL

$(".collapsed[data-target='" + window.location.hash + "']")?.click();

Did I mention that optional chaining absolutely rocks?

Export promise with arguments

const module = require("./module");
module("Hello!").then(console.log); // -> Hello!

module.exports = (input) => {
    return new Promise((resolve, reject) => resolve(input));

exports won’t work, only module.exports will!

Get DOM element from jQuery element


Use either, see the jQuery FAQ.

insertAdjacentHTML() positions

<!-- beforebegin -->
    <!-- afterbegin -->
    <!-- beforeend -->
<!-- afterend -->

Copied from the MDN documentation.

Shift array without mutation

var array = [1, 2, 3, 4, 5];
var [head, ...tail] = array;

console.log(array); // -> [1, 2, 3, 4, 5]
console.log(head); // -> 1
console.log(tail); // -> [2, 3, 4, 5]

Swap out variable values

var a = 1;
var b = 2;

[a, b] = [b, a];

console.log(a); // -> 2
console.log(b); // -> 1

You can also specify more (or less) than two variables.

Temporarily edit page in browser

document.body.contentEditable = "true";
document.designMode = "on";

Changes, of course, won’t be saved, but it may still prove helpful in some situations.

Write to clipboard

navigator.clipboard.writeText("Text").then(function() {
    // Success!
}, function() {
    // Error!

This is not supported in IE, and Firefox hides it behind a flag in some cases.


Temporarily disable Composer cache

COMPOSER_CACHE_DIR=/dev/null composer

See the Composer documentation for details.

Use PHP variables in variable names

$foo = "bar";
$$foo = "baz";
echo $bar; // -> baz

Here, $$foo resolves to $bar!


Connect via ZOC from WinSCP

WinSCP → Options → Preferences → Applications → PuTTY/Terminal client path:

"zoc.exe" /CONNECT:!U:!P@!@:!# "/RUN:%USERPROFILE%\Documents\ZOC8 Files\REXX\cd.zrx" "/RUNARG:!/"

%USERPROFILE%\Documents\ZOC8 Files\REXX\cd.zrx:

CALL ZocSend "cd '"ARG(1)"'^M"

Copy input to output on Linux

cat input > output
cp input output
dd if=input of=output
tee < input > output

Change video framerate without interpolation or re-encoding

To convert a video with X FPS to a video with Y FPS, divide X by Y, and use the result like so:

ffmpeg -itsscale X/Y -i input.mp4 -c copy output.mp4

This only accounts for video frames; the audio will not speed up or slow down.

Create new PostgreSQL user and database


Don’t kill process when logging out

First, press CTRL+Z on the running command. Then:


Don’t kill user systemd units when logging out

loginctl enable-linger

Download input to output

aria2c input -o output
bitsadmin /transfer "" input output
curl input -o output
http input > output
https input > output
httrack -g input -N output
lftp -c get input -o output
powershell iwr input -outf output
pwsh -c iwr input -outf output
rclone copyurl input output
snarf input output
wget input -O output
wget2 input -O output

Uses either aria2, BITSAdmin, curl, HTTPie, HTTrack, LFTP, Windows PowerShell, PowerShell, rclone, snarf, Wget or Wget2.

Fix choppy video playback in Firefox installed via Flatpak

First, run the following:

flatpak install flathub org.freedesktop.Platform.ffmpeg-full

When asked for a version to install, choose the latest version (at the time of writing, this is 21.08) and make a mental note of it.

Then add the following lines to /var/lib/flatpak/app/org.mozilla.firefox/current/active/metadata, replacing 21.08 with the version you installed:

[Org.freedesktop.Platform.ffmpeg-full extension]
directory = lib/ffmpeg
add-ld-path = .
no-autodownload = true
version = 21.08

Adapted from bug 1628203. I have found that the relevant metadata section is already present in some cases, in which you don’t have to add it manually.

Fix error 0x80073D05 when installing WSL on Windows

Remove-Item -Recurse $env:LOCALAPPDATA\Packages\CanonicalGroupLimited.UbuntuonWindows_79rhkp1fndgsc # Ubuntu
Remove-Item -Recurse $env:LOCALAPPDATA\Packages\TheDebianProject.DebianGNULinux_76v4gfsz19hv4       # Debian

Fix Puddletag not starting on Linux

The respective repositories may currently ship an outdated version of Puddletag that uses a deprecated pyparsing function. To make it use the new one:

sudo sed -i "s/operatorPrecedence/infixNotation/g" /usr/lib/python3/dist-packages/puddlestuff/

Thanks to Bloom on the Debian User Forums.

Install Docker on Raspberry Pi

curl | sh
sudo apt install uidmap install
echo export DOCKER_HOST=unix:///run/user/1000/docker.sock >> ~/.bashrc
source ~/.bashrc

Open .URL files with default browser on Linux via Nemo

Right-click on any .URL file, select “Open With”, “Other Application” and enter the following in the “Enter a custom command…” field:

sh -c "cat %F | grep URL= | cut -d '=' -f2- | xargs -n 1 xdg-open"

Pin retweets to Twitter profile

  1. If applicable, undo the retweet of the respective tweet.
  2. Open the browser’s network inspector and retweet it again.
  3. Open the response of the POST request to CreateRetweet.
  4. Copy the value of data.create_retweet.retweet_results.result.rest_id.
  5. Run twurl -d "tweet_mode=extended&id=rest_id" /1.1/account/pin_tweet.json, replacing the rest_id placeholder.

Re-use blocks in Caddyfile

(foo) {
} {
    import foo

See the Caddy documentation for details.

Run Flatpak apps over SSH with X11 forwarding

flatpak run --share=network --command=bash com.example -c "DISPLAY=$DISPLAY example"

Set up X11 on WSL 2

First, start an X11 server on the host machine, for example:

vcxsrv.exe -ac -multiwindow

Then, update the DISPLAY variable with the appropriate IP address:

export DISPLAY=$(cat /etc/resolv.conf | grep nameserver | awk '{print $2}'):0

Use video as wallpaper on Linux

xwinwrap -fdt -g 1920x1080      -ni -- mpv -wid WID --loop  LEFT.MP4 &
xwinwrap -fdt -g 1920x1080+1920 -ni -- mpv -wid WID --loop RIGHT.MP4 &

This example is optimized for my two-minitor setup and uses xwinwrap as well as mpv.