More refactoring: Logger and Logbrowser out of application class.

This commit is contained in:
Klaas Freitag 2013-10-02 15:28:33 +02:00
parent 48abe62151
commit 55722099fa
9 changed files with 207 additions and 175 deletions

View file

@ -19,7 +19,6 @@
#include "config.h"
#include "mirall/application.h"
#include "mirall/systray.h"
#include "mirall/folder.h"
#include "mirall/folderman.h"
#include "mirall/folderwatcher.h"
@ -32,10 +31,7 @@
#include "mirall/mirallconfigfile.h"
#include "mirall/updatedetector.h"
#include "mirall/logger.h"
#include "mirall/settingsdialog.h"
#include "mirall/itemprogressdialog.h"
#include "mirall/utility.h"
#include "mirall/inotify.h"
#include "mirall/connectionvalidator.h"
#include "creds/abstractcredentials.h"
@ -56,14 +52,6 @@
namespace Mirall {
// application logging handler.
void mirallLogCatcher(QtMsgType type, const char *msg)
{
Q_UNUSED(type)
// qDebug() exports to local8Bit, which is not always UTF-8
Logger::instance()->mirallLog( QString::fromLocal8Bit(msg) );
}
namespace {
static const char optionsC[] =
@ -98,14 +86,13 @@ QString applicationTrPath()
Application::Application(int &argc, char **argv) :
SharedTools::QtSingleApplication(argc, argv),
_gui(0),
_networkMgr(new QNetworkConfigurationManager(this)),
// _networkMgr(new QNetworkConfigurationManager(this)), <- Not used yet.
_sslErrorDialog(0),
_theme(Theme::instance()),
_logBrowser(0),
_logExpire(0),
_helpOnly(false),
_showLogWindow(false),
_logFlush(false),
_helpOnly(false)
_logExpire(0),
_logFlush(false)
{
setApplicationName( _theme->appNameGUI() );
setWindowIcon( _theme->applicationIcon() );
@ -115,8 +102,12 @@ Application::Application(int &argc, char **argv) :
if ( _helpOnly ) return;
_gui = new ownCloudGui(this);
if( _showLogWindow ) {
_gui->slotToggleLogBrowser(); // _showLogWindow is set in parseOptions.
}
connect( _gui, SIGNAL(setupProxy()), SLOT(slotSetupProxy()));
setupLogBrowser();
setupLogging();
setupTranslations();
connect( this, SIGNAL(messageReceived(QString)), SLOT(slotParseOptions(QString)));
@ -127,11 +118,7 @@ Application::Application(int &argc, char **argv) :
connect( Logger::instance(), SIGNAL(guiMessage(QString,QString)),
_gui, SLOT(slotShowGuiMessage(QString,QString)));
// create folder manager for sync folder management
FolderMan *folderMan = FolderMan::instance();
connect( folderMan, SIGNAL(folderSyncStateChange(QString)),
this,SLOT(slotSyncStateChange(QString)));
folderMan->setSyncEnabled(false);
FolderMan::instance()->setSyncEnabled(false);
setQuitOnLastWindowClosed(false);
@ -150,7 +137,7 @@ Application::Application(int &argc, char **argv) :
slotSetupProxy();
folderMan->setupFolders();
FolderMan::instance()->setupFolders();
// startup procedure.
QTimer::singleShot( 0, this, SLOT( slotCheckConnection() ));
@ -169,17 +156,16 @@ Application::Application(int &argc, char **argv) :
Application::~Application()
{
qDebug() << "* Mirall shutdown";
// qDebug() << "* Mirall shutdown";
}
void Application::slotCleanup()
{
// explicitly close windows. This is somewhat of a hack to ensure
// that saving the geometries happens ASAP during a OS shutdown
_gui->shutdown();
_gui->slotShutdown();
_gui->deleteLater();
if (!_logBrowser.isNull()) _logBrowser->deleteLater();
}
void Application::slotStartUpdateDetector()
@ -301,24 +287,15 @@ void Application::slotownCloudWizardDone( int res )
}
void Application::setupLogBrowser()
void Application::setupLogging()
{
// might be called from second instance
if (_logBrowser.isNull()) {
// init the log browser.
qInstallMsgHandler( mirallLogCatcher );
_logBrowser = new LogBrowser;
// ## TODO: allow new log name maybe?
if (!_logDirectory.isEmpty()) {
enterNextLogFile();
} else if (!_logFile.isEmpty()) {
qDebug() << "Logging into logfile: " << _logFile << " with flush " << _logFlush;
_logBrowser->setLogFile( _logFile, _logFlush );
}
}
Logger::instance()->setLogFile(_logFile);
Logger::instance()->setLogDir(_logDir);
Logger::instance()->setLogExpire(_logExpire);
Logger::instance()->setLogFlush(_logFlush);
if (_showLogWindow)
slotOpenLogBrowser();
Logger::instance()->enterNextLogFile();
qDebug() << QString::fromLatin1( "################## %1 %2 (%3) %4").arg(_theme->appName())
.arg( QLocale::system().name() )
@ -327,37 +304,6 @@ void Application::setupLogBrowser()
}
void Application::enterNextLogFile()
{
if (_logBrowser && !_logDirectory.isEmpty()) {
QDir dir(_logDirectory);
if (!dir.exists()) {
dir.mkpath(".");
}
// Find out what is the file with the highest nymber if any
QStringList files = dir.entryList(QStringList("owncloud.log.*"),
QDir::Files);
QRegExp rx("owncloud.log.(\\d+)");
uint maxNumber = 0;
QDateTime now = QDateTime::currentDateTime();
foreach(const QString &s, files) {
if (rx.exactMatch(s)) {
maxNumber = qMax(maxNumber, rx.cap(1).toUInt());
if (_logExpire > 0) {
QFileInfo fileInfo = dir.absoluteFilePath(s);
if (fileInfo.lastModified().addSecs(60*60 * _logExpire) < now) {
dir.remove(s);
}
}
}
}
QString filename = _logDirectory + "/owncloud.log." + QString::number(maxNumber+1);
_logBrowser->setLogFile(filename , _logFlush);
}
}
QNetworkProxy proxyFromConfig(const MirallConfigFile& cfg)
{
QNetworkProxy proxy;
@ -405,33 +351,14 @@ void Application::slotSetupProxy()
void Application::slotUseMonoIconsChanged(bool)
{
_gui->computeOverallSyncStatus();
}
void Application::slotOpenLogBrowser()
{
_logBrowser->show();
_logBrowser->raise();
_gui->slotComputeOverallSyncStatus();
}
void Application::slotParseOptions(const QString &opts)
{
QStringList options = opts.split(QLatin1Char('|'));
parseOptions(options);
setupLogBrowser();
}
// only used to start a new logfile
void Application::slotSyncStateChange( const QString& alias )
{
FolderMan *folderMan = FolderMan::instance();
const SyncResult& result = folderMan->syncResult( alias );
qDebug() << "Sync state changed for folder " << alias << ": " << result.statusString();
if (result.status() == SyncResult::Success || result.status() == SyncResult::Error) {
enterNextLogFile();
}
setupLogging();
}
void Application::parseOptions(const QStringList &options)
@ -447,17 +374,17 @@ void Application::parseOptions(const QStringList &options)
setHelp();
break;
} else if (option == QLatin1String("--logwindow") ||
option == QLatin1String("-l")) {
option == QLatin1String("-l")) {
_showLogWindow = true;
} else if (option == QLatin1String("--logfile")) {
if (it.hasNext() && !it.peekNext().startsWith(QLatin1String("--"))) {
_logFile = it.next();
_logFile = it.next();
} else {
setHelp();
}
} else if (option == QLatin1String("--logdir")) {
if (it.hasNext() && !it.peekNext().startsWith(QLatin1String("--"))) {
_logDirectory = it.next();
_logDir = it.next();
} else {
setHelp();
}
@ -480,7 +407,7 @@ void Application::parseOptions(const QStringList &options)
setHelp();
break;
}
}
}
}
// Helpers for displaying messages. Note that there is no console on Windows.
@ -522,7 +449,7 @@ void Application::showHelp()
<< QLatin1String(optionsC);
if (_theme->appName() == QLatin1String("ownCloud"))
stream << endl << "For more information, see http://www.owncloud.org" << endl;
stream << endl << "For more information, see http://www.owncloud.org" << endl << endl;
displayHelpText(helpText);
}

View file

@ -63,7 +63,7 @@ protected:
void parseOptions(const QStringList& );
void setupTranslations();
void setupContextMenu();
void setupLogBrowser();
void setupLogging();
void enterNextLogFile();
bool checkConfigExists(bool openSettings);
@ -80,8 +80,6 @@ protected slots:
void slotParseOptions( const QString& );
void slotCheckConnection();
void slotConnectionValidatorResult(ConnectionValidator::Status);
void slotSyncStateChange( const QString& );
void slotOpenLogBrowser();
void slotSSLFailed( QNetworkReply *reply, QList<QSslError> errors );
void slotStartUpdateDetector();
void slotSetupProxy();
@ -90,26 +88,26 @@ protected slots:
void slotCleanup();
private:
void setHelp();
void raiseDialog( QWidget* );
void rebuildRecentMenus();
void runValidator();
QPointer<ownCloudGui> _gui;
QNetworkConfigurationManager *_networkMgr;
// QNetworkConfigurationManager *_networkMgr;
SslErrorDialog *_sslErrorDialog;
SslErrorDialog *_sslErrorDialog;
ConnectionValidator *_conValidator;
Theme *_theme;
QPointer<LogBrowser>_logBrowser;
QString _logFile;
QString _logDirectory;
int _logExpire;
bool _showLogWindow;
bool _logFlush;
bool _helpOnly;
// options from command line:
bool _showLogWindow;
QString _logFile;
QString _logDir;
int _logExpire;
bool _logFlush;
};
} // namespace Mirall

View file

@ -52,8 +52,7 @@ LogWidget::LogWidget(QWidget *parent)
LogBrowser::LogBrowser(QWidget *parent) :
QDialog(parent),
_logWidget( new LogWidget(parent) ),
_doFileFlush(false)
_logWidget( new LogWidget(parent) )
{
setObjectName("LogBrowser"); // for save/restoreGeometry()
setWindowTitle(tr("Log Output"));
@ -142,39 +141,8 @@ void LogBrowser::slotNewLog( const QString& msg )
if( _logWidget->isVisible() ) {
_logWidget->appendPlainText( msg );
}
if( _logstream ) {
(*_logstream) << msg << endl;
if( _doFileFlush ) _logstream->flush();
}
}
void LogBrowser::setLogFile( const QString & name, bool flush )
{
if( _logstream ) {
_logFile.close();
}
bool openSucceeded = false;
if (name == QLatin1String("-")) {
openSucceeded = _logFile.open(1, QIODevice::WriteOnly);
} else {
_logFile.setFileName( name );
openSucceeded = _logFile.open(QIODevice::WriteOnly);
}
if(!openSucceeded) {
QMessageBox::warning(
this,
tr("Error"),
QString(tr("<nobr>File '%1'<br/>cannot be opened for writing.<br/><br/>"
"The log output can <b>not</b> be saved!</nobr>"))
.arg(name));
return;
}
_doFileFlush = flush;
_logstream.reset(new QTextStream( &_logFile ));
}
void LogBrowser::slotFind()
{

View file

@ -64,9 +64,6 @@ private:
QPushButton *_clearBtn;
QLabel *_statusLabel;
QFile _logFile;
bool _doFileFlush;
QScopedPointer<QTextStream> _logstream;
};
} // namespace

View file

@ -14,8 +14,19 @@
#include "mirall/logger.h"
#include <QDir>
#include <QStringList>
namespace Mirall {
// logging handler.
void mirallLogCatcher(QtMsgType type, const char *msg)
{
Q_UNUSED(type)
// qDebug() exports to local8Bit, which is not always UTF-8
Logger::instance()->mirallLog( QString::fromLocal8Bit(msg) );
}
Logger* Logger::_instance=0;
Logger::Logger( QObject* parent)
@ -26,7 +37,10 @@ Logger::Logger( QObject* parent)
Logger *Logger::instance()
{
if( !Logger::_instance ) Logger::_instance = new Logger;
if( !Logger::_instance ) {
Logger::_instance = new Logger;
qInstallMsgHandler( mirallLogCatcher );
}
return Logger::_instance;
}
@ -50,7 +64,7 @@ void Logger::postOptionalGuiLog(const QString &title, const QString &message)
void Logger::postGuiMessage(const QString &title, const QString &message)
{
emit postGuiMessage(title, message);
// emit postGuiMessage(title, message);
}
void Logger::log(Log log)
@ -68,6 +82,12 @@ void Logger::log(Log log)
msg += log.message;
// _logs.append(log);
// std::cout << qPrintable(log.message) << std::endl;
if( _logstream ) {
(*_logstream) << msg << endl;
if( _doFileFlush ) _logstream->flush();
}
emit newLog(msg);
}
@ -91,4 +111,75 @@ void Logger::mirallLog( const QString& message )
Logger::instance()->log( log_ );
}
void Logger::setLogFile(const QString & name)
{
if( _logstream ) {
_logFile.close();
}
bool openSucceeded = false;
if (name == QLatin1String("-")) {
openSucceeded = _logFile.open(1, QIODevice::WriteOnly);
} else {
_logFile.setFileName( name );
openSucceeded = _logFile.open(QIODevice::WriteOnly);
}
if(!openSucceeded) {
postGuiMessage( tr("Error"),
QString(tr("<nobr>File '%1'<br/>cannot be opened for writing.<br/><br/>"
"The log output can <b>not</b> be saved!</nobr>"))
.arg(name));
return;
}
_logstream.reset(new QTextStream( &_logFile ));
}
void Logger::setLogExpire( int expire )
{
_logExpire = expire;
}
void Logger::setLogDir( const QString& dir )
{
_logDirectory = dir;
}
void Logger::setLogFlush( bool flush )
{
_doFileFlush = flush;
}
void Logger::enterNextLogFile()
{
if (!_logDirectory.isEmpty()) {
QDir dir(_logDirectory);
if (!dir.exists()) {
dir.mkpath(".");
}
// Find out what is the file with the highest nymber if any
QStringList files = dir.entryList(QStringList("owncloud.log.*"),
QDir::Files);
QRegExp rx("owncloud.log.(\\d+)");
uint maxNumber = 0;
QDateTime now = QDateTime::currentDateTime();
foreach(const QString &s, files) {
if (rx.exactMatch(s)) {
maxNumber = qMax(maxNumber, rx.cap(1).toUInt());
if (_logExpire > 0) {
QFileInfo fileInfo = dir.absoluteFilePath(s);
if (fileInfo.lastModified().addSecs(60*60 * _logExpire) < now) {
dir.remove(s);
}
}
}
}
QString filename = _logDirectory + "/owncloud.log." + QString::number(maxNumber+1);
setLogFile(filename);
}
}
} // namespace Mirall

View file

@ -18,6 +18,8 @@
#include <QObject>
#include <QList>
#include <QDateTime>
#include <QFile>
#include <QTextStream>
namespace Mirall {
@ -50,12 +52,19 @@ public:
void postOptionalGuiLog(const QString& title, const QString& message);
void postGuiMessage(const QString& title, const QString& message);
void setLogFile( const QString & name );
void setLogExpire( int expire );
void setLogDir( const QString& dir );
void setLogFlush( bool flush );
signals:
void newLog(const QString&);
void guiLog(const QString&, const QString&);
void guiMessage(const QString&, const QString&);
void optionalGuiLog(const QString&, const QString&);
public slots:
void enterNextLogFile();
protected:
Logger(QObject* parent=0);
QList<Log> _logs;
@ -63,6 +72,13 @@ protected:
bool _doLogging;
static Logger* _instance;
QFile _logFile;
bool _doFileFlush;
int _logExpire;
QScopedPointer<QTextStream> _logstream;
QString _logDirectory;
};
} // namespace Mirall

View file

@ -22,6 +22,8 @@
#include "mirall/itemprogressdialog.h"
#include "mirall/owncloudsetupwizard.h"
#include "mirall/settingsdialog.h"
#include "mirall/logger.h"
#include "mirall/logbrowser.h"
#include <QDesktopServices>
#include <QMessageBox>
@ -30,7 +32,10 @@ namespace Mirall {
ownCloudGui::ownCloudGui(Application *parent) :
QObject(parent),
_tray(0),
_settingsDialog(0),
_progressDialog(0),
_logBrowser(0),
_contextMenu(0),
_recentActionsMenu(0),
_app(parent)
@ -63,7 +68,7 @@ ownCloudGui::ownCloudGui(Application *parent) :
}
// REFACTOR: This should rather be in application.... or rather in MirallConfigFile?
// This should rather be in application.... or rather in MirallConfigFile?
bool ownCloudGui::checkConfigExists(bool openSettings)
{
// if no config file is there, start the configuration wizard.
@ -97,26 +102,24 @@ void ownCloudGui::slotSyncStateChange( const QString& alias )
FolderMan *folderMan = FolderMan::instance();
const SyncResult& result = folderMan->syncResult( alias );
computeOverallSyncStatus();
slotComputeOverallSyncStatus();
qDebug() << "Sync state changed for folder " << alias << ": " << result.statusString();
if( _progressDialog ) {
_progressDialog->setSyncResult(result);
}
if (result.status() == SyncResult::Success || result.status() == SyncResult::Error) {
Logger::instance()->enterNextLogFile();
}
}
void ownCloudGui::slotFoldersChanged()
{
computeOverallSyncStatus();
slotComputeOverallSyncStatus();
setupContextMenu();
}
void ownCloudGui::slotOpenLogBrowser()
{
// REFACTOR: do somehting useful.
}
void ownCloudGui::startupConnected( bool connected, const QStringList& fails )
{
FolderMan *folderMan = FolderMan::instance();
@ -136,7 +139,7 @@ void ownCloudGui::startupConnected( bool connected, const QStringList& fails )
}
void ownCloudGui::computeOverallSyncStatus()
void ownCloudGui::slotComputeOverallSyncStatus()
{
// display the info of the least successful sync (eg. not just display the result of the latest sync
QString trayMessage;
@ -328,10 +331,10 @@ void ownCloudGui::slotProgressSyncProblem(const QString& folder, const Progress:
QIcon warnIcon(":/mirall/resources/warning-16");
_actionRecent->setIcon(warnIcon);
rebuildRecentMenus();
slotRebuildRecentMenus();
}
void ownCloudGui::rebuildRecentMenus()
void ownCloudGui::slotRebuildRecentMenus()
{
_recentActionsMenu->clear();
const QList<Progress::Info>& progressInfoList = ProgressDispatcher::instance()->recentChangedItems(5);
@ -373,11 +376,11 @@ void ownCloudGui::slotUpdateProgress(const QString &folder, const Progress::Info
// If there was a change in the file list, redo the progress menu.
if( progress.kind == Progress::EndDownload || progress.kind == Progress::EndUpload ||
progress.kind == Progress::EndDelete ) {
rebuildRecentMenus();
slotRebuildRecentMenus();
}
if (progress.kind == Progress::EndSync) {
rebuildRecentMenus(); // show errors.
slotRebuildRecentMenus(); // show errors.
QTimer::singleShot(2000, this, SLOT(slotDisplayIdle()));
}
}
@ -420,11 +423,41 @@ void ownCloudGui::slotItemProgressDialog()
Utility::raiseDialog(_progressDialog.data());
}
void ownCloudGui::shutdown()
void ownCloudGui::slotShutdown()
{
// those do delete on close
if (!_settingsDialog.isNull()) _settingsDialog->close();
if (!_progressDialog.isNull()) _progressDialog->close();
if (!_logBrowser.isNull()) _logBrowser->deleteLater();
}
void ownCloudGui::slotToggleLogBrowser()
{
if (_logBrowser.isNull()) {
// init the log browser.
_logBrowser = new LogBrowser;
// ## TODO: allow new log name maybe?
}
if (_logBrowser->isVisible() ) {
_logBrowser->hide();
} else {
Utility::raiseDialog(_logBrowser);
}
}
void ownCloudGui::slotOpenOwnCloud()
{
MirallConfigFile cfgFile;
QString url = cfgFile.ownCloudUrl();
QDesktopServices::openUrl( url );
}
void ownCloudGui::slotHelp()
{
QDesktopServices::openUrl(QUrl(Theme::instance()->helpUrl()));
}
} // end namespace

View file

@ -29,6 +29,7 @@ namespace Mirall {
class SettingsDialog;
class ItemProgressDialog;
class Application;
class LogBrowser;
class ownCloudGui : public QObject
{
@ -42,24 +43,27 @@ public:
bool checkConfigExists(bool openSettings);
signals:
void setupProxy();
public slots:
void computeOverallSyncStatus();
void slotComputeOverallSyncStatus();
void slotShowTrayMessage(const QString &title, const QString &msg);
void slotShowOptionalTrayMessage(const QString &title, const QString &msg);
void slotFolderOpenAction( const QString& alias );
void slotRefreshQuotaDisplay( qint64 total, qint64 used );
void rebuildRecentMenus();
void slotRebuildRecentMenus();
void slotProgressSyncProblem(const QString& folder, const Progress::SyncProblem& problem);
void slotUpdateProgress(const QString &folder, const Progress::Info& progress);
void slotShowGuiMessage(const QString &title, const QString &message);
void slotFoldersChanged();
void slotItemProgressDialog();
void slotSettings();
void shutdown();
void slotShutdown();
void slotSyncStateChange( const QString& alias );
void slotTrayClicked( QSystemTrayIcon::ActivationReason reason );
void slotOpenLogBrowser();
void slotToggleLogBrowser();
void slotOpenOwnCloud();
void slotHelp();
private slots:
void slotDisplayIdle();
@ -70,8 +74,8 @@ private:
QPointer<Systray> _tray;
QPointer<SettingsDialog> _settingsDialog;
QPointer<ItemProgressDialog> _progressDialog;
// tray's menu
QPointer<LogBrowser>_logBrowser;
// tray's menu
QMenu *_contextMenu;
QMenu *_recentActionsMenu;

View file

@ -50,7 +50,6 @@ SettingsDialog::SettingsDialog(ownCloudGui *gui, QWidget *parent) :
_accountSettings = new AccountSettings(this);
addAccount(tr("Account"), _accountSettings);
// slotUpdateAccountState(); REFACTOR: Do we still need this? Now in slotSyncStateChange
QIcon generalIcon(QLatin1String(":/mirall/resources/settings.png"));
QListWidgetItem *general = new QListWidgetItem(generalIcon, tr("General"), _ui->labelWidget);
@ -65,9 +64,8 @@ SettingsDialog::SettingsDialog(ownCloudGui *gui, QWidget *parent) :
_ui->labelWidget->addItem(network);
NetworkSettings *networkSettings = new NetworkSettings;
_ui->stack->addWidget(networkSettings);
// REFACTOR check: connect(networkSettings, SIGNAL(proxySettingsChanged()), app, SLOT(slotSetupProxy()));
connect(networkSettings, SIGNAL(proxySettingsChanged()), gui, SIGNAL(setupProxy()));
//connect(generalSettings, SIGNAL(resizeToSizeHint()), SLOT(resizeToSizeHint()));
FolderMan *folderMan = FolderMan::instance();
connect( folderMan, SIGNAL(folderSyncStateChange(QString)),
this, SLOT(slotSyncStateChange(QString)));
@ -92,7 +90,7 @@ SettingsDialog::SettingsDialog(ownCloudGui *gui, QWidget *parent) :
QAction *showLogWindow = new QAction(this);
showLogWindow->setShortcut(QKeySequence("F12"));
connect(showLogWindow, SIGNAL(triggered()), gui, SLOT(slotOpenLogBrowser()));
connect(showLogWindow, SIGNAL(triggered()), gui, SLOT(slotToggleLogBrowser()));
addAction(showLogWindow);
int iconSize = 32;