open/close mapset

git-svn-id: http://svn.osgeo.org/qgis/trunk/qgis@3988 c8812cc2-4d05-0410-92ff-de0c093fc19c
This commit is contained in:
rabla 2005-09-27 09:17:41 +00:00
parent 2069ffaeca
commit f1dbe41ab6
2 changed files with 230 additions and 0 deletions

View File

@ -18,6 +18,11 @@
#include <iostream>
#include "qstring.h"
#include "qprocess.h"
#include "qfile.h"
#include "qfileinfo.h"
#include "qdir.h"
#include "qtextstream.h"
#include "qgsgrass.h"
void QgsGrass::init( void ) {
@ -45,6 +50,22 @@ void QgsGrass::init( void ) {
// Set program name
G_set_program_name ("QGIS");
// Add path to GRASS modules
// TODO: do that portable
QString gisBase = getenv("GISBASE");
QString path = "PATH=" + gisBase + "/bin";
path.append ( ":" + gisBase + "/scripts" );
QString p = getenv ("PATH");
path.append ( ":" + p );
#ifdef QGISDEBUG
std::cerr << "set PATH: " << path.local8Bit() << std::endl;
#endif
char *pathEnvChar = new char[path.length()+1];
strcpy ( pathEnvChar, const_cast<char *>(path.ascii()) );
putenv( pathEnvChar );
initialized = 1;
}
}
@ -141,3 +162,194 @@ QString QgsGrass::getErrorMessage ( void ) {
return error_message;
}
QString QgsGrass::openMapset ( QString gisdbase, QString location, QString mapset )
{
#ifdef QGISDEBUG
std::cerr << "QgsGrass::openMapset" << std::endl;
std::cerr << "gisdbase = " << gisdbase << std::endl;
std::cerr << "location = " << location << std::endl;
std::cerr << "mapset = " << mapset << std::endl;
#endif
QString mapsetPath = gisdbase + "/" + location + "/" + mapset;
// Check if the mapset is in use
QString gisBase = getenv("GISBASE");
if ( gisBase.isNull() ) return "GISBASE is not set.";
QString lock = mapsetPath + "/.gislock";
QFile lockFile ( lock );
QProcess *process = new QProcess();
process->addArgument ( gisBase + "/etc/lock" ); // lock program
process->addArgument ( lock ); // lock file
// TODO: getpid() probably is not portable
int pid = getpid();
#ifdef QGISDEBUG
std::cerr << "pid = " << pid << std::endl;
#endif
process->addArgument ( QString::number(pid) );
if ( !process->start() )
{
return "Cannot start " + gisBase + "/etc/lock";
}
// TODO better wait
while ( process->isRunning () ) { }
int status = process->exitStatus ();
delete process;
#ifdef QGISDEBUG
std::cerr << "status = " << status << std::endl;
#endif
if ( status > 0 ) return "Mapset is already in use.";
// Create temporary directory
QFileInfo info ( mapsetPath );
QString user = info.owner();
mTmp = "/tmp/grass6-" + user + "-" + QString::number(pid);
QDir dir ( mTmp );
if ( dir.exists() )
{
QFileInfo dirInfo(mTmp);
if ( !dirInfo.isWritable() )
{
lockFile.remove();
return "Temporary directory " + mTmp + " exist but is not writable";
}
}
else if ( !dir.mkdir( mTmp ) )
{
lockFile.remove();
return "Cannot create temporary directory " + mTmp;
}
// Create GISRC file
QString globalGisrc = QDir::home().path() + "/.grassrc6";
mGisrc = mTmp + "/gisrc";
#ifdef QGISDEBUG
std::cerr << "globalGisrc = " << globalGisrc << std::endl;
std::cerr << "mGisrc = " << mGisrc << std::endl;
#endif
QFile out ( mGisrc );
if ( !out.open( IO_WriteOnly ) )
{
lockFile.remove();
return "Cannot create " + mGisrc;
}
QTextStream stream ( &out );
QFile in ( globalGisrc );
QString line;
if ( in.open( IO_ReadOnly ) )
{
while ( in.readLine( line, 1000 ) != -1 )
{
if ( line.contains("GISDBASE:") ||
line.contains("LOCATION_NAME:") ||
line.contains("MAPSET:") )
{
continue;
}
stream << line;
}
in.close();
}
line = "GISDBASE: " + gisdbase + "\n";
stream << line;
line = "LOCATION_NAME: " + location + "\n";
stream << line;
line = "MAPSET: " + mapset + "\n";
stream << line;
out.close();
// Set GISRC enviroment variable
/* _Correct_ putenv() implementation is not making copy! */
QString gisrcEnv = "GISRC=" + mGisrc;
char *gisrcEnvChar = new char[gisrcEnv.length()+1];
strcpy ( gisrcEnvChar, const_cast<char *>(gisrcEnv.ascii()) );
putenv( gisrcEnvChar );
// Reinitialize GRASS
G__setenv( "GISRC", const_cast<char *>(gisrcEnv.ascii()) );
G__setenv( "GISDBASE", const_cast<char *>(gisdbase.ascii()) );
G__setenv( "LOCATION_NAME", const_cast<char *>(location.ascii()) );
G__setenv( "MAPSET", const_cast<char *>(mapset.ascii()) );
defaultGisdbase = gisdbase;
defaultLocation = location;
defaultMapset = mapset;
active = true;
// Close old mapset
if ( mMapsetLock.length() > 0 )
{
QFile file ( mMapsetLock );
file.remove();
}
mMapsetLock = lock;
return NULL;
}
QString QgsGrass::closeMapset ( )
{
#ifdef QGISDEBUG
std::cerr << "QgsGrass::closeMapset" << std::endl;
#endif
if ( mMapsetLock.length() > 0 )
{
QFile file ( mMapsetLock );
if ( !file.remove() )
{
return "Cannot remove mapset lock: " + mMapsetLock;
}
mMapsetLock = "";
putenv( "GISRC" );
// Reinitialize GRASS
G__setenv( "GISRC", "" );
G__setenv( "GISDBASE", "" );
G__setenv( "LOCATION_NAME", "" );
G__setenv( "MAPSET", "" );
defaultGisdbase = "";
defaultLocation = "";
defaultMapset = "";
active = 0;
// Delete temporary dir
// To be sure that we dont delete '/' for example
if ( mTmp.left(4) == "/tmp" )
{
QDir dir ( mTmp );
for ( int i = 0; i < dir.count(); i++ )
{
if ( dir[i] == "." || dir[i] == ".." ) continue;
dir.remove(dir[i]);
if ( dir.remove(dir[i]) )
{
std::cerr << "Cannot remove temporary file " << dir[i] << std::endl;
}
}
if ( !dir.rmdir(mTmp) )
{
std::cerr << "Cannot remove temporary directory " << mTmp << std::endl;
}
}
}
return NULL;
}

View File

@ -74,6 +74,18 @@ public:
//! Get last error message
static QString getErrorMessage ( void );
/** \brief Open existing GRASS mapset
* \return NULL string or error message
*/
static QString openMapset ( QString gisdbase,
QString location, QString mapset );
/** \brief Close mapset if it was opened from QGIS.
* Delete GISRC, lock and temporary directory
* \return NULL string or error message
*/
static QString closeMapset ();
private:
static int initialized; // Set to 1 after initialization
static bool active; // is active mode
@ -88,5 +100,11 @@ private:
static int error_routine ( char *msg, int fatal); // static because pointer to this function is set later
};
// Current mapset lock file path
static QString mMapsetLock;
// Current mapset GISRC file path
static QString mGisrc;
// Temporary directory where GISRC and sockets are stored
static QString mTmp;
#endif // QGSGRASS_H