Skip to content

Instantly share code, notes, and snippets.

View freddi301's full-sized avatar

Frederik Batuna freddi301

View GitHub Profile
@freddi301
freddi301 / download-liferay-openapi.mjs
Created April 17, 2026 12:15
Download all liferay open api specs
import { writeFile, mkdir } from 'fs/promises';
import { dirname, join } from 'path';
const BASE_URL = 'http://localhost:8080';
const AUTH = 'Basic ' + Buffer.from('[email protected]:password').toString('base64');
const OUT_DIR = './openapi-specs';
console.log('Fetching API list...');
const res = await fetch(`${BASE_URL}/o/openapi`, { headers: { Authorization: AUTH } });
const data = await res.json();
@freddi301
freddi301 / vite-injector.js
Created April 17, 2026 10:20
Liferay 7.4 Fragment to load React component with fast refresh trough vite
// create a fragment in liferay trough Site menu -> Design -> Fragment -> Blank and put this in js section
// you can also frely edit config pane and it will be forwarded to the component
// start a vite project
// change file variable to your liking, it must export a render function
// that takes the fragment DOM element and the configuration as arguments
// for react it would be
// export function render(fragmentElement, configuration) {
// createRoot(fragmentElement).render(<MyFragmentComponent configuration={configuration} />);
// }
// MyFragmentComponent must be in different file than the render function
@freddi301
freddi301 / SimplyTypedLamba.idr
Created September 24, 2025 07:23
Simply Typed Lmabda Calculus in Idris
module FunctionBuilder2
import Data.Nat
import Data.Fin
import Data.Vect
import Decidable.Equality
%default total
namespace Untyped
@freddi301
freddi301 / Exact.ts
Created July 16, 2025 13:34
Typescript exact type
type Exact<A, B extends A> = A extends B
? B
: B extends Record<any, any>
? { [K in keyof B]: K extends keyof A ? Exact<A[K], B[K]> : never }
: B extends Array<any>
? { [K in keyof B]: K extends keyof A ? Exact<A[K], B[K]> : never }
: never;
function invariantize<A, R>(
fun: (a: A) => R
@freddi301
freddi301 / useAdjustedRefreshingValue.ts
Created October 3, 2024 07:54
React hook use adjusted refreshing value
// adjust refreshing value in time for more pleasant loading indicator animation
// it is true if it was awlays true in the last 0.3 seconds
// it stays true for at least 1.0 second
function useAdjustedRefreshingValue(isRefreshing: boolean): boolean {
const DO_NOT_SHOW_BEFORE_MILLIS = 300;
const SHOW_FOR_AT_LEAST_MILLIS = 1000;
const [adjustedIsRefreshing, setAdjustedIsRefreshing] =
React.useState(isRefreshing);
const [isRefrescingSince, setIsRefreshingSince] = React.useState(0);
React.useEffect(() => {
@freddi301
freddi301 / DependentState.idr
Created July 29, 2024 09:55
Dependent State monad in idris2
data DependentState : Type -> Type -> Type -> Type where
MakeDependentState : (s' -> (s'', r)) -> DependentState s' s'' r
ret : r -> DependentState s s r
ret r = MakeDependentState $ \s => (s, r)
get : DependentState s s s
get = MakeDependentState $ \s => (s, s)
set : s'' -> DependentState s' s'' ()
@freddi301
freddi301 / Heap.idr
Created July 24, 2024 15:03
Heap allocated object in Idris2
data Heap : Nat -> (Nat -> Type) -> Type where
Lin : Heap Z a
(:<) : Heap l a -> a l -> Heap (S l) a
data Tree : Nat -> Type where
Leaf : String -> Tree n
Branch : Fin n -> Fin n -> Tree n
u1 : Heap 4 Tree
u1 = [<
@freddi301
freddi301 / Idempotent.idr
Created July 19, 2024 22:53
Example of idempotent function and related proof
interface Idempotent (action : stateType -> stateType) where
law : (state : stateType) -> let u = action state in action u = u
IncFrom : Nat -> Nat -> Nat
IncFrom original state = case decEq state original of
Yes _ => S state
No _ => state
{o : Nat} -> Idempotent (IncFrom o) where
law s with (decEq s o)
@freddi301
freddi301 / Parser.idr
Created July 16, 2024 04:56
Idris 2 Parser based on combinators
module Parser
import Data.Nat
import Data.List
%default total
-- interface Codec input output where
-- encode : input -> output
-- decode : output -> Maybe input
@freddi301
freddi301 / validation.ts
Created May 22, 2024 00:16
typescript validation library experiment
export type Outcome<Value, Report> = { type: "valid"; value: Value } | { type: "invalid"; reports: Array<Report> };
export type ValidatorSyncBase<Value, Report> = {
validateSync(value: unknown): Outcome<Value, Report>;
};
export function makeValidatorSync<const Value, const Report>(validatorSyncBase: ValidatorSyncBase<Value, Report>) {
return {
...validatorSyncBase,
refine: refine(validatorSyncBase),