Skip to content

Commit

Permalink
lib.types: init mergeTypes
Browse files Browse the repository at this point in the history
  • Loading branch information
hsjobeki committed Dec 12, 2024
1 parent f3ab2ef commit 0421581
Show file tree
Hide file tree
Showing 2 changed files with 83 additions and 0 deletions.
41 changes: 41 additions & 0 deletions lib/tests/misc.nix
Original file line number Diff line number Diff line change
Expand Up @@ -2564,4 +2564,45 @@ runTests {
};
expected = "c";
};

testMergeTypesSimple =
let
mergedType = types.mergeTypes types.str types.str;
in
{
expr = mergedType.name;
expected = "str";
};

testMergeTypesFail =
let
mergedType = types.mergeTypes types.str types.int;
in
{
expr = mergedType;
expected = null;
};

testMergeTypesEnum =
let
enumAB = lib.types.enum ["A" "B"];
enumXY = lib.types.enum ["X" "Y"];
merged = lib.types.mergeTypes enumAB enumXY; # -> enum [ "A" "B" "X" "Y" ]
in
{
expr = {
checkA = merged.check "A";
checkB = merged.check "B";
checkX = merged.check "X";
checkY = merged.check "Y";
checkC = merged.check "C";
};
expected = {
checkA = true;
checkB = true;
checkX = true;
checkY = true;
checkC = false;
};
};
}
42 changes: 42 additions & 0 deletions lib/types.nix
Original file line number Diff line number Diff line change
Expand Up @@ -1107,6 +1107,48 @@ rec {
addCheck = elemType: check: elemType // { check = x: elemType.check x && check x; };

};

/**
Merges two option types together.
:::{.note}
Uses the merge function of the first type, to merge it with the second type.
Usually types can only be merged if they are of the same type
:::
# Inputs
: `a` (option type): The first option type.
: `b` (option type): The second option type.
# Returns
- The merged option type.
- `null` if the types can't be merged.
# Examples
:::{.example}
## `lib.types.mergeTypes` usage example
```nix
let
enumAB = lib.types.enum ["A" "B"];
enumXY = lib.types.enum ["X" "Y"];
merged = lib.types.mergeTypes enumAB enumXY; # -> enum [ "A" "B" "X" "Y" ]
=>
merged.check "A" # true
merged.check "B" # true
merged.check "X" # true
merged.check "Y" # true
merged.check "C" # false
```
:::
*/
mergeTypes = a: b:
assert isOptionType a && isOptionType b;
a.typeMerge b.functor;
};

in outer_types // outer_types.types

0 comments on commit 0421581

Please sign in to comment.