Blame SOURCES/0001-WebUI-Fix-IPA-Error-3007-RequirmentError-while-addin_rhbz#1757045.patch

2ff659
From c2ba333b9681d008d9c528a79dbdd76ce11a3ecd Mon Sep 17 00:00:00 2001
2ff659
From: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Date: Thu, 28 May 2020 08:47:49 +0200
2ff659
Subject: [PATCH 01/22] WebUI: Fix "IPA Error 3007: RequirmentError" while
2ff659
 adding idoverrideuser association
2ff659
2ff659
Add builder for association adder dialog which allows to override behavior of the component.
2ff659
Replace default implementation with a custom one for idoverrideuser.
2ff659
Replace text filter with 'ID view' select box in the idoverrideuser dialog.
2ff659
2ff659
Ticket: https://pagure.io/freeipa/issue/8335
2ff659
2ff659
Signed-off-by: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
2ff659
---
2ff659
 install/ui/src/freeipa/association.js | 13 ++++-
2ff659
 install/ui/src/freeipa/dialog.js      | 73 ++++++++++++++++-----------
2ff659
 install/ui/src/freeipa/group.js       | 14 +++++
2ff659
 install/ui/src/freeipa/idviews.js     | 58 +++++++++++++++++++++
2ff659
 ipaserver/plugins/internal.py         |  6 +++
2ff659
 5 files changed, 133 insertions(+), 31 deletions(-)
2ff659
2ff659
diff --git a/install/ui/src/freeipa/association.js b/install/ui/src/freeipa/association.js
2ff659
index f10ccb2a5..b083a79f9 100644
2ff659
--- a/install/ui/src/freeipa/association.js
2ff659
+++ b/install/ui/src/freeipa/association.js
2ff659
@@ -25,6 +25,7 @@
2ff659
 define([
2ff659
     'dojo/_base/lang',
2ff659
     'dojo/Deferred',
2ff659
+    './builder',
2ff659
     './metadata',
2ff659
     './ipa',
2ff659
     './jquery',
2ff659
@@ -38,7 +39,7 @@ define([
2ff659
     './facet',
2ff659
     './search',
2ff659
     './dialog'],
2ff659
-        function(lang, Deferred, metadata_provider, IPA, $, metadata,
2ff659
+        function(lang, Deferred, builder, metadata_provider, IPA, $, metadata,
2ff659
                  navigation, phases, reg, rpc, su, text) {
2ff659
 
2ff659
 /**
2ff659
@@ -1209,7 +1210,8 @@ exp.association_facet = IPA.association_facet = function (spec, no_init) {
2ff659
 
2ff659
         var pkeys = that.data.result.result[that.get_attribute_name()];
2ff659
 
2ff659
-        var dialog = IPA.association_adder_dialog({
2ff659
+        var dialog = builder.build('association_adder_dialog', {
2ff659
+            $type: that.other_entity.name,
2ff659
             title: title,
2ff659
             entity: that.entity,
2ff659
             pkey: pkey,
2ff659
@@ -1675,6 +1677,13 @@ IPA.attr_read_only_evaluator = function(spec) {
2ff659
     return that;
2ff659
 };
2ff659
 
2ff659
+// Create a registry for adder dialogs where key is name of 'other entity'.
2ff659
+// It allows to override dialogs for some specific cases of association
2ff659
+// creation.
2ff659
+var dialog_builder = builder.get('association_adder_dialog');
2ff659
+dialog_builder.factory = IPA.association_adder_dialog;
2ff659
+reg.set('association_adder_dialog', dialog_builder.registry);
2ff659
+
2ff659
 phases.on('registration', function() {
2ff659
     var w = reg.widget;
2ff659
     var f = reg.field;
2ff659
diff --git a/install/ui/src/freeipa/dialog.js b/install/ui/src/freeipa/dialog.js
2ff659
index c153120df..d67d63b6d 100644
2ff659
--- a/install/ui/src/freeipa/dialog.js
2ff659
+++ b/install/ui/src/freeipa/dialog.js
2ff659
@@ -919,35 +919,7 @@ IPA.adder_dialog = function(spec) {
2ff659
             'class': 'input-group col-md-12 adder-dialog-top'
2ff659
         }).appendTo(container);
2ff659
 
2ff659
-        var filter_placeholder = text.get('@i18n:association.filter_placeholder');
2ff659
-        filter_placeholder = filter_placeholder.replace('${other_entity}',
2ff659
-            that.other_entity.metadata.label);
2ff659
-
2ff659
-        that.filter_field = $('<input/>', {
2ff659
-            type: 'text',
2ff659
-            name: 'filter',
2ff659
-            'class': 'form-control',
2ff659
-            'placeholder': filter_placeholder,
2ff659
-            keyup: function(event) {
2ff659
-                if (event.keyCode === keys.ENTER) {
2ff659
-                    that.search();
2ff659
-                    return false;
2ff659
-                }
2ff659
-            }
2ff659
-        }).appendTo(input_group);
2ff659
-
2ff659
-        var input_group_btn = $('
', {
2ff659
-            'class': 'input-group-btn'
2ff659
-        }).appendTo(input_group);
2ff659
-
2ff659
-        that.find_button = IPA.button({
2ff659
-            name: 'find',
2ff659
-            label: '@i18n:buttons.filter',
2ff659
-            click: function() {
2ff659
-                that.search();
2ff659
-                return false;
2ff659
-            }
2ff659
-        }).appendTo(input_group_btn);
2ff659
+        that.filter_field = that.get_filter_field(input_group);
2ff659
 
2ff659
         var row = $('
', { 'class': 'row adder-dialog-main'}).appendTo(container);
2ff659
         //
2ff659
@@ -1132,6 +1104,49 @@ IPA.adder_dialog = function(spec) {
2ff659
         return that.filter_field.val();
2ff659
     };
2ff659
 
2ff659
+    /**
2ff659
+     * Return field for filtering available items
2ff659
+     *
2ff659
+     * Default implementation returns text input + "Filter" button.
2ff659
+     * It can be overridden.
2ff659
+     *
2ff659
+     * @param {HTMLElement} input_group - container for a filter field
2ff659
+     * @return {HTMLElement}
2ff659
+     */
2ff659
+    that.get_filter_field = function(input_group) {
2ff659
+        var filter_placeholder = text.get(
2ff659
+            '@i18n:association.filter_placeholder'
2ff659
+        ).replace('${other_entity}', that.other_entity.metadata.label);
2ff659
+
2ff659
+        var filter_field = $('<input/>', {
2ff659
+            type: 'text',
2ff659
+            name: 'filter',
2ff659
+            'class': 'form-control',
2ff659
+            'placeholder': filter_placeholder,
2ff659
+            keyup: function(event) {
2ff659
+                if (event.keyCode === keys.ENTER) {
2ff659
+                    that.search();
2ff659
+                    return false;
2ff659
+                }
2ff659
+            }
2ff659
+        }).appendTo(input_group);
2ff659
+
2ff659
+        var input_group_btn = $('
', {
2ff659
+            'class': 'input-group-btn'
2ff659
+        }).appendTo(input_group);
2ff659
+
2ff659
+        that.find_button = IPA.button({
2ff659
+            name: 'find',
2ff659
+            label: '@i18n:buttons.filter',
2ff659
+            click: function() {
2ff659
+                that.search();
2ff659
+                return false;
2ff659
+            }
2ff659
+        }).appendTo(input_group_btn);
2ff659
+
2ff659
+        return filter_field;
2ff659
+    };
2ff659
+
2ff659
     /**
2ff659
      * Clear rows in available table
2ff659
      */
2ff659
diff --git a/install/ui/src/freeipa/group.js b/install/ui/src/freeipa/group.js
2ff659
index e46d8c7e3..2984bd4b2 100644
2ff659
--- a/install/ui/src/freeipa/group.js
2ff659
+++ b/install/ui/src/freeipa/group.js
2ff659
@@ -205,6 +205,20 @@ return {
2ff659
             add_title: '@i18n:objects.group.add_into_sudo',
2ff659
             remove_method: 'remove_user',
2ff659
             remove_title: '@i18n:objects.group.remove_from_sudo'
2ff659
+        },
2ff659
+        {
2ff659
+            $type: 'association',
2ff659
+            name: 'member_idoverrideuser',
2ff659
+            associator: IPA.serial_associator,
2ff659
+            add_title: '@i18n:objects.group.add_idoverride_user',
2ff659
+            remove_title: '@i18n:objects.group.remove_idoverride_users',
2ff659
+            columns: [
2ff659
+                {
2ff659
+                    name: 'ipaanchoruuid',
2ff659
+                    label: '@i18n:objects.idoverrideuser.anchor_label',
2ff659
+                    link: false
2ff659
+                }
2ff659
+            ]
2ff659
         }
2ff659
     ],
2ff659
     standard_association_facets: true,
2ff659
diff --git a/install/ui/src/freeipa/idviews.js b/install/ui/src/freeipa/idviews.js
2ff659
index 35dc998c8..a4fca6205 100644
2ff659
--- a/install/ui/src/freeipa/idviews.js
2ff659
+++ b/install/ui/src/freeipa/idviews.js
2ff659
@@ -966,6 +966,58 @@ idviews.unapply_action = function(spec) {
2ff659
     return that;
2ff659
 };
2ff659
 
2ff659
+idviews.idoverrideuser_adder_dialog = function(spec) {
2ff659
+
2ff659
+    spec = spec || {};
2ff659
+
2ff659
+    var that = IPA.association_adder_dialog(spec);
2ff659
+
2ff659
+    that.base_search = that.search;
2ff659
+
2ff659
+    that.search = function() {
2ff659
+        // Search for users only in case a ID view is selected
2ff659
+        if (that.get_filter()) {
2ff659
+            that.base_search();
2ff659
+        }
2ff659
+    };
2ff659
+
2ff659
+    /**
2ff659
+     * Replace default text filter with a select box for filtering by ID view
2ff659
+     */
2ff659
+    that.get_filter_field = function(input_group) {
2ff659
+
2ff659
+        var filter_field = $('<select/>', {
2ff659
+            name: 'filter',
2ff659
+            'class': 'form-control',
2ff659
+            change: function(event) {
2ff659
+                that.search();
2ff659
+            }
2ff659
+        }).appendTo(input_group);
2ff659
+
2ff659
+        rpc.command({
2ff659
+            entity: 'idview',
2ff659
+            method: 'find',
2ff659
+            on_success: function(data) {
2ff659
+                var results = data.result;
2ff659
+
2ff659
+                for (var i=0; i
2ff659
+                    var result = results.result[i];
2ff659
+                    $('<option/>', {
2ff659
+                        text: result.cn[0],
2ff659
+                        value: result.cn[0]
2ff659
+                    }).appendTo(filter_field);
2ff659
+                }
2ff659
+
2ff659
+                that.search();
2ff659
+            }
2ff659
+        }).execute();
2ff659
+
2ff659
+        return filter_field;
2ff659
+    };
2ff659
+
2ff659
+    return that;
2ff659
+};
2ff659
+
2ff659
 /**
2ff659
  * ID View entity specification object
2ff659
  * @member idviews
2ff659
@@ -993,6 +1045,7 @@ idviews.register = function() {
2ff659
     var f = reg.facet;
2ff659
     var a = reg.action;
2ff659
     var w = reg.widget;
2ff659
+    var ad = reg.association_adder_dialog;
2ff659
 
2ff659
     e.register({type: 'idview', spec: idviews.spec});
2ff659
     e.register({
2ff659
@@ -1012,6 +1065,11 @@ idviews.register = function() {
2ff659
 
2ff659
     w.register('idviews_certs', idviews.idviews_certs_widget);
2ff659
     w.register('cert_textarea', idviews.cert_textarea_widget);
2ff659
+
2ff659
+    ad.register({
2ff659
+        type: 'idoverrideuser',
2ff659
+        factory: idviews.idoverrideuser_adder_dialog
2ff659
+    });
2ff659
 };
2ff659
 
2ff659
 phases.on('registration', idviews.register);
2ff659
diff --git a/ipaserver/plugins/internal.py b/ipaserver/plugins/internal.py
2ff659
index 5f2b1fdc2..7622e65dc 100644
2ff659
--- a/ipaserver/plugins/internal.py
2ff659
+++ b/ipaserver/plugins/internal.py
2ff659
@@ -835,6 +835,9 @@ class i18n_messages(Command):
2ff659
                     "Remove users from member managers for user group "
2ff659
                     "'${primary_key}'"
2ff659
                 ),
2ff659
+                "add_idoverride_user": _(
2ff659
+                    "Add user ID override into user group '${primary_key}'"
2ff659
+                ),
2ff659
                 "details": _("Group Settings"),
2ff659
                 "external": _("External"),
2ff659
                 "groups": _("Groups"),
2ff659
@@ -868,6 +871,9 @@ class i18n_messages(Command):
2ff659
                 "remove_users": _(
2ff659
                     "Remove users from user group '${primary_key}'"
2ff659
                 ),
2ff659
+                "remove_idoverride_users": _(
2ff659
+                    "Remove user ID overrides from user group '${primary_key}'"
2ff659
+                ),
2ff659
                 "type": _("Group Type"),
2ff659
                 "user_groups": _("User Groups"),
2ff659
             },
2ff659
-- 
2ff659
2.26.2
2ff659
2ff659
From f6c460aee8542d4d81cd9970d71051c240156973 Mon Sep 17 00:00:00 2001
2ff659
From: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Date: Thu, 16 Jul 2020 18:52:24 +0200
2ff659
Subject: [PATCH] WebUI: Fix error "unknown command
2ff659
 'idoverrideuser_add_member'"
2ff659
2ff659
There was wrong IPA.associator class used for 'Groups' -> 'User ID overrides' association,
2ff659
as a result a wrong command was sent to the server.
2ff659
2ff659
Ticket: https://pagure.io/freeipa/issue/8416
2ff659
2ff659
Signed-off-by: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Reviewed-By: Petr Vobornik <pvoborni@redhat.com>
2ff659
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
2ff659
---
2ff659
 install/ui/src/freeipa/group.js | 1 -
2ff659
 1 file changed, 1 deletion(-)
2ff659
2ff659
diff --git a/install/ui/src/freeipa/group.js b/install/ui/src/freeipa/group.js
2ff659
index 2984bd4b2..61c19a82f 100644
2ff659
--- a/install/ui/src/freeipa/group.js
2ff659
+++ b/install/ui/src/freeipa/group.js
2ff659
@@ -209,7 +209,6 @@ return {
2ff659
         {
2ff659
             $type: 'association',
2ff659
             name: 'member_idoverrideuser',
2ff659
-            associator: IPA.serial_associator,
2ff659
             add_title: '@i18n:objects.group.add_idoverride_user',
2ff659
             remove_title: '@i18n:objects.group.remove_idoverride_users',
2ff659
             columns: [
2ff659
-- 
2ff659
2.26.2
2ff659
2ff659
From e35739b7e9f6bb016b37abbd92bdaee71a59a288 Mon Sep 17 00:00:00 2001
2ff659
From: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Date: Wed, 29 Jul 2020 09:41:36 +0200
2ff659
Subject: [PATCH] WebUI tests: Add test case to cover user ID override feature
2ff659
2ff659
The test case includes adding an user ID override to Default Trust View
2ff659
and adding the ID override to some IPA group.
2ff659
2ff659
Ticket: https://pagure.io/freeipa/issue/8416
2ff659
2ff659
Signed-off-by: Serhii Tsymbaliuk <stsymbal@redhat.com>
2ff659
Reviewed-By: Petr Vobornik <pvoborni@redhat.com>
2ff659
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
2ff659
---
2ff659
 ipatests/test_webui/test_trust.py | 41 +++++++++++++++++++++++++++++++
2ff659
 1 file changed, 41 insertions(+)
2ff659
2ff659
diff --git a/ipatests/test_webui/test_trust.py b/ipatests/test_webui/test_trust.py
2ff659
index c04c2fcd8..605f8a2a7 100644
2ff659
--- a/ipatests/test_webui/test_trust.py
2ff659
+++ b/ipatests/test_webui/test_trust.py
2ff659
@@ -21,6 +21,8 @@
2ff659
 Trust tests
2ff659
 """
2ff659
 
2ff659
+import ipatests.test_webui.data_group as group
2ff659
+import ipatests.test_webui.data_idviews as idview
2ff659
 from ipatests.test_webui.ui_driver import UI_driver
2ff659
 from ipatests.test_webui.ui_driver import screenshot
2ff659
 from ipatests.test_webui.task_range import range_tasks
2ff659
@@ -29,6 +31,8 @@ import pytest
2ff659
 ENTITY = 'trust'
2ff659
 CONFIG_ENTITY = 'trustconfig'
2ff659
 
2ff659
+DEFAULT_TRUST_VIEW = 'Default Trust View'
2ff659
+
2ff659
 CONFIG_DATA = {
2ff659
     'mod': [
2ff659
         ['combobox', 'ipantfallbackprimarygroup', 'admins'],
2ff659
@@ -164,3 +168,40 @@ class test_trust(trust_tasks):
2ff659
 
2ff659
         self.mod_record(CONFIG_ENTITY, CONFIG_DATA)
2ff659
         self.mod_record(CONFIG_ENTITY, CONFIG_DATA2)
2ff659
+
2ff659
+    @screenshot
2ff659
+    def test_group_member_idoverrideuser(self):
2ff659
+
2ff659
+        self.init_app()
2ff659
+
2ff659
+        # Create new trust
2ff659
+        data = self.get_data()
2ff659
+        self.add_record(ENTITY, data)
2ff659
+
2ff659
+        # Create an user ID override
2ff659
+        ad_domain = self.config.get('ad_domain')
2ff659
+        ad_admin = self.config.get('ad_admin')
2ff659
+        idoverrideuser_pkey = '{}@{}'.format(ad_admin, ad_domain).lower()
2ff659
+
2ff659
+        self.navigate_to_record(DEFAULT_TRUST_VIEW, entity=idview.ENTITY)
2ff659
+        self.add_record(idview.ENTITY, {
2ff659
+            'pkey': idoverrideuser_pkey,
2ff659
+            'add': [
2ff659
+                ('textbox', 'ipaanchoruuid_default', idoverrideuser_pkey),
2ff659
+            ],
2ff659
+        }, facet='idoverrideuser')
2ff659
+
2ff659
+        # Create new group and add the user ID override there
2ff659
+        self.navigate_to_entity(group.ENTITY)
2ff659
+        self.add_record(group.ENTITY, group.DATA)
2ff659
+        self.navigate_to_record(group.PKEY)
2ff659
+        self.add_associations([idoverrideuser_pkey],
2ff659
+                              facet='member_idoverrideuser', delete=True)
2ff659
+
2ff659
+        # Clean up data
2ff659
+        self.navigate_to_entity(group.ENTITY)
2ff659
+        self.delete_record(group.PKEY)
2ff659
+        self.navigate_to_record(DEFAULT_TRUST_VIEW, entity=idview.ENTITY)
2ff659
+        self.delete_record(idoverrideuser_pkey)
2ff659
+        self.navigate_to_entity(ENTITY)
2ff659
+        self.delete_record(ad_domain)
2ff659
-- 
2ff659
2.26.2
2ff659