diff options
| author | William Boman <william@redwill.se> | 2022-12-10 19:55:41 +0100 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-12-10 18:55:41 +0000 |
| commit | fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d (patch) | |
| tree | be37b4bd7b0320dbfa3e08dae8c90540c0eaa335 | |
| parent | chore: update generated code (#754) (diff) | |
| download | mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar.gz mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar.bz2 mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar.lz mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar.xz mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.tar.zst mason-fbc72a0c2fe16a93b18ce8facdc9b66e7183f75d.zip | |
feat(functional): add some more functions (#755)
| -rw-r--r-- | lua/mason-core/functional/function.lua | 18 | ||||
| -rw-r--r-- | lua/mason-core/functional/init.lua | 8 | ||||
| -rw-r--r-- | lua/mason-core/functional/list.lua | 25 | ||||
| -rw-r--r-- | lua/mason-core/functional/string.lua | 10 | ||||
| -rw-r--r-- | lua/mason-core/functional/table.lua | 43 | ||||
| -rw-r--r-- | tests/mason-core/functional/function_spec.lua | 17 | ||||
| -rw-r--r-- | tests/mason-core/functional/list_spec.lua | 28 | ||||
| -rw-r--r-- | tests/mason-core/functional/string_spec.lua | 5 | ||||
| -rw-r--r-- | tests/mason-core/functional/table_spec.lua | 43 |
9 files changed, 197 insertions, 0 deletions
diff --git a/lua/mason-core/functional/function.lua b/lua/mason-core/functional/function.lua index 6f1806db..863df28e 100644 --- a/lua/mason-core/functional/function.lua +++ b/lua/mason-core/functional/function.lua @@ -119,4 +119,22 @@ _.converge = _.curryN(function(fn, fns, val) return fn(unpack(vim.tbl_map(_.apply_to(val), fns))) end, 3) +---@param spec table +---@param value any +---@return table +_.apply_spec = _.curryN(function(spec, value) + spec = vim.deepcopy(spec) + local function transform(item) + if type(item) == "table" then + for k, v in pairs(item) do + item[k] = transform(v) + end + return item + else + return item(value) + end + end + return transform(spec) +end, 2) + return _ diff --git a/lua/mason-core/functional/init.lua b/lua/mason-core/functional/init.lua index f03eb3d5..dbb27ddd 100644 --- a/lua/mason-core/functional/init.lua +++ b/lua/mason-core/functional/init.lua @@ -31,6 +31,7 @@ _.tap = fun.tap _.apply_to = fun.apply_to _.apply = fun.apply _.converge = fun.converge +_.apply_spec = fun.apply_spec ---@module "mason-core.functional.list" local list = lazy_require "mason-core.functional.list" @@ -39,6 +40,7 @@ _.list_not_nil = list.list_not_nil _.list_copy = list.list_copy _.find_first = list.find_first _.any = list.any +_.all = list.all _.filter = list.filter _.map = list.map _.filter_map = list.filter_map @@ -58,6 +60,7 @@ _.join = list.join _.partition = list.partition _.take = list.take _.drop = list.drop +_.drop_last = list.drop_last ---@module "mason-core.functional.relation" local relation = lazy_require "mason-core.functional.relation" @@ -97,6 +100,8 @@ _.gsub = string.gsub _.trim = string.trim _.dedent = string.dedent _.starts_with = string.starts_with +_.to_upper = string.to_upper +_.to_lower = string.to_lower ---@module "mason-core.functional.table" local tbl = lazy_require "mason-core.functional.table" @@ -108,6 +113,9 @@ _.size = tbl.size _.to_pairs = tbl.to_pairs _.from_pairs = tbl.from_pairs _.invert = tbl.invert +_.evolve = tbl.evolve +_.merge_left = tbl.merge_left +_.dissoc = tbl.dissoc ---@module "mason-core.functional.type" local typ = lazy_require "mason-core.functional.type" diff --git a/lua/mason-core/functional/list.lua b/lua/mason-core/functional/list.lua index b40e0046..7c66ccac 100644 --- a/lua/mason-core/functional/list.lua +++ b/lua/mason-core/functional/list.lua @@ -54,6 +54,19 @@ _.any = fun.curryN(function(predicate, list) end, 2) ---@generic T +---@param predicate fun(item: T): boolean +---@param list T[] +---@return boolean +_.all = fun.curryN(function(predicate, list) + for i = 1, #list do + if not predicate(list[i]) then + return false + end + end + return true +end, 2) + +---@generic T ---@type fun(filter_fn: (fun(item: T): boolean), items: T[]): T[] _.filter = fun.curryN(vim.tbl_filter, 2) @@ -232,4 +245,16 @@ _.drop = fun.curryN(function(n, list) return result end, 2) +---@generic T +---@param n integer +---@param list T[] +---@return T[] +_.drop_last = fun.curryN(function(n, list) + local result = {} + for i = 1, #list - n do + result[#result + 1] = list[i] + end + return result +end, 2) + return _ diff --git a/lua/mason-core/functional/string.lua b/lua/mason-core/functional/string.lua index 9b7da979..8c66dbc0 100644 --- a/lua/mason-core/functional/string.lua +++ b/lua/mason-core/functional/string.lua @@ -75,4 +75,14 @@ _.starts_with = fun.curryN(function(prefix, str) return vim.startswith(str, prefix) end, 2) +---@param str string +_.to_upper = function(str) + return str:upper() +end + +---@param str string +_.to_lower = function(str) + return str:lower() +end + return _ diff --git a/lua/mason-core/functional/table.lua b/lua/mason-core/functional/table.lua index eb673d64..276a3180 100644 --- a/lua/mason-core/functional/table.lua +++ b/lua/mason-core/functional/table.lua @@ -2,6 +2,17 @@ local fun = require "mason-core.functional.function" local _ = {} +---@generic T : table +---@param tbl T +---@return T +local function shallow_clone(tbl) + local res = {} + for k, v in pairs(tbl) do + res[k] = v + end + return res +end + ---@generic T, U ---@param index T ---@param tbl table<T, U> @@ -64,4 +75,36 @@ _.invert = fun.curryN(function(tbl) return result end, 1) +---@generic K, V +---@param transforms table<K, fun (value: V): V> +---@param tbl table<K, V> +---@return table<K, V> +_.evolve = fun.curryN(function(transforms, tbl) + local result = shallow_clone(tbl) + for key, value in pairs(tbl) do + if transforms[key] then + result[key] = transforms[key](value) + end + end + return result +end, 2) + +---@generic T : table +---@param left T +---@param right T +---@return T +_.merge_left = fun.curryN(function(left, right) + return vim.tbl_extend("force", right, left) +end, 2) + +---@generic T : table +---@param key any +---@param tbl T +---@return T +_.dissoc = fun.curryN(function(key, tbl) + local res = shallow_clone(tbl) + res[key] = nil + return res +end, 2) + return _ diff --git a/tests/mason-core/functional/function_spec.lua b/tests/mason-core/functional/function_spec.lua index 23af1933..6b36b53b 100644 --- a/tests/mason-core/functional/function_spec.lua +++ b/tests/mason-core/functional/function_spec.lua @@ -160,4 +160,21 @@ describe("functional: function", function() assert.spy(target).was_called(1) assert.spy(target).was_called_with("These", "Nuts") end) + + it("should apply spec", function() + local apply = _.apply_spec { + sum = _.add(2), + list = { _.add(2), _.add(6) }, + nested = { + sum = _.min(2), + }, + } + assert.same({ + sum = 4, + list = { 4, 8 }, + nested = { + sum = 0, + }, + }, apply(2)) + end) end) diff --git a/tests/mason-core/functional/list_spec.lua b/tests/mason-core/functional/list_spec.lua index f9de9fdc..a53da4ac 100644 --- a/tests/mason-core/functional/list_spec.lua +++ b/tests/mason-core/functional/list_spec.lua @@ -94,6 +94,27 @@ describe("functional: list", function() assert.spy(predicate).was.called(2) end) + it("should check that all items in list fulfills predicate", function() + assert.is_true(_.all(_.is "string", { + "Where", + "On Earth", + "Is", + "Waldo", + "?", + })) + + local predicate = spy.new(_.is "string") + + assert.is_false(_.all(predicate, { + "Five", + "Plus", + 42, + "Equals", + 47, + })) + assert.spy(predicate).was_called(3) + end) + it("should iterate list in .each", function() local list = { "BLUE", "YELLOW", "RED" } local iterate_fn = spy.new() @@ -225,4 +246,11 @@ describe("functional: list", function() assert.same({ "First", "Second", "Third", "I", "Have", "Poor", "Imagination" }, _.drop(0, list)) assert.same({}, _.drop(10000, list)) end) + + it("should drop last n items", function() + local list = { "First", "Second", "Third", "I", "Have", "Poor", "Imagination" } + assert.same({ "First", "Second", "Third" }, _.drop_last(4, list)) + assert.same({ "First", "Second", "Third", "I", "Have", "Poor", "Imagination" }, _.drop_last(0, list)) + assert.same({}, _.drop_last(10000, list)) + end) end) diff --git a/tests/mason-core/functional/string_spec.lua b/tests/mason-core/functional/string_spec.lua index 6fb99c45..7bbe06c5 100644 --- a/tests/mason-core/functional/string_spec.lua +++ b/tests/mason-core/functional/string_spec.lua @@ -45,4 +45,9 @@ Ipsum ]] ) end) + + it("should transform casing", function() + assert.equals("HELLO!", _.to_upper "Hello!") + assert.equals("hello!", _.to_lower "Hello!") + end) end) diff --git a/tests/mason-core/functional/table_spec.lua b/tests/mason-core/functional/table_spec.lua index c897b5ca..357f7120 100644 --- a/tests/mason-core/functional/table_spec.lua +++ b/tests/mason-core/functional/table_spec.lua @@ -68,4 +68,47 @@ describe("functional: table", function() } ) end) + + it("should evolve table", function() + assert.same( + { + non_existent = nil, + firstname = "JOHN", + lastname = "DOE", + age = 42, + }, + _.evolve({ + non_existent = _.always "hello", + firstname = _.to_upper, + lastname = _.to_upper, + age = _.add(2), + }, { + firstname = "John", + lastname = "Doe", + age = 40, + }) + ) + end) + + it("should merge left", function() + assert.same( + { + firstname = "John", + lastname = "Doe", + }, + _.merge_left({ + firstname = "John", + }, { + firstname = "Jane", + lastname = "Doe", + }) + ) + end) + + it("should dissoc keys", function() + assert.same({ + a = "a", + c = "c", + }, _.dissoc("b", { a = "a", b = "b", c = "c" })) + end) end) |
