Skip to content

Commit

Permalink
[bugfix] wrapper kills eXist if it takes too long to start up or shut…
Browse files Browse the repository at this point in the history
… down, resulting in fatal errors and potential data loss. Broker pool used to send signals to the wrapper to keep it waiting, but recently this failed due to broker pool being synchronized during startup. Solution: implement Observable on StatusReporter, which runs in a separate thread and is not subject to broker pool locks. Make it notify observers every 500ms.
  • Loading branch information
wolfgangmm committed Aug 13, 2013
1 parent b922e8c commit 70009b4
Show file tree
Hide file tree
Showing 2 changed files with 20 additions and 17 deletions.
4 changes: 1 addition & 3 deletions src/org/exist/Database.java
Expand Up @@ -55,9 +55,7 @@ public interface Database {

//TODO: javadocs

public String getId();

public void addObserver(Observer o);
public String getId();

/**
*
Expand Down
33 changes: 19 additions & 14 deletions src/org/exist/storage/BrokerPool.java
Expand Up @@ -92,7 +92,7 @@
*/
//TODO : in the future, separate the design between the Map of DBInstances and their non static implementation
@ConfigurationClass("pool")
public class BrokerPool extends Observable implements Database {
public class BrokerPool implements Database {

private final static Logger LOG = Logger.getLogger(BrokerPool.class);

Expand Down Expand Up @@ -617,9 +617,6 @@ private BrokerPool(String instanceName, int minBrokers, int maxBrokers, Configur
Boolean aBoolean;
final NumberFormat nf = NumberFormat.getNumberInstance();

if (statusObserver != null)
{addObserver(statusObserver);}

this.classLoader = Thread.currentThread().getContextClassLoader();

//TODO : ensure that the instance name is unique ?
Expand Down Expand Up @@ -813,7 +810,11 @@ protected void initialize() throws EXistException, DatabaseConfigurationExceptio
synchronized (this) {
try {
statusReporter = new StatusReporter(SIGNAL_STARTUP);
statusReporter.start();
if (statusObserver != null) {
statusReporter.addObserver(statusObserver);
}
Thread statusThread = new Thread(statusReporter);
statusThread.start();

// statusReporter may have to be terminated or the thread can/will hang.
try {
Expand Down Expand Up @@ -1886,7 +1887,11 @@ public void shutdown(boolean killed) {
// these may be used and set by other threads for the same or some other purpose
// (unlikely). Take no chances.
statusReporter = new StatusReporter(SIGNAL_SHUTDOWN);
statusReporter.start();
if (statusObserver != null) {
statusReporter.addObserver(statusObserver);
}
Thread statusThread = new Thread(statusReporter);
statusThread.start();

// release transaction log to allow remaining brokers to complete
// their job
Expand Down Expand Up @@ -2084,7 +2089,7 @@ public void printSystemInfo() {
System.err.println(s);
}

private class StatusReporter extends Thread {
private class StatusReporter extends Observable implements Runnable {

private String status;
private volatile boolean terminate = false;
Expand All @@ -2095,27 +2100,27 @@ public StatusReporter(String status) {

public synchronized void setStatus(String status) {
this.status = status;
BrokerPool.this.setChanged();
BrokerPool.this.notifyObservers(status);
this.setChanged();
this.notifyObservers(status);
}

public void terminate() {
public synchronized void terminate() {
this.terminate = true;
interrupt();
this.notifyAll();
}

public void run() {
while (!terminate) {
synchronized (this) {
try {
wait(300);
wait(500);
} catch (final InterruptedException e) {
// nothing to do
}
}
this.setChanged();
this.notifyObservers(status);
}
BrokerPool.this.setChanged();
BrokerPool.this.notifyObservers(status);
}
}

Expand Down

1 comment on commit 70009b4

@dizzzz
Copy link
Member

@dizzzz dizzzz commented on 70009b4 Aug 18, 2013

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this changes causes a build issue in the debugger extension:

compile-src:
     [echo] Compiling sources 'debugger'
    [mkdir] Created dir: /mypath/exist/extensions/debuggee/build/classes
    [javac] Compiling 60 source files to /mypath/exist/extensions/debuggee/build/classes
    [javac] warning: [options] bootstrap class path not set in conjunction with -source 1.6
    [javac] /mypath/exist/extensions/debuggee/src/org/exist/debuggee/ScriptRunner.java:75: error: cannot find symbol
    [javac]             db.addObserver(this);
    [javac]               ^
    [javac]   symbol:   method addObserver(ScriptRunner)
    [javac]   location: variable db of type Database
    [javac] Note: /mypath/exist/extensions/debuggee/src/org/exist/debuggee/SessionImpl.java uses or overrides a deprecated API.
    [javac] Note: Recompile with -Xlint:deprecation for details.
    [javac] 1 error
    [javac] 1 warning

please could you ( @wolfgangmm @shabanovd ) have a look?

Please sign in to comment.