From 0b0221c97e64e840e648f2ac3c74eb7e31bcccc0 Mon Sep 17 00:00:00 2001 From: srosse <none@none> Date: Tue, 1 Mar 2016 09:32:37 +0100 Subject: [PATCH] OO-1854: handle concurrent edit / delete of a parent message --- .../olat/modules/fo/manager/ForumManager.java | 13 ++++++ .../modules/fo/ui/MessageEditController.java | 17 ++++++- .../modules/fo/ui/MessageListController.java | 44 ++++++++++++++----- .../fo/ui/events/ErrorEditMessage.java | 42 ++++++++++++++++++ 4 files changed, 103 insertions(+), 13 deletions(-) create mode 100644 src/main/java/org/olat/modules/fo/ui/events/ErrorEditMessage.java diff --git a/src/main/java/org/olat/modules/fo/manager/ForumManager.java b/src/main/java/org/olat/modules/fo/manager/ForumManager.java index c171dab3e6c..6dcdd3ed861 100644 --- a/src/main/java/org/olat/modules/fo/manager/ForumManager.java +++ b/src/main/java/org/olat/modules/fo/manager/ForumManager.java @@ -321,6 +321,19 @@ public class ForumManager { return threadList; } + public boolean existsMessageById(Long messageKey) { + StringBuilder query = new StringBuilder(); + query.append("select msg.key from fomessage as msg") + .append(" where msg.key=:messageKey"); + + List<Long> messages = dbInstance.getCurrentEntityManager() + .createQuery(query.toString(), Long.class) + .setParameter("messageKey", messageKey) + .getResultList(); + return messages == null || messages.isEmpty() || messages.get(0) == null + ? false : messages.get(0).longValue() > -1; + } + public Message getMessageById(Long messageKey) { StringBuilder query = new StringBuilder(); query.append("select msg from fomessage as msg") diff --git a/src/main/java/org/olat/modules/fo/ui/MessageEditController.java b/src/main/java/org/olat/modules/fo/ui/MessageEditController.java index 0ac9d795e53..bd6f04f6ede 100644 --- a/src/main/java/org/olat/modules/fo/ui/MessageEditController.java +++ b/src/main/java/org/olat/modules/fo/ui/MessageEditController.java @@ -27,6 +27,8 @@ import java.util.Collections; import java.util.Comparator; import java.util.List; +import javax.persistence.PersistenceException; + import org.olat.basesecurity.BaseSecurity; import org.olat.basesecurity.IdentityShort; import org.olat.core.commons.modules.bc.FolderConfig; @@ -52,6 +54,7 @@ import org.olat.core.gui.control.generic.modal.DialogBoxController; import org.olat.core.gui.control.generic.modal.DialogBoxUIFactory; import org.olat.core.id.Identity; import org.olat.core.logging.AssertException; +import org.olat.core.logging.DBRuntimeException; import org.olat.core.logging.activity.ThreadLocalUserActivityLogger; import org.olat.core.util.CodeHelper; import org.olat.core.util.FileUtils; @@ -70,6 +73,7 @@ import org.olat.modules.fo.ForumChangedEvent; import org.olat.modules.fo.ForumLoggingAction; import org.olat.modules.fo.Message; import org.olat.modules.fo.manager.ForumManager; +import org.olat.modules.fo.ui.events.ErrorEditMessage; import org.olat.user.DisplayPortraitController; import org.olat.util.logging.activity.LoggingResourceable; import org.springframework.beans.factory.annotation.Autowired; @@ -363,6 +367,17 @@ public class MessageEditController extends FormBasicController { */ @Override protected void formOK(UserRequest ureq) { + try { + commitMessage(ureq); + fireEvent(ureq, Event.DONE_EVENT); + } catch(DBRuntimeException | PersistenceException e) { + DBFactory.getInstance().rollback(); + logError("", e); + fireEvent(ureq, new ErrorEditMessage()); + } + } + + private void commitMessage(UserRequest ureq) { // if msg exist -> persist uploads directly to final dest if (message.getKey() != null) { message = fm.loadMessage(message.getKey()); @@ -432,8 +447,6 @@ public class MessageEditController extends FormBasicController { ThreadLocalUserActivityLogger.log(ForumLoggingAction.FORUM_REPLY_MESSAGE_CREATE, getClass(), LoggingResourceable.wrap(message)); } - - fireEvent(ureq, Event.DONE_EVENT); } private void notifiySubscription() { diff --git a/src/main/java/org/olat/modules/fo/ui/MessageListController.java b/src/main/java/org/olat/modules/fo/ui/MessageListController.java index be468487779..72e9dfb34db 100644 --- a/src/main/java/org/olat/modules/fo/ui/MessageListController.java +++ b/src/main/java/org/olat/modules/fo/ui/MessageListController.java @@ -88,6 +88,7 @@ import org.olat.modules.fo.manager.ForumManager; import org.olat.modules.fo.ui.MessageEditController.EditMode; import org.olat.modules.fo.ui.events.DeleteMessageEvent; import org.olat.modules.fo.ui.events.DeleteThreadEvent; +import org.olat.modules.fo.ui.events.ErrorEditMessage; import org.olat.modules.fo.ui.events.SelectMessageEvent; import org.olat.portfolio.EPUIFactory; import org.olat.portfolio.manager.EPFrontendManager; @@ -748,22 +749,30 @@ public class MessageListController extends BasicController implements GenericEve } } else if(editMessageCtrl == source) { // edit done -> save - Message message = editMessageCtrl.getMessage(); - if(message != null) { - if(thread != null && thread.getKey().equals(message.getKey())) { - thread = message; - } - reloadModel(ureq, message); + if(event instanceof ErrorEditMessage) { + handleEditError(ureq); } else { - showInfo("header.cannoteditmessage"); + Message message = editMessageCtrl.getMessage(); + if(message != null) { + if(thread != null && thread.getKey().equals(message.getKey())) { + thread = message; + } + reloadModel(ureq, message); + } else { + showInfo("header.cannoteditmessage"); + } } cmc.deactivate(); } else if(replyMessageCtrl == source) { - Message reply = replyMessageCtrl.getMessage(); - if(reply != null) { - reloadModel(ureq, reply); + if(event instanceof ErrorEditMessage) { + handleEditError(ureq); } else { - showInfo("header.cannotsavemessage"); + Message reply = replyMessageCtrl.getMessage(); + if(reply != null) { + reloadModel(ureq, reply); + } else { + showInfo("header.cannotsavemessage"); + } } cmc.deactivate(); } else if(messageTableCtrl == source) { @@ -796,6 +805,19 @@ public class MessageListController extends BasicController implements GenericEve editMessageCtrl = null; cmc = null; } + + private void handleEditError(UserRequest ureq) { + if(thread == null) { + fireEvent(ureq, Event.BACK_EVENT); + showWarning("error.message.deleted"); + } else if(forumManager.existsMessageById(thread.getKey())) { + reloadModel(ureq, null); + showWarning("error.message.deleted"); + } else { + fireEvent(ureq, Event.BACK_EVENT); + showWarning("error.message.deleted"); + } + } private void doReply(UserRequest ureq, MessageView parent, boolean quote) { // user has clicked on button 'reply' diff --git a/src/main/java/org/olat/modules/fo/ui/events/ErrorEditMessage.java b/src/main/java/org/olat/modules/fo/ui/events/ErrorEditMessage.java new file mode 100644 index 00000000000..b255c9e1c03 --- /dev/null +++ b/src/main/java/org/olat/modules/fo/ui/events/ErrorEditMessage.java @@ -0,0 +1,42 @@ +/** + * <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.fo.ui.events; + +import org.olat.core.gui.control.Event; + +/** + * + * This error is send from MessageEditController if + * a database error occur. + * + * Initial date: 01.03.2016<br> + * @author srosse, stephane.rosse@frentix.com, http://www.frentix.com + * + */ +public class ErrorEditMessage extends Event { + + private static final long serialVersionUID = 8096812282751520199L; + public static final String CMD = "db-error"; + + public ErrorEditMessage() { + super(CMD); + } + +} -- GitLab