ARTEMIS-2088 - Page.write() should throw exception if file is closed

In Page.write(final PagedMessage message) if the page file is closed
it returns silently. The caller has no way to know that if the message
is paged to file or not. It should throw an exception so that the
caller can handle it correctly.

This causes random failure PagingTest#testExpireLargeMessageOnPaging().
The test shows that when the server stops it closes the page file.
In the mean time a message is expired to the expiry queue and if
the expiry queue is in paging mode, it goes to Page.write() and
returns without any error. The result is that the message is removed
from the original queue and not added to the expiry queue.

If we throw exception here it makes the expiration failed, the message
will not be removed from the orginal queue. Next time broker is started,
the message will be reloaded and expired again. no message lost.
This commit is contained in:
Howard Gao 2018-09-14 10:52:02 +08:00 committed by Clebert Suconic
parent 3ac96491ec
commit 90ca87c5e1
2 changed files with 6 additions and 1 deletions

View File

@ -223,7 +223,7 @@ public final class Page implements Comparable<Page> {
public synchronized void write(final PagedMessage message) throws Exception { public synchronized void write(final PagedMessage message) throws Exception {
if (!file.isOpen()) { if (!file.isOpen()) {
return; throw ActiveMQMessageBundle.BUNDLE.cannotWriteToClosedFile(file);
} }
final int messageEncodedSize = message.getEncodeSize(); final int messageEncodedSize = message.getEncodeSize();
final int bufferSize = messageEncodedSize + Page.SIZE_RECORD; final int bufferSize = messageEncodedSize + Page.SIZE_RECORD;

View File

@ -44,6 +44,7 @@ import org.apache.activemq.artemis.api.core.ActiveMQUnexpectedRoutingTypeForAddr
import org.apache.activemq.artemis.api.core.DiscoveryGroupConfiguration; import org.apache.activemq.artemis.api.core.DiscoveryGroupConfiguration;
import org.apache.activemq.artemis.api.core.RoutingType; import org.apache.activemq.artemis.api.core.RoutingType;
import org.apache.activemq.artemis.api.core.SimpleString; import org.apache.activemq.artemis.api.core.SimpleString;
import org.apache.activemq.artemis.core.io.SequentialFile;
import org.apache.activemq.artemis.core.postoffice.Binding; import org.apache.activemq.artemis.core.postoffice.Binding;
import org.apache.activemq.artemis.core.protocol.core.impl.wireformat.ReplicationSyncFileMessage; import org.apache.activemq.artemis.core.protocol.core.impl.wireformat.ReplicationSyncFileMessage;
import org.apache.activemq.artemis.core.security.CheckType; import org.apache.activemq.artemis.core.security.CheckType;
@ -444,4 +445,8 @@ public interface ActiveMQMessageBundle {
@Message(id = 229216, value = "Invalid queue name: {0}", format = Message.Format.MESSAGE_FORMAT) @Message(id = 229216, value = "Invalid queue name: {0}", format = Message.Format.MESSAGE_FORMAT)
ActiveMQIllegalStateException invalidQueueName(SimpleString queueName); ActiveMQIllegalStateException invalidQueueName(SimpleString queueName);
@Message(id = 119217, value = "Can't write to closed file: {0}", format = Message.Format.MESSAGE_FORMAT)
ActiveMQIOErrorException cannotWriteToClosedFile(SequentialFile file);
} }