Find a random port number to use for the application server to avoid conflicts
with any other apps that may have already bound to the default port used by CP.pull/3/head
parent
a1524f3726
commit
457a842cec
|
|
@ -32,8 +32,12 @@
|
||||||
|
|
||||||
|
|
||||||
// Constructor
|
// Constructor
|
||||||
BrowserWindow::BrowserWindow()
|
BrowserWindow::BrowserWindow(quint16 port)
|
||||||
{
|
{
|
||||||
|
// Setup the URL the browser will connect to
|
||||||
|
m_appServerUrl = QString("http://localhost:%1").arg(port);
|
||||||
|
|
||||||
|
// Setup the UI
|
||||||
createActions();
|
createActions();
|
||||||
createMenus();
|
createMenus();
|
||||||
|
|
||||||
|
|
@ -48,9 +52,9 @@ BrowserWindow::BrowserWindow()
|
||||||
restoreState(settings.value("windowState").toByteArray());
|
restoreState(settings.value("windowState").toByteArray());
|
||||||
|
|
||||||
// Display the app
|
// Display the app
|
||||||
m_initialload = true;
|
m_initialLoad = true;
|
||||||
m_loadattempt = 1;
|
m_loadAttempt = 1;
|
||||||
webView->setUrl(PGA_SERVER_URL);
|
webView->setUrl(QString("http://localhost/:%1").arg(9876));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -106,43 +110,38 @@ void BrowserWindow::createMenus()
|
||||||
// Process loading finished signals from the web view.
|
// Process loading finished signals from the web view.
|
||||||
void BrowserWindow::finishLoading(bool ok)
|
void BrowserWindow::finishLoading(bool ok)
|
||||||
{
|
{
|
||||||
if (m_initialload && !ok)
|
if (m_initialLoad && !ok)
|
||||||
{
|
{
|
||||||
// The load attempt failed. Try again up to 4 times with an
|
// The load attempt failed. Try again up to 4 times with an
|
||||||
// incremental backoff.
|
// incremental backoff.
|
||||||
if (m_loadattempt < 5)
|
if (m_loadAttempt < 5)
|
||||||
{
|
{
|
||||||
qDebug() << "Initial load failed. Retrying in" << m_loadattempt << "seconds.";
|
if (m_loadAttempt > 1)
|
||||||
|
|
||||||
if (m_loadattempt == 1)
|
|
||||||
{
|
{
|
||||||
webView->setHtml(tr("<p>Connecting...</p>"));
|
qDebug() << "Initial connection failed. Retrying in" << m_loadAttempt << "seconds.";
|
||||||
|
webView->setHtml(QString(tr("<p>Failed to connect to the pgAdmin application server. Retrying in %1 seconds, ") +
|
||||||
|
tr("or click <a href=\"%2\">here</a> to try again now.</p>")).arg(m_loadAttempt).arg(m_appServerUrl));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
webView->setHtml(QString(tr("<p>Failed to connect to the pgAdmin application server. Retrying in %1 seconds, ") +
|
webView->setHtml(QString(tr("<p>Connecting to the application server...</p>")));
|
||||||
tr("or click <a href=\"%2\">here</a> to try again now.</p>")).arg(m_loadattempt).arg(PGA_SERVER_URL));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pause(m_loadattempt);
|
pause(m_loadAttempt);
|
||||||
webView->setUrl(PGA_SERVER_URL);
|
webView->setUrl(m_appServerUrl);
|
||||||
|
m_loadAttempt++;
|
||||||
// Even if the server comes up while we're looping, Linux won't
|
|
||||||
// properly display the HTML data unless we explicitly process events.
|
|
||||||
QCoreApplication::processEvents(QEventLoop::AllEvents, 100);
|
|
||||||
|
|
||||||
m_loadattempt++;
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
qDebug() << "Initial page load failed after multiple attempts. Aborting.";
|
qDebug() << "Initial connection failed after multiple attempts. Aborting.";
|
||||||
webView->setHtml(QString(tr("<p>Failed to connect to the pgAdmin application server. ") +
|
webView->setHtml(QString(tr("<p>Failed to connect to the pgAdmin application server. ") +
|
||||||
tr("Click <a href=\"%1\">here</a> to try again.</p>")).arg(PGA_SERVER_URL));
|
tr("Click <a href=\"%1\">here</a> to try again.</p>")).arg(m_appServerUrl));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
m_initialload = false;
|
m_initialLoad = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,7 @@ class BrowserWindow : public QMainWindow
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
public:
|
public:
|
||||||
BrowserWindow();
|
BrowserWindow(quint16 port);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void closeEvent(QCloseEvent *event);
|
void closeEvent(QCloseEvent *event);
|
||||||
|
|
@ -47,6 +47,7 @@ private slots:
|
||||||
void about();
|
void about();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
QString m_appServerUrl;
|
||||||
QWebView *webView;
|
QWebView *webView;
|
||||||
QMenu *fileMenu;
|
QMenu *fileMenu;
|
||||||
QMenu *helpMenu;
|
QMenu *helpMenu;
|
||||||
|
|
@ -54,8 +55,8 @@ private:
|
||||||
QAction *exitAction;
|
QAction *exitAction;
|
||||||
QAction *aboutAction;
|
QAction *aboutAction;
|
||||||
|
|
||||||
bool m_initialload;
|
bool m_initialLoad;
|
||||||
int m_loadattempt;
|
int m_loadAttempt;
|
||||||
|
|
||||||
void createActions();
|
void createActions();
|
||||||
void createMenus();
|
void createMenus();
|
||||||
|
|
|
||||||
|
|
@ -22,8 +22,11 @@
|
||||||
// App headers
|
// App headers
|
||||||
#include "Server.h"
|
#include "Server.h"
|
||||||
|
|
||||||
Server::Server()
|
Server::Server(quint16 port)
|
||||||
{
|
{
|
||||||
|
// Appserver port
|
||||||
|
m_port = port;
|
||||||
|
|
||||||
// Initialise Python
|
// Initialise Python
|
||||||
Py_SetProgramName(PGA_APP_NAME.toUtf8().data());
|
Py_SetProgramName(PGA_APP_NAME.toUtf8().data());
|
||||||
Py_Initialize();
|
Py_Initialize();
|
||||||
|
|
@ -74,6 +77,9 @@ void Server::run()
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Set the port number
|
||||||
|
PyRun_SimpleString(QString("PGADMIN_PORT = %1").arg(m_port).toLatin1());
|
||||||
|
|
||||||
if (PyRun_SimpleFile(cp, m_appfile.toUtf8().data()) != 0)
|
if (PyRun_SimpleFile(cp, m_appfile.toUtf8().data()) != 0)
|
||||||
setError("Failed to launch the application server, server thread exiting.");
|
setError("Failed to launch the application server, server thread exiting.");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ class Server : public QThread
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Server();
|
Server(quint16 port);
|
||||||
~Server();
|
~Server();
|
||||||
|
|
||||||
bool Init();
|
bool Init();
|
||||||
|
|
@ -37,6 +37,8 @@ private:
|
||||||
|
|
||||||
QString m_appfile;
|
QString m_appfile;
|
||||||
QString m_error;
|
QString m_error;
|
||||||
|
|
||||||
|
quint16 m_port;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SERVER_H
|
#endif // SERVER_H
|
||||||
|
|
|
||||||
|
|
@ -38,13 +38,17 @@ int main(int argc, char * argv[])
|
||||||
QCoreApplication::setOrganizationDomain("pgadmin.org");
|
QCoreApplication::setOrganizationDomain("pgadmin.org");
|
||||||
QCoreApplication::setApplicationName(PGA_APP_NAME);
|
QCoreApplication::setApplicationName(PGA_APP_NAME);
|
||||||
|
|
||||||
|
// Find an unused port number.
|
||||||
|
QTcpSocket socket;
|
||||||
|
socket.bind(0, QAbstractSocket::DontShareAddress);
|
||||||
|
quint16 port = socket.localPort();
|
||||||
|
|
||||||
// Fire up the webserver
|
// Fire up the webserver
|
||||||
// TODO: Find an unused port number to use
|
Server *server = new Server(port);
|
||||||
Server *server = new Server();
|
|
||||||
|
|
||||||
if (!server->Init())
|
if (!server->Init())
|
||||||
{
|
{
|
||||||
qDebug() << server->getError();
|
qDebug() << server->getError();
|
||||||
|
|
||||||
QString error("An error occurred initialising the application server:\n\n" + server->getError());
|
QString error("An error occurred initialising the application server:\n\n" + server->getError());
|
||||||
QMessageBox::critical(NULL, QString("Fatal Error"), error);
|
QMessageBox::critical(NULL, QString("Fatal Error"), error);
|
||||||
|
|
@ -55,11 +59,10 @@ int main(int argc, char * argv[])
|
||||||
server->start();
|
server->start();
|
||||||
|
|
||||||
// Create & show the main window
|
// Create & show the main window
|
||||||
BrowserWindow browserWindow;
|
BrowserWindow browserWindow(port);
|
||||||
browserWindow.show();
|
browserWindow.show();
|
||||||
|
|
||||||
// Go!
|
// Go!
|
||||||
return app.exec();
|
return app.exec();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,4 @@
|
||||||
// Application name
|
// Application name
|
||||||
const QString PGA_APP_NAME = QString("pgAdmin 4");
|
const QString PGA_APP_NAME = QString("pgAdmin 4");
|
||||||
|
|
||||||
// Server URL
|
|
||||||
const QString PGA_SERVER_URL = QString("http://127.0.0.1:8080");
|
|
||||||
|
|
||||||
#endif // PGADMIN4_H
|
#endif // PGADMIN4_H
|
||||||
|
|
|
||||||
|
|
@ -7,11 +7,14 @@ includedir = os.path.realpath(os.path.abspath(os.path.join(os.path.split(inspect
|
||||||
if includedir not in sys.path:
|
if includedir not in sys.path:
|
||||||
sys.path.insert(0, includedir)
|
sys.path.insert(0, includedir)
|
||||||
|
|
||||||
# Do some stuff
|
# Rock n' roll...
|
||||||
import cherrypy
|
import cherrypy
|
||||||
from time import time,ctime
|
from time import time,ctime
|
||||||
|
|
||||||
class HelloWorld(object):
|
|
||||||
|
# This is the main application class that we'll run under CherryPy. For now,
|
||||||
|
# we'll just output some basic HTML so we can see that everything is running.
|
||||||
|
class pgAdmin4(object):
|
||||||
def index(self):
|
def index(self):
|
||||||
output = """
|
output = """
|
||||||
Today is <b>%s</b>
|
Today is <b>%s</b>
|
||||||
|
|
@ -21,6 +24,21 @@ Today is <b>%s</b>
|
||||||
<a href="http://www.pgadmin.org/">pgAdmin 4</a>""" % ctime(time())
|
<a href="http://www.pgadmin.org/">pgAdmin 4</a>""" % ctime(time())
|
||||||
|
|
||||||
return output
|
return output
|
||||||
|
|
||||||
index.exposed = True
|
index.exposed = True
|
||||||
|
|
||||||
cherrypy.quickstart(HelloWorld())
|
|
||||||
|
# Start the web server. The port number should have already been set by the
|
||||||
|
# runtime if we're running in desktop mode, otherwise we'll just use the
|
||||||
|
# CherryPy default.
|
||||||
|
|
||||||
|
try:
|
||||||
|
cherrypy.server.socket_port = PGADMIN_PORT
|
||||||
|
except:
|
||||||
|
pass
|
||||||
|
|
||||||
|
try:
|
||||||
|
cherrypy.quickstart(pgAdmin4())
|
||||||
|
except IOError:
|
||||||
|
print "Unexpected error: ", sys.exc_info()[0]
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue