Reputation: 157
I found some problem on the handling after if/else logic checking. Let's take an example.
Basic config
const result = {
data: 1,
state: {
pass: 'N'
}
}
For JS if/else checking, the log should not show after logic checking
function checking() {
if(result.state.pass !== 'Y') {
return result;
}
console.log("Should not appear the log")
}
checking()
Then, I tried to translate it using Ramda cond function
function checking() {
R.cond([
[
R.compose(R.not, R.equals('Y'), R.prop('pass'), R.prop('state')),
(res) => res
]
])(result)
console.log("Should not appear the log")
}
checking()
However, the log appear in Ramda cond example. May i know
is there anything wrong?
anything i can enhance on the example?
Thanks.
Upvotes: 0
Views: 5761
Reputation: 50807
Updated: I'd originally read this backward about when the log is supposed to show.
My suggestion would look like this:
const checking = R.when(
R.compose(R.equals('Y'), R.path(['state', 'pass'])),
(res) => {console.log("Should not appear in the log"); return res;}
)
Here's how I got there from your code: My first pass would be to fix up the use of cond
:
const result1 = {data: 1, state: {pass: 'N'}}
const result2 = {data: 2, state: {pass: 'Y'}}
const checking = R.cond([
[
R.compose(R.not, R.equals('Y'), R.prop('pass'), R.prop('state')),
R.identity
],
[
R.T,
(res) => {console.log("Should not appear in the log"); return res;}
]
])
checking(result1);
//=> {data: 1, state: {pass: 'N'}}
checking(result2);
// logs "Should not appear in the log
//=> {data: 2, state: {pass: 'Y'}}
Note that cond
is most like a switch
statement: it takes a collection of condition-consequent pairs and returns a function which passes its argument to each pair until it finds one whose condition is true, then it returns the result of calling its consequent. Thus for the second condition, we just check R.T
, which is a function that always returns true
, and use identity
to return the input.
This new function now accepts a result
object and returns it unchanged, logging a message to the console if it doesn't match the initial test.
But this isn't the end. This code can be refactored.
Here's one simple fix I would apply:
const checking = R.cond([
[
R.compose(R.not, R.equals('Y'), R.path(['state', 'pass'])),
R.identity
],
[
R.T,
(res) => {console.log("Should not appear in the log"); return res;}
]
])
This simply changed from compose(prop('pass'), prop('state'))
to path(['state', 'pass'])
. It's a minor tweak, but I think this is cleaner.
The next change is more substantive.
const checking = R.ifElse(
R.compose(R.not, R.equals('Y'), R.path(['state', 'pass'])),
R.identity,
(res) => {console.log("Should not appear in the log"); return res;}
)
When we have a cond
statement with only two branches, and the second one tests on R.T
, we can write this more clearly with ifElse
. This takes a condition and two consequents, one for when the condition passes, one for when it fails.
This might be as far as you would want to go, especially if you're eventually planning on doing something different in the fail condition. But if you're not, and you really only need one consequent, then R.unless
offers a further simplification on ifElse
, for those cases where the second consequent is just a pass-through:
const checking = R.unless(
R.compose(R.not, R.equals('Y'), R.path(['state', 'pass'])),
(res) => {console.log("Should not appear in the log"); return res;}
)
unless
simply checks the condition and runs the consequent if the condition is false and returns the input intact if it's true.
But we can pull out the not
as well by switching from unless
to when
:
const checking = R.when(
R.compose(R.equals('Y'), R.path(['state', 'pass'])),
(res) => {console.log("Should not appear in the log"); return res;}
)
And I would probably leave it there, although I might factor out a log
function for clarity.
All of this is available (including a final version with a log
function) on the Ramda REPL.
Upvotes: 4
Reputation: 727
You forgot to add a return statement.
const result = {
data: 1,
state: {
pass: 'N'
}
}
function checking() {
// Need to add return statement below
return R.cond([
[
R.compose(
R.not,
R.equals('Y'),
R.prop('pass'),
R.prop('state')),
(res) => res
]
])(result)
console.log("Should not appear the log")
}
checking()
<script src="https://cdnjs.cloudflare.com/ajax/libs/ramda/0.23.0/ramda.min.js"></script>
Upvotes: -1