在流程中使用lodash的fp函数

时间:2018-07-10 09:48:20

标签: javascript functional-programming lodash

已经知道_.chain方法是“ considered harmful”,我想我应该尝试一些流程。但是,我在使用fp方法时遇到了问题。

我在a repl中添加了一个小示例,并复制了下面的代码。

const flow = require('lodash/fp/flow');
const truncate = require('lodash/fp/truncate');
const mapValues = require('lodash/fp/mapValues');
const { inspect, format } = require('util');

const input = {
    firstField: 'I am a fairly long string so I want to be truncated',
    secondField: {
        foo: 'bar',
        bar: 'baz',
        baz: 'boo',
        boo: 'hoo',
        hoo: 'boy',
        boy: 'howdy'
    }
};

const doTheThing = data =>
    flow(
        mapValues(inspect), 
        mapValues(s => s.replace(/\s*\n\s*/g, ' ')),
        mapValues(truncate)
    )(data);

console.log(doTheThing(input));

运行此命令时,truncate未被激活,我得到了

{ firstField: { [Function: wrapper] placeholder: {} },
  secondField: { [Function: wrapper] placeholder: {} } }

我期望返回两个截断的字符串,而不是返回toString的函数。为此,我必须将其更改为mapValues(s => truncate(s)(s))。至少可以这样说,这似乎是错误的,那么我是错误地将flow和fp方法组合在一起了吗,还是我使用了错误的方法?

1 个答案:

答案 0 :(得分:1)

您错误地使用了它们。首先,对于普通的Lodash,truncate函数具有两个参数:

  

_。truncate([string =''],[options = {}])

第二个是:

  

[options = {}](对象):选项对象。

使用Lodash fp there are no optional argumentssome functions' arguments are rearranged可以使合成更加容易。因此在fp中,truncate有两个参数,第一个是options对象。要使用fp截断字符串,您需要提供两个参数:

const truncFn = _.truncate({ length: 20 }); // is a function
const truncatedString = truncFn('I am a fairly long string so I want to be truncated'); // only this results in truncated string

console.log(truncatedString);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.10/lodash.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.10/lodash.fp.min.js"></script>

您的代码段,固定版本(repl link):

const flow = require('lodash/fp/flow');
const truncate = require('lodash/fp/truncate');
const mapValues = require('lodash/fp/mapValues');
const { inspect, format } = require('util');

const input = {
    firstField: 'I am a fairly long string so I want to be truncated',
    secondField: {
        foo: 'bar',
        bar: 'baz',
        baz: 'boo',
        boo: 'hoo',
        hoo: 'boy',
        boy: 'howdy'
    }
};

const doTheThing = data =>
    flow(
        mapValues(inspect), 
        mapValues(s => s.replace(/\s*\n\s*/g, ' ')),
        mapValues(truncate({})) // <--- FIX
    )(data);

console.log(doTheThing(input));