luci-base: form.js: add a new "contains" dependency mode
authorJo-Philipp Wich <jo@mein.io>
Sun, 19 Jan 2020 15:00:57 +0000 (16:00 +0100)
committerJo-Philipp Wich <jo@mein.io>
Sun, 19 Jan 2020 15:15:22 +0000 (16:15 +0100)
By tagging option dependencies with `!contains`, dependencies are
considered satisfied when the value is contained in the value of
a related field, instead of being equal to it.

Signed-off-by: Jo-Philipp Wich <jo@mein.io>
modules/luci-base/htdocs/luci-static/resources/form.js

index 88e566519c06de469e0809971b8fa5afddf3e03f..4ce5e45ebe6d1c1319074f79e5b890efdbb278bd 100644 (file)
@@ -403,11 +403,12 @@ var CBIMap = CBINode.extend({
 
                for (var i = 0; i < depends.length; i++) {
                        var istat = true,
-                           reverse = false;
+                           reverse = depends[i]['!reverse'],
+                           contains = depends[i]['!contains'];
 
                        for (var dep in depends[i]) {
-                               if (dep == '!reverse') {
-                                       reverse = true;
+                               if (dep == '!reverse' || dep == '!contains') {
+                                       continue;
                                }
                                else if (dep == '!default') {
                                        def = true;
@@ -417,7 +418,11 @@ var CBIMap = CBINode.extend({
                                        var res = this.lookupOption(dep, section_id, config_name),
                                            val = (res && res[0].isActive(res[1])) ? res[0].formvalue(res[1]) : null;
 
-                                       istat = (istat && isEqual(val, depends[i][dep]));
+                                       var equal = contains
+                                               ? isContained(val, depends[i][dep])
+                                               : isEqual(val, depends[i][dep]);
+
+                                       istat = (istat && equal);
                                }
                        }
 
@@ -633,6 +638,23 @@ var isEqual = function(x, y) {
        return true;
 };
 
+var isContained = function(x, y) {
+       if (Array.isArray(x)) {
+               for (var i = 0; i < x.length; i++)
+                       if (x[i] == y)
+                               return true;
+       }
+       else if (L.isObject(x)) {
+               if (x.hasOwnProperty(y) && x[y] != null)
+                       return true;
+       }
+       else if (typeof(x) == 'string') {
+               return (x.indexOf(y) > -1);
+       }
+
+       return false;
+};
+
 var CBIAbstractValue = CBINode.extend({
        __init__: function(map, section, option /*, ... */) {
                this.super('__init__', this.varargs(arguments, 3));