From 1ba14958545b4beb1f8403c9c1b3d4a03298bdc4 Mon Sep 17 00:00:00 2001
From: uhensler <urs.hensler@frentix.com>
Date: Wed, 14 Nov 2018 15:44:24 +0100
Subject: [PATCH] OO-3304: A quality manager is only allowed to edit the data
 collections and generators of his organisations

---
 .../quality/QualitySecurityCallback.java      | 112 -------
 .../analysis/ui/AnalysisController.java       |   6 +-
 .../analysis/ui/AnalysisListController.java   |   6 +-
 .../ui/AnalysisSegmentsController.java        |   6 +-
 .../generator/QualityGeneratorProvider.java   |   4 +-
 .../generator/QualityGeneratorService.java    |   4 +-
 .../manager/QualityGeneratorServiceImpl.java  |   4 +-
 .../provider/course/CourseProvider.java       |   4 +-
 .../CourseLecturesFollowUpProvider.java       |   4 +-
 .../CourseLecturesProvider.java               |   4 +-
 .../CurriculumElementProvider.java            |   4 +-
 .../provider/fallback/FallbackProvider.java   |   4 +-
 .../CurriculumElementWhiteListController.java |   5 -
 .../ui/GeneratorConfigController.java         |  17 +-
 .../generator/ui/GeneratorController.java     |  41 +--
 .../generator/ui/GeneratorEditController.java |  19 +-
 .../generator/ui/GeneratorListController.java |  16 +-
 .../ui/GeneratorWhiteListController.java      |   2 +-
 .../RepositoryEntryWhiteListController.java   |   6 -
 ...DataCollectionConfigurationController.java |  15 +-
 .../quality/ui/DataCollectionController.java  |  49 +--
 .../quality/ui/DataCollectionDataModel.java   |   6 +-
 .../ui/DataCollectionListController.java      |   9 +-
 .../DataCollectionReportAccessController.java |  18 +-
 .../ui/ExecutorParticipationDataModel.java    |   6 +-
 .../ExecutorParticipationsListController.java |   6 +-
 .../ui/GeneratorReportAccessController.java   |  22 +-
 .../ui/ParticipationListController.java       |  20 +-
 .../quality/ui/QualityHomeController.java     |   6 +-
 .../quality/ui/QualityMainController.java     |   6 +-
 .../ui/QualitySecurityCallbackImpl.java       | 303 ------------------
 .../quality/ui/RemindersController.java       |  15 +-
 ...ataCollectionReadOnlySecurityCallback.java | 102 ++++++
 .../DataCollectionSecurityCallback.java       |  60 ++++
 .../DataCollectionStatusSecurityCallback.java | 129 ++++++++
 .../GeneratorReadOnlySecurityCallback.java    |  65 ++++
 .../security/GeneratorSecurityCallback.java}  |  23 +-
 .../GeneratorStatusSecurityCallback.java      |  71 ++++
 .../ui/security/MainSecurityCallback.java     |  58 ++++
 .../ui/security/MainSecurityCallbackImpl.java | 132 ++++++++
 .../QualitySecurityCallbackFactory.java       |  77 +++++
 41 files changed, 875 insertions(+), 591 deletions(-)
 delete mode 100644 src/main/java/org/olat/modules/quality/QualitySecurityCallback.java
 delete mode 100644 src/main/java/org/olat/modules/quality/ui/QualitySecurityCallbackImpl.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/DataCollectionReadOnlySecurityCallback.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/DataCollectionSecurityCallback.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/DataCollectionStatusSecurityCallback.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/GeneratorReadOnlySecurityCallback.java
 rename src/main/java/org/olat/modules/quality/{generator/ui/GeneratorChangedController.java => ui/security/GeneratorSecurityCallback.java} (65%)
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/GeneratorStatusSecurityCallback.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallback.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallbackImpl.java
 create mode 100644 src/main/java/org/olat/modules/quality/ui/security/QualitySecurityCallbackFactory.java

diff --git a/src/main/java/org/olat/modules/quality/QualitySecurityCallback.java b/src/main/java/org/olat/modules/quality/QualitySecurityCallback.java
deleted file mode 100644
index e21bc415599..00000000000
--- a/src/main/java/org/olat/modules/quality/QualitySecurityCallback.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/**
- * <a href="http://www.openolat.org">
- * OpenOLAT - Online Learning and Training</a><br>
- * <p>
- * Licensed under the Apache License, Version 2.0 (the "License"); <br>
- * you may not use this file except in compliance with the License.<br>
- * You may obtain a copy of the License at the
- * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
- * <p>
- * Unless required by applicable law or agreed to in writing,<br>
- * software distributed under the License is distributed on an "AS IS" BASIS, <br>
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
- * See the License for the specific language governing permissions and <br>
- * limitations under the License.
- * <p>
- * Initial code contributed and copyrighted by<br>
- * frentix GmbH, http://www.frentix.com
- * <p>
- */
-package org.olat.modules.quality;
-
-import org.olat.basesecurity.OrganisationRoles;
-import org.olat.modules.quality.analysis.AnalysisPresentation;
-import org.olat.modules.quality.generator.QualityGenerator;
-
-/**
- * 
- * Initial date: 08.06.2018<br>
- * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
- *
- */
-public interface QualitySecurityCallback {
-
-	public boolean canCreateSuggestion();
-
-	public boolean canViewDataCollections();
-	
-	public OrganisationRoles[] getViewDataCollectionRoles();
-	
-	public boolean canCreateDataCollections();
-	
-	public boolean canEditDataCollections();
-	
-	public boolean canViewDataCollectionConfigurations();
-	
-	public boolean canUpdateBaseConfiguration(QualityDataCollectionLight dataCollection);
-	
-	public boolean canSetPreparation(QualityDataCollectionLight dataCollection);
-	
-	public boolean canSetReady(QualityDataCollectionLight dataCollection);
-	
-	public boolean canSetRunning(QualityDataCollectionLight dataCollection);
-	
-	public boolean canSetFinished(QualityDataCollectionLight dataCollection);
-	
-	public boolean canDeleteDataCollections();
-	
-	public boolean canDeleteDataCollection(QualityDataCollectionLight dataCollection);
-	
-	public boolean canAddParticipants(QualityDataCollectionLight dataCollection);
-	
-	public boolean canRevomeParticipation(QualityDataCollectionLight dataCollection);
-
-	public boolean canEditReminders();
-
-	public boolean canEditReminder(QualityDataCollectionLight dataCollection, QualityReminder reminder);
-	
-	public boolean canEditReportAccessOnline(QualityDataCollection dataCollection);
-	
-	public boolean canEditReportAccessEmail(QualityDataCollection dataCollection);
-
-	public boolean canEditReportAccessMembers(QualityDataCollection dataCollection);
-
-	public boolean canViewReports();
-
-	public boolean canViewReport(QualityDataCollectionLight dataCollection);
-
-	public boolean canExecute(QualityExecutorParticipation participation);
-
-	public boolean canViewGenerators();
-	
-	public boolean canCreateGenerators();
-
-	public boolean canEditGenerators();
-
-	public boolean canEditGenerator(QualityGenerator generator);
-
-	public boolean canEditGeneratorForm(QualityGenerator generator, Long numOfDataCollections);
-	
-	public boolean canEditReportAccessOnline(QualityGenerator generator);
-	
-	public boolean canEditReportAccessEmail(QualityGenerator generator);
-
-	public boolean canEditReportAccessMembers(QualityGenerator generator);
-
-	public boolean canActivateGenerators();
-
-	public boolean canDeleteGenerators();
-
-	public boolean canDeleteGenerator(long numberDataCollections);
-
-	public boolean canViewAnalysis();
-	
-	public OrganisationRoles[] getViewAnalysisRoles();
-	
-	public OrganisationRoles[] getViewPresentationRoles();
-	
-	public boolean canEditPresentations();
-
-	public boolean canDeletePresentation(AnalysisPresentation presentation);
-
-}
diff --git a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisController.java b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisController.java
index abf16d73ec3..be02408fbdf 100644
--- a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisController.java
+++ b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisController.java
@@ -37,7 +37,6 @@ import org.olat.modules.forms.EvaluationFormManager;
 import org.olat.modules.forms.model.xml.Form;
 import org.olat.modules.forms.ui.ReportSegment;
 import org.olat.modules.forms.ui.ReportSegmentEvent;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.analysis.AnalysisPresentation;
 import org.olat.modules.quality.analysis.AnalysisSearchParameter;
 import org.olat.modules.quality.analysis.AnalysisSegment;
@@ -45,6 +44,7 @@ import org.olat.modules.quality.analysis.AvailableAttributes;
 import org.olat.modules.quality.analysis.MultiGroupBy;
 import org.olat.modules.quality.analysis.QualityAnalysisService;
 import org.olat.modules.quality.analysis.ui.PresentationEvent.Action;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -66,7 +66,7 @@ public class AnalysisController extends BasicController implements TooledControl
 	private CloseableModalController cmc;
 	private PresentationController presentationCtrl;
 	private PresentationDeleteConfirmationController presentationDeleteCtrl;
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	private final TooledStackedPanel stackPanel;
 	
 	private final Form form;
@@ -79,7 +79,7 @@ public class AnalysisController extends BasicController implements TooledControl
 	@Autowired
 	private EvaluationFormManager evaluationFormManager;
 
-	protected AnalysisController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
+	protected AnalysisController(UserRequest ureq, WindowControl wControl, MainSecurityCallback secCallback,
 			TooledStackedPanel stackPanel, AnalysisPresentation presentation) {
 		super(ureq, wControl);
 		this.secCallback = secCallback;
diff --git a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisListController.java b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisListController.java
index 709e2e71ec6..fd8c39670cb 100644
--- a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisListController.java
+++ b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisListController.java
@@ -53,12 +53,12 @@ import org.olat.core.id.Organisation;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
 import org.olat.core.util.resource.OresHelper;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.analysis.AnalysisPresentation;
 import org.olat.modules.quality.analysis.EvaluationFormView;
 import org.olat.modules.quality.analysis.EvaluationFormViewSearchParams;
 import org.olat.modules.quality.analysis.QualityAnalysisService;
 import org.olat.modules.quality.analysis.ui.AnalysisDataModel.AnalysisCols;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -76,7 +76,7 @@ public class AnalysisListController extends FormBasicController implements Flexi
 			(f1, f2) -> f2.getLatestDataCollectionFinishedDate().compareTo(f1.getLatestDataCollectionFinishedDate());
 	
 	private final TooledStackedPanel stackPanel;
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	private FlexiTableElement tableEl;
 	private AnalysisDataModel dataModel;
 	
@@ -92,7 +92,7 @@ public class AnalysisListController extends FormBasicController implements Flexi
 	private OrganisationService organisationService;
 	
 	public AnalysisListController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel,
-			QualitySecurityCallback secCallback) {
+			MainSecurityCallback secCallback) {
 		super(ureq, wControl, "analysis_list");
 		this.stackPanel = stackPanel;
 		stackPanel.addListener(this);
diff --git a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisSegmentsController.java b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisSegmentsController.java
index ecf86854867..23f746413e4 100644
--- a/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisSegmentsController.java
+++ b/src/main/java/org/olat/modules/quality/analysis/ui/AnalysisSegmentsController.java
@@ -38,9 +38,9 @@ import org.olat.core.gui.control.controller.BasicController;
 import org.olat.core.gui.control.generic.dtabs.Activateable2;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.analysis.AnalysisPresentation;
 import org.olat.modules.quality.analysis.AnalysisSegment;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 
 /**
  * 
@@ -58,10 +58,10 @@ public class AnalysisSegmentsController extends BasicController implements Toole
 
 	private AnalysisController analysisCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	private final AnalysisPresentation presentation;
 	
-	public AnalysisSegmentsController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
+	public AnalysisSegmentsController(UserRequest ureq, WindowControl wControl, MainSecurityCallback secCallback,
 			TooledStackedPanel stackPanel, AnalysisPresentation presentation) {
 		super(ureq, wControl);
 		this.secCallback = secCallback;
diff --git a/src/main/java/org/olat/modules/quality/generator/QualityGeneratorProvider.java b/src/main/java/org/olat/modules/quality/generator/QualityGeneratorProvider.java
index 01b7b0b276a..ffd0b973642 100644
--- a/src/main/java/org/olat/modules/quality/generator/QualityGeneratorProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/QualityGeneratorProvider.java
@@ -28,9 +28,9 @@ import org.olat.core.gui.components.form.flexible.impl.Form;
 import org.olat.core.gui.components.stack.TooledStackedPanel;
 import org.olat.core.gui.control.WindowControl;
 import org.olat.modules.quality.QualityDataCollection;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 
 /**
  * 
@@ -53,7 +53,7 @@ public interface QualityGeneratorProvider {
 	public boolean hasWhiteListController();
 
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs);
 
 	public List<QualityDataCollection> generate(QualityGenerator generator, QualityGeneratorConfigs configs,
diff --git a/src/main/java/org/olat/modules/quality/generator/QualityGeneratorService.java b/src/main/java/org/olat/modules/quality/generator/QualityGeneratorService.java
index 53828d5ce07..b0467eeb65d 100644
--- a/src/main/java/org/olat/modules/quality/generator/QualityGeneratorService.java
+++ b/src/main/java/org/olat/modules/quality/generator/QualityGeneratorService.java
@@ -30,9 +30,9 @@ import org.olat.core.gui.components.stack.TooledStackedPanel;
 import org.olat.core.gui.control.WindowControl;
 import org.olat.core.id.Organisation;
 import org.olat.modules.quality.QualityGeneratorProviderReferenceable;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 
 /**
  * 
@@ -70,7 +70,7 @@ public interface QualityGeneratorService {
 	public boolean hasWhiteListController(QualityGenerator generator);
 	
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator);
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator);
 
 	public void generateDataCollections();
 
diff --git a/src/main/java/org/olat/modules/quality/generator/manager/QualityGeneratorServiceImpl.java b/src/main/java/org/olat/modules/quality/generator/manager/QualityGeneratorServiceImpl.java
index 99f6ada652d..cc669f6ab1a 100644
--- a/src/main/java/org/olat/modules/quality/generator/manager/QualityGeneratorServiceImpl.java
+++ b/src/main/java/org/olat/modules/quality/generator/manager/QualityGeneratorServiceImpl.java
@@ -41,7 +41,6 @@ import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityGeneratorProviderReferenceable;
 import org.olat.modules.quality.QualityReportAccess;
 import org.olat.modules.quality.QualityReportAccessSearchParams;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorConfigs;
@@ -53,6 +52,7 @@ import org.olat.modules.quality.generator.QualityGeneratorToOrganisation;
 import org.olat.modules.quality.generator.QualityGeneratorView;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
@@ -178,7 +178,7 @@ public class QualityGeneratorServiceImpl implements QualityGeneratorService {
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator) {
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator) {
 		QualityGeneratorProvider provider = providerFactory.getProvider(generator.getType());
 		QualityGeneratorConfigsImpl configs = new QualityGeneratorConfigsImpl(generator);
 		return provider.getWhiteListController(ureq, wControl, secCallback, stackPanel, generator, configs);
diff --git a/src/main/java/org/olat/modules/quality/generator/provider/course/CourseProvider.java b/src/main/java/org/olat/modules/quality/generator/provider/course/CourseProvider.java
index 15c3a64687e..395bfa337e6 100644
--- a/src/main/java/org/olat/modules/quality/generator/provider/course/CourseProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/provider/course/CourseProvider.java
@@ -51,7 +51,6 @@ import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionStatus;
 import org.olat.modules.quality.QualityDataCollectionTopicType;
 import org.olat.modules.quality.QualityReminderType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.generator.ProviderHelper;
 import org.olat.modules.quality.generator.QualityGenerator;
@@ -65,6 +64,7 @@ import org.olat.modules.quality.generator.provider.course.ui.CourseProviderConfi
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
 import org.olat.modules.quality.generator.ui.RepositoryEntryWhiteListController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.RepositoryEntryRef;
 import org.olat.repository.RepositoryEntryRelationType;
@@ -161,7 +161,7 @@ public class CourseProvider implements QualityGeneratorProvider {
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs) {
 		return new RepositoryEntryWhiteListController(ureq, wControl, stackPanel, configs);
 	}
diff --git a/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesFollowUpProvider.java b/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesFollowUpProvider.java
index 3d9bfe37041..6abe61e0e78 100644
--- a/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesFollowUpProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesFollowUpProvider.java
@@ -58,7 +58,6 @@ import org.olat.modules.quality.QualityDataCollectionSearchParams;
 import org.olat.modules.quality.QualityDataCollectionStatus;
 import org.olat.modules.quality.QualityDataCollectionTopicType;
 import org.olat.modules.quality.QualityReminderType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.generator.ProviderHelper;
 import org.olat.modules.quality.generator.QualityGenerator;
@@ -73,6 +72,7 @@ import org.olat.modules.quality.generator.provider.courselectures.manager.Search
 import org.olat.modules.quality.generator.provider.courselectures.ui.CourseLectureFollowUpProviderConfigController;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.RepositoryEntryRelationType;
 import org.olat.repository.RepositoryService;
@@ -161,7 +161,7 @@ public class CourseLecturesFollowUpProvider implements QualityGeneratorProvider
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs) {
 		return null;
 	}
diff --git a/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesProvider.java b/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesProvider.java
index 9b8a5d1d5a6..3709b2ae48e 100644
--- a/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/provider/courselectures/CourseLecturesProvider.java
@@ -50,7 +50,6 @@ import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionStatus;
 import org.olat.modules.quality.QualityDataCollectionTopicType;
 import org.olat.modules.quality.QualityReminderType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorConfigs;
@@ -64,6 +63,7 @@ import org.olat.modules.quality.generator.provider.courselectures.ui.CourseLectu
 import org.olat.modules.quality.generator.ui.CurriculumElementWhiteListController;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.RepositoryEntryRelationType;
 import org.olat.repository.RepositoryService;
@@ -150,7 +150,7 @@ public class CourseLecturesProvider implements QualityGeneratorProvider {
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs) {
 		return new CurriculumElementWhiteListController(ureq, wControl, stackPanel, generator, configs);
 	}
diff --git a/src/main/java/org/olat/modules/quality/generator/provider/curriculumelement/CurriculumElementProvider.java b/src/main/java/org/olat/modules/quality/generator/provider/curriculumelement/CurriculumElementProvider.java
index 8be3efff867..9886cf87981 100644
--- a/src/main/java/org/olat/modules/quality/generator/provider/curriculumelement/CurriculumElementProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/provider/curriculumelement/CurriculumElementProvider.java
@@ -47,7 +47,6 @@ import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionStatus;
 import org.olat.modules.quality.QualityDataCollectionTopicType;
 import org.olat.modules.quality.QualityReminderType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorConfigs;
@@ -60,6 +59,7 @@ import org.olat.modules.quality.generator.provider.curriculumelement.ui.Curricul
 import org.olat.modules.quality.generator.ui.CurriculumElementWhiteListController;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
@@ -135,7 +135,7 @@ public class CurriculumElementProvider implements QualityGeneratorProvider {
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs) {
 		return new CurriculumElementWhiteListController(ureq, wControl, stackPanel, generator, configs);
 	}
diff --git a/src/main/java/org/olat/modules/quality/generator/provider/fallback/FallbackProvider.java b/src/main/java/org/olat/modules/quality/generator/provider/fallback/FallbackProvider.java
index 2eb5631d00e..77930dc1f39 100644
--- a/src/main/java/org/olat/modules/quality/generator/provider/fallback/FallbackProvider.java
+++ b/src/main/java/org/olat/modules/quality/generator/provider/fallback/FallbackProvider.java
@@ -31,13 +31,13 @@ import org.olat.core.gui.control.WindowControl;
 import org.olat.core.gui.translator.Translator;
 import org.olat.core.util.Util;
 import org.olat.modules.quality.QualityDataCollection;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorConfigs;
 import org.olat.modules.quality.generator.QualityGeneratorProvider;
 import org.olat.modules.quality.generator.ui.GeneratorListController;
 import org.olat.modules.quality.generator.ui.GeneratorWhiteListController;
 import org.olat.modules.quality.generator.ui.ProviderConfigController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.springframework.stereotype.Service;
 
 /**
@@ -80,7 +80,7 @@ public class FallbackProvider implements QualityGeneratorProvider {
 
 	@Override
 	public GeneratorWhiteListController getWhiteListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGenerator generator,
 			QualityGeneratorConfigs configs) {
 		return null;
 	}
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/CurriculumElementWhiteListController.java b/src/main/java/org/olat/modules/quality/generator/ui/CurriculumElementWhiteListController.java
index d08b59aafbe..458e4da7b60 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/CurriculumElementWhiteListController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/CurriculumElementWhiteListController.java
@@ -276,9 +276,4 @@ implements GeneratorWhiteListController, TooledController {
 		//
 	}
 
-	@Override
-	public void onChanged(QualityGenerator generator, UserRequest ureq) {
-		//
-	}
-
 }
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorConfigController.java b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorConfigController.java
index e8794a56016..45836518889 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorConfigController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorConfigController.java
@@ -50,13 +50,13 @@ import org.olat.core.util.StringHelper;
 import org.olat.fileresource.FileResourceManager;
 import org.olat.modules.forms.handler.EvaluationFormResource;
 import org.olat.modules.forms.ui.EvaluationFormExecutionController;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorRef;
 import org.olat.modules.quality.generator.QualityGeneratorSearchParams;
 import org.olat.modules.quality.generator.QualityGeneratorService;
 import org.olat.modules.quality.generator.QualityGeneratorView;
 import org.olat.modules.quality.ui.QualityUIFactory;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.controllers.ReferencableEntriesSearchController;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -80,7 +80,7 @@ public class GeneratorConfigController extends FormBasicController {
 	private CloseableModalController cmc;
 	private ReferencableEntriesSearchController formSearchCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private GeneratorSecurityCallback secCallback;
 	private final TooledStackedPanel stackPanel;
 	private QualityGenerator generator;
 	private List<Organisation> currentOrganisations;
@@ -92,7 +92,7 @@ public class GeneratorConfigController extends FormBasicController {
 	private OrganisationModule organisationModule;
 
 	public GeneratorConfigController(UserRequest ureq, WindowControl wControl, Form mainForm,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGeneratorRef generatorRef) {
+			GeneratorSecurityCallback secCallback, TooledStackedPanel stackPanel, QualityGeneratorRef generatorRef) {
 		super(ureq, wControl, LAYOUT_DEFAULT, null, mainForm);
 		this.secCallback = secCallback;
 		this.stackPanel = stackPanel;
@@ -128,14 +128,15 @@ public class GeneratorConfigController extends FormBasicController {
 		updateUI();
 	}
 
-	public void setGenerator(QualityGeneratorRef generatorRef) {
-		generator = generatorService.loadGenerator(generatorRef);
-		formEntry = generator.getFormEntry();
+	public void onChanged(QualityGeneratorRef generatorRef, GeneratorSecurityCallback secCallback) {
+		this.generator = generatorService.loadGenerator(generatorRef);
+		this.formEntry = generator.getFormEntry();
+		this.secCallback = secCallback;
 		updateUI();
 	}
 
 	protected void updateUI() {
-		boolean editGenerator = secCallback.canEditGenerator(generator);
+		boolean editGenerator = secCallback.canEditGenerator();
 		titleEl.setEnabled(editGenerator);
 		organisationsEl.setEnabled(editGenerator);
 		organisationsEl.setVisible(organisationModule.isEnabled());
@@ -151,7 +152,7 @@ public class GeneratorConfigController extends FormBasicController {
 		searchParams.setGeneratorRefs(Collections.singletonList(generator));
 		List<QualityGeneratorView> generators = generatorService.loadGenerators(searchParams);
 		Long numOfDataCollections = generators.isEmpty()? 0l: generators.get(0).getNumberDataCollections();
-		boolean editGeneratorForm = secCallback.canEditGeneratorForm(generator, numOfDataCollections);
+		boolean editGeneratorForm = secCallback.canEditGeneratorForm(numOfDataCollections);
 		evaFormNotChoosen.setVisible(!hasRepoConfig);
 		evaFormSelectLink.setVisible(!hasRepoConfig);
 		evaFormPreviewLink.setVisible(hasRepoConfig);
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorController.java b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorController.java
index 51dbe923bf6..15b04d01690 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorController.java
@@ -42,12 +42,14 @@ import org.olat.core.gui.control.WindowControl;
 import org.olat.core.gui.control.controller.BasicController;
 import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController;
 import org.olat.core.gui.control.generic.dtabs.Activateable2;
+import org.olat.core.id.Organisation;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorService;
 import org.olat.modules.quality.ui.GeneratorReportAccessController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
+import org.olat.modules.quality.ui.security.QualitySecurityCallbackFactory;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -76,30 +78,31 @@ public class GeneratorController extends BasicController implements TooledContro
 	private GeneratorEnableConfirmationController enableConfirmationCtrl;
 	private GeneratorDisableConfirmationController disableConfirmationCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private GeneratorSecurityCallback secCallback;
 	private QualityGenerator generator;
+	private final List<Organisation> organisations;
 	
 	@Autowired
 	private QualityGeneratorService generatorService;
 
-	public GeneratorController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
-			TooledStackedPanel stackPanel, QualityGenerator generator) {
+	public GeneratorController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel,
+			QualityGenerator generator) {
 		super(ureq, wControl);
-		this.secCallback = secCallback;
 		this.stackPanel = stackPanel;
 		stackPanel.addListener(this);
 		this.generator = generator;
+		organisations = generatorService.loadGeneratorOrganisations(generator);
+		this.secCallback = QualitySecurityCallbackFactory
+				.createGeneratorSecurityCallback(ureq.getUserSession().getRoles(), generator, organisations);
 		
 		segmentButtonsCmp = new ButtonGroupComponent("segments");
-		if (secCallback.canViewGenerators()) {
-			configurationLink = LinkFactory.createLink("generator.configuration", getTranslator(), this);
-			segmentButtonsCmp.addButton(configurationLink, false);
-			reportAccessLink = LinkFactory.createLink("generator.report.access", getTranslator(), this);
-			segmentButtonsCmp.addButton(reportAccessLink, false);
-			if (generatorService.hasWhiteListController(generator)) {
-				whiteListLink = LinkFactory.createLink("generator.white.list", getTranslator(), this);
-				segmentButtonsCmp.addButton(whiteListLink, false);
-			}
+		configurationLink = LinkFactory.createLink("generator.configuration", getTranslator(), this);
+		segmentButtonsCmp.addButton(configurationLink, false);
+		reportAccessLink = LinkFactory.createLink("generator.report.access", getTranslator(), this);
+		segmentButtonsCmp.addButton(reportAccessLink, false);
+		if (generatorService.hasWhiteListController(generator)) {
+			whiteListLink = LinkFactory.createLink("generator.white.list", getTranslator(), this);
+			segmentButtonsCmp.addButton(whiteListLink, false);
 		}
 		
 		mainPanel = putInitialPanel(new SimpleStackedPanel("dataCollectionSegments"));
@@ -281,15 +284,15 @@ public class GeneratorController extends BasicController implements TooledContro
 	}
 	
 	private void updateUI(UserRequest ureq) {
+		secCallback = QualitySecurityCallbackFactory.createGeneratorSecurityCallback(ureq.getUserSession().getRoles(),
+				generator, organisations);
+		
 		initButtons();
 		if (configCtrl != null) {
-			configCtrl.onChanged(generator, ureq);
+			configCtrl.onChanged(generator, secCallback);
 		}
 		if (reportAccessCtrl != null) {
-			reportAccessCtrl.onChanged(generator, ureq);
-		}
-		if (whiteListCtrl != null) {
-			whiteListCtrl.onChanged(generator, ureq);
+			reportAccessCtrl.onChanged(secCallback, ureq);
 		}
 	}
 
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorEditController.java b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorEditController.java
index ca795a7bf40..b5732138732 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorEditController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorEditController.java
@@ -27,9 +27,9 @@ import org.olat.core.gui.components.stack.TooledStackedPanel;
 import org.olat.core.gui.control.Controller;
 import org.olat.core.gui.control.Event;
 import org.olat.core.gui.control.WindowControl;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorService;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -38,23 +38,23 @@ import org.springframework.beans.factory.annotation.Autowired;
  * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
  *
  */
-public class GeneratorEditController extends FormBasicController implements GeneratorChangedController {
+public class GeneratorEditController extends FormBasicController {
 	
 	private GeneratorConfigController configCtrl;
 	private ProviderConfigController providerConfigCtrl;
 
-	private QualitySecurityCallback secCallback;
 	private TooledStackedPanel stackPanel;
 	
+	private GeneratorSecurityCallback secCallback;
 	private QualityGenerator generator;
 	
 	@Autowired
 	private QualityGeneratorService generatorService;
 	
-	public GeneratorEditController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
+	public GeneratorEditController(UserRequest ureq, WindowControl wControl, GeneratorSecurityCallback secCallback2,
 			TooledStackedPanel stackPanel, QualityGenerator generator, boolean validate) {
 		super(ureq, wControl, LAYOUT_BAREBONE);
-		this.secCallback = secCallback;
+		this.secCallback = secCallback2;
 		this.stackPanel = stackPanel;
 		this.generator = generator;
 		initForm(ureq);
@@ -86,14 +86,15 @@ public class GeneratorEditController extends FormBasicController implements Gene
 		updateUI();
 	}
 
-	@Override
-	public void onChanged(QualityGenerator generator, UserRequest ureq) {
-		configCtrl.setGenerator(generator);
+	public void onChanged(QualityGenerator generator, GeneratorSecurityCallback secCallback) {
+		this.generator = generator;
+		this.secCallback = secCallback;
+		configCtrl.onChanged(generator, secCallback);
 		updateUI();
 	}
 	
 	private void updateUI() {
-		providerConfigCtrl.setReadOnly(generator.isEnabled());
+		providerConfigCtrl.setReadOnly(!secCallback.canEditGenerator());
 	}
 
 	@Override
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorListController.java b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorListController.java
index f1c0e366a12..f0c9260facb 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorListController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorListController.java
@@ -55,13 +55,13 @@ import org.olat.core.id.context.StateEntry;
 import org.olat.core.util.Formatter;
 import org.olat.core.util.StringHelper;
 import org.olat.core.util.mail.ui.BooleanCSSCellRenderer;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorRef;
 import org.olat.modules.quality.generator.QualityGeneratorSearchParams;
 import org.olat.modules.quality.generator.QualityGeneratorService;
 import org.olat.modules.quality.generator.QualityGeneratorView;
 import org.olat.modules.quality.generator.ui.GeneratorDataModel.GeneratorCols;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -86,7 +86,7 @@ public class GeneratorListController extends FormBasicController implements Tool
 	private GeneratorController generatorCtrl;
 	private GeneratorDeleteConfirmationController deleteConfirmationCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	private final List<Organisation> organisations;
 	
 	@Autowired
@@ -96,7 +96,7 @@ public class GeneratorListController extends FormBasicController implements Tool
 
 
 	public GeneratorListController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel,
-			QualitySecurityCallback secCallback) {
+			MainSecurityCallback secCallback) {
 		super(ureq, wControl, LAYOUT_BAREBONE);
 		this.stackPanel = stackPanel;
 		stackPanel.addListener(this);
@@ -113,11 +113,7 @@ public class GeneratorListController extends FormBasicController implements Tool
 				"o_icon o_icon-lg o_icon_qual_gen_enabled", "o_icon o_icon-lg o_icon_qual_gen_disabled",
 				"generator.enabled.hover", "generator.disabled.hover");
 		columnsModel.addFlexiColumnModel(new DefaultFlexiColumnModel(GeneratorCols.enabled, enabledRenderer));
-		if (secCallback.canEditGenerators() || secCallback.canViewGenerators()) {
-			columnsModel.addFlexiColumnModel(new DefaultFlexiColumnModel(GeneratorCols.title, CMD_EDIT));
-		} else {
-			columnsModel.addFlexiColumnModel(new DefaultFlexiColumnModel(GeneratorCols.title));
-		}
+		columnsModel.addFlexiColumnModel(new DefaultFlexiColumnModel(GeneratorCols.title, CMD_EDIT));
 		columnsModel.addFlexiColumnModel(new DefaultFlexiColumnModel(GeneratorCols.providerName));
 		DefaultFlexiColumnModel numDataCollectionsColumn = new DefaultFlexiColumnModel(GeneratorCols.numberDataCollections);
 		numDataCollectionsColumn.setAlignment(FlexiColumnModel.ALIGNMENT_RIGHT);
@@ -270,7 +266,7 @@ public class GeneratorListController extends FormBasicController implements Tool
 
 	private void doEditGenerator(UserRequest ureq, QualityGenerator generator) {
 		WindowControl bwControl = addToHistory(ureq, generator, null);
-		generatorCtrl = new GeneratorController(ureq, bwControl, secCallback, stackPanel, generator);
+		generatorCtrl = new GeneratorController(ureq, bwControl, stackPanel, generator);
 		listenTo(generatorCtrl);
 		String title = generator.getTitle();
 		String formattedTitle = StringHelper.containsNonWhitespace(title)
@@ -292,7 +288,7 @@ public class GeneratorListController extends FormBasicController implements Tool
 
 	private void doDeleteGenerator(QualityGenerator generator) {
 		long numberDataCollections = generatorService.getNumberOfDataCollections(generator);
-		if (secCallback.canDeleteGenerator(numberDataCollections)) {
+		if (numberDataCollections == 0) {
 			generatorService.deleteGenerator(generator);
 			stackPanel.popUpToController(this);
 			loadModel();
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorWhiteListController.java b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorWhiteListController.java
index 103e4348092..64dca8fbe36 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorWhiteListController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/GeneratorWhiteListController.java
@@ -27,6 +27,6 @@ import org.olat.core.gui.control.Controller;
  * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
  *
  */
-public interface GeneratorWhiteListController extends Controller, GeneratorChangedController {
+public interface GeneratorWhiteListController extends Controller {
 
 }
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/RepositoryEntryWhiteListController.java b/src/main/java/org/olat/modules/quality/generator/ui/RepositoryEntryWhiteListController.java
index 6ce9c1c36ed..f3d2e8ab133 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/RepositoryEntryWhiteListController.java
+++ b/src/main/java/org/olat/modules/quality/generator/ui/RepositoryEntryWhiteListController.java
@@ -50,7 +50,6 @@ import org.olat.core.gui.control.WindowControl;
 import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController;
 import org.olat.core.util.StringHelper;
 import org.olat.course.CourseModule;
-import org.olat.modules.quality.generator.QualityGenerator;
 import org.olat.modules.quality.generator.QualityGeneratorConfigs;
 import org.olat.modules.quality.generator.ui.RepositoryEntryWhiteListDataModel.Cols;
 import org.olat.repository.RepositoryEntry;
@@ -270,11 +269,6 @@ public class RepositoryEntryWhiteListController extends FormBasicController
 		loadModel();
 	}
 
-	@Override
-	public void onChanged(QualityGenerator generator, UserRequest ureq) {
-		//
-	}
-
 	@Override
 	protected void formOK(UserRequest ureq) {
 		//
diff --git a/src/main/java/org/olat/modules/quality/ui/DataCollectionConfigurationController.java b/src/main/java/org/olat/modules/quality/ui/DataCollectionConfigurationController.java
index 7253a916c9d..c3d63faf287 100644
--- a/src/main/java/org/olat/modules/quality/ui/DataCollectionConfigurationController.java
+++ b/src/main/java/org/olat/modules/quality/ui/DataCollectionConfigurationController.java
@@ -65,11 +65,11 @@ import org.olat.modules.forms.handler.EvaluationFormResource;
 import org.olat.modules.forms.ui.EvaluationFormExecutionController;
 import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionTopicType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.ui.QualityUIFactory.KeysValues;
 import org.olat.modules.quality.ui.event.DataCollectionEvent;
 import org.olat.modules.quality.ui.event.DataCollectionEvent.Action;
+import org.olat.modules.quality.ui.security.DataCollectionSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.controllers.ReferencableEntriesSearchController;
 import org.olat.user.UserManager;
@@ -119,7 +119,7 @@ public class DataCollectionConfigurationController extends FormBasicController {
 	private RepositoryEntry topicRepository;
 	
 	private final TooledStackedPanel stackPanel;
-	private final QualitySecurityCallback secCallback;
+	private DataCollectionSecurityCallback secCallback;
 	private QualityDataCollection dataCollection;
 	
 	@Autowired
@@ -134,7 +134,7 @@ public class DataCollectionConfigurationController extends FormBasicController {
 	private CurriculumService curriculumService;
 
 	public DataCollectionConfigurationController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel,
+			DataCollectionSecurityCallback secCallback, TooledStackedPanel stackPanel,
 			QualityDataCollection dataCollection, boolean validate) {
 		super(ureq, wControl);
 		this.secCallback = secCallback;
@@ -224,15 +224,16 @@ public class DataCollectionConfigurationController extends FormBasicController {
 		updateUI();
 	}
 	
-	public void setDataCollection(QualityDataCollection dataCollection) {
+	public void onChanged(QualityDataCollection dataCollection, DataCollectionSecurityCallback secCallback) {
 		this.dataCollection = dataCollection;
+		this.secCallback = secCallback;
 		startEl.setDate(dataCollection.getStart());
 		deadlineEl.setDate(dataCollection.getDeadline());
 		updateUI();
 	}
 	
 	private void updateUI() {
-		boolean updateBaseConfiguration = secCallback.canUpdateBaseConfiguration(dataCollection);
+		boolean updateBaseConfiguration = secCallback.canUpdateBaseConfiguration();
 		titleEl.setEnabled(updateBaseConfiguration);
 		evaFormReplaceLink.setVisible(updateBaseConfiguration);
 		evaFormEditLink.setVisible(updateBaseConfiguration);
@@ -279,7 +280,7 @@ public class DataCollectionConfigurationController extends FormBasicController {
 					: translate("data.collection.topic.identity.none");
 				topicIdentityNameEl.setValue(userName);
 				topicIdentityNameEl.setVisible(true);
-				topicIdentitySelectLink.setVisible(secCallback.canUpdateBaseConfiguration(dataCollection));
+				topicIdentitySelectLink.setVisible(secCallback.canUpdateBaseConfiguration());
 				break;
 			case ORGANISATION:
 				List<Organisation> organisations = organisationService.getOrganisations(getIdentity(),
@@ -334,7 +335,7 @@ public class DataCollectionConfigurationController extends FormBasicController {
 						: translate("data.collection.topic.repository.none");
 				topicRepositoryNameEl.setValue(repositoryName);
 				topicRepositoryNameEl.setVisible(true);
-				topicRepositorySelectLink.setVisible(secCallback.canUpdateBaseConfiguration(dataCollection));
+				topicRepositorySelectLink.setVisible(secCallback.canUpdateBaseConfiguration());
 				break;
 			}
 		}
diff --git a/src/main/java/org/olat/modules/quality/ui/DataCollectionController.java b/src/main/java/org/olat/modules/quality/ui/DataCollectionController.java
index 8a332d82395..066c7a3d2dd 100644
--- a/src/main/java/org/olat/modules/quality/ui/DataCollectionController.java
+++ b/src/main/java/org/olat/modules/quality/ui/DataCollectionController.java
@@ -48,15 +48,17 @@ import org.olat.core.gui.control.controller.BasicController;
 import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController;
 import org.olat.core.gui.control.generic.dtabs.Activateable2;
 import org.olat.core.id.OLATResourceable;
+import org.olat.core.id.Organisation;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
 import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionLight;
 import org.olat.modules.quality.QualityDataCollectionStatus;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.ui.event.DataCollectionEvent;
 import org.olat.modules.quality.ui.event.DataCollectionEvent.Action;
+import org.olat.modules.quality.ui.security.DataCollectionSecurityCallback;
+import org.olat.modules.quality.ui.security.QualitySecurityCallbackFactory;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -97,21 +99,24 @@ public class DataCollectionController extends BasicController implements TooledC
 	private DataCollectionStartConfirmationController startConfirmationController;
 	private DataCollectionFinishConfirmationController finishConfirmationController;
 	
-	private final QualitySecurityCallback secCallback;
+	private DataCollectionSecurityCallback secCallback;
 	private QualityDataCollection dataCollection;
+	private List<Organisation> organisations;
 	private QualityDataCollection previousDataCollection;
 	private QualityDataCollection followUpDataCollection;
 	
 	@Autowired
 	private QualityService qualityService;
 
-	protected DataCollectionController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
-			TooledStackedPanel stackPanel, QualityDataCollectionLight dataCollectionLight) {
+	protected DataCollectionController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel,
+			QualityDataCollectionLight dataCollectionLight) {
 		super(ureq, wControl);
-		this.secCallback = secCallback;
 		this.stackPanel = stackPanel;
 		stackPanel.addListener(this);
 		this.dataCollection = qualityService.loadDataCollectionByKey(dataCollectionLight);
+		organisations = qualityService.loadDataCollectionOrganisations(dataCollectionLight);
+		secCallback = QualitySecurityCallbackFactory.createDataCollectionSecurityCallback(
+				ureq.getUserSession().getRoles(), dataCollectionLight, organisations);
 		
 		segmentButtonsCmp = new ButtonGroupComponent("segments");
 		if (secCallback.canViewDataCollectionConfigurations()) {
@@ -131,7 +136,7 @@ public class DataCollectionController extends BasicController implements TooledC
 	}
 	
 	private void addReportButtons() {
-		if (secCallback.canViewReport(dataCollection)) {
+		if (secCallback.canViewReport()) {
 			if (segmentButtonsCmp.getComponent("data.collection.report") == null) {
 				reportLink = LinkFactory.createLink("data.collection.report", getTranslator(), this);
 				segmentButtonsCmp.addButton(reportLink, false);
@@ -154,12 +159,12 @@ public class DataCollectionController extends BasicController implements TooledC
 		if (entries != null && !entries.isEmpty()) {
 			OLATResourceable resource = entries.get(0).getOLATResourceable();
 			if (ORES_REPORT_TYPE.equalsIgnoreCase(resource.getResourceableTypeName())
-					&& secCallback.canViewReport(dataCollection)) {
+					&& secCallback.canViewReport()) {
 				doOpenReport(ureq);
 			}
 		} else if (secCallback.canViewDataCollectionConfigurations()) {
 			doOpenConfiguration(ureq);
-		} else if (secCallback.canViewReport(dataCollection)) {
+		} else if (secCallback.canViewReport()) {
 			doOpenReport(ureq);
 		}
 	}
@@ -182,10 +187,10 @@ public class DataCollectionController extends BasicController implements TooledC
 	}
 
 	private boolean canChangeStatus() {
-		return secCallback.canSetPreparation(dataCollection)
-				|| secCallback.canSetReady(dataCollection)
-				|| secCallback.canSetRunning(dataCollection)
-				|| secCallback.canSetFinished(dataCollection);
+		return secCallback.canSetPreparation()
+				|| secCallback.canSetReady()
+				|| secCallback.canSetRunning()
+				|| secCallback.canSetFinished();
 	}
 
 	private Dropdown buildStatusDrowdown() {
@@ -201,25 +206,25 @@ public class DataCollectionController extends BasicController implements TooledC
 		statusPreparationLink = LinkFactory.createToolLink("data.collection.status.preparation", translate("data.collection.status.preparation"), this);
 		statusPreparationLink.setIconLeftCSS("o_icon o_icon-fw o_icon_qual_dc_preparation");
 		statusPreparationLink.setElementCssClass("o_labeled o_qual_dc_status_preparation");
-		statusPreparationLink.setVisible(secCallback.canSetPreparation(dataCollection));
+		statusPreparationLink.setVisible(secCallback.canSetPreparation());
 		statusDropdown.addComponent(statusPreparationLink);
 	
 		statusReadyLink = LinkFactory.createToolLink("data.collection.status.ready", translate("data.collection.status.ready"), this);
 		statusReadyLink.setIconLeftCSS("o_icon o_icon-fw o_icon_qual_dc_ready");
 		statusReadyLink.setElementCssClass("o_labeled o_qual_dc_status_ready");
-		statusReadyLink.setVisible(secCallback.canSetReady(dataCollection));
+		statusReadyLink.setVisible(secCallback.canSetReady());
 		statusDropdown.addComponent(statusReadyLink);
 		
 		statusRunningLink = LinkFactory.createToolLink("data.collection.status.running", translate("data.collection.status.running"), this);
 		statusRunningLink.setIconLeftCSS("o_icon o_icon-fw o_icon_qual_dc_running");
 		statusRunningLink.setElementCssClass("o_labeled o_qual_dc_status_running");
-		statusRunningLink.setVisible(secCallback.canSetRunning(dataCollection));
+		statusRunningLink.setVisible(secCallback.canSetRunning());
 		statusDropdown.addComponent(statusRunningLink);
 		
 		statusFinishedLink = LinkFactory.createToolLink("data.collection.status.finished", translate("data.collection.status.finished"), this);
 		statusFinishedLink.setIconLeftCSS("o_icon o_icon-fw o_icon_qual_dc_finished");
 		statusFinishedLink.setElementCssClass("o_labeled o_qual_dc_status_finished");
-		statusFinishedLink.setVisible(secCallback.canSetFinished(dataCollection));
+		statusFinishedLink.setVisible(secCallback.canSetFinished());
 		statusDropdown.addComponent(statusFinishedLink);
 		
 		return statusDropdown;
@@ -236,7 +241,7 @@ public class DataCollectionController extends BasicController implements TooledC
 
 	private void initButtons() {
 		if (deleteLink != null) stackPanel.removeTool(deleteLink, this);
-		if (secCallback.canDeleteDataCollection(dataCollection) ) {
+		if (secCallback.canDeleteDataCollection() ) {
 			deleteLink = LinkFactory.createToolLink("data.collection.delete", translate("data.collection.delete"),
 					this);
 			deleteLink.setIconLeftCSS("o_icon o_icon-fw o_icon_qual_dc_delete");
@@ -447,18 +452,20 @@ public class DataCollectionController extends BasicController implements TooledC
 	}
 	
 	private void afterDataCollectionUpdated(UserRequest ureq) {
+		secCallback = QualitySecurityCallbackFactory.createDataCollectionSecurityCallback(
+				ureq.getUserSession().getRoles(), dataCollection, organisations);
 		initTools();
 		if (configurationCtrl != null) {
-			configurationCtrl.setDataCollection(dataCollection);
+			configurationCtrl.onChanged(dataCollection, secCallback);
 		}
 		if (participationsCtrl != null) {
-			participationsCtrl.setDataCollection(dataCollection, ureq);
+			participationsCtrl.onChanged(dataCollection, secCallback, ureq);
 		}
 		if (remindersCtrl != null) {
-			remindersCtrl.setDataCollection(dataCollection);
+			remindersCtrl.onChanged(dataCollection, secCallback);
 		}
 		if (reportAccessCtrl != null) {
-			reportAccessCtrl.setDataCollection(dataCollection, ureq);
+			reportAccessCtrl.onChanged(secCallback, ureq);
 		}
 		addReportButtons();
 	}
diff --git a/src/main/java/org/olat/modules/quality/ui/DataCollectionDataModel.java b/src/main/java/org/olat/modules/quality/ui/DataCollectionDataModel.java
index b63b100d2c2..c09778b3c04 100644
--- a/src/main/java/org/olat/modules/quality/ui/DataCollectionDataModel.java
+++ b/src/main/java/org/olat/modules/quality/ui/DataCollectionDataModel.java
@@ -27,7 +27,7 @@ import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTable
 import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableDataSourceDelegate;
 import org.olat.core.gui.translator.Translator;
 import org.olat.core.util.StringHelper;
-import org.olat.modules.quality.QualitySecurityCallback;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 
 /**
  * 
@@ -38,10 +38,10 @@ import org.olat.modules.quality.QualitySecurityCallback;
 public class DataCollectionDataModel extends DefaultFlexiTableDataSourceModel<DataCollectionRow> {
 
 	private final Translator translator;
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	
 	public DataCollectionDataModel(FlexiTableDataSourceDelegate<DataCollectionRow> dataSource,
-			FlexiTableColumnModel columnsModel, Translator translator, QualitySecurityCallback secCallback) {
+			FlexiTableColumnModel columnsModel, Translator translator, MainSecurityCallback secCallback) {
 		super(dataSource, columnsModel);
 		this.translator = translator;
 		this.secCallback = secCallback;
diff --git a/src/main/java/org/olat/modules/quality/ui/DataCollectionListController.java b/src/main/java/org/olat/modules/quality/ui/DataCollectionListController.java
index c40e770d437..279c9eac0e3 100644
--- a/src/main/java/org/olat/modules/quality/ui/DataCollectionListController.java
+++ b/src/main/java/org/olat/modules/quality/ui/DataCollectionListController.java
@@ -57,11 +57,11 @@ import org.olat.modules.forms.handler.EvaluationFormResource;
 import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityDataCollectionLight;
 import org.olat.modules.quality.QualityDataCollectionView;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.ui.DataCollectionDataModel.DataCollectionCols;
 import org.olat.modules.quality.ui.event.DataCollectionEvent;
 import org.olat.modules.quality.ui.event.DataCollectionEvent.Action;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 import org.olat.repository.RepositoryEntry;
 import org.olat.repository.controllers.ReferencableEntriesSearchController;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -86,7 +86,7 @@ public class DataCollectionListController extends FormBasicController implements
 	private ReferencableEntriesSearchController formSearchCtrl;
 	private DataCollectionDeleteConfirmationController deleteConfirmationCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	
 	@Autowired
 	private QualityService qualityService;
@@ -94,7 +94,7 @@ public class DataCollectionListController extends FormBasicController implements
 	private OrganisationService organisationService;
 
 	public DataCollectionListController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel,
-			QualitySecurityCallback secCallback) {
+			MainSecurityCallback secCallback) {
 		super(ureq, wControl, LAYOUT_BAREBONE);
 		this.stackPanel = stackPanel;
 		stackPanel.addListener(this);
@@ -257,8 +257,7 @@ public class DataCollectionListController extends FormBasicController implements
 	
 	private void doEditDataCollection(UserRequest ureq, QualityDataCollectionLight dataCollection) {
 		WindowControl bwControl = addToHistory(ureq, dataCollection, null);
-		dataCollectionCtrl = new DataCollectionController(ureq, bwControl, secCallback, stackPanel,
-				dataCollection);
+		dataCollectionCtrl = new DataCollectionController(ureq, bwControl, stackPanel, dataCollection);
 		listenTo(dataCollectionCtrl);
 		String title = dataCollection.getTitle();
 		String formattedTitle = StringHelper.containsNonWhitespace(title)
diff --git a/src/main/java/org/olat/modules/quality/ui/DataCollectionReportAccessController.java b/src/main/java/org/olat/modules/quality/ui/DataCollectionReportAccessController.java
index 50276f3bf18..5ca738e2ca8 100644
--- a/src/main/java/org/olat/modules/quality/ui/DataCollectionReportAccessController.java
+++ b/src/main/java/org/olat/modules/quality/ui/DataCollectionReportAccessController.java
@@ -24,7 +24,7 @@ import static org.olat.modules.quality.QualityReportAccessReference.of;
 import org.olat.core.gui.UserRequest;
 import org.olat.core.gui.control.WindowControl;
 import org.olat.modules.quality.QualityDataCollection;
-import org.olat.modules.quality.QualitySecurityCallback;
+import org.olat.modules.quality.ui.security.DataCollectionSecurityCallback;
 
 /**
  * 
@@ -34,35 +34,33 @@ import org.olat.modules.quality.QualitySecurityCallback;
  */
 public class DataCollectionReportAccessController extends ReportAccessController {
 
-	private final QualitySecurityCallback secCallback;
-	private QualityDataCollection dataCollection;
+	private DataCollectionSecurityCallback secCallback;
 
 	protected DataCollectionReportAccessController(UserRequest ureq, WindowControl wControl, 
-			QualitySecurityCallback secCallback, QualityDataCollection dataCollection) {
+			DataCollectionSecurityCallback secCallback, QualityDataCollection dataCollection) {
 		super(ureq, wControl, of(dataCollection));
 		this.secCallback = secCallback;
-		this.dataCollection = dataCollection;
 		initForm(ureq);
 	}
 	
-	public void setDataCollection(QualityDataCollection dataCollection, UserRequest ureq) {
-		this.dataCollection = dataCollection;
+	public void onChanged(DataCollectionSecurityCallback secCallback, UserRequest ureq) {
+		this.secCallback = secCallback;
 		initForm(ureq);
 	}
 
 	@Override
 	protected boolean canEditReportAccessOnline() {
-		return secCallback.canEditReportAccessOnline(dataCollection);
+		return secCallback.canEditReportAccessOnline();
 	}
 
 	@Override
 	protected boolean canEditReportAccessEmail() {
-		return secCallback.canEditReportAccessEmail(dataCollection);
+		return secCallback.canEditReportAccessEmail();
 	}
 
 	@Override
 	protected boolean canEditReportMembers() {
-		return secCallback.canEditReportAccessMembers(dataCollection);
+		return secCallback.canEditReportAccessMembers();
 	}
 
 }
diff --git a/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationDataModel.java b/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationDataModel.java
index 10adc1bbe12..6c37a686c93 100644
--- a/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationDataModel.java
+++ b/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationDataModel.java
@@ -26,7 +26,7 @@ import org.olat.core.gui.components.form.flexible.impl.elements.table.DefaultFle
 import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiSortableColumnDef;
 import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableColumnModel;
 import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableDataSourceDelegate;
-import org.olat.modules.quality.QualitySecurityCallback;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 
 /**
  * 
@@ -36,11 +36,11 @@ import org.olat.modules.quality.QualitySecurityCallback;
  */
 public class ExecutorParticipationDataModel extends DefaultFlexiTableDataSourceModel<ExecutorParticipationRow> {
 
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	private final Locale locale;
 
 	public ExecutorParticipationDataModel(FlexiTableDataSourceDelegate<ExecutorParticipationRow> dataSource,
-			FlexiTableColumnModel columnsModel, QualitySecurityCallback secCallback, Locale locale) {
+			FlexiTableColumnModel columnsModel, MainSecurityCallback secCallback, Locale locale) {
 		super(dataSource, columnsModel);
 		this.secCallback = secCallback;
 		this.locale = locale;
diff --git a/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationsListController.java b/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationsListController.java
index 69f4de61864..335be8e6b33 100644
--- a/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationsListController.java
+++ b/src/main/java/org/olat/modules/quality/ui/ExecutorParticipationsListController.java
@@ -52,8 +52,8 @@ import org.olat.core.util.resource.OresHelper;
 import org.olat.modules.quality.QualityDataCollectionStatus;
 import org.olat.modules.quality.QualityExecutorParticipation;
 import org.olat.modules.quality.QualityExecutorParticipationSearchParams;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.ui.ExecutorParticipationDataModel.ExecutorParticipationCols;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 
 /**
  * 
@@ -75,10 +75,10 @@ public class ExecutorParticipationsListController extends FormBasicController im
 
 	private ExecutionController executionCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 
 	public ExecutorParticipationsListController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback) {
+			MainSecurityCallback secCallback) {
 		super(ureq, wControl, LAYOUT_BAREBONE);
 		this.secCallback = secCallback;
 		initForm(ureq);
diff --git a/src/main/java/org/olat/modules/quality/ui/GeneratorReportAccessController.java b/src/main/java/org/olat/modules/quality/ui/GeneratorReportAccessController.java
index 4d74f115ed1..a492e02bd61 100644
--- a/src/main/java/org/olat/modules/quality/ui/GeneratorReportAccessController.java
+++ b/src/main/java/org/olat/modules/quality/ui/GeneratorReportAccessController.java
@@ -23,9 +23,8 @@ import static org.olat.modules.quality.QualityReportAccessReference.of;
 
 import org.olat.core.gui.UserRequest;
 import org.olat.core.gui.control.WindowControl;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.generator.QualityGenerator;
-import org.olat.modules.quality.generator.ui.GeneratorChangedController;
+import org.olat.modules.quality.ui.security.GeneratorSecurityCallback;
 
 /**
  * 
@@ -33,38 +32,35 @@ import org.olat.modules.quality.generator.ui.GeneratorChangedController;
  * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
  *
  */
-public class GeneratorReportAccessController extends ReportAccessController implements GeneratorChangedController {
+public class GeneratorReportAccessController extends ReportAccessController {
 
-	private final QualitySecurityCallback secCallback;
-	private QualityGenerator generator;
+	private GeneratorSecurityCallback secCallback;
 
 	public GeneratorReportAccessController(UserRequest ureq, WindowControl wControl,
-			QualitySecurityCallback secCallback, QualityGenerator generator) {
+			GeneratorSecurityCallback secCallback, QualityGenerator generator) {
 		super(ureq, wControl, of(generator));
 		this.secCallback = secCallback;
-		this.generator = generator;
 		initForm(ureq);
 	}
 
-	@Override
-	public void onChanged(QualityGenerator generator, UserRequest ureq) {
-		this.generator = generator;
+	public void onChanged(GeneratorSecurityCallback secCallback, UserRequest ureq) {
+		this.secCallback = secCallback;
 		initForm(ureq);
 	}
 
 	@Override
 	protected boolean canEditReportAccessOnline() {
-		return secCallback.canEditReportAccessOnline(generator);
+		return secCallback.canEditReportAccessOnline();
 	}
 
 	@Override
 	protected boolean canEditReportAccessEmail() {
-		return secCallback.canEditReportAccessEmail(generator);
+		return secCallback.canEditReportAccessEmail();
 	}
 
 	@Override
 	protected boolean canEditReportMembers() {
-		return secCallback.canEditReportAccessMembers(generator);
+		return secCallback.canEditReportAccessMembers();
 	}
 
 }
diff --git a/src/main/java/org/olat/modules/quality/ui/ParticipationListController.java b/src/main/java/org/olat/modules/quality/ui/ParticipationListController.java
index d231f1af413..7e875038a02 100644
--- a/src/main/java/org/olat/modules/quality/ui/ParticipationListController.java
+++ b/src/main/java/org/olat/modules/quality/ui/ParticipationListController.java
@@ -56,9 +56,9 @@ import org.olat.modules.curriculum.CurriculumService;
 import org.olat.modules.forms.EvaluationFormParticipation;
 import org.olat.modules.quality.QualityContextRef;
 import org.olat.modules.quality.QualityDataCollection;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
 import org.olat.modules.quality.ui.ParticipationDataModel.ParticipationCols;
+import org.olat.modules.quality.ui.security.DataCollectionSecurityCallback;
 import org.olat.modules.quality.ui.wizard.AddCourseUser_1_ChooseCourseStep;
 import org.olat.modules.quality.ui.wizard.AddCurriculumElementUser_1_ChooseCurriculumElementStep;
 import org.olat.modules.quality.ui.wizard.AddUser_1_ChooseUserStep;
@@ -91,7 +91,7 @@ public class ParticipationListController extends FormBasicController implements
 	private ParticipationRemoveConfirmationController removeConfirmationCtrl;
 	
 	private final TooledStackedPanel stackPanel;
-	private final QualitySecurityCallback secCallback;
+	private DataCollectionSecurityCallback secCallback;
 	private QualityDataCollection dataCollection;
 	
 	@Autowired
@@ -104,7 +104,7 @@ public class ParticipationListController extends FormBasicController implements
 	private CurriculumService curriculumService;
 
 	public ParticipationListController(UserRequest ureq, WindowControl windowControl,
-			QualitySecurityCallback secCallback, TooledStackedPanel stackPanel,
+			DataCollectionSecurityCallback secCallback, TooledStackedPanel stackPanel,
 			QualityDataCollection dataCollection) {
 		super(ureq, windowControl, LAYOUT_BAREBONE);
 		this.secCallback = secCallback;
@@ -118,10 +118,11 @@ public class ParticipationListController extends FormBasicController implements
 		initTable(ureq);
 	}
 	
-	public void setDataCollection(QualityDataCollection dataCollection, UserRequest ureq) {
+	public void onChanged(QualityDataCollection dataCollection, DataCollectionSecurityCallback secCallback, UserRequest ureq) {
 		this.dataCollection = dataCollection;
-//		initTools();
+		this.secCallback = secCallback;
 		initTable(ureq);
+		initTools();
 	}
 
 	private void initTable(UserRequest ureq) {
@@ -139,13 +140,13 @@ public class ParticipationListController extends FormBasicController implements
 		tableEl = uifactory.addTableElement(getWindowControl(), "participations", dataModel, 25, true, getTranslator(), flc);
 		tableEl.setAndLoadPersistedPreferences(ureq, "quality-participations");
 		tableEl.setEmtpyTableMessageKey("participation.empty.table");
-		if (secCallback.canRevomeParticipation(dataCollection)) {
+		if (secCallback.canRevomeParticipation()) {
 			tableEl.setMultiSelect(true);
 			tableEl.setSelectAllEnable(true);
 		}
 		
 		if (buttons != null) flc.remove(buttons);
-		if (secCallback.canRevomeParticipation(dataCollection)) {
+		if (secCallback.canRevomeParticipation()) {
 			buttons = FormLayoutContainer.createButtonLayout("buttons", getTranslator());
 			flc.add("buttons", buttons);
 			buttons.setElementCssClass("o_button_group");
@@ -155,7 +156,10 @@ public class ParticipationListController extends FormBasicController implements
 
 	@Override
 	public void initTools() {
-		if (secCallback.canAddParticipants(dataCollection)) {
+		stackPanel.removeTool(addCourseUsersLink);
+		stackPanel.removeTool(addCurriculumElementUsersLink);
+		stackPanel.removeTool(addUsersLink);
+		if (secCallback.canAddParticipants()) {
 			addCourseUsersLink = LinkFactory.createToolLink("participation.user.add.course", translate("participation.user.add.course"), this);
 			addCourseUsersLink.setIconLeftCSS("o_icon o_icon-lg o_icon_qual_part_user_add_course");
 			stackPanel.addTool(addCourseUsersLink, Align.right);
diff --git a/src/main/java/org/olat/modules/quality/ui/QualityHomeController.java b/src/main/java/org/olat/modules/quality/ui/QualityHomeController.java
index 42fad0a1030..11e635a809f 100644
--- a/src/main/java/org/olat/modules/quality/ui/QualityHomeController.java
+++ b/src/main/java/org/olat/modules/quality/ui/QualityHomeController.java
@@ -41,12 +41,12 @@ import org.olat.core.id.context.BusinessControlFactory;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
 import org.olat.core.util.resource.OresHelper;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.analysis.AnalysisPresentation;
 import org.olat.modules.quality.analysis.AnalysisPresentationSearchParameter;
 import org.olat.modules.quality.analysis.QualityAnalysisService;
 import org.olat.modules.quality.analysis.ui.AnalysisListController;
 import org.olat.modules.quality.generator.ui.GeneratorListController;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -78,14 +78,14 @@ public class QualityHomeController extends BasicController implements Activateab
 	private GeneratorListController generatorsListCtrl;
 	private AnalysisListController analysisListCtrl;
 	
-	private final QualitySecurityCallback secCallback;
+	private final MainSecurityCallback secCallback;
 	
 	@Autowired
 	private QualityAnalysisService analysisService;
 	@Autowired
 	private OrganisationService organisationService;
 	
-	public QualityHomeController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel, QualitySecurityCallback secCallback) {
+	public QualityHomeController(UserRequest ureq, WindowControl wControl, TooledStackedPanel stackPanel, MainSecurityCallback secCallback) {
 		super(ureq, wControl);
 		this.stackPanel = stackPanel;
 		this.stackPanel.setToolbarAutoEnabled(true);
diff --git a/src/main/java/org/olat/modules/quality/ui/QualityMainController.java b/src/main/java/org/olat/modules/quality/ui/QualityMainController.java
index 06209987660..60e5bc0a481 100644
--- a/src/main/java/org/olat/modules/quality/ui/QualityMainController.java
+++ b/src/main/java/org/olat/modules/quality/ui/QualityMainController.java
@@ -32,7 +32,8 @@ import org.olat.core.id.OLATResourceable;
 import org.olat.core.id.context.ContextEntry;
 import org.olat.core.id.context.StateEntry;
 import org.olat.core.util.resource.OresHelper;
-import org.olat.modules.quality.QualitySecurityCallback;
+import org.olat.modules.quality.ui.security.MainSecurityCallback;
+import org.olat.modules.quality.ui.security.QualitySecurityCallbackFactory;
 
 /**
  * 
@@ -49,8 +50,7 @@ public class QualityMainController extends MainLayoutBasicController implements
 	
 	public QualityMainController(UserRequest ureq, WindowControl wControl) {
 		super(ureq, wControl);
-		QualitySecurityCallback secCallback = new QualitySecurityCallbackImpl(getIdentity(),
-				ureq.getUserSession().getRoles());
+		MainSecurityCallback secCallback = QualitySecurityCallbackFactory.createMainSecurityCallback(ureq.getUserSession().getRoles(), getIdentity());
 		
 		stackPanel = new TooledStackedPanel("qualitiy.management", getTranslator(), this);
 		stackPanel.setToolbarAutoEnabled(true);
diff --git a/src/main/java/org/olat/modules/quality/ui/QualitySecurityCallbackImpl.java b/src/main/java/org/olat/modules/quality/ui/QualitySecurityCallbackImpl.java
deleted file mode 100644
index 33e56bf80da..00000000000
--- a/src/main/java/org/olat/modules/quality/ui/QualitySecurityCallbackImpl.java
+++ /dev/null
@@ -1,303 +0,0 @@
-/**
- * <a href="http://www.openolat.org">
- * OpenOLAT - Online Learning and Training</a><br>
- * <p>
- * Licensed under the Apache License, Version 2.0 (the "License"); <br>
- * you may not use this file except in compliance with the License.<br>
- * You may obtain a copy of the License at the
- * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
- * <p>
- * Unless required by applicable law or agreed to in writing,<br>
- * software distributed under the License is distributed on an "AS IS" BASIS, <br>
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
- * See the License for the specific language governing permissions and <br>
- * limitations under the License.
- * <p>
- * Initial code contributed and copyrighted by<br>
- * frentix GmbH, http://www.frentix.com
- * <p>
- */
-package org.olat.modules.quality.ui;
-
-import static org.olat.modules.quality.QualityDataCollectionStatus.FINISHED;
-import static org.olat.modules.quality.QualityDataCollectionStatus.PREPARATION;
-import static org.olat.modules.quality.QualityDataCollectionStatus.READY;
-
-import org.olat.basesecurity.IdentityRef;
-import org.olat.basesecurity.OrganisationRoles;
-import org.olat.core.CoreSpringFactory;
-import org.olat.core.id.Roles;
-import org.olat.modules.quality.QualityDataCollection;
-import org.olat.modules.quality.QualityDataCollectionLight;
-import org.olat.modules.quality.QualityDataCollectionStatus;
-import org.olat.modules.quality.QualityDataCollectionViewSearchParams;
-import org.olat.modules.quality.QualityExecutorParticipation;
-import org.olat.modules.quality.QualityExecutorParticipationStatus;
-import org.olat.modules.quality.QualityModule;
-import org.olat.modules.quality.QualityReminder;
-import org.olat.modules.quality.QualitySecurityCallback;
-import org.olat.modules.quality.QualityService;
-import org.olat.modules.quality.analysis.AnalysisPresentation;
-import org.olat.modules.quality.generator.QualityGenerator;
-import org.springframework.beans.factory.annotation.Autowired;
-
-/**
- * 
- * Initial date: 08.06.2018<br>
- * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
- *
- */
-public class QualitySecurityCallbackImpl implements QualitySecurityCallback {
-
-	private final Roles roles;
-	private final QualityDataCollectionViewSearchParams reportAccessParams;
-	private boolean canViewDataCollections;
-	
-	@Autowired
-	private QualityModule qualityModule;
-	@Autowired
-	private QualityService qualityService;
-
-	public QualitySecurityCallbackImpl(IdentityRef identityRef, Roles roles) {
-		this.roles = roles;
-		CoreSpringFactory.autowireObject(this);
-		
-		reportAccessParams = new QualityDataCollectionViewSearchParams();
-		reportAccessParams.setReportAccessIdentity(identityRef);
-	}
-
-	@Override
-	public boolean canCreateSuggestion() {
-		return qualityModule.isSuggestionEnabled();
-	}
-
-	@Override
-	public boolean canViewDataCollections() {
-		if (!canViewDataCollections) {
-			// Check if the user has access gained in the meantime, e.g because he has now report access
-			canViewDataCollections = canEditDataCollections() || roles.isPrincipal() || hasReportAccess();
-		}
-		return canViewDataCollections;
-	}
-
-	private boolean hasReportAccess() {
-		return qualityService.getDataCollectionCount(reportAccessParams) > 0;
-	}
-
-	@Override
-	public OrganisationRoles[] getViewDataCollectionRoles() {
-		return new OrganisationRoles[] { 
-				OrganisationRoles.qualitymanager,
-				OrganisationRoles.administrator,
-				OrganisationRoles.principal 
-			};
-	}
-
-	@Override
-	public boolean canEditDataCollections() {
-		return roles.isQualityManager() || roles.isAdministrator();
-	}
-
-	@Override
-	public boolean canCreateDataCollections() {
-		return canEditDataCollections();
-	}
-
-	@Override
-	public boolean canViewDataCollectionConfigurations() {
-		return canEditDataCollections() || roles.isPrincipal();
-	}
-	
-	@Override
-	public boolean canUpdateBaseConfiguration(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && PREPARATION.equals(dataCollection.getStatus());
-	}
-
-	@Override
-	public boolean canSetPreparation(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && READY.equals(dataCollection.getStatus());
-	}
-
-	@Override
-	public boolean canSetReady(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && PREPARATION.equals(dataCollection.getStatus());
-	}
-
-	@Override
-	public boolean canSetRunning(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && isNotRunning(dataCollection);
-	}
-
-	@Override
-	public boolean canSetFinished(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && isNotFinished(dataCollection);
-	}
-
-	@Override
-	public boolean canDeleteDataCollections() {
-		return canEditDataCollections();
-	}
-
-	@Override
-	public boolean canDeleteDataCollection(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && isNotRunning(dataCollection);
-	}
-
-	@Override
-	public boolean canAddParticipants(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && isNotFinished(dataCollection);
-	}
-
-	@Override
-	public boolean canRevomeParticipation(QualityDataCollectionLight dataCollection) {
-		return canEditDataCollections() && isNotRunning(dataCollection);
-	}
-
-	@Override
-	public boolean canEditReminders() {
-		return canEditDataCollections();
-	}
-
-	@Override
-	public boolean canEditReminder(QualityDataCollectionLight dataCollection, QualityReminder reminder) {
-		return canEditReminders() && isNotSent(reminder) && isNotFinished(dataCollection);
-	}
-
-	private boolean isNotSent(QualityReminder reminder) {
-		return reminder == null || !reminder.isSent();
-	}
-
-	@Override
-	public boolean canEditReportAccessOnline(QualityDataCollection dataCollection) {
-		return canEditDataCollections();
-	}
-	
-	@Override
-	public boolean canEditReportAccessEmail(QualityDataCollection dataCollection) {
-		return canEditDataCollections() && isNotFinished(dataCollection);
-	}
-
-	@Override
-	public boolean canEditReportAccessMembers(QualityDataCollection dataCollection) {
-		return canEditDataCollections();
-	}
-
-	@Override
-	public boolean canViewReports() {
-		return canViewDataCollections;
-	}
-
-	@Override
-	public boolean canViewReport(QualityDataCollectionLight dataCollection) {
-		return canViewReports() && isRunning(dataCollection);
-	}
-
-	@Override
-	public boolean canExecute(QualityExecutorParticipation participation) {
-		QualityExecutorParticipationStatus status = participation.getExecutionStatus();
-		return QualityExecutorParticipationStatus.READY.equals(status)
-				|| QualityExecutorParticipationStatus.PARTICIPATING.equals(status);
-	}
-
-	private boolean isRunning(QualityDataCollectionLight dataCollection) {
-		return !isNotRunning(dataCollection);
-	}
-	
-	private boolean isNotRunning(QualityDataCollectionLight dataCollection) {
-		QualityDataCollectionStatus status = dataCollection.getStatus();
-		return PREPARATION.equals(status) || READY.equals(status);
-	}
-
-	private boolean isNotFinished(QualityDataCollectionLight dataCollection) {
-		return !FINISHED.equals(dataCollection.getStatus());
-	}
-
-	@Override
-	public boolean canViewGenerators() {
-		return roles.isQualityManager() || roles.isAdministrator() || roles.isPrincipal();
-	}
-
-	@Override
-	public boolean canCreateGenerators() {
-		return canEditGenerators();
-	}
-
-	@Override
-	public boolean canEditGenerators() {
-		return canEditDataCollections();
-	}
-
-	@Override
-	public boolean canEditGenerator(QualityGenerator generator) {
-		return canEditGenerators() && !generator.isEnabled();
-	}
-
-	@Override
-	public boolean canEditGeneratorForm(QualityGenerator generator, Long numOfDataCollections) {
-		return canEditGenerator(generator) && numOfDataCollections < 1;
-	}
-
-	@Override
-	public boolean canEditReportAccessOnline(QualityGenerator generator) {
-		return canEditGenerator(generator);
-	}
-
-	@Override
-	public boolean canEditReportAccessEmail(QualityGenerator generator) {
-		return canEditGenerator(generator);
-	}
-
-	@Override
-	public boolean canEditReportAccessMembers(QualityGenerator generator) {
-		return canEditGenerator(generator);
-	}
-
-	@Override
-	public boolean canActivateGenerators() {
-		return canEditGenerators();
-	}
-
-	@Override
-	public boolean canDeleteGenerators() {
-		return canEditGenerators();
-	}
-
-	@Override
-	public boolean canDeleteGenerator(long numberDataCollections) {
-		return canDeleteGenerators() && numberDataCollections < 1;
-	}
-
-	@Override
-	public boolean canViewAnalysis() {
-		return roles.isQualityManager() || roles.isAdministrator() || roles.isPrincipal();
-	}
-
-	@Override
-	public OrganisationRoles[] getViewAnalysisRoles() {
-		return new OrganisationRoles[] { 
-				OrganisationRoles.qualitymanager,
-				OrganisationRoles.administrator,
-				OrganisationRoles.principal 
-			};
-	}
-
-	@Override
-	public OrganisationRoles[] getViewPresentationRoles() {
-		return new OrganisationRoles[] { 
-				OrganisationRoles.qualitymanager,
-				OrganisationRoles.administrator,
-				OrganisationRoles.principal 
-			};
-	}
-
-	@Override
-	public boolean canEditPresentations() {
-		return roles.isQualityManager() || roles.isAdministrator();
-	}
-
-	@Override
-	public boolean canDeletePresentation(AnalysisPresentation presentation) {
-		return canEditPresentations() && presentation.getKey() != null;
-	}
-
-}
diff --git a/src/main/java/org/olat/modules/quality/ui/RemindersController.java b/src/main/java/org/olat/modules/quality/ui/RemindersController.java
index 13f543839f6..61c570b6e84 100644
--- a/src/main/java/org/olat/modules/quality/ui/RemindersController.java
+++ b/src/main/java/org/olat/modules/quality/ui/RemindersController.java
@@ -31,8 +31,8 @@ import org.olat.core.gui.control.WindowControl;
 import org.olat.modules.quality.QualityDataCollection;
 import org.olat.modules.quality.QualityReminder;
 import org.olat.modules.quality.QualityReminderType;
-import org.olat.modules.quality.QualitySecurityCallback;
 import org.olat.modules.quality.QualityService;
+import org.olat.modules.quality.ui.security.DataCollectionSecurityCallback;
 import org.springframework.beans.factory.annotation.Autowired;
 
 /**
@@ -48,7 +48,7 @@ public class RemindersController extends FormBasicController {
 	private DateChooser reminder2El;
 	private FormLayoutContainer buttonLayout;
 	
-	private final QualitySecurityCallback secCallback;
+	private DataCollectionSecurityCallback secCallback;
 	private QualityDataCollection dataCollection;
 	
 	private QualityReminder invitation;
@@ -58,7 +58,7 @@ public class RemindersController extends FormBasicController {
 	@Autowired
 	private QualityService qualityService;
 
-	public RemindersController(UserRequest ureq, WindowControl wControl, QualitySecurityCallback secCallback,
+	public RemindersController(UserRequest ureq, WindowControl wControl, DataCollectionSecurityCallback secCallback,
 			QualityDataCollection dataCollection) {
 		super(ureq, wControl);
 		this.secCallback = secCallback;
@@ -89,17 +89,18 @@ public class RemindersController extends FormBasicController {
 		updateUI();
 	}
 
-	protected void setDataCollection(QualityDataCollection dataCollection) {
+	protected void onChanged(QualityDataCollection dataCollection, DataCollectionSecurityCallback secCallback) {
 		this.dataCollection = dataCollection;
+		this.secCallback = secCallback;
 		updateUI();
 	}
 	
 	private void updateUI() {
-		boolean canEditInvitation = secCallback.canEditReminder(dataCollection, invitation);
+		boolean canEditInvitation = secCallback.canEditReminder(invitation);
 		invitationEl.setEnabled(canEditInvitation);
-		boolean canEditReminder1 = secCallback.canEditReminder(dataCollection, reminder1);
+		boolean canEditReminder1 = secCallback.canEditReminder(reminder1);
 		reminder1El.setEnabled(canEditReminder1);
-		boolean canEditReminder2 = secCallback.canEditReminder(dataCollection, reminder2);
+		boolean canEditReminder2 = secCallback.canEditReminder(reminder2);
 		reminder2El.setEnabled(canEditReminder2);
 		buttonLayout.setVisible(canEditInvitation || canEditReminder1 || canEditReminder2);
 	}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/DataCollectionReadOnlySecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionReadOnlySecurityCallback.java
new file mode 100644
index 00000000000..3e826c60b56
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionReadOnlySecurityCallback.java
@@ -0,0 +1,102 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import org.olat.modules.quality.QualityReminder;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+class DataCollectionReadOnlySecurityCallback implements DataCollectionSecurityCallback {
+
+	@Override
+	public boolean canViewDataCollectionConfigurations() {
+		return true;
+	}
+
+	@Override
+	public boolean canUpdateBaseConfiguration() {
+		return false;
+	}
+
+	@Override
+	public boolean canSetPreparation() {
+		return false;
+	}
+
+	@Override
+	public boolean canSetReady() {
+		return false;
+	}
+
+	@Override
+	public boolean canSetRunning() {
+		return false;
+	}
+
+	@Override
+	public boolean canSetFinished() {
+		return false;
+	}
+
+	@Override
+	public boolean canDeleteDataCollection() {
+		return false;
+	}
+
+	@Override
+	public boolean canAddParticipants() {
+		return false;
+	}
+
+	@Override
+	public boolean canRevomeParticipation() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReminder(QualityReminder reminder) {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessOnline() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessEmail() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessMembers() {
+		return false;
+	}
+
+	@Override
+	public boolean canViewReport() {
+		return true;
+	}
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/DataCollectionSecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionSecurityCallback.java
new file mode 100644
index 00000000000..8dd3d984191
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionSecurityCallback.java
@@ -0,0 +1,60 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import org.olat.modules.quality.QualityReminder;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+public interface DataCollectionSecurityCallback {
+	
+	public boolean canViewDataCollectionConfigurations();
+	
+	public boolean canUpdateBaseConfiguration();
+	
+	public boolean canSetPreparation();
+	
+	public boolean canSetReady();
+	
+	public boolean canSetRunning();
+	
+	public boolean canSetFinished();
+	
+	public boolean canDeleteDataCollection();
+	
+	public boolean canAddParticipants();
+	
+	public boolean canRevomeParticipation();
+
+	public boolean canEditReminder(QualityReminder reminder);
+	
+	public boolean canEditReportAccessOnline();
+	
+	public boolean canEditReportAccessEmail();
+
+	public boolean canEditReportAccessMembers();
+
+	public boolean canViewReport();
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/DataCollectionStatusSecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionStatusSecurityCallback.java
new file mode 100644
index 00000000000..1f337193de5
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/DataCollectionStatusSecurityCallback.java
@@ -0,0 +1,129 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import static org.olat.modules.quality.QualityDataCollectionStatus.FINISHED;
+import static org.olat.modules.quality.QualityDataCollectionStatus.PREPARATION;
+import static org.olat.modules.quality.QualityDataCollectionStatus.READY;
+
+import org.olat.modules.quality.QualityDataCollectionStatus;
+import org.olat.modules.quality.QualityReminder;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+class DataCollectionStatusSecurityCallback implements DataCollectionSecurityCallback {
+
+	private final QualityDataCollectionStatus status;
+
+	public DataCollectionStatusSecurityCallback(QualityDataCollectionStatus status) {
+		this.status = status;
+	}
+
+	@Override
+	public boolean canViewDataCollectionConfigurations() {
+		return true;
+	}
+	
+	@Override
+	public boolean canUpdateBaseConfiguration() {
+		return PREPARATION.equals(status);
+	}
+
+	@Override
+	public boolean canSetPreparation() {
+		return READY.equals(status);
+	}
+
+	@Override
+	public boolean canSetReady() {
+		return PREPARATION.equals(status);
+	}
+
+	@Override
+	public boolean canSetRunning() {
+		return isNotRunning();
+	}
+
+	@Override
+	public boolean canSetFinished() {
+		return isNotFinished();
+	}
+
+	@Override
+	public boolean canDeleteDataCollection() {
+		return isNotRunning();
+	}
+
+	@Override
+	public boolean canAddParticipants() {
+		return isNotFinished();
+	}
+
+	@Override
+	public boolean canRevomeParticipation() {
+		return isNotRunning();
+	}
+
+	@Override
+	public boolean canEditReminder(QualityReminder reminder) {
+		return isNotFinished() && isNotSent(reminder);
+	}
+
+	private boolean isNotSent(QualityReminder reminder) {
+		return reminder == null || !reminder.isSent();
+	}
+
+	@Override
+	public boolean canEditReportAccessOnline() {
+		return true;
+	}
+	
+	@Override
+	public boolean canEditReportAccessEmail() {
+		return isNotFinished();
+	}
+
+	@Override
+	public boolean canEditReportAccessMembers() {
+		return true;
+	}
+
+	@Override
+	public boolean canViewReport() {
+		return isRunning();
+	}
+
+	private boolean isRunning() {
+		return !isNotRunning();
+	}
+	
+	private boolean isNotRunning() {
+		return PREPARATION.equals(status) || READY.equals(status);
+	}
+
+	private boolean isNotFinished() {
+		return !FINISHED.equals(status);
+	}
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/GeneratorReadOnlySecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/GeneratorReadOnlySecurityCallback.java
new file mode 100644
index 00000000000..9238e6a6427
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/GeneratorReadOnlySecurityCallback.java
@@ -0,0 +1,65 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+class GeneratorReadOnlySecurityCallback implements GeneratorSecurityCallback {
+
+	@Override
+	public boolean canEditGenerator() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditGeneratorForm(long numOfDataCollections) {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessOnline() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessEmail() {
+		return false;
+	}
+
+	@Override
+	public boolean canEditReportAccessMembers() {
+		return false;
+	}
+
+	@Override
+	public boolean canActivateGenerators() {
+		return false;
+	}
+
+	@Override
+	public boolean canDeleteGenerator(long numberDataCollections) {
+		return false;
+	}
+
+}
diff --git a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorChangedController.java b/src/main/java/org/olat/modules/quality/ui/security/GeneratorSecurityCallback.java
similarity index 65%
rename from src/main/java/org/olat/modules/quality/generator/ui/GeneratorChangedController.java
rename to src/main/java/org/olat/modules/quality/ui/security/GeneratorSecurityCallback.java
index a6ffe60c64f..a2b431f99ee 100644
--- a/src/main/java/org/olat/modules/quality/generator/ui/GeneratorChangedController.java
+++ b/src/main/java/org/olat/modules/quality/ui/security/GeneratorSecurityCallback.java
@@ -17,19 +17,28 @@
  * frentix GmbH, http://www.frentix.com
  * <p>
  */
-package org.olat.modules.quality.generator.ui;
-
-import org.olat.core.gui.UserRequest;
-import org.olat.modules.quality.generator.QualityGenerator;
+package org.olat.modules.quality.ui.security;
 
 /**
  * 
- * Initial date: 03.11.2018<br>
+ * Initial date: 14 Nov 2018<br>
  * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
  *
  */
-public interface GeneratorChangedController {
+public interface GeneratorSecurityCallback {
+
+	public boolean canEditGenerator();
+
+	public boolean canEditGeneratorForm(long numOfDataCollections);
+	
+	public boolean canEditReportAccessOnline();
 	
-	public void onChanged(QualityGenerator generator, UserRequest ureq);
+	public boolean canEditReportAccessEmail();
 
+	public boolean canEditReportAccessMembers();
+
+	public boolean canActivateGenerators();
+
+	public boolean canDeleteGenerator(long numberDataCollections);
+	
 }
diff --git a/src/main/java/org/olat/modules/quality/ui/security/GeneratorStatusSecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/GeneratorStatusSecurityCallback.java
new file mode 100644
index 00000000000..a0cf2f933eb
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/GeneratorStatusSecurityCallback.java
@@ -0,0 +1,71 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+class GeneratorStatusSecurityCallback implements GeneratorSecurityCallback {
+
+	private boolean enabled;
+
+	public GeneratorStatusSecurityCallback(Boolean enabled) {
+		this.enabled = enabled.booleanValue();
+	}
+
+	@Override
+	public boolean canEditGenerator() {
+		return !enabled;
+	}
+
+	@Override
+	public boolean canEditGeneratorForm(long numOfDataCollections) {
+		return canEditGenerator() && numOfDataCollections < 1;
+	}
+
+	@Override
+	public boolean canEditReportAccessOnline() {
+		return canEditGenerator();
+	}
+
+	@Override
+	public boolean canEditReportAccessEmail() {
+		return canEditGenerator();
+	}
+
+	@Override
+	public boolean canEditReportAccessMembers() {
+		return canEditGenerator();
+	}
+
+	@Override
+	public boolean canActivateGenerators() {
+		return true;
+	}
+
+	@Override
+	public boolean canDeleteGenerator(long numberDataCollections) {
+		return numberDataCollections < 1;
+	}
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallback.java b/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallback.java
new file mode 100644
index 00000000000..ef659f4d019
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallback.java
@@ -0,0 +1,58 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import org.olat.basesecurity.OrganisationRoles;
+import org.olat.modules.quality.QualityExecutorParticipation;
+import org.olat.modules.quality.analysis.AnalysisPresentation;
+
+/**
+ * 
+ * Initial date: 08.06.2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+public interface MainSecurityCallback {
+
+	public boolean canCreateSuggestion();
+
+	public boolean canExecute(QualityExecutorParticipation participation);
+
+	public boolean canViewDataCollections();
+	
+	public OrganisationRoles[] getViewDataCollectionRoles();
+	
+	public boolean canCreateDataCollections();
+	
+	public boolean canViewGenerators();
+	
+	public boolean canCreateGenerators();
+
+	public boolean canViewAnalysis();
+	
+	public OrganisationRoles[] getViewAnalysisRoles();
+	
+	public OrganisationRoles[] getViewPresentationRoles();
+	
+	public boolean canEditPresentations();
+
+	public boolean canDeletePresentation(AnalysisPresentation presentation);
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallbackImpl.java b/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallbackImpl.java
new file mode 100644
index 00000000000..2f6e84140dd
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/MainSecurityCallbackImpl.java
@@ -0,0 +1,132 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import org.olat.basesecurity.IdentityRef;
+import org.olat.basesecurity.OrganisationRoles;
+import org.olat.core.CoreSpringFactory;
+import org.olat.modules.quality.QualityDataCollectionViewSearchParams;
+import org.olat.modules.quality.QualityExecutorParticipation;
+import org.olat.modules.quality.QualityExecutorParticipationStatus;
+import org.olat.modules.quality.QualityModule;
+import org.olat.modules.quality.QualityService;
+import org.olat.modules.quality.analysis.AnalysisPresentation;
+import org.springframework.beans.factory.annotation.Autowired;
+
+/**
+ * 
+ * Initial date: 08.06.2018<br>
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+class MainSecurityCallbackImpl implements MainSecurityCallback {
+
+	private final boolean canView;
+	private final boolean canEdit;
+	private OrganisationRoles[] viewerRoles;
+	private final QualityDataCollectionViewSearchParams reportAccessParams;
+	private boolean canViewDataCollections;
+	
+	@Autowired
+	private QualityModule qualityModule;
+	@Autowired
+	private QualityService qualityService;
+
+	public MainSecurityCallbackImpl(IdentityRef identityRef, boolean canView, boolean canEdit, OrganisationRoles[] viewerRoles) {
+		this.canView = canView;
+		this.canEdit = canEdit;
+		this.viewerRoles = viewerRoles;
+		CoreSpringFactory.autowireObject(this);
+		
+		reportAccessParams = new QualityDataCollectionViewSearchParams();
+		reportAccessParams.setReportAccessIdentity(identityRef);
+	}
+
+	@Override
+	public boolean canCreateSuggestion() {
+		return qualityModule.isSuggestionEnabled();
+	}
+
+	@Override
+	public boolean canExecute(QualityExecutorParticipation participation) {
+		QualityExecutorParticipationStatus status = participation.getExecutionStatus();
+		return QualityExecutorParticipationStatus.READY.equals(status)
+				|| QualityExecutorParticipationStatus.PARTICIPATING.equals(status);
+	}
+
+	@Override
+	public boolean canViewDataCollections() {
+		if (!canViewDataCollections) {
+			// Check if the user has access gained in the meantime, e.g because he has now report access
+			canViewDataCollections = canView || hasReportAccess();
+		}
+		return canViewDataCollections;
+	}
+
+	private boolean hasReportAccess() {
+		return qualityService.getDataCollectionCount(reportAccessParams) > 0;
+	}
+
+	@Override
+	public OrganisationRoles[] getViewDataCollectionRoles() {
+		return viewerRoles;
+	}
+
+	@Override
+	public boolean canCreateDataCollections() {
+		return canEdit;
+	}
+	
+	@Override
+	public boolean canViewGenerators() {
+		return canCreateDataCollections();
+	}
+
+	@Override
+	public boolean canCreateGenerators() {
+		return canCreateDataCollections();
+	}
+
+	@Override
+	public boolean canViewAnalysis() {
+		return canView;
+	}
+
+	@Override
+	public OrganisationRoles[] getViewAnalysisRoles() {
+		return viewerRoles;
+	}
+
+	@Override
+	public OrganisationRoles[] getViewPresentationRoles() {
+		return viewerRoles;
+	}
+
+	@Override
+	public boolean canEditPresentations() {
+		return canEdit;
+	}
+
+	@Override
+	public boolean canDeletePresentation(AnalysisPresentation presentation) {
+		return canEditPresentations() && presentation.getKey() != null;
+	}
+
+}
diff --git a/src/main/java/org/olat/modules/quality/ui/security/QualitySecurityCallbackFactory.java b/src/main/java/org/olat/modules/quality/ui/security/QualitySecurityCallbackFactory.java
new file mode 100644
index 00000000000..591647a5d49
--- /dev/null
+++ b/src/main/java/org/olat/modules/quality/ui/security/QualitySecurityCallbackFactory.java
@@ -0,0 +1,77 @@
+/**
+ * <a href="http://www.openolat.org">
+ * OpenOLAT - Online Learning and Training</a><br>
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); <br>
+ * you may not use this file except in compliance with the License.<br>
+ * You may obtain a copy of the License at the
+ * <a href="http://www.apache.org/licenses/LICENSE-2.0">Apache homepage</a>
+ * <p>
+ * Unless required by applicable law or agreed to in writing,<br>
+ * software distributed under the License is distributed on an "AS IS" BASIS, <br>
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. <br>
+ * See the License for the specific language governing permissions and <br>
+ * limitations under the License.
+ * <p>
+ * Initial code contributed and copyrighted by<br>
+ * frentix GmbH, http://www.frentix.com
+ * <p>
+ */
+package org.olat.modules.quality.ui.security;
+
+import java.util.Collection;
+
+import org.olat.basesecurity.IdentityRef;
+import org.olat.basesecurity.OrganisationRoles;
+import org.olat.core.id.OrganisationRef;
+import org.olat.core.id.Roles;
+import org.olat.modules.quality.QualityDataCollectionLight;
+import org.olat.modules.quality.generator.QualityGenerator;
+
+/**
+ * 
+ * Initial date: 14 Nov 2018<br>
+ * 
+ * @author uhensler, urs.hensler@frentix.com, http://www.frentix.com
+ *
+ */
+public class QualitySecurityCallbackFactory {
+
+	private static final DataCollectionReadOnlySecurityCallback DATA_COLLECTION_READ_ONLY_SECURITY_CALLBACK = new DataCollectionReadOnlySecurityCallback();
+	private static final GeneratorReadOnlySecurityCallback GENERATOR_READ_ONLY_SECURITY_CALLBACK = new GeneratorReadOnlySecurityCallback();
+	private static final OrganisationRoles[] QUALITY_MANAGER_ROLES = new OrganisationRoles[] {
+			OrganisationRoles.qualitymanager, OrganisationRoles.administrator };
+	private static final OrganisationRoles[] QUALITY_VIEWER_ROLES = new OrganisationRoles[] {
+			OrganisationRoles.qualitymanager, OrganisationRoles.administrator, OrganisationRoles.principal };
+
+	public static MainSecurityCallback createMainSecurityCallback(Roles roles, IdentityRef identityRef) {
+		boolean canEdit = roles.isAdministrator() || roles.isQualityManager();
+		boolean canView = canEdit || roles.isPrincipal();
+		return new MainSecurityCallbackImpl(identityRef, canView, canEdit, QUALITY_VIEWER_ROLES);
+	}
+	
+	public static DataCollectionSecurityCallback createDataCollectionSecurityCallback(Roles roles,
+			QualityDataCollectionLight dataCollection, Collection<? extends OrganisationRef> organisationRefs) {
+		if (isQualityManager(roles, organisationRefs)) {
+			return new DataCollectionStatusSecurityCallback(dataCollection.getStatus());
+		}
+		return DATA_COLLECTION_READ_ONLY_SECURITY_CALLBACK;
+	}
+	
+	public static GeneratorSecurityCallback createGeneratorSecurityCallback(Roles roles, QualityGenerator generator,
+			Collection<? extends OrganisationRef> organisationRefs) {
+		if (isQualityManager(roles, organisationRefs)) {
+			return new GeneratorStatusSecurityCallback(generator.isEnabled());
+		}
+		return GENERATOR_READ_ONLY_SECURITY_CALLBACK;
+	}
+
+	private static boolean isQualityManager(Roles roles, Collection<? extends OrganisationRef> organisationRefs) {
+		for (OrganisationRef organisationRef : organisationRefs) {
+			if (roles.hasSomeRoles(organisationRef, QUALITY_MANAGER_ROLES)) {
+				return true;
+			}
+		}
+		return false;
+	}
+}
-- 
GitLab