Skip to content

Instantly share code, notes, and snippets.

View fabianeichinger's full-sized avatar

Fabian Eichinger fabianeichinger

  • Munich, Germany
View GitHub Profile

Compiling Telegram for iOS

Tested only in a simulator.

Compiles the official Telegram iOS Repo on Github as of 9bd7c529b2212b1195d21346bbd7b8c04dfdb8ae.

You'll need an API Key / Hash pair to build a working client.

  1. Clone Telegram repo
$ git clone --recursive https://github.com/peter-iakovlev/Telegram
@fabianeichinger
fabianeichinger / vue-router-multi-type-slug.md
Last active December 18, 2023 19:06
Matching routes based on entity types with slugs in Vue Router

Vue Router (v3) might provide a very simple way to do slug-based routing where the routing for a given URL depends on the entity referenced by the slug. It has advantages to some of the other solutions around, being quite compact and also compatible with routing guards. As an example, think of an online store with category URLs like example.com/catalog/games and product URLs like example.com/catalog/among-us. The path /catalog/games should match with a route that displays the Category component, while the route for /catalog/among-us should display a Product component. But there is no pattern in the paths for the router to detect. We have to check if either a category or product exists with this slug (and usually do so asynchronously) or show a 404 page in case neither exists.

Below is a very basic implementation that works with some bugs and missing features. I'll explain how it works and what is missing further down. A more feature-complete example can be found here: https://jsfiddle.net/zkpbseL

@fabianeichinger
fabianeichinger / radiobutton.md
Created September 2, 2021 15:23
Vue 2 Custom Input Component Skeletons

Radio Button

<template>
  <label
    :class="isChecked ? 'bg-red' : 'bg-green'"
  >
    <input
      type="radio"
      v-bind="$attrs"
 :value="value"
@fabianeichinger
fabianeichinger / Find Apple Watch.md
Created May 19, 2022 22:28
Find your Apple Watch without Find My

You can play a sound on your Apple Watch from your iPhone without Find My. It needs to be powered on and in range. I usually prefer that when I know it's somewhere close. The sound is less annoying and there is no email from Apple about a sound being played. Also it won't randomly trigger the sound at a later time in case the Watch is turned off.

  1. Open the Watch app
  2. Go to Sounds & Haptics
  3. Tap on the louder end of the Alert Volume slider
  4. Your Apple Watch should play a click sound
  5. Repeat 3. until you find it
@fabianeichinger
fabianeichinger / _htmx-ext-shopify.md
Last active November 10, 2024 18:52
htmx extension for Shopify Ajax API

htmx-ext-shopify gives you access to the Shopify Ajax API from HTML to progressively enhance your Liquid templates. It's an unofficial, experimental extension for htmx.

The extension manipulates API requests and responses in order to replace / update Liquid sections on the current page. The new HTML for sections comes from Bundled section rendering and inserted using htmx swapping and out of band swaps.

This behavior is controlled using existing and new (see below) hx-* attributes on the form triggering the request.

Current features

Update the customer's cart through the Shopify Ajax API and update the current page in response.

Installation

Basic type coersion support for JSON Type Definition schemas in Ajv. This is currently an unimplemented feature in Ajv. Works by wrapping compiled ValidatorFunctions and handling resulting type errors. Uses lodash for JS type checking and deep get and sets on the data object.

Supports coercing from JSON types string, number, boolean, and null to JTD types string, uint8, uint16, uint32, int8, int16, int32, float32, float64, boolean, and null. The coercion rules should mirror that of Ajv. Coercing to arrays is currently not supported.

The implementation is in Typescript and should work fine with JTDDataType etc.

@fabianeichinger
fabianeichinger / C.mjs
Last active July 30, 2023 14:42
Redis Tag Cache
import { WatchError, createClient } from 'redis';
import { readFileSync } from 'fs';
const SET_SCRIPT = readFileSync(`SET.lua`, 'utf-8')
const VACUUM_SCRIPT = readFileSync(`VACUUM.lua`, 'utf-8');
/**
* @param {string} key
*/
function valueKey(key) {