Skip to content
Snippets Groups Projects
Commit 01750970 authored by srosse's avatar srosse
Browse files

OO-2451: add configuration for a bcc to send a copy of the certificate

parent ea990c82
No related branches found
No related tags found
No related merge requests found
Showing
with 534 additions and 175 deletions
...@@ -64,6 +64,10 @@ public class ContactList extends LogDelegator { ...@@ -64,6 +64,10 @@ public class ContactList extends LogDelegator {
private Map<String, Identity> identiEmails = new HashMap<String, Identity>(); private Map<String, Identity> identiEmails = new HashMap<String, Identity>();
private boolean emailPrioInstitutional = false; private boolean emailPrioInstitutional = false;
public ContactList() {
//
}
/** /**
* A ContacList must have at least a name != null, matching ^[^;,:]*$ * A ContacList must have at least a name != null, matching ^[^;,:]*$
* *
...@@ -71,7 +75,6 @@ public class ContactList extends LogDelegator { ...@@ -71,7 +75,6 @@ public class ContactList extends LogDelegator {
*/ */
public ContactList(String name) { public ContactList(String name) {
setName(name); setName(name);
this.description = null;
} }
/** /**
......
/**
* <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.course.certificate;
import java.util.ArrayList;
import java.util.List;
import org.olat.core.configuration.AbstractSpringModule;
import org.olat.core.util.StringHelper;
import org.olat.core.util.coordinate.CoordinatorManager;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
/**
*
* Initial date: 31 janv. 2017<br>
* @author srosse, stephane.rosse@frentix.com, http://www.frentix.com
*
*/
@Service
public class CertificatesModule extends AbstractSpringModule {
private static final String CERTIFICATE_BCC = "certificate.bcc";
@Value("${certificate.bcc}")
private String certificateBcc;
@Autowired
public CertificatesModule(CoordinatorManager coordinatorManager) {
super(coordinatorManager);
}
@Override
public void init() {
String bccObj = getStringPropertyValue(CERTIFICATE_BCC, true);
if(StringHelper.containsNonWhitespace(bccObj)) {
certificateBcc = bccObj;
}
}
@Override
protected void initFromChangedProperties() {
init();
}
public String getCertificateBcc() {
return certificateBcc;
}
public void setCertificateBcc(String email) {
certificateBcc = email;
setStringProperty(CERTIFICATE_BCC, email, true);
}
public List<String> getCertificatesBccEmails() {
return splitEmails(certificateBcc);
}
public List<String> splitEmails(String emails) {
List<String> emailList = new ArrayList<>();
if(StringHelper.containsNonWhitespace(emails)) {
String[] emailArr = emails.split("[;,]");
for(String email:emailArr) {
emailList.add(email);
}
}
return emailList;
}
}
...@@ -74,6 +74,7 @@ import org.olat.core.util.Util; ...@@ -74,6 +74,7 @@ import org.olat.core.util.Util;
import org.olat.core.util.WebappHelper; import org.olat.core.util.WebappHelper;
import org.olat.core.util.coordinate.CoordinatorManager; import org.olat.core.util.coordinate.CoordinatorManager;
import org.olat.core.util.i18n.I18nManager; import org.olat.core.util.i18n.I18nManager;
import org.olat.core.util.mail.ContactList;
import org.olat.core.util.mail.MailBundle; import org.olat.core.util.mail.MailBundle;
import org.olat.core.util.mail.MailManager; import org.olat.core.util.mail.MailManager;
import org.olat.core.util.mail.MailerResult; import org.olat.core.util.mail.MailerResult;
...@@ -92,6 +93,7 @@ import org.olat.course.certificate.CertificateLight; ...@@ -92,6 +93,7 @@ import org.olat.course.certificate.CertificateLight;
import org.olat.course.certificate.CertificateStatus; import org.olat.course.certificate.CertificateStatus;
import org.olat.course.certificate.CertificateTemplate; import org.olat.course.certificate.CertificateTemplate;
import org.olat.course.certificate.CertificatesManager; import org.olat.course.certificate.CertificatesManager;
import org.olat.course.certificate.CertificatesModule;
import org.olat.course.certificate.EmailStatus; import org.olat.course.certificate.EmailStatus;
import org.olat.course.certificate.RecertificationTimeUnit; import org.olat.course.certificate.RecertificationTimeUnit;
import org.olat.course.certificate.model.CertificateImpl; import org.olat.course.certificate.model.CertificateImpl;
...@@ -160,6 +162,8 @@ public class CertificatesManagerImpl implements CertificatesManager, MessageList ...@@ -160,6 +162,8 @@ public class CertificatesManagerImpl implements CertificatesManager, MessageList
private NotificationsManager notificationsManager; private NotificationsManager notificationsManager;
@Autowired @Autowired
private FolderModule folderModule; private FolderModule folderModule;
@Autowired
private CertificatesModule certificatesModule;
@Resource(name="certificateQueue") @Resource(name="certificateQueue")
...@@ -935,6 +939,13 @@ public class CertificatesManagerImpl implements CertificatesManager, MessageList ...@@ -935,6 +939,13 @@ public class CertificatesManagerImpl implements CertificatesManager, MessageList
bundle.setToId(to); bundle.setToId(to);
bundle.setFrom(WebappHelper.getMailConfig("mailReplyTo")); bundle.setFrom(WebappHelper.getMailConfig("mailReplyTo"));
List<String> bccs = certificatesModule.getCertificatesBccEmails();
if(bccs.size() > 0) {
ContactList bcc = new ContactList();
bccs.forEach(email -> { bcc.add(email); });
bundle.setContactList(bcc);
}
String[] args = new String[] { String[] args = new String[] {
entry.getDisplayname(), entry.getDisplayname(),
userManager.getUserDisplayName(to) userManager.getUserDisplayName(to)
......
...@@ -19,200 +19,92 @@ ...@@ -19,200 +19,92 @@
*/ */
package org.olat.course.certificate.ui; package org.olat.course.certificate.ui;
import java.util.List;
import org.olat.core.gui.UserRequest; import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.form.flexible.FormItem; import org.olat.core.gui.components.Component;
import org.olat.core.gui.components.form.flexible.FormItemContainer;
import org.olat.core.gui.components.form.flexible.elements.FlexiTableElement;
import org.olat.core.gui.components.form.flexible.elements.FormLink;
import org.olat.core.gui.components.form.flexible.impl.FormBasicController;
import org.olat.core.gui.components.form.flexible.impl.FormEvent;
import org.olat.core.gui.components.form.flexible.impl.elements.table.DefaultFlexiColumnModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.DefaultFlexiTableDataModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableColumnModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableDataModelFactory;
import org.olat.core.gui.components.form.flexible.impl.elements.table.SelectionEvent;
import org.olat.core.gui.components.link.Link; import org.olat.core.gui.components.link.Link;
import org.olat.core.gui.control.Controller; import org.olat.core.gui.components.link.LinkFactory;
import org.olat.core.gui.components.segmentedview.SegmentViewComponent;
import org.olat.core.gui.components.segmentedview.SegmentViewEvent;
import org.olat.core.gui.components.segmentedview.SegmentViewFactory;
import org.olat.core.gui.components.velocity.VelocityContainer;
import org.olat.core.gui.control.Event; import org.olat.core.gui.control.Event;
import org.olat.core.gui.control.WindowControl; import org.olat.core.gui.control.WindowControl;
import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController; import org.olat.core.gui.control.controller.BasicController;
import org.olat.core.gui.control.generic.modal.DialogBoxController; import org.olat.core.id.OLATResourceable;
import org.olat.core.gui.control.generic.modal.DialogBoxUIFactory; import org.olat.core.id.context.BusinessControlFactory;
import org.olat.course.certificate.CertificateTemplate; import org.olat.core.util.resource.OresHelper;
import org.olat.course.certificate.CertificatesManager;
import org.springframework.beans.factory.annotation.Autowired;
/** /**
* *
* Initial date: 20.10.2014<br> * Initial date: 31 janv. 2017<br>
* @author srosse, stephane.rosse@frentix.com, http://www.frentix.com * @author srosse, stephane.rosse@frentix.com, http://www.frentix.com
* *
*/ */
public class CertificatesAdminController extends FormBasicController { public class CertificatesAdminController extends BasicController {
private FormLink uploadLink; private final VelocityContainer mainVC;
private FlexiTableElement tableEl; private final Link settingsLink, certificatesLink;
private TemplatesDataModel tableModel; private final SegmentViewComponent segmentView;
private CloseableModalController cmc; private CertificatesSettingsAdminController settingsCtrl;
private UploadCertificateController uploadCtrl; private CertificatesListAdminController certificatesCtrl;
private DialogBoxController confirmDeleteCtrl;
@Autowired
private CertificatesManager certificatesManager;
public CertificatesAdminController(UserRequest ureq, WindowControl wControl) { public CertificatesAdminController(UserRequest ureq, WindowControl wControl) {
super(ureq, wControl, "admin_certificates"); super(ureq, wControl);
initForm(ureq); mainVC = createVelocityContainer("admin_certificates");
}
segmentView = SegmentViewFactory.createSegmentView("segments", mainVC, this);
segmentView.setReselect(true);
@Override settingsLink = LinkFactory.createLink("admin.certificates.settings", mainVC, this);
protected void initForm(FormItemContainer formLayout, Controller listener, UserRequest ureq) { segmentView.addSegment(settingsLink, true);
certificatesLink = LinkFactory.createLink("admin.certificates.templates", mainVC, this);
segmentView.addSegment(certificatesLink, false);
FlexiTableColumnModel tableColumnModel = FlexiTableDataModelFactory.createFlexiTableColumnModel(); doOpenSettings(ureq);
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel(Cols.name.i18n(), Cols.name.ordinal()));
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("replace", translate("replace"), "replace"));
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("delete", translate("delete"), "delete"));
tableModel = new TemplatesDataModel(tableColumnModel); putInitialPanel(mainVC);
tableEl = uifactory.addTableElement(getWindowControl(), "templates", tableModel, getTranslator(), formLayout);
uploadLink = uifactory.addFormLink("upload", formLayout, Link.BUTTON);
updateDataModel();
}
private void updateDataModel() {
List<CertificateTemplate> templates = certificatesManager.getTemplates();
tableModel.setObjects(templates);
tableEl.reset();
} }
@Override @Override
protected void doDispose() { protected void doDispose() {
// //
} }
@Override
protected void formOK(UserRequest ureq) {
//
}
@Override
protected void formInnerEvent(UserRequest ureq, FormItem source, FormEvent event) {
if(source == uploadLink) {
doUpload(ureq);
} else if(source == tableEl) {
SelectionEvent se = (SelectionEvent)event;
String cmd = se.getCommand();
CertificateTemplate selectedTemplate = tableModel.getObject(se.getIndex());
if("replace".equals(cmd)) {
doReplace(ureq, selectedTemplate);
} else if("delete".equals(cmd)) {
doConfirmDelete(ureq, selectedTemplate);
}
}
}
@Override @Override
protected void event(UserRequest ureq, Controller source, Event event) { protected void event(UserRequest ureq, Component source, Event event) {
if(uploadCtrl == source) { if(source == segmentView) {
if(event == Event.DONE_EVENT) { if(event instanceof SegmentViewEvent) {
updateDataModel(); SegmentViewEvent sve = (SegmentViewEvent)event;
} String segmentCName = sve.getComponentName();
cmc.deactivate(); Component clickedLink = mainVC.getComponent(segmentCName);
cleanUp(); if (clickedLink == settingsLink) {
} else if(confirmDeleteCtrl == source) { doOpenSettings(ureq);
if(DialogBoxUIFactory.isOkEvent(event)) { } else if (clickedLink == certificatesLink) {
CertificateTemplate template = (CertificateTemplate)confirmDeleteCtrl.getUserObject(); doOpenCertificatesList(ureq);
doDelete(template); }
} }
} else if(cmc == source) {
cleanUp();
} }
super.event(ureq, source, event);
}
private void cleanUp() {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = null;
cmc = null;
}
private void doConfirmDelete(UserRequest ureq, CertificateTemplate selectedTemplate) {
String title = translate("confirm.delete.title");
String text = translate("confirm.delete.text");
confirmDeleteCtrl = activateOkCancelDialog(ureq, title, text, confirmDeleteCtrl);
confirmDeleteCtrl.setUserObject(selectedTemplate);
} }
private void doDelete(CertificateTemplate template) { private void doOpenSettings(UserRequest ureq) {
certificatesManager.deleteTemplate(template); if(settingsCtrl == null) {
updateDataModel(); OLATResourceable ores = OresHelper.createOLATResourceableInstance("Certificates", 0l);
showInfo("confirm.certificate.template.deleted", template.getName()); WindowControl bwControl = BusinessControlFactory.getInstance().createBusinessWindowControl(ores, null, getWindowControl());
} settingsCtrl = new CertificatesSettingsAdminController(ureq, bwControl);
listenTo(settingsCtrl);
private void doUpload(UserRequest ureq) {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = new UploadCertificateController(ureq, getWindowControl());
listenTo(uploadCtrl);
String title = translate("upload.title");
cmc = new CloseableModalController(getWindowControl(), "close", uploadCtrl.getInitialComponent(), true, title);
listenTo(cmc);
cmc.activate();
}
private void doReplace(UserRequest ureq, CertificateTemplate template) {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = new UploadCertificateController(ureq, getWindowControl(), template);
listenTo(uploadCtrl);
String title = translate("upload.title");
cmc = new CloseableModalController(getWindowControl(), "close", uploadCtrl.getInitialComponent(), true, title);
listenTo(cmc);
cmc.activate();
}
public static enum Cols {
name("template.name");
private final String i18n;
private Cols(String i18n) {
this.i18n = i18n;
}
public String i18n() {
return i18n;
} }
mainVC.put("segmentCmp", settingsCtrl.getInitialComponent());
} }
private static class TemplatesDataModel extends DefaultFlexiTableDataModel<CertificateTemplate> { private void doOpenCertificatesList(UserRequest ureq) {
if(certificatesCtrl == null) {
public TemplatesDataModel(FlexiTableColumnModel columnModel) { OLATResourceable ores = OresHelper.createOLATResourceableInstance("Certificates", 0l);
super(columnModel); WindowControl bwControl = BusinessControlFactory.getInstance().createBusinessWindowControl(ores, null, getWindowControl());
} certificatesCtrl = new CertificatesListAdminController(ureq, bwControl);
listenTo(certificatesCtrl);
@Override
public DefaultFlexiTableDataModel<CertificateTemplate> createCopyWithEmptyList() {
return new TemplatesDataModel(getTableColumnModel());
}
@Override
public Object getValueAt(int row, int col) {
CertificateTemplate template = getObject(row);
switch(Cols.values()[col]) {
case name: return template.getName();
}
return null;
} }
mainVC.put("segmentCmp", certificatesCtrl.getInitialComponent());
} }
} }
/**
* <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.course.certificate.ui;
import java.util.List;
import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.form.flexible.FormItem;
import org.olat.core.gui.components.form.flexible.FormItemContainer;
import org.olat.core.gui.components.form.flexible.elements.FlexiTableElement;
import org.olat.core.gui.components.form.flexible.elements.FormLink;
import org.olat.core.gui.components.form.flexible.impl.FormBasicController;
import org.olat.core.gui.components.form.flexible.impl.FormEvent;
import org.olat.core.gui.components.form.flexible.impl.elements.table.DefaultFlexiColumnModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.DefaultFlexiTableDataModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableColumnModel;
import org.olat.core.gui.components.form.flexible.impl.elements.table.FlexiTableDataModelFactory;
import org.olat.core.gui.components.form.flexible.impl.elements.table.SelectionEvent;
import org.olat.core.gui.components.link.Link;
import org.olat.core.gui.control.Controller;
import org.olat.core.gui.control.Event;
import org.olat.core.gui.control.WindowControl;
import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController;
import org.olat.core.gui.control.generic.modal.DialogBoxController;
import org.olat.core.gui.control.generic.modal.DialogBoxUIFactory;
import org.olat.course.certificate.CertificateTemplate;
import org.olat.course.certificate.CertificatesManager;
import org.springframework.beans.factory.annotation.Autowired;
/**
*
* Initial date: 20.10.2014<br>
* @author srosse, stephane.rosse@frentix.com, http://www.frentix.com
*
*/
public class CertificatesListAdminController extends FormBasicController {
private FormLink uploadLink;
private FlexiTableElement tableEl;
private TemplatesDataModel tableModel;
private CloseableModalController cmc;
private UploadCertificateController uploadCtrl;
private DialogBoxController confirmDeleteCtrl;
@Autowired
private CertificatesManager certificatesManager;
public CertificatesListAdminController(UserRequest ureq, WindowControl wControl) {
super(ureq, wControl, "certificate_list");
initForm(ureq);
}
@Override
protected void initForm(FormItemContainer formLayout, Controller listener, UserRequest ureq) {
FlexiTableColumnModel tableColumnModel = FlexiTableDataModelFactory.createFlexiTableColumnModel();
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel(Cols.name.i18n(), Cols.name.ordinal()));
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("replace", translate("replace"), "replace"));
tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("delete", translate("delete"), "delete"));
tableModel = new TemplatesDataModel(tableColumnModel);
tableEl = uifactory.addTableElement(getWindowControl(), "templates", tableModel, getTranslator(), formLayout);
uploadLink = uifactory.addFormLink("upload", formLayout, Link.BUTTON);
updateDataModel();
}
private void updateDataModel() {
List<CertificateTemplate> templates = certificatesManager.getTemplates();
tableModel.setObjects(templates);
tableEl.reset();
}
@Override
protected void doDispose() {
//
}
@Override
protected void formOK(UserRequest ureq) {
//
}
@Override
protected void formInnerEvent(UserRequest ureq, FormItem source, FormEvent event) {
if(source == uploadLink) {
doUpload(ureq);
} else if(source == tableEl) {
SelectionEvent se = (SelectionEvent)event;
String cmd = se.getCommand();
CertificateTemplate selectedTemplate = tableModel.getObject(se.getIndex());
if("replace".equals(cmd)) {
doReplace(ureq, selectedTemplate);
} else if("delete".equals(cmd)) {
doConfirmDelete(ureq, selectedTemplate);
}
}
}
@Override
protected void event(UserRequest ureq, Controller source, Event event) {
if(uploadCtrl == source) {
if(event == Event.DONE_EVENT) {
updateDataModel();
}
cmc.deactivate();
cleanUp();
} else if(confirmDeleteCtrl == source) {
if(DialogBoxUIFactory.isOkEvent(event)) {
CertificateTemplate template = (CertificateTemplate)confirmDeleteCtrl.getUserObject();
doDelete(template);
}
} else if(cmc == source) {
cleanUp();
}
super.event(ureq, source, event);
}
private void cleanUp() {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = null;
cmc = null;
}
private void doConfirmDelete(UserRequest ureq, CertificateTemplate selectedTemplate) {
String title = translate("confirm.delete.title");
String text = translate("confirm.delete.text");
confirmDeleteCtrl = activateOkCancelDialog(ureq, title, text, confirmDeleteCtrl);
confirmDeleteCtrl.setUserObject(selectedTemplate);
}
private void doDelete(CertificateTemplate template) {
certificatesManager.deleteTemplate(template);
updateDataModel();
showInfo("confirm.certificate.template.deleted", template.getName());
}
private void doUpload(UserRequest ureq) {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = new UploadCertificateController(ureq, getWindowControl());
listenTo(uploadCtrl);
String title = translate("upload.title");
cmc = new CloseableModalController(getWindowControl(), "close", uploadCtrl.getInitialComponent(), true, title);
listenTo(cmc);
cmc.activate();
}
private void doReplace(UserRequest ureq, CertificateTemplate template) {
removeAsListenerAndDispose(uploadCtrl);
removeAsListenerAndDispose(cmc);
uploadCtrl = new UploadCertificateController(ureq, getWindowControl(), template);
listenTo(uploadCtrl);
String title = translate("upload.title");
cmc = new CloseableModalController(getWindowControl(), "close", uploadCtrl.getInitialComponent(), true, title);
listenTo(cmc);
cmc.activate();
}
public static enum Cols {
name("template.name");
private final String i18n;
private Cols(String i18n) {
this.i18n = i18n;
}
public String i18n() {
return i18n;
}
}
private static class TemplatesDataModel extends DefaultFlexiTableDataModel<CertificateTemplate> {
public TemplatesDataModel(FlexiTableColumnModel columnModel) {
super(columnModel);
}
@Override
public DefaultFlexiTableDataModel<CertificateTemplate> createCopyWithEmptyList() {
return new TemplatesDataModel(getTableColumnModel());
}
@Override
public Object getValueAt(int row, int col) {
CertificateTemplate template = getObject(row);
switch(Cols.values()[col]) {
case name: return template.getName();
}
return null;
}
}
}
/**
* <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.course.certificate.ui;
import java.util.List;
import org.olat.core.gui.UserRequest;
import org.olat.core.gui.components.form.flexible.FormItem;
import org.olat.core.gui.components.form.flexible.FormItemContainer;
import org.olat.core.gui.components.form.flexible.elements.MultipleSelectionElement;
import org.olat.core.gui.components.form.flexible.elements.TextElement;
import org.olat.core.gui.components.form.flexible.impl.FormBasicController;
import org.olat.core.gui.components.form.flexible.impl.FormEvent;
import org.olat.core.gui.components.form.flexible.impl.FormLayoutContainer;
import org.olat.core.gui.control.Controller;
import org.olat.core.gui.control.WindowControl;
import org.olat.core.util.StringHelper;
import org.olat.core.util.mail.EmailAddressValidator;
import org.olat.course.certificate.CertificatesModule;
import org.springframework.beans.factory.annotation.Autowired;
/**
*
* Initial date: 31 janv. 2017<br>
* @author srosse, stephane.rosse@frentix.com, http://www.frentix.com
*
*/
public class CertificatesSettingsAdminController extends FormBasicController {
private static final String[] onKeys = new String[]{ "on" };
private static final String[] onValues = new String[]{ "" };
private TextElement bccEl;
private MultipleSelectionElement enableBccEl;
@Autowired
private CertificatesModule certificatesModule;
/**
* @param name
* @param chatEnabled
*/
public CertificatesSettingsAdminController(UserRequest ureq, WindowControl wControl) {
super(ureq, wControl);
initForm (ureq);
}
@Override
protected void doDispose() {
//
}
@Override
protected void initForm(FormItemContainer formLayout, Controller listener, UserRequest ureq) {
setFormTitle("admin.certificates.options.title");
setFormDescription("admin.certificates.options.descr", null);
String bcc = certificatesModule.getCertificateBcc();
enableBccEl = uifactory.addCheckboxesHorizontal("enableBcc", "admin.certificates.bcc.enable", formLayout, onKeys, onValues);
enableBccEl.addActionListener(FormEvent.ONCHANGE);
if(StringHelper.containsNonWhitespace(bcc)) {
enableBccEl.select(onKeys[0], true);
}
bccEl = uifactory.addTextElement("bcc", "admin.certificates.bcc", 1024, bcc, formLayout);
bccEl.setVisible(enableBccEl.isAtLeastSelected(1));
FormLayoutContainer buttonsCont = FormLayoutContainer.createButtonLayout("buttons", getTranslator());
formLayout.add(buttonsCont);
uifactory.addFormSubmitButton("save", buttonsCont);
}
@Override
protected boolean validateFormLogic(UserRequest ureq) {
boolean allOk = true;
bccEl.clearError();
if(enableBccEl.isAtLeastSelected(1)) {
String emails = bccEl.getValue();
if(!StringHelper.containsNonWhitespace(emails)) {
bccEl.setErrorKey("form.legende.mandatory", null);
allOk &= false;
} else {
List<String> emailList = certificatesModule.splitEmails(bccEl.getValue());
for(String email:emailList) {
if(!EmailAddressValidator.isValidEmailAddress(email)) {
bccEl.setErrorKey("error.mail.invalid", null);
allOk &= false;
}
}
}
}
return allOk & super.validateFormLogic(ureq);
}
@Override
protected void formInnerEvent(UserRequest ureq, FormItem source, FormEvent event) {
if(enableBccEl == source) {
bccEl.setVisible(enableBccEl.isAtLeastSelected(1));
}
super.formInnerEvent(ureq, source, event);
}
@Override
protected void formOK(UserRequest ureq) {
if(enableBccEl.isAtLeastSelected(1)) {
certificatesModule.setCertificateBcc(bccEl.getValue());
} else {
certificatesModule.setCertificateBcc("");
}
}
}
\ No newline at end of file
<fieldset> $r.render("segments")
<legend> <div class="o_segments_content clearfix">
$r.translate("admin.certificates.title")</legend> $r.render("segmentCmp")
<div class="o_desc">$r.translate("admin.certificates.description")</div> </div>
\ No newline at end of file
$r.render("templates")
<div class="o_button_group">
$r.render("upload")
</div>
</fieldset>
\ No newline at end of file
<fieldset class="o_form">
<div class="o_info">$r.translate("admin.certificates.description")</div>
$r.render("templates")
<div class="o_button_group">
$r.render("upload")
</div>
</fieldset>
\ No newline at end of file
...@@ -2,6 +2,12 @@ admin.menu.title=Zertifikate ...@@ -2,6 +2,12 @@ admin.menu.title=Zertifikate
admin.menu.title.alt=Zertifikate einstellen admin.menu.title.alt=Zertifikate einstellen
admin.certificates.title=Zertifikate admin.certificates.title=Zertifikate
admin.certificates.description=Laden Sie PDF-Formulare als Vorlagen f\u00FCr OpenOLAT Kurszertifikate hoch. admin.certificates.description=Laden Sie PDF-Formulare als Vorlagen f\u00FCr OpenOLAT Kurszertifikate hoch.
admin.certificates.settings=Zertifikate Konfiguration
admin.certificates.templates=Zertifikate Vorlage
admin.certificates.options.title=Konfiguration
admin.certificates.options.descr=Zertifikate k\u00F6nnen an eine E-Mail-Adresse geschickt werden, zum Beispiel der Personalabteilung. Schaltet die Option an und f\u00FCllen Sie die gew\u00FCnschte Adresse ein.
admin.certificates.bcc=BCC E-Mail-Adresse
admin.certificates.bcc.enable=Zertifikate BCC einschalten
certificate=Zertifikate certificate=Zertifikate
certificate.creationdate=Zertifikat ausgestellt am {0} certificate.creationdate=Zertifikat ausgestellt am {0}
coaching.tool=Coaching coaching.tool=Coaching
...@@ -13,7 +19,7 @@ default.template=Standardvorlage ...@@ -13,7 +19,7 @@ default.template=Standardvorlage
details.certificate=Zertifikat details.certificate=Zertifikat
details.course.infos=Kursdetails details.course.infos=Kursdetails
download.button=Zertifikat herunterladen download.button=Zertifikat herunterladen
error.mail.invalid=Bitte geben Sie eine g\u00FCltige E-Mailadresse an.
options.certificates.title=Konfiguration Leistungnachweis options.certificates.title=Konfiguration Leistungnachweis
options.certificates.descr=Damit Kurse als bestanden angezeigt werden k\u00F6nnen, muss im Kurshauptknoten zwingend im "Punkte"-Tab die Option <strong>Bestanden berechnen?</strong> aktiviert werden. options.certificates.descr=Damit Kurse als bestanden angezeigt werden k\u00F6nnen, muss im Kurshauptknoten zwingend im "Punkte"-Tab die Option <strong>Bestanden berechnen?</strong> aktiviert werden.
......
...@@ -3,6 +3,12 @@ admin.certificates.description=Upload PDF forms as templates for the course cert ...@@ -3,6 +3,12 @@ admin.certificates.description=Upload PDF forms as templates for the course cert
admin.certificates.title=Certificates admin.certificates.title=Certificates
admin.menu.title=Certificates admin.menu.title=Certificates
admin.menu.title.alt=Certificates configuration admin.menu.title.alt=Certificates configuration
admin.certificates.settings=Certificates configuration
admin.certificates.templates=Templates for certificates
admin.certificates.options.title=Configuration
admin.certificates.options.descr=Certificates can be sent to an email address e.g. to the HR department. Enable this option and fill in the desired email address.
admin.certificates.bcc=BCC email address
admin.certificates.bcc.enable=Enable BCC of certificates
certificate=Certificates certificate=Certificates
certificate.creationdate=Certificate issued on {0} certificate.creationdate=Certificate issued on {0}
certificates.wizard.overview=Overview certificates.wizard.overview=Overview
...@@ -10,7 +16,7 @@ certificates.wizard.select=Select user ...@@ -10,7 +16,7 @@ certificates.wizard.select=Select user
certificates.wizard.title=Create certificates certificates.wizard.title=Create certificates
certification.email.body=Congratulations\!\r\n\r\nYou have received a certification.\r\nPlease find attached the certificate to the course "{0}". certification.email.body=Congratulations\!\r\n\r\nYou have received a certification.\r\nPlease find attached the certificate to the course "{0}".
certification.email.subject=You have received an OpenOLAT certification certification.email.subject=You have received an OpenOLAT certification
error.mail.invalid=Please provide a valid e-mail address.
choose.title=Select template choose.title=Select template
coaching.tool=Coaching coaching.tool=Coaching
confirm.certificate.deleted=The certificate from {0} was deleted. confirm.certificate.deleted=The certificate from {0} was deleted.
......
...@@ -24,6 +24,7 @@ default.template=Mod\u00E8le par d\u00E9faut ...@@ -24,6 +24,7 @@ default.template=Mod\u00E8le par d\u00E9faut
details.certificate=Certificat details.certificate=Certificat
details.course.infos=D\u00E9tails du cours details.course.infos=D\u00E9tails du cours
download.button=T\u00E9l\u00E9charger le certificat download.button=T\u00E9l\u00E9charger le certificat
error.mail.invalid=Indiquez une adresse courriel valide, svp.
format=Format format=Format
generate.certificate=G\u00E9n\u00E9rer un certificat generate.certificate=G\u00E9n\u00E9rer un certificat
landscape=Paysage landscape=Paysage
......
...@@ -326,6 +326,11 @@ onyx.plugin.exammodelocation=${onyx.plugin.wslocation}/onyxexamservices ...@@ -326,6 +326,11 @@ onyx.plugin.exammodelocation=${onyx.plugin.wslocation}/onyxexamservices
### set or overwrite this switch to "true" if this olat-node is either a single-node or should be the controlling entity in a clustered-olat ### set or overwrite this switch to "true" if this olat-node is either a single-node or should be the controlling entity in a clustered-olat
exam.mode.masternode=true exam.mode.masternode=true
########################################################################
# Certificates
########################################################################
# Send a copy of the certificates mails to someone
certificate.bcc=
##### #####
# Help course and context help # Help course and context help
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment