Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-12-07 Thread Petr Vobornik

Summary to maintain order in the list:

This effort was split into patches:

freeipa-pvoborni-0030-Extending-facet-s-mechanism-of-gathering-changes
freeipa-pvoborni-0045-Code-cleanup-of-HBAC-Sudo-rules.patch - a part of 
greater UI refactoring effort ticket #2040 (patches 32-49).


Patches mentioned above were ACKed and pushed to master.

On 10/29/2011 03:45 AM, Adam Young wrote:

On 10/27/2011 08:55 PM, Endi Sukma Dewata wrote:

On 10/27/2011 6:39 PM, Adam Young wrote:

We might need to distinguish 2 different usages of 'entity'. The first
one represents a collection of entries:


Call that an instance. Entity is the term that is the analogue of Class


Not sure I understand correctly. You mean entity is a class which is a
collection, similar to a table in database? And instance is an object
or individual entry or row in a table?

Yes, that is a pretty good analogy.

So we want to distinguish getting the primary key field for the entity,
as opposed to the primary key of the instance.


From the URL we want to get the primary key for a particular
instance/object to show in the detail page.

Yes. In a RESTful scheme it would be /IPA/entities/users/ayoung to get
my user object



The IPA.client will represent a connection to the IPA server. In a
browser IPA.client can only connect to the server it's loaded from:

var client = IPA.client();

but in a JS engine like Rhino the IPA.client can connect to any IPA
server:

var client = IPA.client('ipa.example.com');


This will work now, but you will not be able to see the results of the
command. Integrations like this are how the Like buttons from Facebook
work. Cross site posting is tricky, but permitted, and might be useful
in some cases. Possibly we should call it connection.


The second code is not supposed to be used inside a browser. This is
suppose you're writing a JS script running in Rhino, you need to
specify the IPA server you're connecting to. I haven't tried this, but
I suppose in Rhino we will be able to set the Referer to match the
server name.

I'd rather call it IPA.client because it will do other things too, not
just connection.



___
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel



--
Petr Vobornik

___
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel


Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-28 Thread Adam Young

On 10/27/2011 08:55 PM, Endi Sukma Dewata wrote:

On 10/27/2011 6:39 PM, Adam Young wrote:

We might need to distinguish 2 different usages of 'entity'. The first
one represents a collection of entries:


Call that an instance. Entity is the term that is the analogue of Class


Not sure I understand correctly. You mean entity is a class which is a 
collection, similar to a table in database? And instance is an object 
or individual entry or row in a table?

Yes, that is a pretty good analogy.

So we want to distinguish getting the primary key field for the entity,
as opposed to the primary key of the instance.


From the URL we want to get the primary key for a particular 
instance/object to show in the detail page.
Yes.  In a RESTful  scheme it would be /IPA/entities/users/ayoung  to 
get my user object



The IPA.client will represent a connection to the IPA server. In a
browser IPA.client can only connect to the server it's loaded from:

var client = IPA.client();

but in a JS engine like Rhino the IPA.client can connect to any IPA
server:

var client = IPA.client('ipa.example.com');


This will work now, but you will not be able to see the results of the
command. Integrations like this are how the Like buttons from Facebook
work. Cross site posting is tricky, but permitted, and might be useful
in some cases. Possibly we should call it connection.


The second code is not supposed to be used inside a browser. This is 
suppose you're writing a JS script running in Rhino, you need to 
specify the IPA server you're connecting to. I haven't tried this, but 
I suppose in Rhino we will be able to set the Referer to match the 
server name.


I'd rather call it IPA.client because it will do other things too, not 
just connection.




___
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel


Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-27 Thread Petr Vobornik

I'll rebase this patch on recent patches (which will be soon pushed).

This effort is doing too many things, I'll split the patch into several.


On 10/25/2011 07:57 PM, Endi Sukma Dewata wrote:

On 10/25/2011 7:49 AM, Petr Vobornik wrote:

2. The set_facet() is added to widget. I don't think we want to make
widget dependent on facet. The facet so far is only used by
IPA.sudo.enable_widget. In IPA.sudo.options_section the facet object is
passed as a parameter in spec.



Are you saying that dependency on facet in ALL widgets is bad and only
in a few is good, or in any is bad?


In general less dependency is better. More dependency will limit its
usage. This is inline with the goal to make purely HTML widget.

But if a widget is meant to be used only with a facet then it's
certainly ok to make it depends on facet. However, the rest should not
become unnecessarily dependent on facet too.

I think it doesn't matter if all is dependant when one is dependant.

Anyway currently all association table widgets are dependant
(association.js:386).


Let's use this as an example. The association table explicitly checks if
the facet is dirty and asks the user whether to update/reset/cancel.
Suppose we want to use this inside a dialog, it will still check whether
the current facet is dirty instead of the dialog itself, which may not
be what we want.


Removed. Using instead: that.entity.get_facet() and 
that.entity.get_primary_key().


But still I think it would be better to be able to get container 
(facet/dialog) for a widget. As you wrote, that.entity.get_facet() may 
not always be what we want.





Btw similar topic could be: How to get current entity's pkey?'.
Dependancy on facet.get_primary_key() or
IPA.nav.get_state(that.entity.name+'-pkey') seems wrong too.


Yes. Ideally we should have a path (REST-style URL) instead of the
current parameter-based URL. We should get the pkey from that path.


From dependency point of view, widgets would be still dependant on the 
implementation of navigation (IMHO bad).


But it seems that using entity.get_primary key partially solves the problem.

Maybe it would be better if navigation would inject pkey to entity. 
Entity wouldn't be that much dependant on navigation implementation.



3. When updating sudo rule, in the original code the rule is
enabled/disabled after all the modifications are done. In the new code
it's reversed. I'm not sure the importance of the execution order for
this particular situation, but suppose it is, is there a way to maintain
the original order?


I was thinking about a command or widget priority. The 'mod' command
would have some default priority or it would get it from facet. The
commands would be sorted by priority before adding them to batch. This
way we can set exact order in facet update.


It's possible, but managing priority could be problematic if they are
spread out, because we have to know all existing priorities before we
can add a new one.


The priority could be part of update info. As there is a field_info we 
can create a command_info: { command, priority }.

 The original code uses an ordered list of commands.
Before adding commands to batch_command, array of command_info objects 
would joined with 'mod' command with default priority and then sorted by 
priority.


If the priority was set on each widget, priority management will be on 
facet level, which may be fine. There can be some corner case like 
dynamic change of priority.



The order which is implemented now is reflecting the order in HBAC
details facet - there were errors when 'mod' was executed before
clearing associations.


Right, so for certain things the order is important.


4. The IPA.header_widget is not really a widget, it's actually part of
layout. In the current implementation a widget always corresponds to an
attribute, so it will be loaded, saved, etc. Since there is no attribute
name matching the header name currently this is not a problem, but it
can pollute the namespace.


This is part of widget nesting topic. In this manner composite_widget
isn't a proper widget too (it can correspond to several or none
attribute).

Purely html rendering widgets can be separated from attribute widgets,
but it would be nice to have them because they can provide easier form
composing. Without them it would be required to override the create
method (in facet or composite_widget/section) which is sometimes better
but often it creates only code duplication with little added logic.


One other solution is to split widgets into non-visual fields and purely
HTML components. Then in the facet we use separate lists for the fields
and HTML components. The fields will have a reference to the
corresponding HTML components. There can be more HTML components than
fields. But this will require a significant restructuring.


Maybe we can use hybrid solution: html widgets would be simple object 
with some properties and create() method. They should not be called 
widgets. They would 

Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-27 Thread Endi Sukma Dewata

On 10/27/2011 8:39 AM, Petr Vobornik wrote:

But still I think it would be better to be able to get container
(facet/dialog) for a widget. As you wrote, that.entity.get_facet() may
not always be what we want.


One possibility is to convert the facet  dialog into subclasses of an 
abstract container class. The container needs to provide functions such 
as refresh() so the widget doesn't need to know whether it's a facet or 
dialog.



Btw similar topic could be: How to get current entity's pkey?'.
Dependancy on facet.get_primary_key() or
IPA.nav.get_state(that.entity.name+'-pkey') seems wrong too.


Yes. Ideally we should have a path (REST-style URL) instead of the
current parameter-based URL. We should get the pkey from that path.


 From dependency point of view, widgets would be still dependant on the
implementation of navigation (IMHO bad).

But it seems that using entity.get_primary key partially solves the
problem.


It could be argued that since this is a web app everything will have a 
path, but for now getting primary key from entity is fine since 
everything also has an associated entity.



Maybe it would be better if navigation would inject pkey to entity.
Entity wouldn't be that much dependant on navigation implementation.


We might need to distinguish 2 different usages of 'entity'. The first 
one represents a collection of entries:


  var users = IPA.get_entity('user');
  users.add([ 'test' ], { givenName: 'Test', ... });
  var result = users.find('t*');

The second one represents individual entry:

  var user = result.result[0];
  user.update({ sn: 'User' });

The entity collection should be 'stateless', it will be used in search 
pages. The individual entity will be 'stateful', it contains the pkey 
and the values of its attributes, and it will be used in the details page.


The entity.get_primary_key() is an interface to get the primary keys for 
a particular entity from the current path. So when you open a URL for an 
entry's details facet, it will execute the following command:


  var pkeys = entity.get_primary_key();
  var object = entity.get(pkeys);

Then the facet will use the object to populate the page.


The priority could be part of update info. As there is a field_info we
can create a command_info: { command, priority }.



Before adding commands to batch_command, array of command_info objects
would joined with 'mod' command with default priority and then sorted by
priority.

If the priority was set on each widget, priority management will be on
facet level, which may be fine. There can be some corner case like
dynamic change of priority.


I'd have to see how it's implemented.


One other solution is to split widgets into non-visual fields and purely
HTML components. Then in the facet we use separate lists for the fields
and HTML components. The fields will have a reference to the
corresponding HTML components. There can be more HTML components than
fields. But this will require a significant restructuring.


Maybe we can use hybrid solution: html widgets would be simple object
with some properties and create() method. They should not be called
widgets. They would not be part of sections fields. Rendering would be
done in widgets/sections create() method (as it is now).


I'm not very clear, we could be talking about the same thing. The 
(non-HTML) fields could be defined like this:


  fields: [
  {
  name: 'cn',
  widget: 'identity.cn'
  },
  {
  name: 'email',
  widget: 'identity.email'
  },
  {
  factory: IPA.password_field,
  name: 'userpassword',
  widgets: [ 'account.password1', 'account.password2' ]
  }
  ]

The specs above will be used to create IPA.field objects (not widget) to 
assist loading/saving attributes. Then we could also define the HTML 
components (let's call it widget) separately:


  widgets: [
  {
  factory: IPA.table_section,
  name: 'identity',
  label: 'Identity'
  widgets: [
  {
  factory: IPA.text_widget,
  name: 'cn'
  },
  {
  factory: IPA.multivalued_widget,
  name: 'email',
  widget: IPA.text_widget
  }
  ]
  }
  ]

The specs above will be used to create IPA.widget objects to generate 
the HTML content. If there is no widget specs specified, we could 
generate it automatically from the field specs.



Pros:
- reusable layouts, headers...
- not polluting field names
Cons:
- not so declarative - need to override update method, create custom
section/widget factories - same as now


The above example should be quite declarative.


Question:
- what with widget nesting? rule_details_section is in fact a composite
widget. I would like to keep the concept, because it offers better code
reuse.


As shown above, widget (not field) nesting is possible.

A section is a composite widget with a specific 

Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-27 Thread Adam Young

On 10/27/2011 05:51 PM, Endi Sukma Dewata wrote:

On 10/27/2011 8:39 AM, Petr Vobornik wrote:

But still I think it would be better to be able to get container
(facet/dialog) for a widget. As you wrote, that.entity.get_facet() may
not always be what we want.


One possibility is to convert the facet  dialog into subclasses of an 
abstract container class. The container needs to provide functions 
such as refresh() so the widget doesn't need to know whether it's a 
facet or dialog.



Btw similar topic could be: How to get current entity's pkey?'.
Dependancy on facet.get_primary_key() or
IPA.nav.get_state(that.entity.name+'-pkey') seems wrong too.


Yes. Ideally we should have a path (REST-style URL) instead of the
current parameter-based URL. We should get the pkey from that path.


 From dependency point of view, widgets would be still dependant on the
implementation of navigation (IMHO bad).

But it seems that using entity.get_primary key partially solves the
problem.





It could be argued that since this is a web app everything will have a 
path, but for now getting primary key from entity is fine since 
everything also has an associated entity.



Maybe it would be better if navigation would inject pkey to entity.
Entity wouldn't be that much dependant on navigation implementation.


We might need to distinguish 2 different usages of 'entity'. The first 
one represents a collection of entries:


Call that an instance.  Entity is the  term that is the analogue of  Class

So we want to distinguish getting the primary key field for the entity, 
as opposed to the primary key of the instance.




  var users = IPA.get_entity('user');
  users.add([ 'test' ], { givenName: 'Test', ... });
  var result = users.find('t*');

The second one represents individual entry:

  var user = result.result[0];
  user.update({ sn: 'User' });

The entity collection should be 'stateless', it will be used in search 
pages. The individual entity will be 'stateful', it contains the pkey 
and the values of its attributes, and it will be used in the details 
page.


The entity.get_primary_key() is an interface to get the primary keys 
for a particular entity from the current path. So when you open a URL 
for an entry's details facet, it will execute the following command:


  var pkeys = entity.get_primary_key();
  var object = entity.get(pkeys);

Then the facet will use the object to populate the page.


The priority could be part of update info. As there is a field_info we
can create a command_info: { command, priority }.


I'm a little unclear on the usage of priority.



Before adding commands to batch_command, array of command_info objects
would joined with 'mod' command with default priority and then sorted by
priority.

If the priority was set on each widget, priority management will be on
facet level, which may be fine. There can be some corner case like
dynamic change of priority.


I'd have to see how it's implemented.

One other solution is to split widgets into non-visual fields and 
purely

HTML components. Then in the facet we use separate lists for the fields
and HTML components. The fields will have a reference to the
corresponding HTML components. There can be more HTML components than
fields. But this will require a significant restructuring.


Maybe we can use hybrid solution: html widgets would be simple object
with some properties and create() method. They should not be called
widgets. They would not be part of sections fields. Rendering would be
done in widgets/sections create() method (as it is now).


I think this is  not quite right.  Widget is just a generic term for an 
element of the UI object model.  It is intentionally generic.  A Widget 
can be just about anything.  Some bind down to the individual fields, or 
in somcses, even smaller, but widget could easily be the base class for 
Facets, sections and the widget we have now.




I'm not very clear, we could be talking about the same thing. The 
(non-HTML) fields could be defined like this:


  fields: [
  {
  name: 'cn',
  widget: 'identity.cn'
  },
  {
  name: 'email',
  widget: 'identity.email'
  },
  {
  factory: IPA.password_field,
  name: 'userpassword',
  widgets: [ 'account.password1', 'account.password2' ]
  }
  ]

The specs above will be used to create IPA.field objects (not widget) 
to assist loading/saving attributes. Then we could also define the 
HTML components (let's call it widget) separately:


  widgets: [
  {
  factory: IPA.table_section,
  name: 'identity',
  label: 'Identity'
  widgets: [
  {
  factory: IPA.text_widget,
  name: 'cn'
  },
  {
  factory: IPA.multivalued_widget,
  name: 'email',
  widget: IPA.text_widget
  }
  ]
  }
  ]

The specs above will be used to create 

Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-25 Thread Petr Vobornik
Comments in text. New patch not supplied yet - some topics may require 
further discussion. Most of the comments should be part of the 'Nesting 
widgets' thread.


On 10/24/2011 06:29 PM, Endi Sukma Dewata wrote:

On 10/24/2011 3:29 AM, Petr Vobornik wrote:

https://fedorahosted.org/freeipa/ticket/1515


Some issues:

1. The IPA.hbacrule_details_facet uses IPA.sudo.enable_widget(). This
makes HBAC unnecessarily dependent on sudo. The enable_widget should be
moved to widget.js or rule.js which is shared between HBAC and sudo.


 * enable_widget moved to widget.js
 * rule_association_table_widget and rule_association_adder_dialog 
moved to rule.js



2. The set_facet() is added to widget. I don't think we want to make
widget dependent on facet. The facet so far is only used by
IPA.sudo.enable_widget. In IPA.sudo.options_section the facet object is
passed as a parameter in spec.
Are you saying that dependency on facet in ALL widgets is bad and only 
in a few is good, or in any is bad?


I think it doesn't matter if all is dependant when one is dependant.

Anyway currently all association table widgets are dependant 
(association.js:386).


Btw similar topic could be: How to get current entity's pkey?'. 
Dependancy on facet.get_primary_key() or 
IPA.nav.get_state(that.entity.name+'-pkey') seems wrong too.




3. When updating sudo rule, in the original code the rule is
enabled/disabled after all the modifications are done. In the new code
it's reversed. I'm not sure the importance of the execution order for
this particular situation, but suppose it is, is there a way to maintain
the original order?


I was thinking about a command or widget priority. The 'mod' command 
would have some default priority or it would get it from facet. The 
commands would be sorted by priority before adding them to batch. This 
way we can set exact order in facet update.


The order which is implemented now is reflecting the order in HBAC 
details facet - there were errors when 'mod' was executed before 
clearing associations.



4. The IPA.header_widget is not really a widget, it's actually part of
layout. In the current implementation a widget always corresponds to an
attribute, so it will be loaded, saved, etc. Since there is no attribute
name matching the header name currently this is not a problem, but it
can pollute the namespace.


This is part of widget nesting topic. In this manner composite_widget 
isn't a proper widget too (it can correspond to several or none attribute).


Purely html rendering widgets can be separated from attribute widgets, 
but it would be nice to have them because they can provide easier form 
composing. Without them it would be required to override the create 
method (in facet or composite_widget/section) which is sometimes better 
but often it creates only code duplication with little added logic.




5. In details facet update(), instead of storing the callbacks in
update_custom_on_win and update_custom_on_fail and requiring the
subclasses to call them, it might be better to call them from the
update() itself:

var command = IPA.command({
...
on_success: function(data, text_status, xhr) {
that.on_update_success(data, text_status, xhr)
if (on_win) on_win.call(this, data, text_status, xhr);
},
on_error: function(xhr, text_status, error_thrown) {
that.on_update_error(xhr, text_status, error_thrown);
if (on_fail) on_fail.call(
this, xhr, text_status, error_thrown);
}
});


There are two types of success/error handlers:
1) the default ones in details facet
2) the ones supplied to update(win, fail) method.

In my implementation I have separated 1) from update method so if 
default behaviour isn't suitable these methods can be overridden without 
overriding whole update method. Overriding isn't required. This is IMHO 
good (less code duplication).





6. Can IPA.batch_details_facet be combined into IPA.details_facet? I
think the base details facet should support both regular mod and batch.


The only point where they overlap is the update method. It's possible to 
add a logic to switch between command creations - maybe based on 
attribute (could be defined in spec). But should we do that? Isn't this 
the reason for inheriting the class?




7. In sudo details page, the As Whom category is missing the RunAs
User category radio buttons.


Fixed


8. The IPA.sudo.rule_details_runas_widget uses composite widget instead
of section. They are right now functionally identical, but I suppose the
composite widget is an abstract class and the section will later contain
code specific to section.


Part of widget nesting topic. This was briefly discussed with Adam (in 
that topic). The important question is what is a section? I understand 
section as top level container (in facet) which contains widgets (even 
composites) and semantically separates parts of the facet (with headers 
and section folding...). From this point of view, composite_widget isn't 
an abstract class, but it isn't used used anywhere else 

Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-25 Thread Endi Sukma Dewata

On 10/25/2011 7:49 AM, Petr Vobornik wrote:

2. The set_facet() is added to widget. I don't think we want to make
widget dependent on facet. The facet so far is only used by
IPA.sudo.enable_widget. In IPA.sudo.options_section the facet object is
passed as a parameter in spec.



Are you saying that dependency on facet in ALL widgets is bad and only
in a few is good, or in any is bad?


In general less dependency is better. More dependency will limit its 
usage. This is inline with the goal to make purely HTML widget.


But if a widget is meant to be used only with a facet then it's 
certainly ok to make it depends on facet. However, the rest should not 
become unnecessarily dependent on facet too.



I think it doesn't matter if all is dependant when one is dependant.

Anyway currently all association table widgets are dependant
(association.js:386).


Let's use this as an example. The association table explicitly checks if 
the facet is dirty and asks the user whether to update/reset/cancel. 
Suppose we want to use this inside a dialog, it will still check whether 
the current facet is dirty instead of the dialog itself, which may not 
be what we want.



Btw similar topic could be: How to get current entity's pkey?'.
Dependancy on facet.get_primary_key() or
IPA.nav.get_state(that.entity.name+'-pkey') seems wrong too.


Yes. Ideally we should have a path (REST-style URL) instead of the 
current parameter-based URL. We should get the pkey from that path.



3. When updating sudo rule, in the original code the rule is
enabled/disabled after all the modifications are done. In the new code
it's reversed. I'm not sure the importance of the execution order for
this particular situation, but suppose it is, is there a way to maintain
the original order?


I was thinking about a command or widget priority. The 'mod' command
would have some default priority or it would get it from facet. The
commands would be sorted by priority before adding them to batch. This
way we can set exact order in facet update.


It's possible, but managing priority could be problematic if they are 
spread out, because we have to know all existing priorities before we 
can add a new one. The original code uses an ordered list of commands.



The order which is implemented now is reflecting the order in HBAC
details facet - there were errors when 'mod' was executed before
clearing associations.


Right, so for certain things the order is important.


4. The IPA.header_widget is not really a widget, it's actually part of
layout. In the current implementation a widget always corresponds to an
attribute, so it will be loaded, saved, etc. Since there is no attribute
name matching the header name currently this is not a problem, but it
can pollute the namespace.


This is part of widget nesting topic. In this manner composite_widget
isn't a proper widget too (it can correspond to several or none attribute).

Purely html rendering widgets can be separated from attribute widgets,
but it would be nice to have them because they can provide easier form
composing. Without them it would be required to override the create
method (in facet or composite_widget/section) which is sometimes better
but often it creates only code duplication with little added logic.


One other solution is to split widgets into non-visual fields and purely 
HTML components. Then in the facet we use separate lists for the fields 
and HTML components. The fields will have a reference to the 
corresponding HTML components. There can be more HTML components than 
fields. But this will require a significant restructuring.



5. In details facet update(), instead of storing the callbacks in
update_custom_on_win and update_custom_on_fail and requiring the
subclasses to call them, it might be better to call them from the
update() itself:

var command = IPA.command({
...
on_success: function(data, text_status, xhr) {
that.on_update_success(data, text_status, xhr)
if (on_win) on_win.call(this, data, text_status, xhr);
},
on_error: function(xhr, text_status, error_thrown) {
that.on_update_error(xhr, text_status, error_thrown);
if (on_fail) on_fail.call(
this, xhr, text_status, error_thrown);
}
});


There are two types of success/error handlers:
1) the default ones in details facet
2) the ones supplied to update(win, fail) method.

In my implementation I have separated 1) from update method so if
default behaviour isn't suitable these methods can be overridden without
overriding whole update method. Overriding isn't required. This is IMHO
good (less code duplication).


There is still code duplication, the subclass that overrides the 
on_update_success/error (#1) will still have to call 
update_custom_on_win/error (#2) manually. In the changes that I proposed 
you don't have to do that because #2 are called inside update().



6. Can IPA.batch_details_facet be combined into IPA.details_facet? I
think the base details facet should support both regular mod and batch.


The only point 

Re: [Freeipa-devel] [PATCH] 028 Code cleanup of HBAC, Sudo rules

2011-10-24 Thread Endi Sukma Dewata

On 10/24/2011 3:29 AM, Petr Vobornik wrote:

https://fedorahosted.org/freeipa/ticket/1515

Changes:
* Added functionality for widget composition. This allows to gather
update information from nested widgets and gradually combine it to the
facet level.
* Details' facet update method was split to several parts to allow finer
overriding in subclasses.
* Sudo rule and HBAC rule details facet was reworked to use new
functionality.

Changes in composite_widget (formal details_facet):
* added get_update_info method (for all widgets)
* modified save method
* added links to parent widget and facet

Note: cleanup of sudo options section may be part of
https://fedorahosted.org/freeipa/ticket/1690


Some issues:

1. The IPA.hbacrule_details_facet uses IPA.sudo.enable_widget(). This 
makes HBAC unnecessarily dependent on sudo. The enable_widget should be 
moved to widget.js or rule.js which is shared between HBAC and sudo.


2. The set_facet() is added to widget. I don't think we want to make 
widget dependent on facet. The facet so far is only used by 
IPA.sudo.enable_widget. In IPA.sudo.options_section the facet object is 
passed as a parameter in spec.


3. When updating sudo rule, in the original code the rule is 
enabled/disabled after all the modifications are done. In the new code 
it's reversed. I'm not sure the importance of the execution order for 
this particular situation, but suppose it is, is there a way to maintain 
the original order?


4. The IPA.header_widget is not really a widget, it's actually part of 
layout. In the current implementation a widget always corresponds to an 
attribute, so it will be loaded, saved, etc. Since there is no attribute 
name matching the header name currently this is not a problem, but it 
can pollute the namespace.


5. In details facet update(), instead of storing the callbacks in 
update_custom_on_win and update_custom_on_fail and requiring the 
subclasses to call them, it might be better to call them from the 
update() itself:


var command = IPA.command({
...
on_success: function(data, text_status, xhr) {
that.on_update_success(data, text_status, xhr)
if (on_win) on_win.call(this, data, text_status, xhr);
},
on_error: function(xhr, text_status, error_thrown) {
that.on_update_error(xhr, text_status, error_thrown);
if (on_fail) on_fail.call(
this, xhr, text_status, error_thrown);
}
});

6. Can IPA.batch_details_facet be combined into IPA.details_facet? I 
think the base details facet should support both regular mod and batch.


7. In sudo details page, the As Whom category is missing the RunAs 
User category radio buttons.


8. The IPA.sudo.rule_details_runas_widget uses composite widget instead 
of section. They are right now functionally identical, but I suppose the 
composite widget is an abstract class and the section will later contain 
code specific to section.


9. It's probably better to define the proper update_info and field_info 
classes rather than constructing them on the fly.


10. There are some whitespace warnings during git am.

11. The following code doesn't seem to be used:
 * param_info in details.js:469
 * update_command_name in details.js:597

--
Endi S. Dewata

___
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel