Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
erp5_fork
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Eteri
erp5_fork
Commits
5272e987
Commit
5272e987
authored
Sep 14, 2012
by
Ivan Tyagov
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'security_groups'
parents
90fb36be
88e9c81e
Changes
34
Expand all
Show whitespace changes
Inline
Side-by-side
Showing
34 changed files
with
1704 additions
and
159 deletions
+1704
-159
bt5/erp5_administration/SkinTemplateItem/portal_skins/erp5_administration/z_refresh_roles_and_users.xml
...l_skins/erp5_administration/z_refresh_roles_and_users.xml
+2
-2
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.catalog_keys.xml
...ql_innodb/z_catalog_roles_and_users_list.catalog_keys.xml
+5
-0
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
...alog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
+84
-0
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.catalog_keys.xml
...p5_mysql_innodb/z_create_roles_and_users.catalog_keys.xml
+5
-0
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
...al_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
+78
-0
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.catalog_keys.xml
...alog/erp5_mysql_innodb/z_search_security.catalog_keys.xml
+5
-0
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.xml
...em/portal_catalog/erp5_mysql_innodb/z_search_security.xml
+73
-0
bt5/erp5_security_uid_innodb_catalog/bt/change_log
bt5/erp5_security_uid_innodb_catalog/bt/change_log
+2
-0
bt5/erp5_security_uid_innodb_catalog/bt/description
bt5/erp5_security_uid_innodb_catalog/bt/description
+7
-0
bt5/erp5_security_uid_innodb_catalog/bt/revision
bt5/erp5_security_uid_innodb_catalog/bt/revision
+1
-0
bt5/erp5_security_uid_innodb_catalog/bt/template_catalog_method_id_list
...ity_uid_innodb_catalog/bt/template_catalog_method_id_list
+3
-0
bt5/erp5_security_uid_innodb_catalog/bt/template_format_version
...p5_security_uid_innodb_catalog/bt/template_format_version
+1
-0
bt5/erp5_security_uid_innodb_catalog/bt/title
bt5/erp5_security_uid_innodb_catalog/bt/title
+1
-0
product/ERP5/Document/BusinessTemplate.py
product/ERP5/Document/BusinessTemplate.py
+84
-11
product/ERP5/bootstrap/erp5_core/CategoryTemplateItem/portal_categories/local_role_group.xml
...tegoryTemplateItem/portal_categories/local_role_group.xml
+117
-0
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/BusinessTemplate_viewCatalog.xml
...m/portal_skins/erp5_core/BusinessTemplate_viewCatalog.xml
+1
-0
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/BusinessTemplate_viewCatalog/my_template_catalog_security_uid_column_list.xml
...wCatalog/my_template_catalog_security_uid_column_list.xml
+298
-0
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/RoleInformation_view.xml
...plateItem/portal_skins/erp5_core/RoleInformation_view.xml
+1
-0
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/RoleInformation_view/my_local_roles_group_id.xml
...rp5_core/RoleInformation_view/my_local_roles_group_id.xml
+277
-0
product/ERP5/bootstrap/erp5_core/bt/template_base_category_list
...t/ERP5/bootstrap/erp5_core/bt/template_base_category_list
+1
-0
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
...alog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
+6
-9
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
...al_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
+6
-0
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.xml
...em/portal_catalog/erp5_mysql_innodb/z_search_security.xml
+3
-3
product/ERP5/bootstrap/erp5_property_sheets/PropertySheetTemplateItem/portal_property_sheets/BusinessTemplate/template_catalog_security_uid_column_property.xml
...emplate/template_catalog_security_uid_column_property.xml
+59
-0
product/ERP5/bootstrap/erp5_property_sheets/PropertySheetTemplateItem/portal_property_sheets/RoleInformation/local_role_group_category.xml
...erty_sheets/RoleInformation/local_role_group_category.xml
+20
-0
product/ERP5/tests/testBusinessTemplate.py
product/ERP5/tests/testBusinessTemplate.py
+84
-0
product/ERP5Catalog/CatalogTool.py
product/ERP5Catalog/CatalogTool.py
+120
-51
product/ERP5Catalog/tests/testERP5CatalogSecurityUidOptimization.py
...P5Catalog/tests/testERP5CatalogSecurityUidOptimization.py
+191
-0
product/ERP5Security/tests/testERP5Security.py
product/ERP5Security/tests/testERP5Security.py
+23
-0
product/ERP5Type/Core/RoleInformation.py
product/ERP5Type/Core/RoleInformation.py
+0
-1
product/ERP5Type/ERP5Type.py
product/ERP5Type/ERP5Type.py
+27
-16
product/ERP5Type/interfaces/role_provider.py
product/ERP5Type/interfaces/role_provider.py
+1
-1
product/ERP5Type/patches/WorkflowTool.py
product/ERP5Type/patches/WorkflowTool.py
+34
-15
product/ZSQLCatalog/SQLCatalog.py
product/ZSQLCatalog/SQLCatalog.py
+84
-50
No files found.
bt5/erp5_administration/SkinTemplateItem/portal_skins/erp5_administration/z_refresh_roles_and_users.xml
View file @
5272e987
...
...
@@ -31,8 +31,8 @@
DELETE FROM roles_and_users\n
<dtml-var sql_delimiter>
\n
INSERT INTO roles_and_users (uid, allowedRolesAndUsers) VALUES\n
<dtml-in
expr=
"getPortalObject().portal_catalog.getSQLCatalog().getRoleAndSecurityUidList()"
>
\n
(
<dtml-sqlvar
sequence-item
type=
"int"
>
,
<dtml-sqlvar
sequence-key
type=
"string"
>
)
<dtml-if
sequence-end
><dtml-else>
,
</dtml-if>
\n
<dtml-in
expr=
"
role"
expr=
"
getPortalObject().portal_catalog.getSQLCatalog().getRoleAndSecurityUidList()"
>
\n
(
<dtml-sqlvar
expr=
"role_item[0]"
type=
"int"
>
,
<dtml-sqlvar
expr=
"role_item[1]"
type=
"string"
>
,
<dtml-sqlvar
expr=
"role_item[2]"
type=
"string"
>
)
<dtml-if
sequence-end
><dtml-else>
,
</dtml-if>
\n
\n
</dtml-in>
...
...
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.catalog_keys.xml
0 → 100644
View file @
5272e987
<catalog_method>
<item
key=
"sql_catalog_object_list"
type=
"int"
>
<value>
1
</value>
</item>
</catalog_method>
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"SQL"
module=
"Products.ZSQLMethods.SQL"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
allow_simple_one_argument_traversal
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
arguments_src
</string>
</key>
<value>
<string>
optimised_roles_and_users
</string>
</value>
</item>
<item>
<key>
<string>
cache_time_
</string>
</key>
<value>
<int>
0
</int>
</value>
</item>
<item>
<key>
<string>
class_file_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
class_name_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
connection_hook
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
connection_id
</string>
</key>
<value>
<string>
erp5_sql_connection
</string>
</value>
</item>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
z_catalog_roles_and_users_list
</string>
</value>
</item>
<item>
<key>
<string>
max_cache_
</string>
</key>
<value>
<int>
100
</int>
</value>
</item>
<item>
<key>
<string>
max_rows_
</string>
</key>
<value>
<int>
1000
</int>
</value>
</item>
<item>
<key>
<string>
src
</string>
</key>
<value>
<string
encoding=
"cdata"
>
<![CDATA[
<dtml-let row_list="[]">
\n
<dtml-in
prefix=
"loop"
expr=
"_.range(_.len(optimised_roles_and_users))"
>
\n
<dtml-in
prefix=
"role"
expr=
"optimised_roles_and_users[loop_item]"
>
\n
<dtml-call
expr=
"row_list.append([role_item[0], role_item[1], role_item[2]])"
>
\n
</dtml-in>
\n
</dtml-in>
\n
<dtml-if
expr=
"row_list"
>
\n
INSERT INTO\n
roles_and_users(uid, local_roles_group_id, allowedRolesAndUsers)\n
VALUES\n
<dtml-in
prefix=
"row"
expr=
"row_list"
>
\n
(
<dtml-sqlvar
expr=
"row_item[0]"
type=
"string"
>
,
<dtml-sqlvar
expr=
"row_item[1]"
type=
"string"
>
,
<dtml-sqlvar
expr=
"row_item[2]"
type=
"string"
>
)\n
<dtml-if
sequence-end
><dtml-else>
,
</dtml-if>
\n
</dtml-in>
\n
</dtml-if>
\n
</dtml-let>
\n
]]>
</string>
</value>
</item>
<item>
<key>
<string>
title
</string>
</key>
<value>
<string></string>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.catalog_keys.xml
0 → 100644
View file @
5272e987
<catalog_method>
<item
key=
"sql_clear_catalog"
type=
"int"
>
<value>
1
</value>
</item>
</catalog_method>
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"SQL"
module=
"Products.ZSQLMethods.SQL"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
_col
</string>
</key>
<value>
<tuple/>
</value>
</item>
<item>
<key>
<string>
allow_simple_one_argument_traversal
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
arguments_src
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
cache_time_
</string>
</key>
<value>
<int>
0
</int>
</value>
</item>
<item>
<key>
<string>
class_file_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
class_name_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
connection_hook
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
connection_id
</string>
</key>
<value>
<string>
erp5_sql_connection
</string>
</value>
</item>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
z_create_roles_and_users
</string>
</value>
</item>
<item>
<key>
<string>
max_cache_
</string>
</key>
<value>
<int>
100
</int>
</value>
</item>
<item>
<key>
<string>
max_rows_
</string>
</key>
<value>
<int>
1000
</int>
</value>
</item>
<item>
<key>
<string>
src
</string>
</key>
<value>
<string>
CREATE TABLE roles_and_users (\n
uid INT UNSIGNED,\n
local_roles_group_id VARCHAR(255) default \'\',\n
allowedRolesAndUsers VARCHAR(255),\n
KEY `uid` (`uid`),\n
KEY `allowedRolesAndUsers` (`allowedRolesAndUsers`),\n
KEY `local_roles_group_id` (`local_roles_group_id`)\n
) ENGINE=InnoDB;\n
</string>
</value>
</item>
<item>
<key>
<string>
title
</string>
</key>
<value>
<string></string>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.catalog_keys.xml
0 → 100644
View file @
5272e987
<catalog_method>
<item
key=
"sql_search_security"
type=
"int"
>
<value>
1
</value>
</item>
</catalog_method>
bt5/erp5_security_uid_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"SQL"
module=
"Products.ZSQLMethods.SQL"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
allow_simple_one_argument_traversal
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
arguments_src
</string>
</key>
<value>
<string>
security_roles_list
</string>
</value>
</item>
<item>
<key>
<string>
cache_time_
</string>
</key>
<value>
<int>
0
</int>
</value>
</item>
<item>
<key>
<string>
class_file_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
class_name_
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
connection_hook
</string>
</key>
<value>
<string></string>
</value>
</item>
<item>
<key>
<string>
connection_id
</string>
</key>
<value>
<string>
erp5_sql_connection
</string>
</value>
</item>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
z_search_security
</string>
</value>
</item>
<item>
<key>
<string>
max_cache_
</string>
</key>
<value>
<int>
100
</int>
</value>
</item>
<item>
<key>
<string>
max_rows_
</string>
</key>
<value>
<int>
0
</int>
</value>
</item>
<item>
<key>
<string>
src
</string>
</key>
<value>
<string
encoding=
"cdata"
>
<![CDATA[
SELECT\n
DISTINCT uid, local_roles_group_id\n
FROM \n
roles_and_users\n
WHERE \n
allowedRolesAndUsers \n
IN (<dtml-in security_roles_list>
<dtml-var
sequence-item
><dtml-if
sequence-end
><dtml-else>
,
</dtml-if></dtml-in>
)\n
]]>
</string>
</value>
</item>
<item>
<key>
<string>
title
</string>
</key>
<value>
<string></string>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
bt5/erp5_security_uid_innodb_catalog/bt/change_log
0 → 100644
View file @
5272e987
2012-07-12 Ivan
* Initial import
\ No newline at end of file
bt5/erp5_security_uid_innodb_catalog/bt/description
0 → 100644
View file @
5272e987
This bt5 provides generic Z SQL methods that allows a site developer to split security uids into different catalog columns.
In order to use this optimization it's required to:
1. Make analyze which are most common uids
2. Place them in a new catalog column
3. Adjust respective z_catalog_object_list and z_create_catalog
Note: In order to use this technique a full catalog re-index is required.
\ No newline at end of file
bt5/erp5_security_uid_innodb_catalog/bt/revision
0 → 100644
View file @
5272e987
3
\ No newline at end of file
bt5/erp5_security_uid_innodb_catalog/bt/template_catalog_method_id_list
0 → 100644
View file @
5272e987
erp5_mysql_innodb/z_catalog_roles_and_users_list
erp5_mysql_innodb/z_create_roles_and_users
erp5_mysql_innodb/z_search_security
\ No newline at end of file
bt5/erp5_security_uid_innodb_catalog/bt/template_format_version
0 → 100644
View file @
5272e987
1
\ No newline at end of file
bt5/erp5_security_uid_innodb_catalog/bt/title
0 → 100644
View file @
5272e987
erp5_security_uid_innodb_catalog
\ No newline at end of file
product/ERP5/Document/BusinessTemplate.py
View file @
5272e987
...
...
@@ -545,7 +545,7 @@ class BaseTemplateItem(Implicit, Persistent):
classname
=
klass
.
__name__
attr_set
=
set
((
'_dav_writelocks'
,
'_filepath'
,
'_owner'
,
'last_id'
,
'uid'
,
'__ac_local_roles__'
))
'__ac_local_roles__'
,
'__ac_local_roles_group_id_dict__'
))
if
export
:
if
not
keep_workflow_history
:
attr_set
.
add
(
'workflow_history'
)
...
...
@@ -3047,11 +3047,12 @@ class PortalTypeRolesTemplateItem(BaseTemplateItem):
k
=
k
[
5
:]
elif
k
==
'role_name'
:
k
,
v
=
'id'
,
'; '
.
join
(
v
)
elif
k
not
in
(
'title'
,
'description'
):
elif
k
not
in
(
'title'
,
'description'
,
'categories'
):
k
=
{
'id'
:
'object_id'
,
# for stable sort
'role_base_category'
:
'base_category'
,
'role_base_category_script_id'
:
'base_category_script'
,
'role_category'
:
'category'
}.
get
(
k
)
'role_category'
:
'category'
,
'local_roles_group_id'
:
'local_roles_group_id'
}.
get
(
k
)
if
not
k
:
continue
type_role_dict
[
k
]
=
v
...
...
@@ -3074,7 +3075,7 @@ class PortalTypeRolesTemplateItem(BaseTemplateItem):
xml_data
+=
"
\
n
<property id='%s'>%s</property>"
%
\
(
property
,
prop_value
)
# multi
for
property
in
(
'category'
,
'base_category'
):
for
property
in
(
'categor
ies'
,
'categor
y'
,
'base_category'
):
for
prop_value
in
role
.
get
(
property
,
[]):
if
isinstance
(
prop_value
,
str
):
prop_value
=
prop_value
.
decode
(
'utf-8'
)
...
...
@@ -3161,7 +3162,7 @@ class PortalTypeRolesTemplateItem(BaseTemplateItem):
path
=
'portal_types/%s'
%
roles_path
.
split
(
'/'
,
1
)[
1
]
try
:
obj
=
p
.
unrestrictedTraverse
(
path
)
setattr
(
obj
,
'_roles'
,
[
])
obj
.
manage_delObjects
([
x
.
id
for
x
in
obj
.
getRoleInformationList
()
])
except
(
NotFound
,
KeyError
):
pass
...
...
@@ -4360,6 +4361,12 @@ class CatalogLocalRoleKeyTemplateItem(CatalogUniqueKeyTemplateItemBase):
key_list_title
=
'local_role_key_list'
key_title
=
'LocalRole key'
class
CatalogSecurityUidColumnTemplateItem
(
CatalogSearchKeyTemplateItem
):
key_list_attr
=
'sql_catalog_security_uid_columns'
key_list_title
=
'security_uid_column_list'
key_title
=
'Security Uid Columns'
class
MessageTranslationTemplateItem
(
BaseTemplateItem
):
def
build
(
self
,
context
,
**
kw
):
...
...
@@ -4532,13 +4539,27 @@ class LocalRolesTemplateItem(BaseTemplateItem):
obj
=
p
.
unrestrictedTraverse
(
path
.
split
(
'/'
,
1
)[
1
])
local_roles_dict
=
getattr
(
obj
,
'__ac_local_roles__'
,
{})
or
{}
self
.
_objects
[
path
]
=
(
local_roles_dict
,
)
local_roles_group_id_dict
=
getattr
(
obj
,
'__ac_local_roles_group_id_dict__'
,
{})
or
{}
self
.
_objects
[
path
]
=
(
local_roles_dict
,
local_roles_group_id_dict
)
# Function to generate XML Code Manually
def
generateXml
(
self
,
path
=
None
):
local_roles_dict
=
self
.
_objects
[
path
][
0
]
# local roles
# With local roles groups id, self._object contains for each path a tuple
# containing the dict of local roles and the dict of local roles group ids.
# Before it was only containing the dict of local roles. This method is
# also used on installed business templates to show a diff during
# installation, so it might be called on old format objects.
if
len
(
self
.
_objects
[
path
])
==
2
:
# new format
local_roles_dict
,
local_roles_group_id_dict
=
self
.
_objects
[
path
]
else
:
# old format, before local roles group id
local_roles_group_id_dict
=
dict
()
local_roles_dict
,
=
self
.
_objects
[
path
]
xml_data
=
'<local_roles_item>'
# local roles
xml_data
+=
'
\
n
<local_roles>'
for
key
in
sorted
(
local_roles_dict
):
xml_data
+=
"
\
n
<role id='%s'>"
%
(
key
,)
...
...
@@ -4547,6 +4568,20 @@ class LocalRolesTemplateItem(BaseTemplateItem):
xml_data
+=
"
\
n
<item>%s</item>"
%
(
item
,)
xml_data
+=
'
\
n
</role>'
xml_data
+=
'
\
n
</local_roles>'
if
local_roles_group_id_dict
:
# local roles group id dict (not included by default to be stable with
# old bts)
xml_data
+=
'
\
n
<local_roles_group_id>'
for
principal
,
local_roles_group_id_list
in
sorted
(
local_roles_group_id_dict
.
items
()):
xml_data
+=
"
\
n
<principal id='%s'>"
%
escape
(
principal
)
for
local_roles_group_id
in
local_roles_group_id_list
:
for
item
in
local_roles_group_id
:
xml_data
+=
"
\
n
<local_roles_group_id>%s</local_roles_group_id>"
%
\
escape
(
item
)
xml_data
+=
"
\
n
</principal>"
xml_data
+=
'
\
n
</local_roles_group_id>'
xml_data
+=
'
\
n
</local_roles_item>'
if
isinstance
(
xml_data
,
unicode
):
xml_data
=
xml_data
.
encode
(
'utf8'
)
...
...
@@ -4571,7 +4606,15 @@ class LocalRolesTemplateItem(BaseTemplateItem):
id
=
role
.
get
(
'id'
)
item_type_list
=
[
item
.
text
for
item
in
role
]
local_roles_dict
[
id
]
=
item_type_list
self
.
_objects
[
'local_roles/%s'
%
(
file_name
[:
-
4
],)]
=
(
local_roles_dict
,
)
# local roles group id
local_roles_group_id_dict
=
{}
for
principal
in
xml
.
findall
(
'//principal'
):
local_roles_group_id_dict
[
principal
.
get
(
'id'
)]
=
set
([
tuple
(
[
group_id
.
text
for
group_id
in
principal
.
findall
(
'./local_roles_group_id'
)])])
self
.
_objects
[
'local_roles/%s'
%
(
file_name
[:
-
4
],)]
=
(
local_roles_dict
,
local_roles_group_id_dict
)
def
install
(
self
,
context
,
trashbin
,
**
kw
):
update_dict
=
kw
.
get
(
'object_to_update'
)
...
...
@@ -4585,8 +4628,22 @@ class LocalRolesTemplateItem(BaseTemplateItem):
continue
path
=
roles_path
.
split
(
'/'
)[
1
:]
obj
=
p
.
unrestrictedTraverse
(
path
)
local_roles_dict
=
self
.
_objects
[
roles_path
][
0
]
# again we might be installing an business template in format before
# existance of local roles group id.
if
len
(
self
.
_objects
[
roles_path
])
==
2
:
local_roles_dict
,
local_roles_group_id_dict
=
self
.
_objects
[
roles_path
]
else
:
local_roles_group_id_dict
=
dict
()
local_roles_dict
,
=
self
.
_objects
[
roles_path
]
setattr
(
obj
,
'__ac_local_roles__'
,
local_roles_dict
)
if
local_roles_group_id_dict
:
setattr
(
obj
,
'__ac_local_roles_group_id_dict__'
,
local_roles_group_id_dict
)
# we try to have __ac_local_roles_group_id_dict__ set only if
# it is actually defining something else than default
elif
getattr
(
aq_base
(
obj
),
'__ac_local_roles_group_id_dict__'
,
None
)
is
not
None
:
delattr
(
obj
,
'__ac_local_roles_group_id_dict__'
)
obj
.
reindexObject
()
def
uninstall
(
self
,
context
,
object_path
=
None
,
**
kw
):
...
...
@@ -4748,6 +4805,7 @@ Business Template is a set of definitions, such as skins, portal types and categ
'_catalog_scriptable_key_item'
,
'_catalog_role_key_item'
,
'_catalog_local_role_key_item'
,
'_catalog_security_uid_column_item'
,
]
def
__init__
(
self
,
*
args
,
**
kw
):
...
...
@@ -4910,6 +4968,14 @@ Business Template is a set of definitions, such as skins, portal types and categ
self
.
_catalog_local_role_key_item
=
\
CatalogLocalRoleKeyTemplateItem
(
self
.
getTemplateCatalogLocalRoleKeyList
())
try
:
self
.
_catalog_security_uid_column_item
=
\
CatalogSecurityUidColumnTemplateItem
(
self
.
getTemplateCatalogSecurityUidColumnList
())
except
AttributeError
:
# be backwards compatible with old zope instances which
# do not contain recent version of erp5_property_sheets
pass
security
.
declareProtected
(
Permissions
.
ManagePortal
,
'build'
)
def
build
(
self
,
no_action
=
0
):
...
...
@@ -5523,7 +5589,12 @@ Business Template is a set of definitions, such as skins, portal types and categ
(
SimpleItem
.
SimpleItem
,),
{
'__module__'
:
module_id
}))
for
item_name
in
self
.
_item_name_list
:
getattr
(
self
,
item_name
).
importFile
(
bta
)
item_object
=
getattr
(
self
,
item_name
,
None
)
# this check is due to backwards compatability when there can be a
# difference between install erp5_property_sheets (esp. BusinessTemplate
# property sheet)
if
item_object
is
not
None
:
item_object
.
importFile
(
bta
)
# Remove temporary modules created above to allow import of real modules
# (during the installation).
...
...
@@ -5631,6 +5702,7 @@ Business Template is a set of definitions, such as skins, portal types and categ
'CatalogScriptableKey'
:
'_catalog_scriptable_key_item'
,
'CatalogRoleKey'
:
'_catalog_role_key_item'
,
'CatalogLocalRoleKey'
:
'_catalog_local_role_key_item'
,
'CatalogSecurityUidColumn'
:
'_catalog_security_uid_column_item'
,
}
object_id
=
REQUEST
.
object_id
...
...
@@ -5693,6 +5765,7 @@ Business Template is a set of definitions, such as skins, portal types and categ
'_catalog_scriptable_key_item'
,
'_catalog_role_key_item'
,
'_catalog_local_role_key_item'
,
'_catalog_security_uid_column_item'
,
'_portal_type_allowed_content_type_item'
,
'_portal_type_hidden_content_type_item'
,
'_portal_type_property_sheet_item'
,
...
...
product/ERP5/bootstrap/erp5_core/CategoryTemplateItem/portal_categories/local_role_group.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"Base Category"
module=
"erp5.portal_type"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
_Add_portal_content_Permission
</string>
</key>
<value>
<tuple>
<string>
Assignor
</string>
<string>
Manager
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
_Add_portal_folders_Permission
</string>
</key>
<value>
<tuple>
<string>
Assignor
</string>
<string>
Manager
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
_Copy_or_Move_Permission
</string>
</key>
<value>
<tuple>
<string>
Assignor
</string>
<string>
Manager
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
_Delete_objects_Permission
</string>
</key>
<value>
<tuple>
<string>
Assignor
</string>
<string>
Manager
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
_Modify_portal_content_Permission
</string>
</key>
<value>
<tuple>
<string>
Assignee
</string>
<string>
Assignor
</string>
<string>
Manager
</string>
<string>
Owner
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
_count
</string>
</key>
<value>
<persistent>
<string
encoding=
"base64"
>
AAAAAAAAAAI=
</string>
</persistent>
</value>
</item>
<item>
<key>
<string>
_mt_index
</string>
</key>
<value>
<persistent>
<string
encoding=
"base64"
>
AAAAAAAAAAM=
</string>
</persistent>
</value>
</item>
<item>
<key>
<string>
_tree
</string>
</key>
<value>
<persistent>
<string
encoding=
"base64"
>
AAAAAAAAAAQ=
</string>
</persistent>
</value>
</item>
<item>
<key>
<string>
description
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
local_role_group
</string>
</value>
</item>
<item>
<key>
<string>
portal_type
</string>
</key>
<value>
<string>
Base Category
</string>
</value>
</item>
<item>
<key>
<string>
title
</string>
</key>
<value>
<string>
Local Role Group
</string>
</value>
</item>
</dictionary>
</pickle>
</record>
<record
id=
"2"
aka=
"AAAAAAAAAAI="
>
<pickle>
<global
name=
"Length"
module=
"BTrees.Length"
/>
</pickle>
<pickle>
<int>
0
</int>
</pickle>
</record>
<record
id=
"3"
aka=
"AAAAAAAAAAM="
>
<pickle>
<global
name=
"OOBTree"
module=
"BTrees.OOBTree"
/>
</pickle>
<pickle>
<none/>
</pickle>
</record>
<record
id=
"4"
aka=
"AAAAAAAAAAQ="
>
<pickle>
<global
name=
"OOBTree"
module=
"BTrees.OOBTree"
/>
</pickle>
<pickle>
<none/>
</pickle>
</record>
</ZopeData>
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/BusinessTemplate_viewCatalog.xml
View file @
5272e987
...
...
@@ -91,6 +91,7 @@
<string>
my_template_catalog_topic_key_list
</string>
<string>
my_template_catalog_scriptable_key_list
</string>
<string>
my_template_catalog_local_role_key_list
</string>
<string>
my_template_catalog_security_uid_column_list
</string>
</list>
</value>
</item>
...
...
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/BusinessTemplate_viewCatalog/my_template_catalog_security_uid_column_list.xml
0 → 100644
View file @
5272e987
This diff is collapsed.
Click to expand it.
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/RoleInformation_view.xml
View file @
5272e987
...
...
@@ -98,6 +98,7 @@
<string>
my_title
</string>
<string>
my_role_name_list
</string>
<string>
my_condition
</string>
<string>
my_local_roles_group_id
</string>
</list>
</value>
</item>
...
...
product/ERP5/bootstrap/erp5_core/SkinTemplateItem/portal_skins/erp5_core/RoleInformation_view/my_local_roles_group_id.xml
0 → 100644
View file @
5272e987
This diff is collapsed.
Click to expand it.
product/ERP5/bootstrap/erp5_core/bt/template_base_category_list
View file @
5272e987
...
...
@@ -16,6 +16,7 @@ destination_project
destination_section
destination_trade
elementary_type
local_role_group
mapping
order
origin
...
...
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_catalog_roles_and_users_list.xml
View file @
5272e987
...
...
@@ -14,8 +14,7 @@
</item>
<item>
<key>
<string>
arguments_src
</string>
</key>
<value>
<string>
security_uid\r\n
optimised_roles_and_users
</string>
</value>
<value>
<string>
optimised_roles_and_users
</string>
</value>
</item>
<item>
<key>
<string>
cache_time_
</string>
</key>
...
...
@@ -56,16 +55,14 @@ optimised_roles_and_users</string> </value>
<value>
<string
encoding=
"cdata"
>
<![CDATA[
<dtml-let row_list="[]">
\n
<dtml-in
prefix=
"loop"
expr=
"_.range(_.len(security_uid))"
>
\n
<dtml-if
expr=
"optimised_roles_and_users[loop_item]"
>
\n
<dtml-in
prefix=
"loop"
expr=
"_.range(_.len(optimised_roles_and_users))"
>
\n
<dtml-in
prefix=
"role"
expr=
"optimised_roles_and_users[loop_item]"
>
\n
<dtml-call
expr=
"row_list.append([security_uid[loop_item], role_item
])"
>
\n
<dtml-call
expr=
"row_list.append([role_item[0], role_item[2]
])"
>
\n
</dtml-in>
\n
</dtml-if>
\n
</dtml-in>
\n
<dtml-if
expr=
"row_list"
>
\n
INSERT INTO\n
roles_and_users\n
roles_and_users
(uid, allowedRolesAndUsers)
\n
VALUES\n
<dtml-in
prefix=
"row"
expr=
"row_list"
>
\n
(
<dtml-sqlvar
expr=
"row_item[0]"
type=
"string"
>
,
<dtml-sqlvar
expr=
"row_item[1]"
type=
"string"
>
)\n
...
...
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_create_roles_and_users.xml
View file @
5272e987
...
...
@@ -6,6 +6,12 @@
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
_col
</string>
</key>
<value>
<tuple/>
</value>
</item>
<item>
<key>
<string>
allow_simple_one_argument_traversal
</string>
</key>
<value>
...
...
product/ERP5/bootstrap/erp5_mysql_innodb_catalog/CatalogMethodTemplateItem/portal_catalog/erp5_mysql_innodb/z_search_security.xml
View file @
5272e987
...
...
@@ -52,10 +52,10 @@
<key>
<string>
src
</string>
</key>
<value>
<string
encoding=
"cdata"
>
<![CDATA[
SELECT
\n
DISTINCT uid
\n
SELECT\n
DISTINCT uid\n
FROM \n
roles_and_users
\n
roles_and_users\n
WHERE \n
allowedRolesAndUsers \n
IN (<dtml-in security_roles_list>
<dtml-var
sequence-item
><dtml-if
sequence-end
><dtml-else>
,
</dtml-if></dtml-in>
)\n
...
...
product/ERP5/bootstrap/erp5_property_sheets/PropertySheetTemplateItem/portal_property_sheets/BusinessTemplate/template_catalog_security_uid_column_property.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"Standard Property"
module=
"erp5.portal_type"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
_local_properties
</string>
</key>
<value>
<tuple>
<dictionary>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
mode
</string>
</value>
</item>
<item>
<key>
<string>
type
</string>
</key>
<value>
<string>
string
</string>
</value>
</item>
</dictionary>
</tuple>
</value>
</item>
<item>
<key>
<string>
categories
</string>
</key>
<value>
<tuple>
<string>
elementary_type/lines
</string>
</tuple>
</value>
</item>
<item>
<key>
<string>
description
</string>
</key>
<value>
<none/>
</value>
</item>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
template_catalog_security_uid_column_property
</string>
</value>
</item>
<item>
<key>
<string>
mode
</string>
</key>
<value>
<string>
w
</string>
</value>
</item>
<item>
<key>
<string>
portal_type
</string>
</key>
<value>
<string>
Standard Property
</string>
</value>
</item>
<item>
<key>
<string>
property_default
</string>
</key>
<value>
<string>
python: ()
</string>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
product/ERP5/bootstrap/erp5_property_sheets/PropertySheetTemplateItem/portal_property_sheets/RoleInformation/local_role_group_category.xml
0 → 100644
View file @
5272e987
<?xml version="1.0"?>
<ZopeData>
<record
id=
"1"
aka=
"AAAAAAAAAAE="
>
<pickle>
<global
name=
"Category Property"
module=
"erp5.portal_type"
/>
</pickle>
<pickle>
<dictionary>
<item>
<key>
<string>
id
</string>
</key>
<value>
<string>
local_role_group_category
</string>
</value>
</item>
<item>
<key>
<string>
portal_type
</string>
</key>
<value>
<string>
Category Property
</string>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
product/ERP5/tests/testBusinessTemplate.py
View file @
5272e987
...
...
@@ -6597,6 +6597,90 @@ class TestBusinessTemplate(BusinessTemplateMixin):
new_bt5_obj
.
build
()
template_tool
.
export
(
new_bt5_obj
)
def
test_local_roles_group_id
(
self
):
"""Tests that roles definition defining local roles group ids are properly
exported and installed.
"""
# change security uid columns
sql_catalog
=
self
.
portal
.
portal_catalog
.
getSQLCatalog
()
saved_sql_catalog_security_uid_columns
=
\
sql_catalog
.
sql_catalog_security_uid_columns
sql_catalog
.
sql_catalog_security_uid_columns
=
(
' | security_uid'
,
'Alternate | alternate_security_uid'
,
)
# add category
self
.
portal
.
portal_categories
.
local_role_group
.
newContent
(
portal_type
=
'Category'
,
reference
=
'Alternate'
,
id
=
'Alternate'
)
types_tool
=
self
.
portal
.
portal_types
object_type
=
types_tool
.
newContent
(
'Geek Object'
,
'Base Type'
,
type_class
=
'Person'
)
types_tool
.
newContent
(
'Geek Module'
,
'Base Type'
,
type_class
=
'Folder'
,
type_filter_content_type
=
1
,
type_allowed_content_type_list
=
(
'Geek Object'
,),
)
self
.
portal
.
newContent
(
portal_type
=
'Geek Module'
,
id
=
'geek_module'
)
new_object
=
self
.
portal
.
geek_module
.
newContent
(
portal_type
=
'Geek Object'
,
id
=
'1'
)
# simulate role assignment
new_object
.
__ac_local_roles__
=
dict
(
group
=
[
'Assignee'
])
initial___ac_local_roles_group_id_dict__
=
dict
(
Alternate
=
set
([(
'group'
,
'Assignee'
)]))
new_object
.
__ac_local_roles_group_id_dict__
=
initial___ac_local_roles_group_id_dict__
self
.
tic
()
object_type
.
newContent
(
portal_type
=
'Role Information'
,
local_role_group_value
=
self
.
portal
.
portal_categories
.
local_role_group
.
Alternate
.
getRelativeUrl
(),
role_name_list
=
(
'Assignee'
,
))
bt
=
self
.
portal
.
portal_templates
.
newContent
(
portal_type
=
'Business Template'
,
title
=
self
.
id
(),
template_local_roles_list
=
(
'geek_module/1'
,),
template_path_list
=
(
'geek_module/1'
,),
template_portal_type_role_list
=
(
'Geek Object'
,),)
self
.
tic
()
bt
.
build
()
self
.
tic
()
export_dir
=
tempfile
.
mkdtemp
()
try
:
bt
.
export
(
path
=
export_dir
,
local
=
True
)
self
.
tic
()
new_bt
=
self
.
portal
.
portal_templates
.
download
(
url
=
'file://%s'
%
export_dir
)
finally
:
shutil
.
rmtree
(
export_dir
)
# uninstall role information and paths
object_type
.
manage_delObjects
([
x
.
id
for
x
in
object_type
.
getRoleInformationList
()])
self
.
portal
.
geek_module
.
manage_delObjects
([
'1'
])
self
.
tic
()
new_bt
.
install
()
try
:
role
,
=
object_type
.
getRoleInformationList
()
self
.
assertEquals
(
self
.
portal
.
portal_categories
.
local_role_group
.
Alternate
,
role
.
getLocalRoleGroupValue
())
path
=
self
.
portal
.
geek_module
[
'1'
]
self
.
assertEquals
([(
'group'
,
[
'Assignee'
],)],
[
item
for
item
in
path
.
__ac_local_roles__
.
items
()
if
item
[
1
]
!=
[
'Owner'
]])
self
.
assertEquals
(
initial___ac_local_roles_group_id_dict__
,
path
.
__ac_local_roles_group_id_dict__
)
finally
:
# restore state
sql_catalog
.
sql_catalog_security_uid_columns
=
\
saved_sql_catalog_security_uid_columns
types_tool
.
manage_delObjects
([
'Geek Object'
,
'Geek Module'
])
self
.
portal
.
manage_delObjects
([
'geek_module'
])
self
.
tic
()
def
test_BusinessTemplateWithTest
(
self
):
sequence_list
=
SequenceList
()
sequence_string
=
'
\
...
...
product/ERP5Catalog/CatalogTool.py
View file @
5272e987
This diff is collapsed.
Click to expand it.
product/ERP5Catalog/tests/testERP5CatalogSecurityUidOptimization.py
0 → 100644
View file @
5272e987
# -*- coding: utf-8 -*-
##############################################################################
#
# Copyright (c) 2005 Nexedi SARL and Contributors. All Rights Reserved.
# Ivan Tyagov <ivan@nexedi.com>
#
# WARNING: This program as such is intended to be used by professional
# programmers who take the whole responsability of assessing all potential
# consequences resulting from its eventual inadequacies and bugs
# End users who are looking for a ready-to-use solution with commercial
# garantees and support are strongly adviced to contract a Free Software
# Service Company
#
# This program is Free Software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#
##############################################################################
import
unittest
from
Testing
import
ZopeTestCase
from
Products.ERP5Type.tests.ERP5TypeTestCase
import
ERP5TypeTestCase
from
Products.ERP5Type.tests.backportUnittest
import
expectedFailure
from
AccessControl.SecurityManagement
import
newSecurityManager
class
TestERP5CatalogSecurityUidOptimization
(
ERP5TypeTestCase
):
"""
TestERP5CatalogSecurityUidOptimization tests security_uid optmization.
It is in a different test than TestERP5Catalog as it requires erp5_security_uid_innodb_catalog
bt5 to be installed in advance.
XXX: Inherit from TestERP5Catalog so we test default and security_uid optmization with same tests.
"""
business_template_list
=
[
'erp5_security_uid_innodb_catalog'
,
'erp5_full_text_myisam_catalog'
,
'erp5_base'
]
def
getBusinessTemplateList
(
self
):
return
self
.
business_template_list
def
afterSetUp
(
self
):
self
.
login
()
portal
=
self
.
getPortal
()
def
test_local_roles_group_id_on_role_information
(
self
):
"""Test usage of local_roles_group_id when searching catalog.
"""
sql_connection
=
self
.
getSQLConnection
()
sql_catalog
=
self
.
portal
.
portal_catalog
.
getSQLCatalog
()
# Add a catalog table (uid, alternate_security_uid)
sql_connection
.
manage_test
(
"""DROP TABLE IF EXISTS alternate_roles_and_users"""
)
sql_connection
.
manage_test
(
"""
CREATE TABLE alternate_roles_and_users (
`uid` BIGINT UNSIGNED NOT NULL,
`alternate_security_uid` INT UNSIGNED) """
)
# make it a search table
current_sql_search_tables
=
sql_catalog
.
sql_search_tables
sql_catalog
.
sql_search_tables
=
sql_catalog
.
sql_search_tables
+
[
'alternate_roles_and_users'
]
# Configure sql method to insert this table
sql_catalog
.
manage_addProduct
[
'ZSQLMethods'
].
manage_addZSQLMethod
(
id
=
'z_catalog_alternate_roles_and_users_list'
,
title
=
''
,
connection_id
=
'erp5_sql_connection'
,
arguments
=
"
\
n
"
.
join
([
'uid'
,
'alternate_security_uid'
]),
template
=
"""REPLACE INTO alternate_roles_and_users VALUES
<dtml-in prefix="loop" expr="_.range(_.len(uid))">
( <dtml-sqlvar expr="uid[loop_item]" type="int">,
<dtml-sqlvar expr="alternate_security_uid[loop_item]" type="int" optional>
)<dtml-unless sequence-end>,</dtml-unless>
</dtml-in>"""
)
current_sql_catalog_object_list
=
sql_catalog
.
sql_catalog_object_list
sql_catalog
.
sql_catalog_object_list
=
\
current_sql_catalog_object_list
+
\
(
'z_catalog_alternate_roles_and_users_list'
,)
# configure Alternate local roles group id to go in alternate_security_uid
current_sql_catalog_security_uid_columns
=
\
sql_catalog
.
sql_catalog_security_uid_columns
sql_catalog
.
sql_catalog_security_uid_columns
=
(
' | security_uid'
,
'Alternate | alternate_security_uid'
,
)
# add category
self
.
portal
.
portal_categories
.
local_role_group
.
newContent
(
portal_type
=
'Category'
,
reference
=
'Alternate'
,
id
=
'Alternate'
)
# configure security on person, each user will be able to see his own
# person thanks to an Auditor role on "Alternate" local roles group id.
self
.
portal
.
portal_types
.
Person
.
newContent
(
portal_type
=
'Role Information'
,
role_name
=
'Auditor'
,
role_base_category_script_id
=
'ERP5Type_getSecurityCategoryFromSelf'
,
role_base_category
=
'agent'
,
local_role_group_value
=
self
.
portal
.
portal_categories
.
local_role_group
.
Alternate
.
getRelativeUrl
())
self
.
portal
.
portal_caches
.
clearAllCache
()
self
.
tic
()
try
:
# create two persons and users
user1
=
self
.
portal
.
person_module
.
newContent
(
portal_type
=
'Person'
,
reference
=
'user1'
)
user1
.
newContent
(
portal_type
=
'Assignment'
).
open
()
user1
.
updateLocalRolesOnSecurityGroups
()
self
.
assertEquals
(
user1
.
__ac_local_roles__
.
get
(
'user1'
),
[
'Auditor'
])
user2
=
self
.
portal
.
person_module
.
newContent
(
portal_type
=
'Person'
,
reference
=
'user2'
)
user2
.
newContent
(
portal_type
=
'Assignment'
).
open
()
user2
.
updateLocalRolesOnSecurityGroups
()
self
.
assertEquals
(
user2
.
__ac_local_roles__
.
get
(
'user2'
),
[
'Auditor'
])
self
.
tic
()
# security_uid_dict in catalog contains entries for user1 and user2:
user1_alternate_security_uid
=
sql_catalog
.
security_uid_dict
[
(
'Alternate'
,
(
'user:user1'
,
'user:user1:Auditor'
))]
bob_alternate_security_uid
=
sql_catalog
.
security_uid_dict
[
(
'Alternate'
,
(
'user:user2'
,
'user:user2:Auditor'
))]
# those entries are in alternate security table
alternate_roles_and_users
=
sql_connection
.
manage_test
(
"SELECT * from alternate_roles_and_users"
).
dictionaries
()
self
.
assertTrue
(
dict
(
uid
=
user1
.
getUid
(),
alternate_security_uid
=
user1_alternate_security_uid
)
in
alternate_roles_and_users
)
self
.
assertTrue
(
dict
(
uid
=
user2
.
getUid
(),
alternate_security_uid
=
bob_alternate_security_uid
)
in
alternate_roles_and_users
)
# low level check of the security query of a logged in user
self
.
login
(
'user1'
)
security_query
=
self
.
portal
.
portal_catalog
.
getSecurityQuery
()
# This query is a complex query wrapping another complex query with a
# criterion on altenate_security_uid. This check is quite low level and
# is subject to change.
security_uid_query
=
security_query
.
query_list
[
0
]
alternate_security_query
,
=
[
q
for
q
in
security_query
.
query_list
[
0
].
query_list
if
q
.
kw
.
get
(
'alternate_security_uid'
)]
self
.
assertEquals
([
user1_alternate_security_uid
],
alternate_security_query
.
kw
[
'alternate_security_uid'
])
# high level check that that logged in user can see document
self
.
assertEquals
([
user1
],
[
o
.
getObject
()
for
o
in
self
.
portal
.
portal_catalog
(
portal_type
=
'Person'
)])
# also with local_roles= argument which is used in worklists
self
.
assertEquals
([
user1
],
[
o
.
getObject
()
for
o
in
self
.
portal
.
portal_catalog
(
portal_type
=
'Person'
,
local_roles
=
'Auditor'
)])
# searches still work for other users
self
.
login
(
'ERP5TypeTestCase'
)
self
.
assertSameSet
([
user1
,
user2
],
[
o
.
getObject
()
for
o
in
self
.
portal
.
portal_catalog
(
portal_type
=
'Person'
)])
finally
:
# restore catalog configuration
sql_catalog
.
sql_search_tables
=
current_sql_search_tables
sql_catalog
.
sql_catalog_object_list
=
current_sql_catalog_object_list
sql_catalog
.
sql_catalog_security_uid_columns
=
\
current_sql_catalog_security_uid_columns
self
.
portal
.
portal_types
.
Person
.
manage_delObjects
(
[
role
.
getId
()
for
role
in
self
.
portal
.
portal_types
.
Person
.
contentValues
(
portal_type
=
'Role Information'
)])
def
test_suite
():
suite
=
unittest
.
TestSuite
()
suite
.
addTest
(
unittest
.
makeSuite
(
TestERP5CatalogSecurityUidOptimization
))
return
suite
product/ERP5Security/tests/testERP5Security.py
View file @
5272e987
...
...
@@ -580,6 +580,29 @@ class TestLocalRoleManagement(ERP5TypeTestCase):
self
.
assertFalse
(
'Assignee'
in
user
.
getRolesInContext
(
obj
))
self
.
abort
()
def
testLocalRolesGroupId
(
self
):
"""Assigning a role with local roles group id.
"""
self
.
portal
.
portal_categories
.
local_role_group
.
newContent
(
portal_type
=
'Category'
,
reference
=
'Alternate'
,
id
=
'Alternate'
)
self
.
_getTypeInfo
().
newContent
(
portal_type
=
'Role Information'
,
role_name
=
'Assignor'
,
local_role_group_value
=
self
.
portal
.
portal_categories
.
local_role_group
.
Alternate
.
getRelativeUrl
(),
role_category
=
self
.
defined_category
)
self
.
loginAsUser
(
self
.
username
)
user
=
getSecurityManager
().
getUser
()
obj
=
self
.
_makeOne
()
self
.
assertEqual
([
'Assignor'
],
obj
.
__ac_local_roles__
.
get
(
'F1_G1_S1'
))
self
.
assertTrue
(
'Assignor'
in
user
.
getRolesInContext
(
obj
))
self
.
assertEqual
(
set
([(
'F1_G1_S1'
,
'Assignor'
)]),
obj
.
__ac_local_roles_group_id_dict__
.
get
(
'Alternate'
))
self
.
abort
()
def
testDynamicLocalRole
(
self
):
"""Test simple case of setting a dynamic role.
The site category is not defined explictly the role, and will have the
...
...
product/ERP5Type/Core/RoleInformation.py
View file @
5272e987
...
...
@@ -183,5 +183,4 @@ class RoleInformation(XMLObject):
return
group_id_role_dict
InitializeClass
(
RoleInformation
)
product/ERP5Type/ERP5Type.py
View file @
5272e987
...
...
@@ -89,7 +89,25 @@ class LocalRoleAssignorMixIn(object):
else
:
user_name
=
getSecurityManager
().
getUser
().
getId
()
group_id_role_dict
=
self
.
getLocalRolesFor
(
ob
,
user_name
)
group_id_role_dict
=
{}
local_roles_group_id_group_id
=
{}
# Merge results from applicable roles
for
role_generator
in
self
.
getFilteredRoleListFor
(
ob
):
local_roles_group_id
=
''
if
getattr
(
role_generator
,
'getLocalRoleGroupValue'
,
None
)
is
not
None
:
# only some role generators like 'Role Information' support it
local_role_group
=
role_generator
.
getLocalRoleGroupValue
()
if
local_role_group
is
not
None
:
# role definitions use category to classify different types of local roles
# so use their categories' reference
local_roles_group_id
=
local_role_group
.
getReference
()
or
local_role_group
.
getId
()
for
group_id
,
role_list
\
in
role_generator
.
getLocalRolesFor
(
ob
,
user_name
).
iteritems
():
group_id_role_dict
.
setdefault
(
group_id
,
set
()).
update
(
role_list
)
if
local_roles_group_id
:
for
role
in
role_list
:
# Feed local_roles_group_id_group_id with local roles assigned to a group
local_roles_group_id_group_id
.
setdefault
(
local_roles_group_id
,
set
()).
update
(((
group_id
,
role
),))
## Update role assignments to groups
# Save the owner
...
...
@@ -101,24 +119,17 @@ class LocalRoleAssignorMixIn(object):
for
group
,
role_list
in
group_id_role_dict
.
iteritems
():
if
role_list
:
ac_local_roles
[
group
]
=
list
(
role_list
)
if
local_roles_group_id_group_id
:
ob
.
__ac_local_roles_group_id_dict__
=
local_roles_group_id_group_id
elif
getattr
(
aq_base
(
ob
),
'__ac_local_roles_group_id_dict__'
,
None
)
is
not
None
:
delattr
(
ob
,
'__ac_local_roles_group_id_dict__'
)
## Make sure that the object is reindexed
if
reindex
:
ob
.
reindexObjectSecurity
()
security
.
declarePrivate
(
"getLocalRolesFor"
)
def
getLocalRolesFor
(
self
,
ob
,
user_name
=
None
):
"""Compute the security that should be applied on an object
Returned value is a dict: {groud_id: role_name_set, ...}
"""
group_id_role_dict
=
{}
# Merge results from applicable roles
for
role
in
self
.
getFilteredRoleListFor
(
ob
):
for
group_id
,
role_list
\
in
role
.
getLocalRolesFor
(
ob
,
user_name
).
iteritems
():
group_id_role_dict
.
setdefault
(
group_id
,
set
()).
update
(
role_list
)
return
group_id_role_dict
security
.
declarePrivate
(
'getFilteredRoleListFor'
)
def
getFilteredRoleListFor
(
self
,
ob
=
None
):
"""Return all role generators applicable to the object."""
...
...
product/ERP5Type/interfaces/role_provider.py
View file @
5272e987
...
...
@@ -39,7 +39,7 @@ class ILocalRoleGenerator(Interface):
Returned value is a dict: {groud_id: role_name_set, ...}
"""
class
ILocalRoleAssignor
(
I
LocalRoleGenerator
):
class
ILocalRoleAssignor
(
I
nterface
):
"""
"""
def
updateLocalRolesOnDocument
(
ob
,
user_name
=
None
,
reindex
=
True
):
...
...
product/ERP5Type/patches/WorkflowTool.py
View file @
5272e987
...
...
@@ -36,6 +36,7 @@ from Persistence import Persistent
from
Products.ERP5Type.Globals
import
PersistentMapping
from
itertools
import
izip
from
MySQLdb
import
ProgrammingError
,
OperationalError
from
DateTime
import
DateTime
def
DCWorkflowDefinition_notifyWorkflowMethod
(
self
,
ob
,
transition_list
,
args
=
None
,
kw
=
None
):
'''
...
...
@@ -89,7 +90,6 @@ DCWorkflowDefinition.notifySuccess = DCWorkflowDefinition_notifySuccess
WORKLIST_METADATA_KEY
=
'metadata'
SECURITY_PARAMETER_ID
=
'local_roles'
SECURITY_COLUMN_ID
=
'security_uid'
COUNT_COLUMN_TITLE
=
'count'
class
ExclusionList
(
list
):
...
...
@@ -145,7 +145,7 @@ def updateWorklistSetDict(worklist_set_dict, workflow_worklist_key, valid_criter
[
workflow_worklist_key
]
=
valid_criterion_dict
def
groupWorklistListByCondition
(
worklist_dict
,
sql_catalog
,
getSecurityUid
Lis
tAndRoleColumnDict
=
None
):
getSecurityUid
Dic
tAndRoleColumnDict
=
None
):
"""
Get a list of dict of WorklistVariableMatchDict grouped by compatible
conditions.
...
...
@@ -185,7 +185,7 @@ def groupWorklistListByCondition(worklist_dict, sql_catalog,
for
workflow_id
,
worklist
in
worklist_dict
.
iteritems
():
for
worklist_id
,
worklist_match_dict
in
worklist
.
iteritems
():
workflow_worklist_key
=
'/'
.
join
((
workflow_id
,
worklist_id
))
if
getSecurityUid
Lis
tAndRoleColumnDict
is
None
:
if
getSecurityUid
Dic
tAndRoleColumnDict
is
None
:
valid_criterion_dict
,
metadata
=
getValidCriterionDict
(
worklist_match_dict
=
worklist_match_dict
,
sql_catalog
=
sql_catalog
,
...
...
@@ -201,15 +201,18 @@ def groupWorklistListByCondition(worklist_dict, sql_catalog,
security_kw
=
{}
if
len
(
security_parameter
):
security_kw
[
SECURITY_PARAMETER_ID
]
=
security_parameter
uid_
lis
t
,
role_column_dict
,
local_role_column_dict
=
\
getSecurityUid
Lis
tAndRoleColumnDict
(
**
security_kw
)
uid_
dic
t
,
role_column_dict
,
local_role_column_dict
=
\
getSecurityUid
Dic
tAndRoleColumnDict
(
**
security_kw
)
for
key
,
value
in
local_role_column_dict
.
items
():
worklist_match_dict
[
key
]
=
[
value
]
if
len
(
uid_list
):
uid_list
.
sort
()
role_column_dict
[
SECURITY_COLUMN_ID
]
=
uid_list
catalog_security_uid_groups_columns_dict
=
\
sql_catalog
.
getSQLCatalogSecurityUidGroupsColumnsDict
()
for
local_roles_group_id
,
uid_list
in
uid_dict
.
iteritems
():
role_column_dict
[
catalog_security_uid_groups_columns_dict
[
local_roles_group_id
]]
=
uid_list
# Make sure every item is a list - or a tuple
for
security_column_id
in
role_column_dict
.
iterkeys
():
value
=
role_column_dict
[
security_column_id
]
...
...
@@ -271,6 +274,8 @@ def generateNestedQuery(priority_list, criterion_dict,
**
{
my_criterion_id
:
criterion_value
})
if
isinstance
(
criterion_value
,
ExclusionTuple
):
query
=
NegatedQuery
(
query
)
query
=
ComplexQuery
(
operator
=
'OR'
,
*
(
query
,
Query
(
**
{
my_criterion_id
:
None
})))
append
(
ComplexQuery
(
query
,
subcriterion_query
,
operator
=
'AND'
))
else
:
possible_value_list
=
tuple
()
...
...
@@ -296,6 +301,8 @@ def generateNestedQuery(priority_list, criterion_dict,
if
len
(
impossible_value_list
):
query
=
Query
(
operator
=
'IN'
,
**
{
my_criterion_id
:
impossible_value_list
})
query
=
NegatedQuery
(
query
)
query
=
ComplexQuery
(
operator
=
'OR'
,
*
(
query
,
Query
(
**
{
my_criterion_id
:
None
})))
value_query_list
.
append
(
query
)
append
(
ComplexQuery
(
operator
=
'AND'
,
*
value_query_list
))
if
len
(
query_list
):
...
...
@@ -334,6 +341,17 @@ def getWorklistListQuery(grouped_worklist_dict):
assert
COUNT_COLUMN_TITLE
not
in
total_criterion_id_dict
return
(
total_criterion_id_list
,
query
)
# XXX: see ZMySQLDA/db.py:DB.defs
# This dict is used to tell which cast to apply to worklist parameters to get
# values comparable with SQL result content.
_sql_cast_dict
=
{
'i'
:
long
,
'l'
:
long
,
'n'
:
float
,
'd'
:
DateTime
,
}
_sql_cast_fallback
=
str
def
sumCatalogResultByWorklist
(
grouped_worklist_dict
,
catalog_result
):
"""
Return a dict regrouping each worklist's result, extracting it from
...
...
@@ -354,8 +372,8 @@ def sumCatalogResultByWorklist(grouped_worklist_dict, catalog_result):
if
len
(
catalog_result
)
>
0
:
# Transtype all worklist definitions where needed
criterion_id_list
=
[]
class_dict
=
dict
(((
name
,
value
.
__class__
)
for
name
,
value
in
\
izip
(
catalog_result
.
names
(),
catalog_result
[
0
]
)))
class_dict
=
dict
(((
name
,
_sql_cast_dict
.
get
(
x
[
'type'
],
_sql_cast_fallback
))
for
name
,
x
in
catalog_result
.
data_dictionary
().
iteritems
(
)))
for
criterion_dict
in
grouped_worklist_dict
.
itervalues
():
for
criterion_id
,
criterion_value_list
in
criterion_dict
.
iteritems
():
if
type
(
criterion_value_list
)
is
not
ExclusionList
:
...
...
@@ -462,8 +480,8 @@ def WorkflowTool_listActions(self, info=None, object=None, src__=False):
else
:
search_result
=
portal_catalog
.
unrestrictedSearchResults
select_expression_prefix
=
'count(*) as %s'
%
(
COUNT_COLUMN_TITLE
,
)
getSecurityUid
Lis
tAndRoleColumnDict
=
\
portal_catalog
.
getSecurityUid
Lis
tAndRoleColumnDict
getSecurityUid
Dic
tAndRoleColumnDict
=
\
portal_catalog
.
getSecurityUid
Dic
tAndRoleColumnDict
security_query_cache_dict
=
{}
def
_getWorklistActionList
():
worklist_result_dict
=
{}
...
...
@@ -474,8 +492,8 @@ def WorkflowTool_listActions(self, info=None, object=None, src__=False):
groupWorklistListByCondition
(
worklist_dict
=
worklist_dict
,
sql_catalog
=
sql_catalog
,
getSecurityUid
Lis
tAndRoleColumnDict
=
\
getSecurityUid
Lis
tAndRoleColumnDict
)
getSecurityUid
Dic
tAndRoleColumnDict
=
\
getSecurityUid
Dic
tAndRoleColumnDict
)
if
src__
:
action_list
=
[]
for
grouped_worklist_dict
in
worklist_list_grouped_by_condition
:
...
...
@@ -587,7 +605,8 @@ def WorkflowTool_refreshWorklistCache(self):
sql_catalog
=
portal_catalog
.
getSQLCatalog
()
table_column_id_set
=
ImmutableSet
(
[
COUNT_COLUMN_TITLE
]
+
self
.
Base_getWorklistTableColumnIDList
())
security_column_id_list
=
[
'security_uid'
]
+
\
security_column_id_list
=
list
(
sql_catalog
.
getSQLCatalogSecurityUidGroupsColumnsDict
().
values
())
+
\
[
x
[
1
]
for
x
in
sql_catalog
.
getSQLCatalogRoleKeysList
()]
+
\
[
x
[
1
]
for
x
in
sql_catalog
.
getSQLCatalogLocalRoleKeysList
()]
(
worklist_list_grouped_by_condition
,
worklist_metadata
)
=
\
...
...
product/ZSQLCatalog/SQLCatalog.py
View file @
5272e987
...
...
@@ -524,6 +524,14 @@ class Catalog(Folder,
'a monovalued local role'
,
'type'
:
'lines'
,
'mode'
:
'w'
},
{
'id'
:
'sql_catalog_security_uid_columns'
,
'title'
:
'Security Uid Columns'
,
'description'
:
'A list of mappings "local_roles_group_id | security_uid_column"'
' local_roles_group_id will be the name of a local roles'
' group, and security_uid_column is the corresponding'
' column in catalog table'
,
'type'
:
'lines'
,
'mode'
:
'w'
},
{
'id'
:
'sql_catalog_table_vote_scripts'
,
'title'
:
'Table vote scripts'
,
'description'
:
'Scripts helping column mapping resolution'
,
...
...
@@ -575,6 +583,7 @@ class Catalog(Folder,
sql_catalog_scriptable_keys
=
()
sql_catalog_role_keys
=
()
sql_catalog_local_role_keys
=
()
sql_catalog_security_uid_columns
=
(
' | security_uid'
,)
sql_catalog_table_vote_scripts
=
()
sql_catalog_raise_error_on_uid_check
=
True
...
...
@@ -626,6 +635,18 @@ class Catalog(Folder,
role_key_dict
[
role
.
strip
()]
=
column
.
strip
()
return
role_key_dict
.
items
()
def
getSQLCatalogSecurityUidGroupsColumnsDict
(
self
):
"""
Return a mapping of local_roles_group_id name to the name of the column
storing corresponding security_uid.
The default mappiny is {'': 'security_uid'}
"""
local_roles_group_id_dict
=
{}
for
local_roles_group_id_key
in
self
.
sql_catalog_security_uid_columns
:
local_roles_group_id
,
column
=
local_roles_group_id_key
.
split
(
'|'
)
local_roles_group_id_dict
[
local_roles_group_id
.
strip
()]
=
column
.
strip
()
return
local_roles_group_id_dict
def
getSQLCatalogLocalRoleKeysList
(
self
):
"""
Return the list of local role keys.
...
...
@@ -765,38 +786,41 @@ class Catalog(Folder,
self
.
subject_set_uid_dict
=
OIBTree
()
self
.
subject_set_uid_index
=
None
security
.
declarePrivate
(
'getSecurityUid'
)
def
getSecurityUid
(
self
,
wrapped_object
):
security
.
declarePrivate
(
'getSecurityUid
Dict
'
)
def
getSecurityUid
Dict
(
self
,
wrapped_object
):
"""
Cache a uid for each security permission
Return a tuple with a security uid (string) and a new tuple content the
roles and users if not exist already.
With the roles of object, search the security_uid associate in the
catalog_innodb:
- if the security not exist a security uid is generated with id_tool
or security_uid_index property and
return the new security_uid and the tuple contains the new roles
to add the roles in roles_and_user table of the database.
- if the security exist the security uid is returned and the second
element is None for not recreate the security in roles_and_user
table of the database.
We try to create a unique security (to reduce number of lines)
and to assign security only to root document
returns a tuple with a dict of security uid by local group id, and a tuple
containing optimised_roles_and_users that might have been created.
"""
# Get security information
allowed_roles_and_users
=
tuple
(
wrapped_object
.
allowedRolesAndUsers
())
# Make sure no duplicates
if
getattr
(
aq_base
(
self
),
'security_uid_dict'
,
None
)
is
None
:
self
.
_clearSecurityCache
()
elif
self
.
security_uid_dict
.
has_key
(
allowed_roles_and_users
):
return
(
self
.
security_uid_dict
[
allowed_roles_and_users
],
None
)
id_tool
=
getattr
(
self
.
getPortalObject
(),
'portal_ids'
,
None
)
optimised_roles_and_users
=
[]
local_roles_group_id_to_security_uid_mapping
=
dict
()
# Get security information
for
local_roles_group_id
,
allowed_roles_and_users
in
\
wrapped_object
.
getLocalRolesGroupIdDict
().
iteritems
():
allowed_roles_and_users
=
tuple
(
sorted
(
allowed_roles_and_users
))
key
=
(
local_roles_group_id
,
allowed_roles_and_users
)
if
self
.
security_uid_dict
.
has_key
(
key
):
local_roles_group_id_to_security_uid_mapping
[
local_roles_group_id
]
\
=
self
.
security_uid_dict
[
key
]
elif
self
.
security_uid_dict
.
has_key
(
allowed_roles_and_users
)
\
and
not
local_roles_group_id
:
# This key is present in security_uid_dict without
# local_roles_group_id, it has been inserted before
# local_roles_group_id were introduced.
local_roles_group_id_to_security_uid_mapping
[
local_roles_group_id
]
=
\
self
.
security_uid_dict
[
allowed_roles_and_users
]
else
:
# If the id_tool is there, it is better to use it, it allows
# to create many new security uids by the same time
# because with this tool we are sure that we will have 2 different
# uids if two instances are doing this code in the same time
id_tool
=
getattr
(
self
.
getPortalObject
(),
'portal_ids'
,
None
)
if
id_tool
is
not
None
:
default
=
1
# We must keep compatibility with existing sites
...
...
@@ -818,8 +842,17 @@ class Catalog(Folder,
previous_security_uid
=
previous_security_uid
()
security_uid
=
previous_security_uid
+
1
self
.
security_uid_index
=
security_uid
self
.
security_uid_dict
[
allowed_roles_and_users
]
=
security_uid
return
(
security_uid
,
allowed_roles_and_users
)
self
.
security_uid_dict
[
key
]
=
security_uid
local_roles_group_id_to_security_uid_mapping
[
local_roles_group_id
]
\
=
security_uid
# If some optimised_roles_and_users are returned by this method it
# means that new entries will have to be added to roles_and_users table.
for
user
in
allowed_roles_and_users
:
optimised_roles_and_users
.
append
((
security_uid
,
local_roles_group_id
,
user
))
return
(
local_roles_group_id_to_security_uid_mapping
,
optimised_roles_and_users
)
def
getRoleAndSecurityUidList
(
self
):
"""
...
...
@@ -828,7 +861,8 @@ class Catalog(Folder,
"""
result
=
[]
extend
=
result
.
extend
for
role_list
,
security_uid
in
getattr
(
aq_base
(
self
),
'security_uid_dict'
,
{}).
iteritems
():
for
role_list
,
security_uid
in
getattr
(
aq_base
(
self
),
'security_uid_dict'
,
{}).
iteritems
():
extend
([(
role
,
security_uid
)
for
role
in
role_list
])
return
result
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment