<K1 extends string, B>(that: ReadonlyRecord<K1, B>): <
K0 extends string,
A
>(
self: ReadonlyRecord<K0, A>
) => Record<K0 | K1, A | B>
<K0 extends string, A, K1 extends string, B>(
self: ReadonlyRecord<K0, A>,
that: ReadonlyRecord<K1, B>
): Record<K0 | K1, A | B>Merges two records, preserving only the entries that are unique to each record. Keys that exist in both records are excluded from the result.
Example (Keeping keys unique to each record)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(
Record.difference({ a: 1, b: 2 }, { b: 3, c: 4 }),
{ a: 1, c: 4 }
)export const const difference: {
<K1 extends string, B>(
that: ReadonlyRecord<K1, B>
): <K0 extends string, A>(
self: ReadonlyRecord<K0, A>
) => Record<K0 | K1, A | B>
<K0 extends string, A, K1 extends string, B>(
self: ReadonlyRecord<K0, A>,
that: ReadonlyRecord<K1, B>
): Record<K0 | K1, A | B>
}
Merges two records, preserving only the entries that are unique to each record.
Keys that exist in both records are excluded from the result.
Example (Keeping keys unique to each record)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(
Record.difference({ a: 1, b: 2 }, { b: 3, c: 4 }),
{ a: 1, c: 4 }
)
difference: {
<function (type parameter) K1 in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>K1 extends string, function (type parameter) B in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>B>(
that: ReadonlyRecord<K1, B>that: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K1 in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>K1, function (type parameter) B in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>B>
): <function (type parameter) K0 in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>K0 extends string, function (type parameter) A in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>A>(self: ReadonlyRecord<K0, A>self: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K0 in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>K0, function (type parameter) A in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>A>) => type Record<K extends keyof any, T> = {
[P in K]: T
}
Construct a type with a set of properties K of type T
Record<function (type parameter) K0 in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>K0 | function (type parameter) K1 in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>K1, function (type parameter) A in <K0 extends string, A>(self: ReadonlyRecord<K0, A>): Record<K0 | K1, A | B>A | function (type parameter) B in <K1 extends string, B>(that: ReadonlyRecord<K1, B>): <K0 extends string, A>(self: ReadonlyRecord<K0, A>) => Record<K0 | K1, A | B>B>
<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0 extends string, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A, function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1 extends string, function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>(
self: ReadonlyRecord<K0, A>self: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A>,
that: ReadonlyRecord<K1, B>that: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1, function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>
): type Record<K extends keyof any, T> = {
[P in K]: T
}
Construct a type with a set of properties K of type T
Record<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0 | function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A | function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>
} = dual<(...args: Array<any>) => any, <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>) => Record<K0 | K1, A | B>>(arity: 2, body: <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>) => Record<K0 | K1, A | B>): ((...args: Array<any>) => any) & (<K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>) => Record<K0 | K1, A | B>) (+1 overload)Creates a function that can be called in data-first style or data-last
(pipe-friendly) style.
When to use
Use to expose one implementation through both direct and pipe-friendly
call styles.
Details
Pass either the arity of the uncurried function or a predicate that decides
whether the current call is data-first. Arity is the common case. Use a
predicate when optional arguments make arity ambiguous.
Example (Selecting data-first or data-last style by arity)
import { Function, pipe } from "effect"
const sum = Function.dual<
(that: number) => (self: number) => number,
(self: number, that: number) => number
>(2, (self, that) => self + that)
console.log(sum(2, 3)) // 5
console.log(pipe(2, sum(3))) // 5
Example (Defining overloads with call signatures)
import { Function, pipe } from "effect"
const sum: {
(that: number): (self: number) => number
(self: number, that: number): number
} = Function.dual(2, (self: number, that: number): number => self + that)
console.log(sum(2, 3)) // 5
console.log(pipe(2, sum(3))) // 5
Example (Selecting data-first or data-last style with a predicate)
import { Function, pipe } from "effect"
const sum = Function.dual<
(that: number) => (self: number) => number,
(self: number, that: number) => number
>(
(args) => args.length === 2,
(self, that) => self + that
)
console.log(sum(2, 3)) // 5
console.log(pipe(2, sum(3))) // 5
dual(2, <function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0 extends string, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A, function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1 extends string, function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>(
self: ReadonlyRecord<K0, A>self: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A>,
that: ReadonlyRecord<K1, B>that: type ReadonlyRecord<in out K extends string | symbol, out A> = { readonly [P in K]: A; }Represents a readonly record with keys of type K and values of type A.
This is the foundational type for immutable key-value mappings in Effect.
Example (Defining a readonly record type)
import type { Record } from "effect"
// Creating a readonly record type
type UserRecord = Record.ReadonlyRecord<"name" | "age", string | number>
const user: UserRecord = {
name: "John",
age: 30
}
Namespace containing utility types for working with readonly records.
These types help with type-level operations on record keys and values.
Example (Using readonly record helper types)
import type { Record } from "effect"
// Using NonLiteralKey to convert literal keys to generic types
type GenericKey = Record.ReadonlyRecord.NonLiteralKey<"foo" | "bar"> // string
// Using IntersectKeys to find common keys between record types
type CommonKeys = Record.ReadonlyRecord.IntersectKeys<"a" | "b", "b" | "c"> // "b"
ReadonlyRecord<function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1, function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>
): type Record<K extends keyof any, T> = {
[P in K]: T
}
Construct a type with a set of properties K of type T
Record<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0 | function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A | function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B> => {
if (const isEmptyRecord: <K0, A>(
self: Record<K0, A>
) => self is Record<K0, never>
Determines if a mutable record is empty.
Example (Checking for an empty record)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(Record.isEmptyRecord({}), true)
assert.deepStrictEqual(Record.isEmptyRecord({ a: 3 }), false)
isEmptyRecord(self: ReadonlyRecord<K0, A>self)) {
return { ...that: ReadonlyRecord<K1, B>that } as any
}
if (const isEmptyRecord: <K1, B>(
self: Record<K1, B>
) => self is Record<K1, never>
Determines if a mutable record is empty.
Example (Checking for an empty record)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(Record.isEmptyRecord({}), true)
assert.deepStrictEqual(Record.isEmptyRecord({ a: 3 }), false)
isEmptyRecord(that: ReadonlyRecord<K1, B>that)) {
return { ...self: ReadonlyRecord<K0, A>self } as any
}
const const out: Record<K0 | K1, A | B>out = {} as type Record<K extends keyof any, T> = {
[P in K]: T
}
Construct a type with a set of properties K of type T
Record<function (type parameter) K0 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K0 | function (type parameter) K1 in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>K1, function (type parameter) A in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>A | function (type parameter) B in <K0 extends string, A, K1 extends string, B>(self: ReadonlyRecord<K0, A>, that: ReadonlyRecord<K1, B>): Record<K0 | K1, A | B>B>
for (const const key: K0 extends stringkey of const keys: <
K extends string | symbol,
A
>(
self: ReadonlyRecord<K, A>
) => Array<K & string>
Retrieves the keys of a given record as an array.
Example (Getting record keys)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(Record.keys({ a: 1, b: 2, c: 3 }), ["a", "b", "c"])
keys(self: ReadonlyRecord<K0, A>self)) {
if (!const has: {
<K extends string | symbol>(key: NoInfer<K>): <
A
>(
self: ReadonlyRecord<K, A>
) => boolean
<K extends string | symbol, A>(
self: ReadonlyRecord<K, A>,
key: NoInfer<K>
): boolean
}
has(that: ReadonlyRecord<K1, B>that, const key: K0 extends stringkey as any)) {
const out: Record<K0 | K1, A | B>out[const key: K0 extends stringkey] = self: ReadonlyRecord<K0, A>self[const key: K0 extends stringkey]
}
}
for (const const key: K1 extends stringkey of const keys: <
K extends string | symbol,
A
>(
self: ReadonlyRecord<K, A>
) => Array<K & string>
Retrieves the keys of a given record as an array.
Example (Getting record keys)
import { Record } from "effect"
import * as assert from "node:assert"
assert.deepStrictEqual(Record.keys({ a: 1, b: 2, c: 3 }), ["a", "b", "c"])
keys(that: ReadonlyRecord<K1, B>that)) {
if (!const has: {
<K extends string | symbol>(key: NoInfer<K>): <
A
>(
self: ReadonlyRecord<K, A>
) => boolean
<K extends string | symbol, A>(
self: ReadonlyRecord<K, A>,
key: NoInfer<K>
): boolean
}
has(self: ReadonlyRecord<K0, A>self, const key: K1 extends stringkey as any)) {
const out: Record<K0 | K1, A | B>out[const key: K1 extends stringkey] = that: ReadonlyRecord<K1, B>that[const key: K1 extends stringkey]
}
}
return const out: Record<K0 | K1, A | B>out
})