Skip to content

Commit

Permalink
Use {questionName} for question value in conditions. Return false if …
Browse files Browse the repository at this point in the history
…there is underfined value in an expression: #60
  • Loading branch information
andrewtelnov committed Sep 23, 2016
1 parent efdcca5 commit 3ae69f2
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 9 deletions.
18 changes: 16 additions & 2 deletions src/conditions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -99,10 +99,24 @@ module Survey {
}
private runCondition(condition: Condition): boolean {
var left = condition.left;
if (left && this.values[left]) left = this.values[left];
var name = this.getValueName(left);
if (name) {
if (!(name in this.values)) return false;
left = this.values[name];
}
var right = condition.right;
if (right && this.values[right]) right = this.values[right];
name = this.getValueName(right);
if (name) {
if (!(name in this.values)) return false;
right = this.values[name];
}
return condition.perform(left, right);
}
private getValueName(nodeValue: any) {
if (!nodeValue) return null;
if (typeof nodeValue !== 'string') return null;
if (nodeValue.length < 3 || nodeValue[0] != '{' || nodeValue[nodeValue.length - 1] != '}') return null;
return nodeValue.substr(1, nodeValue.length - 2);
}
}
}
13 changes: 8 additions & 5 deletions tests/conditionstests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -173,22 +173,25 @@ module Survey.Tests {
assert.equal(right.children[1].right, 3);
});
QUnit.test("Run one condition", function (assert) {
var runner = new ConditionRunner("'a' > 5");
var runner = new ConditionRunner("{a} > 5");
var values = { a: 6 };
assert.equal(runner.run(values), true, "6 > 5");
values = { a: 5 };
assert.equal(runner.run(values), false, "5 > 5");
var values2 = { b: 5 };
assert.equal(runner.run(values2), false, "undefined > 5");

});
QUnit.test("Run complex condition", function (assert) {
var runner = new ConditionRunner("'age' >= 21 and ('sex' = 'male' or 'kids' > 1)");
var runner = new ConditionRunner("{age} >= 21 and ({sex} = 'male' or {kids} > 1)");
var values = { age: 21, sex: 'male', kids: 1 };
assert.equal(runner.run(values), true, "21 >= 21 and (male = male or 1 > 1");

This comment has been minimized.

Copy link
@thegovind

thegovind Feb 23, 2017

@andrewtelnov - How come you are not ending the condition opener - ( before male =? Also, I think it would help if conditions in visibleIf can be defined in a function

var values = { age: 21, sex: 'female', kids: 1 };
assert.equal(runner.run(values), false, "21 >= 21 and (male = female or 1 > 1");
assert.equal(runner.run(values), false, "21 >= 21 and (male = female or 1 > 1)");
var values = { age: 21, sex: 'female', kids: 2 };
assert.equal(runner.run(values), true, "21 >= 21 and (male = female or 2 > 1");
assert.equal(runner.run(values), true, "21 >= 21 and (male = female or 2 > 1)");
var values = { age: 20, sex: 'male', kids: 2 };
assert.equal(runner.run(values), false, "20 >= 21 and (male = male or 2 > 1");
assert.equal(runner.run(values), false, "20 >= 21 and (male = male or 2 > 1)");
});
QUnit.test("Expression Tree to Text", function (assert) {
var parser = new ConditionsParser();
Expand Down
4 changes: 2 additions & 2 deletions tests/surveytests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -624,9 +624,9 @@ module Survey.Tests {
questions: [
{ type: "checkbox", name: "q1", choices: ["yes", "no"] },
{ type: "checkbox", name: "q2", choices: ["yes", "no"] }]
}, { name : "page2", visibleIf: "q1 = 'yes' or 'q2' = 'no'",
}, { name : "page2", visibleIf: "{q1} = 'yes' or {q2} = 'no'",
questions: [
{ type: "text", name: "q3", visibleIf: "q1 = 'yes' and 'q2' = 'no'", },
{ type: "text", name: "q3", visibleIf: "{q1} = 'yes' and {q2} = 'no'", },
{ type: "text", name: "q4" }]
}
]
Expand Down

0 comments on commit 3ae69f2

Please sign in to comment.