1

I've been dabbling with functional programming for a little bit and I'm trying to get my head around partial application and currying.

I'm looking for some insight on how I can apply partial application and currying to the functions below:

var Page_Validators = [{
  "controltovalidate": "Content_C002_txtAddress",
  "focusOnError": "t",
  "errormessage": "No Address Entered",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtCity",
  "focusOnError": "t",
  "errormessage": "No City Entered",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_drpState",
  "focusOnError": "t",
  "errormessage": "State Required",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtZipcode",
  "focusOnError": "t",
  "errormessage": "No Zipcode Entered",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_phoneNumberFull",
  "focusOnError": "t",
  "errormessage": "Missing Phone Number",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtSupFullName",
  "focusOnError": "t",
  "errormessage": "No Name Entered",
  "display": "Dynamic",
  "validationGroup": "SupervisorControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtSupTitle",
  "focusOnError": "t",
  "errormessage": "No Title Entered",
  "display": "Dynamic",
  "validationGroup": "SupervisorControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtSupPhoneFull",
  "focusOnError": "t",
  "errormessage": "Missing Phone Number",
  "display": "Dynamic",
  "validationGroup": "SupervisorControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_txtSupEmail",
  "focusOnError": "t",
  "errormessage": "No Email Entered",
  "display": "Dynamic",
  "validationGroup": "SupervisorControl",
  "initialvalue": "",
  "isvalid": true
}, {
  "controltovalidate": "Content_C002_SignatureField",
  "focusOnError": "t",
  "errormessage": "Signature Required",
  "display": "Dynamic",
  "validationGroup": "ProfileControl",
  "initialvalue": "",
  "isvalid": true
}];


function filterArrayBy(arr, searchString) {
  return arr.filter(key => key.controltovalidate.toLowerCase().includes(searchString.toLowerCase()));
}

function toggleValidatorsState(arr, condtion) {
  return arr.map(el => ValidatorEnable(el, condition));
}

const supervisorValidators = filterArrayBy(Page_Validators, "txtSup");
const disabledValidators = toggleValidatorsState(supervisorValidators, true);

console.log(disabledValidators);

ASIDE

The toggleValidatorState function is invoking an ASP.NET function so the code snippet will not function (unless you have asp.net)

Except for the ASP.NET function can these functions be simplified or make use of partial application with currying??

I feel like I'm repeating myself by having to pass an array into the two functions.

I've been looking into using Lodash or Ramda but could I achieve the same without the use of an external library.

cpt-crunchy
  • 391
  • 4
  • 23

1 Answers1

2

This might be an overkill here because the code already looks simple.

But you could curry filterArayBy by binding it to Page_Validators. So you would be able to filter it by different searchStrings without a need to pass the array each time.

Also, you could make a new function called disableValidators by partially applying toggleValidatorsState with condition = true.

The easiest way to achieve this would be to use .bind and a simple lambda like this:

function filterArrayBy(arr, searchString) {
    return arr.filter(key => key.controltovalidate.toLowerCase().includes(searchString.toLowerCase()));
}

// We are going to partially apply filterArrayBy function as the first argument is going to be the same.
// (in this context partial application does the same as currying)
const filterPageValidators = filterArrayBy.bind(null, Page_Validators);

function toggleValidatorsState(arr, condtion) {
    return arr.map(el => ValidatorEnable(el, condition));
}

// Also partially applying toggleValidatorsState to make the code more readable
const disableValidators = arr => toggleValidatorsState(arr, true);

// The usage would look like this
const disabledValidators = disableValidators(filterPageValidators('txtSup'));

If you want to make it more complex you could check out this article implement your own curry method and use it to make filterPageValidators.

Then you would need something similar to Ramda's partialRight. So you could use this answer as a reference.

Finally, your functions would look somehow like this:

const filterPageValidators = curry(filterArrayBy)(Page_Validators);
const disableValidators = bind_trailing_args(toggleValidatorsState, true);

But in my humble opinion, this is really too much for this particular case.

Antonio Narkevich
  • 4,206
  • 18
  • 28