2015-06-04 10:29:50 +00:00
# include "qmlmanager.h"
2015-06-04 10:36:36 +00:00
# include <QUrl>
2015-07-10 07:47:26 +00:00
# include <QSettings>
2015-07-13 00:39:13 +00:00
# include <QDebug>
2015-12-05 03:34:59 +00:00
# include <QNetworkAccessManager>
# include <QAuthenticator>
2015-06-04 10:29:50 +00:00
2015-06-11 06:56:18 +00:00
# include "qt-models/divelistmodel.h"
# include "divelist.h"
2015-07-10 07:47:26 +00:00
# include "pref.h"
2015-07-10 08:31:24 +00:00
# include "qthelper.h"
2015-07-13 00:39:13 +00:00
# include "qt-gui.h"
2015-12-15 07:00:19 +00:00
# include "git-access.h"
2015-07-13 00:39:13 +00:00
2015-12-03 23:59:40 +00:00
QMLManager * QMLManager : : m_instance = NULL ;
static void appendTextToLogStandalone ( const char * text )
2015-07-13 00:39:13 +00:00
{
2015-12-03 23:59:40 +00:00
QMLManager * mgr = QMLManager : : instance ( ) ;
if ( mgr )
mgr - > appendTextToLog ( QString ( text ) ) ;
2015-07-13 00:39:13 +00:00
}
2015-06-09 19:20:44 +00:00
2015-12-15 07:00:19 +00:00
extern " C " int gitProgressCB ( int percent )
{
static int lastPercent = - 10 ;
if ( percent - lastPercent > = 10 ) {
lastPercent + = 10 ;
QMLManager * mgr = QMLManager : : instance ( ) ;
if ( mgr )
mgr - > loadDiveProgress ( percent ) ;
}
// return 0 so that we don't end the download
return 0 ;
}
2015-11-11 23:19:09 +00:00
QMLManager : : QMLManager ( ) :
2015-12-05 03:34:59 +00:00
m_locationServiceEnabled ( false ) ,
reply ( 0 ) ,
mgr ( 0 )
2015-06-04 10:29:50 +00:00
{
2015-12-03 23:59:40 +00:00
m_instance = this ;
2015-12-15 07:00:19 +00:00
m_startPageText = tr ( " Searching for dive data " ) ;
2015-11-11 20:32:54 +00:00
// create location manager service
2015-12-03 23:59:40 +00:00
locationProvider = new GpsLocation ( & appendTextToLogStandalone , this ) ;
2015-12-15 07:00:19 +00:00
set_git_update_cb ( & gitProgressCB ) ;
2015-12-05 03:34:59 +00:00
}
2015-11-11 20:32:54 +00:00
2015-12-05 03:34:59 +00:00
void QMLManager : : finishSetup ( )
{
2015-11-11 20:32:54 +00:00
// Initialize cloud credentials.
2015-07-10 07:47:26 +00:00
setCloudUserName ( prefs . cloud_storage_email ) ;
setCloudPassword ( prefs . cloud_storage_password ) ;
2015-07-21 08:57:10 +00:00
setSaveCloudPassword ( prefs . save_password_local ) ;
2015-11-18 21:14:19 +00:00
// if the cloud credentials are valid, we should get the GPS Webservice ID as well
if ( ! same_string ( prefs . cloud_storage_email , " " ) & &
2015-12-20 00:08:10 +00:00
! same_string ( prefs . cloud_storage_password , " " ) ) {
appendTextToLog ( " have cloud credentials, trying to connect " ) ;
2015-12-05 03:34:59 +00:00
tryRetrieveDataFromBackend ( ) ;
2015-12-20 00:08:10 +00:00
} else {
appendTextToLog ( " no cloud credentials, tell user no dives found " ) ;
setStartPageText ( tr ( " No recorded dives found. You can download your dives to this device from the Subsurface cloud storage service, from your dive computer, or add them manually. " ) ) ;
}
2015-11-14 17:10:06 +00:00
setDistanceThreshold ( prefs . distance_threshold ) ;
setTimeThreshold ( prefs . time_threshold / 60 ) ;
2015-06-04 10:29:50 +00:00
}
QMLManager : : ~ QMLManager ( )
{
2015-12-03 23:59:40 +00:00
m_instance = NULL ;
}
QMLManager * QMLManager : : instance ( )
{
return m_instance ;
2015-06-04 10:29:50 +00:00
}
2015-07-10 07:47:26 +00:00
void QMLManager : : savePreferences ( )
{
QSettings s ;
2015-11-14 17:10:06 +00:00
s . beginGroup ( " LocationService " ) ;
s . setValue ( " time_threshold " , timeThreshold ( ) * 60 ) ;
prefs . time_threshold = timeThreshold ( ) * 60 ;
s . setValue ( " distance_threshold " , distanceThreshold ( ) ) ;
prefs . distance_threshold = distanceThreshold ( ) ;
2015-12-05 03:34:59 +00:00
s . sync ( ) ;
2015-12-03 22:30:30 +00:00
}
2015-12-05 03:34:59 +00:00
# define CLOUDURL QString(prefs.cloud_base_url)
# define CLOUDREDIRECTURL CLOUDURL + " / cgi-bin / redirect.pl"
2015-12-03 22:30:30 +00:00
void QMLManager : : saveCloudCredentials ( )
{
QSettings s ;
bool cloudCredentialsChanged = false ;
2015-07-10 07:47:26 +00:00
s . beginGroup ( " CloudStorage " ) ;
s . setValue ( " email " , cloudUserName ( ) ) ;
2015-07-21 08:57:10 +00:00
s . setValue ( " save_password_local " , saveCloudPassword ( ) ) ;
if ( saveCloudPassword ( ) )
s . setValue ( " password " , cloudPassword ( ) ) ;
2015-07-10 07:47:26 +00:00
s . sync ( ) ;
2015-07-13 00:39:13 +00:00
if ( ! same_string ( prefs . cloud_storage_email , qPrintable ( cloudUserName ( ) ) ) ) {
free ( prefs . cloud_storage_email ) ;
prefs . cloud_storage_email = strdup ( qPrintable ( cloudUserName ( ) ) ) ;
2015-11-18 21:14:19 +00:00
cloudCredentialsChanged = true ;
2015-07-13 00:39:13 +00:00
}
2015-11-18 21:12:34 +00:00
if ( saveCloudPassword ( ) ! = prefs . save_password_local )
2015-07-21 08:57:10 +00:00
prefs . save_password_local = saveCloudPassword ( ) ;
2015-11-18 21:14:19 +00:00
cloudCredentialsChanged | = ! same_string ( prefs . cloud_storage_password , qPrintable ( cloudPassword ( ) ) ) ;
2015-07-21 08:57:10 +00:00
if ( saveCloudPassword ( ) ) {
if ( ! same_string ( prefs . cloud_storage_password , qPrintable ( cloudPassword ( ) ) ) ) {
free ( prefs . cloud_storage_password ) ;
prefs . cloud_storage_password = strdup ( qPrintable ( cloudPassword ( ) ) ) ;
}
2015-07-13 00:39:13 +00:00
}
2015-12-05 03:34:59 +00:00
if ( cloudCredentialsChanged ) {
free ( prefs . userid ) ;
prefs . userid = NULL ;
tryRetrieveDataFromBackend ( ) ;
}
}
void QMLManager : : checkCredentialsAndExecute ( execute_function_type execute )
{
// if the cloud credentials are present, we should try to get the GPS Webservice ID
// and (if we haven't done so) load the dive list
2015-11-18 21:14:19 +00:00
if ( ! same_string ( prefs . cloud_storage_email , " " ) & &
! same_string ( prefs . cloud_storage_password , " " ) ) {
2015-12-05 03:34:59 +00:00
appendTextToLog ( " Have credentials, let's see if they are valid " ) ;
if ( ! mgr )
mgr = new QNetworkAccessManager ( this ) ;
2015-12-05 04:39:12 +00:00
connect ( mgr , & QNetworkAccessManager : : authenticationRequired , this , & QMLManager : : provideAuth , Qt : : UniqueConnection ) ;
connect ( mgr , & QNetworkAccessManager : : finished , this , execute , Qt : : UniqueConnection ) ;
2015-12-05 03:34:59 +00:00
QUrl url ( CLOUDREDIRECTURL ) ;
request = QNetworkRequest ( url ) ;
request . setRawHeader ( " User-Agent " , getUserAgent ( ) . toUtf8 ( ) ) ;
request . setRawHeader ( " Accept " , " text/html " ) ;
reply = mgr - > get ( request ) ;
connect ( reply , SIGNAL ( error ( QNetworkReply : : NetworkError ) ) , this , SLOT ( handleError ( QNetworkReply : : NetworkError ) ) ) ;
connect ( reply , & QNetworkReply : : sslErrors , this , & QMLManager : : handleSslErrors ) ;
2015-11-18 21:14:19 +00:00
}
2015-12-05 03:34:59 +00:00
}
void QMLManager : : tryRetrieveDataFromBackend ( )
{
checkCredentialsAndExecute ( & QMLManager : : retrieveUserid ) ;
2015-07-10 07:47:26 +00:00
}
2015-07-10 08:31:24 +00:00
void QMLManager : : loadDives ( )
{
2015-12-05 03:34:59 +00:00
checkCredentialsAndExecute ( & QMLManager : : loadDivesWithValidCredentials ) ;
}
void QMLManager : : provideAuth ( QNetworkReply * reply , QAuthenticator * auth )
{
if ( auth - > user ( ) = = QString ( prefs . cloud_storage_email ) & &
auth - > password ( ) = = QString ( prefs . cloud_storage_password ) ) {
// OK, credentials have been tried and didn't work, so they are invalid
appendTextToLog ( " Cloud credentials are invalid " ) ;
2015-12-20 00:08:10 +00:00
setStartPageText ( tr ( " No recorded dives found. You can download your dives to this device from the Subsurface cloud storage service, from your dive computer, or add them manually. " ) ) ;
2015-12-05 03:34:59 +00:00
reply - > disconnect ( ) ;
reply - > abort ( ) ;
reply - > deleteLater ( ) ;
2015-11-30 18:15:04 +00:00
return ;
}
2015-12-05 03:34:59 +00:00
auth - > setUser ( prefs . cloud_storage_email ) ;
auth - > setPassword ( prefs . cloud_storage_password ) ;
}
void QMLManager : : handleSslErrors ( const QList < QSslError > & errors )
{
2015-12-15 07:00:19 +00:00
setStartPageText ( tr ( " Cannot open cloud storage: Error creating https connection " ) ) ;
2015-12-05 03:34:59 +00:00
Q_FOREACH ( QSslError e , errors ) {
qDebug ( ) < < e . errorString ( ) ;
}
reply - > abort ( ) ;
reply - > deleteLater ( ) ;
}
2015-11-30 18:15:04 +00:00
2015-12-05 03:34:59 +00:00
void QMLManager : : handleError ( QNetworkReply : : NetworkError nError )
{
2015-12-15 07:00:19 +00:00
QString errorString = reply - > errorString ( ) ;
qDebug ( ) < < " handleError " < < nError < < errorString ;
setStartPageText ( tr ( " Cannot open cloud storage: %1 " ) . arg ( errorString ) ) ;
2015-12-05 03:34:59 +00:00
reply - > abort ( ) ;
reply - > deleteLater ( ) ;
}
void QMLManager : : retrieveUserid ( )
{
if ( reply - > attribute ( QNetworkRequest : : HttpStatusCodeAttribute ) ! = 302 ) {
appendTextToLog ( QString ( " Cloud storage connection not working correctly: " ) + reply - > readAll ( ) ) ;
return ;
}
QString userid ( prefs . userid ) ;
2015-12-20 00:20:20 +00:00
if ( userid . isEmpty ( ) ) {
if ( same_string ( prefs . cloud_storage_email , " " ) | | same_string ( prefs . cloud_storage_password , " " ) ) {
appendTextToLog ( " cloud user name or password are empty, can't retrieve web user id " ) ;
return ;
}
appendTextToLog ( QString ( " calling getUserid with user %1 " ) . arg ( prefs . cloud_storage_email ) ) ;
2015-12-05 03:34:59 +00:00
userid = locationProvider - > getUserid ( prefs . cloud_storage_email , prefs . cloud_storage_password ) ;
2015-12-20 00:20:20 +00:00
}
2015-12-05 03:34:59 +00:00
if ( ! userid . isEmpty ( ) ) {
// overwrite the existing userid
free ( prefs . userid ) ;
prefs . userid = strdup ( qPrintable ( userid ) ) ;
QSettings s ;
s . setValue ( " subsurface_webservice_uid " , prefs . userid ) ;
s . sync ( ) ;
}
if ( ! loadFromCloud ( ) )
loadDivesWithValidCredentials ( ) ;
}
2015-12-15 07:00:19 +00:00
void QMLManager : : loadDiveProgress ( int percent )
{
QString text ( tr ( " Loading dive list from cloud storage. " ) ) ;
while ( percent > 0 ) {
text . append ( " . " ) ;
percent - = 10 ;
}
setStartPageText ( text ) ;
}
2015-12-05 03:34:59 +00:00
void QMLManager : : loadDivesWithValidCredentials ( )
{
if ( reply - > attribute ( QNetworkRequest : : HttpStatusCodeAttribute ) ! = 302 ) {
appendTextToLog ( QString ( " Cloud storage connection not working correctly: " ) + reply - > readAll ( ) ) ;
2015-12-15 07:00:19 +00:00
setStartPageText ( tr ( " Cannot connect to cloud storage " ) ) ;
2015-12-05 03:34:59 +00:00
return ;
}
appendTextToLog ( " Cloud credentials valid, loading dives... " ) ;
2015-12-15 07:00:19 +00:00
loadDiveProgress ( 0 ) ;
2015-07-10 08:31:24 +00:00
QString url ;
if ( getCloudURL ( url ) ) {
2015-12-15 07:00:19 +00:00
QString errorString ( get_error_string ( ) ) ;
appendTextToLog ( errorString ) ;
setStartPageText ( tr ( " Cloud storage error: %1 " ) . arg ( errorString ) ) ;
2015-07-10 08:31:24 +00:00
return ;
}
2015-07-24 20:18:30 +00:00
clear_dive_file_data ( ) ;
2015-07-10 08:31:24 +00:00
QByteArray fileNamePrt = QFile : : encodeName ( url ) ;
int error = parse_file ( fileNamePrt . data ( ) ) ;
if ( ! error ) {
2015-07-13 00:39:13 +00:00
report_error ( " filename is now %s " , fileNamePrt . data ( ) ) ;
2015-12-01 17:37:47 +00:00
const char * error_string = get_error_string ( ) ;
appendTextToLog ( error_string ) ;
2015-07-10 08:31:24 +00:00
set_filename ( fileNamePrt . data ( ) , true ) ;
2015-07-13 00:39:13 +00:00
} else {
2015-12-01 17:37:47 +00:00
report_error ( " failed to open file %s " , fileNamePrt . data ( ) ) ;
2015-12-15 07:00:19 +00:00
QString errorString ( get_error_string ( ) ) ;
appendTextToLog ( errorString ) ;
setStartPageText ( tr ( " Cloud storage error: %1 " ) . arg ( errorString ) ) ;
2015-12-03 01:50:47 +00:00
return ;
2015-07-10 08:31:24 +00:00
}
process_dives ( false , false ) ;
2015-07-24 20:18:30 +00:00
2015-07-10 08:31:24 +00:00
int i ;
struct dive * d ;
2015-11-30 18:09:46 +00:00
DiveListModel : : instance ( ) - > clear ( ) ;
2015-07-24 20:18:30 +00:00
for_each_dive ( i , d ) {
DiveListModel : : instance ( ) - > addDive ( d ) ;
}
2015-12-01 17:15:40 +00:00
appendTextToLog ( QString ( " %1 dives loaded " ) . arg ( i ) ) ;
2015-12-15 07:00:19 +00:00
if ( dive_table . nr = = 0 )
setStartPageText ( tr ( " Cloud storage open successfully. No dives in dive list. " ) ) ;
2015-12-03 02:49:02 +00:00
setLoadFromCloud ( true ) ;
2015-07-17 15:28:01 +00:00
}
void QMLManager : : commitChanges ( QString diveId , QString suit , QString buddy , QString diveMaster , QString notes )
{
struct dive * d = get_dive_by_uniq_id ( diveId . toInt ( ) ) ;
bool diveChanged = false ;
2015-12-08 06:22:07 +00:00
if ( ! same_string ( d - > suit , suit . toUtf8 ( ) . data ( ) ) ) {
2015-07-17 15:28:01 +00:00
diveChanged = true ;
free ( d - > suit ) ;
d - > suit = strdup ( suit . toUtf8 ( ) . data ( ) ) ;
}
2015-12-08 06:22:07 +00:00
if ( ! same_string ( d - > buddy , buddy . toUtf8 ( ) . data ( ) ) ) {
2015-07-17 15:28:01 +00:00
diveChanged = true ;
free ( d - > buddy ) ;
d - > buddy = strdup ( buddy . toUtf8 ( ) . data ( ) ) ;
}
2015-12-08 06:22:07 +00:00
if ( ! same_string ( d - > divemaster , diveMaster . toUtf8 ( ) . data ( ) ) ) {
2015-07-17 15:28:01 +00:00
diveChanged = true ;
free ( d - > divemaster ) ;
d - > divemaster = strdup ( diveMaster . toUtf8 ( ) . data ( ) ) ;
}
2015-12-08 06:22:07 +00:00
if ( ! same_string ( d - > notes , notes . toUtf8 ( ) . data ( ) ) ) {
2015-07-17 15:28:01 +00:00
diveChanged = true ;
free ( d - > notes ) ;
d - > notes = strdup ( notes . toUtf8 ( ) . data ( ) ) ;
}
2015-12-08 06:24:56 +00:00
if ( diveChanged ) {
DiveListModel : : instance ( ) - > updateDive ( d ) ;
2015-11-19 03:26:07 +00:00
mark_divelist_changed ( true ) ;
2015-12-08 06:24:56 +00:00
}
2015-07-17 15:28:01 +00:00
}
void QMLManager : : saveChanges ( )
{
2015-12-03 02:49:02 +00:00
if ( ! loadFromCloud ( ) ) {
2015-12-03 23:59:40 +00:00
appendTextToLog ( " Don't save dives without loading from the cloud, first. " ) ;
2015-12-03 02:49:02 +00:00
return ;
}
2015-12-03 23:59:40 +00:00
appendTextToLog ( " Saving dives. " ) ;
2015-07-17 15:28:01 +00:00
QString fileName ;
if ( getCloudURL ( fileName ) ) {
2015-08-19 07:17:52 +00:00
appendTextToLog ( get_error_string ( ) ) ;
2015-07-17 15:28:01 +00:00
return ;
}
if ( save_dives ( fileName . toUtf8 ( ) . data ( ) ) ) {
2015-08-19 07:17:52 +00:00
appendTextToLog ( get_error_string ( ) ) ;
2015-07-17 15:28:01 +00:00
return ;
}
2015-08-19 07:17:52 +00:00
appendTextToLog ( " Dive saved. " ) ;
2015-07-17 15:28:01 +00:00
set_filename ( fileName . toUtf8 ( ) . data ( ) , true ) ;
mark_divelist_changed ( false ) ;
2015-07-10 08:31:24 +00:00
}
2015-08-10 05:35:47 +00:00
void QMLManager : : addDive ( )
{
2015-08-19 07:17:52 +00:00
appendTextToLog ( " Adding new dive. " ) ;
2015-08-16 08:57:18 +00:00
DiveListModel : : instance ( ) - > startAddDive ( ) ;
2015-08-10 05:35:47 +00:00
}
2015-11-13 04:23:00 +00:00
void QMLManager : : applyGpsData ( )
{
locationProvider - > applyLocations ( ) ;
}
2015-11-14 01:21:43 +00:00
void QMLManager : : sendGpsData ( )
{
locationProvider - > uploadToServer ( ) ;
}
2015-11-14 01:20:45 +00:00
void QMLManager : : clearGpsData ( )
{
locationProvider - > clearGpsData ( ) ;
}
2015-08-19 07:17:52 +00:00
QString QMLManager : : logText ( ) const
{
2015-11-13 17:17:13 +00:00
QString logText = m_logText + QString ( " \n Numer of GPS fixes: %1 " ) . arg ( locationProvider - > getGpsNum ( ) ) ;
return logText ;
2015-08-19 07:17:52 +00:00
}
void QMLManager : : setLogText ( const QString & logText )
{
m_logText = logText ;
2015-08-20 09:08:59 +00:00
emit logTextChanged ( ) ;
2015-08-19 07:17:52 +00:00
}
void QMLManager : : appendTextToLog ( const QString & newText )
{
m_logText + = " \n " + newText ;
2015-08-20 09:08:59 +00:00
emit logTextChanged ( ) ;
2015-08-19 07:17:52 +00:00
}
2015-07-21 08:57:10 +00:00
bool QMLManager : : saveCloudPassword ( ) const
{
return m_saveCloudPassword ;
}
void QMLManager : : setSaveCloudPassword ( bool saveCloudPassword )
{
m_saveCloudPassword = saveCloudPassword ;
}
2015-11-11 20:34:56 +00:00
bool QMLManager : : locationServiceEnabled ( ) const
{
return m_locationServiceEnabled ;
}
void QMLManager : : setLocationServiceEnabled ( bool locationServiceEnabled )
{
m_locationServiceEnabled = locationServiceEnabled ;
locationProvider - > serviceEnable ( m_locationServiceEnabled ) ;
}
2015-07-10 08:31:24 +00:00
2015-12-20 02:41:10 +00:00
bool QMLManager : : verboseEnabled ( ) const
{
return m_verboseEnabled ;
}
void QMLManager : : setVerboseEnabled ( bool verboseMode )
{
m_verboseEnabled = verboseMode ;
verbose = verboseMode ;
qDebug ( ) < < " verbose is " < < verbose ;
emit verboseEnabledChanged ( ) ;
}
2015-07-10 07:47:26 +00:00
QString QMLManager : : cloudPassword ( ) const
{
return m_cloudPassword ;
}
void QMLManager : : setCloudPassword ( const QString & cloudPassword )
{
m_cloudPassword = cloudPassword ;
emit cloudPasswordChanged ( ) ;
}
QString QMLManager : : cloudUserName ( ) const
{
return m_cloudUserName ;
}
void QMLManager : : setCloudUserName ( const QString & cloudUserName )
{
m_cloudUserName = cloudUserName ;
emit cloudUserNameChanged ( ) ;
}
2015-11-14 01:14:22 +00:00
2015-11-14 17:10:06 +00:00
int QMLManager : : distanceThreshold ( ) const
{
return m_distanceThreshold ;
}
void QMLManager : : setDistanceThreshold ( int distance )
{
m_distanceThreshold = distance ;
emit distanceThresholdChanged ( ) ;
}
int QMLManager : : timeThreshold ( ) const
{
return m_timeThreshold ;
}
void QMLManager : : setTimeThreshold ( int time )
{
m_timeThreshold = time ;
emit timeThresholdChanged ( ) ;
}
2015-12-03 02:49:02 +00:00
bool QMLManager : : loadFromCloud ( ) const
{
return m_loadFromCloud ;
}
void QMLManager : : setLoadFromCloud ( bool done )
{
m_loadFromCloud = done ;
emit loadFromCloudChanged ( ) ;
}
2015-12-15 07:00:19 +00:00
QString QMLManager : : startPageText ( ) const
{
return m_startPageText ;
}
void QMLManager : : setStartPageText ( QString text )
{
m_startPageText = text ;
emit startPageTextChanged ( ) ;
}