Main | License | Installation | FAQ | Screenshots | Contact | Links | Sf.net | Freshmeat.net | KDE-Apps.org
Requirements | Design | Modules | Class Hierarchy | Alphabetical List | Data Structures | File List | Data Fields | Globals | Related Pages

databaseWizard.ui.h

Go to the documentation of this file.
00001 /****************************************************************************
00002  ** ui.h extension file, included from the uic-generated form implementation.
00003  **
00004  ** If you wish to add, delete or rename functions or slots use
00005  ** Qt Designer which will update this file, preserving your code. Create an
00006  ** init() function in place of a constructor, and a destroy() function in
00007  ** place of a destructor.
00008  *****************************************************************************/
00009 
00010 void DatabaseWizard::init()
00011 {
00012 #ifndef NDEBUG
00013   std::cerr << "Initialise" << std::endl;
00014 #endif
00015 
00016   // Set default values.
00017   databaseUserEdit->setText( getenv( "USER" ) );
00018   // portSpinBox->setValue( MYSQL_PORT );
00019   
00020   setNextEnabled( connectPage       , false );
00021   setNextEnabled( createDatabasePage, false );
00022   setNextEnabled( createUserPage    , false );
00023   setFinishEnabled( importRecipesPage, true );
00024 
00025   const char *home = getenv( "HOME" );
00026 #ifndef NDEBUG
00027   std::cerr << "HOME = " << home << std::endl;
00028 #endif
00029   if ( home != NULL ) {
00030     socketEdit->setText( QString( home ) +
00031                          "/.kde/share/apps/anymeal/db/mysql.sock" );
00032   };
00033   serverWidgetStack->raiseWidget( serverTypeCombo->currentItem() );
00034 }
00035 
00036 
00037 void DatabaseWizard::connectButtonEnable()
00038 {
00039   serverUser.reset();
00040   serverRoot.reset();
00041   daemon.reset();
00042 
00043   connectButton->setEnabled
00044     ( !( serverTypeCombo->currentItem() == 0 ?
00045          serverEdit->text() :
00046          socketEdit->text() ).isEmpty() &&
00047       !rootUserEdit->text().isEmpty() && 
00048       ( !rootPassWordCheckBox->isChecked() ||
00049         !rootPassWordEdit->text().isEmpty() ) );
00050 
00051   setNextEnabled( connectPage, false );
00052   createDatabaseEnable();
00053 }
00054 
00055 
00056 void DatabaseWizard::connectToServer()
00057 {
00058   try {
00059 
00060     assert( serverTypeCombo->count() == 2 );
00061     assert( serverTypeCombo->text( 0 ) == i18n( "Network" ) );
00062     assert( serverTypeCombo->text( 1 ) == i18n( "Embedded" ) );
00063 
00064     assert( !( serverTypeCombo->currentItem() == 0 ?
00065                serverEdit->text() :
00066                socketEdit->text() ).isEmpty() );
00067     assert( !rootUserEdit->text().isEmpty() );
00068     assert( !rootPassWordCheckBox->isChecked() ||
00069             !rootPassWordEdit->text().isEmpty() );
00070 
00071     switch ( serverTypeCombo->currentItem() ) {
00072     case 0: {
00073       DisplayWaitCursor w;
00074       serverRoot = MySQLServerPtr
00075         ( new MySQLNetwork( rootUserEdit->text(), 
00076                             rootPassWordCheckBox->isChecked() ?
00077                             (const char *)rootPassWordEdit->text() : "",
00078                             serverEdit->text(), MYSQL_PORT ) );
00079       break;}
00080     case 1: {
00081       daemon = MySQLDaemonPtr( new MySQLDaemon
00082                                ( createDatabase( folderEdit->text() ),
00083                                  socketEdit->text() ) );
00084       DisplayWaitCursor w;
00085       serverRoot = MySQLServerPtr
00086         ( new MySQLSocket( rootUserEdit->text(), 
00087                            rootPassWordCheckBox->isChecked() ?
00088                            (const char *)rootPassWordEdit->text() : "",
00089                            socketEdit->text(), daemon ) );
00090       break;}
00091     default:
00092       assert( false );
00093     };
00094 
00095     // Lock repetition of this step.
00096     connectButton->setEnabled( false );
00097     // Allow next step.
00098     setNextEnabled( connectPage, true );
00099 
00100   } catch ( std::exception &e ) {
00101     
00102 #ifndef NDEBUG
00103     std::cerr << "Error connecting." << std::endl;
00104 #endif
00105     KMessageBox::error( this, e.what() );
00106 
00107   }; 
00108 }
00109 
00110 
00111 void DatabaseWizard::createDatabaseEnable()
00112 {
00113   createDatabaseButton->setEnabled( !databaseEdit->text().isEmpty() );
00114   setNextEnabled( createDatabasePage, false );
00115   createUserEnable();
00116 }
00117 
00118 
00119 void DatabaseWizard::createDatabase()
00120 {
00121   assert( serverRoot );
00122   assert( !databaseEdit->text().isEmpty() );
00123 
00124   // Update initial value for allowed clients to sensible value.
00125   clientEdit->setText( ( serverEdit->text() == "localhost" ||
00126                          serverTypeCombo->currentItem() == 1 ) ?
00127                        "localhost" : "%" );
00128 
00129   try {
00130 
00131     std::ostringstream createQuery;
00132     createQuery << "CREATE DATABASE " << databaseEdit->text()
00133                 << " DEFAULT CHARACTER SET utf8;";
00134     
00135     bool exist = false;
00136 
00137     // Try to set up a UTF-8 database.
00138     if ( mysql_query( serverRoot->getConnection(),
00139                       createQuery.str().c_str() ) != 0 ) {
00140       if ( mysql_errno( serverRoot->getConnection() ) == ER_DB_CREATE_EXISTS )
00141         exist = true;
00142       else {
00143         // Probably an older version of MySQL. Try initialising without
00144         // UTF-8 character-set.
00145         std::ostringstream createQuery;
00146         createQuery << "CREATE DATABASE " << databaseEdit->text() << ';';
00147         if ( mysql_query( serverRoot->getConnection(),
00148                           createQuery.str().c_str() ) != 0 ) {
00149           if ( mysql_errno( serverRoot->getConnection() ) == ER_DB_CREATE_EXISTS )
00150             exist = true;
00151           else
00152             ERRORMACRO( false,
00153                         Error, , i18n( "Error creating database: %1" ).
00154                         arg( mysql_error( serverRoot->getConnection() ) ) );
00155         };
00156           
00157         KMessageBox::sorry( this,
00158                             i18n( "Could not configure database to use "
00159                                   "UTF-8 character set. "
00160                                   "If you want a UTF-8-aware database, you "
00161                                   "should upgrade to MySQL 4.1 or higher." ) );
00162       };
00163     };
00164 
00165     if ( exist )
00166       ERRORMACRO( KMessageBox::warningContinueCancel
00167                   ( this,
00168                     i18n( "Database '%1' seems to be existing already. "
00169                           "Do you want to use it?" ).
00170                     arg( databaseEdit->text() ) ) == KMessageBox::Continue,
00171                   Error, ,
00172                   i18n( "Database '%1' is existing already." ).
00173                   arg( databaseEdit->text() ) );
00174     
00175     try {
00176 
00177       // Try to connect to database (using administrator-account).
00178       CookBook cookBook
00179         ( DatabasePtr( new MySQLDatabase
00180                        ( serverRoot, databaseEdit->text() ) ),
00181           findAnyMealFile( "appdata", "scripts/mysqlIn.xsl" ),
00182           findAnyMealFile( "appdata", "scripts/mysqlOut.xsl" ),
00183           exist );
00184 
00185       // If database is new, the tables have to be created.
00186       if ( !exist ) {
00187         DisplayWaitCursor w;
00188         std::string query( "<?xml version='1.0' encoding='UTF-8'?><create/>" );
00189         cookBook.getXMLLayer()->translate( query );
00190       };
00191       
00192     } catch ( CookBookDeprecated &e ) {
00193 
00194       // The database is not up to date.
00195       int version = e.getVersion();
00196       
00197       if ( KMessageBox::warningContinueCancel
00198            ( this,
00199              i18n( "Do you want to update the database "
00200                    "from version %1 to version %2? "
00201                    "It is recommended to do a backup "
00202                    "before." ).
00203              arg( versionText( version ) ).
00204              arg( versionText( DATABASEVERSION ) ),
00205              i18n( "Update Database" ) ) == KMessageBox::Continue ) {
00206         
00207         DisplayWaitCursor w;
00208         
00209         // View as cookbook without performing version-check and update.
00210         CookBook cookBook
00211           ( DatabasePtr( new MySQLDatabase
00212                          ( serverRoot, databaseEdit->text() ) ),
00213             findAnyMealFile( "appdata", "scripts/mysqlIn.xsl" ),
00214             findAnyMealFile( "appdata", "scripts/mysqlOut.xsl" ),
00215             false );
00216         
00217         cookBook.update();
00218         
00219       } else
00220         throw e;
00221 
00222     };
00223 
00224     // Lock repetition of this step.
00225     createDatabaseButton->setEnabled( false );
00226     // Allow next step.
00227     setNextEnabled( createDatabasePage, true );
00228 
00229   } catch ( std::exception &e ) {
00230 
00231     KMessageBox::error( this, e.what() );
00232     
00233   };
00234 
00235 }
00236 
00237 
00238 void DatabaseWizard::createUserEnable()
00239 {
00240   // Name of client-host may be empty!
00241   // Changing it requires redoing the grant-command though.
00242   createUserButton->setEnabled
00243     ( !databaseUserEdit->text().isEmpty() &&
00244       ( !databasePassWordCheckBox->isChecked() ||
00245         ( !databasePassWordEdit->text().isEmpty() &&
00246           databasePassWordEdit->text() ==
00247           databasePassWordConfirmEdit->text() ) ) );
00248   setNextEnabled( createUserPage, false );
00249 }
00250 
00251 
00252 void DatabaseWizard::createUser()
00253 {
00254   assert( serverRoot );
00255 
00256   try {
00257     
00258     assert( !databaseUserEdit->text().isEmpty() );
00259     assert( !databasePassWordCheckBox->isChecked() ||
00260             !databasePassWordEdit->text().isEmpty() );
00261 
00262     DisplayWaitCursor w;
00263 
00264     std::ostringstream grantQuery;
00265     grantQuery << "GRANT ALL ON " << databaseEdit->text() << ".* TO "
00266                << databaseUserEdit->text();
00267     if ( !clientEdit->text().isEmpty() )
00268       grantQuery << "@'" << clientEdit->text() << '\'';
00269     if ( databasePassWordCheckBox->isChecked() ) {
00270       assert( !databasePassWordEdit->text().isEmpty() );
00271       grantQuery << " IDENTIFIED BY '" << databasePassWordEdit->text() << "'";
00272     };
00273     grantQuery << ';';
00274 
00275     ERRORMACRO( !mysql_query( serverRoot->getConnection(),
00276                               grantQuery.str().c_str() ), Error, ,
00277                 i18n( "Error setting up database account: %1" ).
00278                 arg( mysql_error( serverRoot->getConnection() ) ) );
00279 
00280     // Try to connect in case user already existed!
00281     switch ( serverTypeCombo->currentItem() ) {
00282     case 0:
00283       serverUser = MySQLServerPtr
00284         ( new MySQLNetwork( databaseUserEdit->text(), 
00285                             databasePassWordCheckBox->isChecked() ?
00286                             (const char *)databasePassWordEdit->text() : "",
00287                             serverEdit->text(), MYSQL_PORT ) );
00288       break;
00289     case 1:
00290       assert( daemon );
00291       serverUser = MySQLServerPtr
00292         ( new MySQLSocket( databaseUserEdit->text(), 
00293                            databasePassWordCheckBox->isChecked() ?
00294                            (const char *)databasePassWordEdit->text() : "",
00295                            socketEdit->text(), daemon ) );
00296       break;
00297     default:
00298       assert( false );
00299     };
00300 
00301     // Check access to database.
00302     MySQLDatabase( serverUser, databaseEdit->text() );
00303 
00304     // Lock repetition of this step.
00305     createUserButton->setEnabled( false );
00306     // Allow next step and finalisation.
00307     setNextEnabled( createUserPage, true );
00308 
00309   } catch ( std::exception &e ) {
00310     
00311     KMessageBox::error( this, e.what() );
00312 
00313   };
00314 }
00315 
00316 
00317 void DatabaseWizard::importRecipes()
00318 {
00319   assert( serverUser );
00320 
00321   try {
00322     
00323     ImportMealMasterDialog importMealMasterDialog( this );
00324     importMealMasterDialog.databaseWizard = true;
00325     importMealMasterDialog.cookBook = CookBookPtr
00326       ( new CookBook
00327         ( DatabasePtr( new MySQLDatabase
00328                        ( serverUser, databaseEdit->text() ) ),
00329           findAnyMealFile( "appdata", "scripts/mysqlIn.xsl" ),
00330           findAnyMealFile( "appdata", "scripts/mysqlOut.xsl" ) ) );
00331     importMealMasterDialog.exec();
00332 
00333   } catch ( std::exception &e ) {
00334     
00335     KMessageBox::error( this, e.what() );
00336 
00337   };
00338 }
00339 
00340 
00341 void DatabaseWizard::selectSocket()
00342 {
00343   QString fileName =
00344     KFileDialog::getOpenFileName( ":dbfolder",
00345                                   i18n( "*.sock|Socket (*.sock)\n"
00346                                         "*|All Files(*)" ),
00347                                   this,
00348                                   i18n( "Select database socket" ) );
00349   if ( fileName != QString::null ) {
00350     socketEdit->setText( fileName );
00351   };
00352 }
00353 
00354 const std::string &DatabaseWizard::createDatabase( const std::string &dir )
00355 {
00356   if ( testFile( dir + "/mysql" ) != EISDIR ) {
00357     ERRORMACRO( KMessageBox::questionYesNo
00358                 ( this, i18n( "Directory '%1' does not exist. Should the "
00359                               "database be created?" ).arg( dir ),
00360                   i18n( "Database does not exist" ) ) == KMessageBox::Yes,
00361                 Error, ,
00362                 "Database '" << dir << "' does not exist." );
00363     std::string info = MySQLDaemon::create( dir, dir + "/mysql.sock" );
00364     KMessageBox::information( this, info, i18n( "Installation log" ) );
00365   };
00366   return dir;
00367 }
00368 
00369 
00370 void DatabaseWizard::socketChanged( const QString &_s )
00371 {
00372   std::string socket( (const char *)_s );
00373   unsigned int pos = socket.find_last_of( "/" );
00374   if ( pos != std::string::npos )
00375     folderEdit->setText( std::string( socket, 0, pos ).c_str() );
00376 }


anymeal 0.30 - recipe management software - Make the most of your food! - © Jan Wedekind Sun Sep 14 16:01:26 2008 - GNU Free Documentation License