1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219 |
- """
- This packages includes all base classes to store basic information
- like id, name, mapset creation and modification time as well as sql
- serialization and de-serialization and the sql database interface.
- Usage:
- .. code-block:: python
- >>> import grass.temporal as tgis
- >>> tgis.init()
- >>> rbase = tgis.RasterBase(ident="soil@PERMANENT")
- >>> vbase = tgis.VectorBase(ident="soil:1@PERMANENT")
- >>> r3base = tgis.Raster3DBase(ident="soil@PERMANENT")
- >>> strdsbase = tgis.STRDSBase(ident="soil@PERMANENT")
- >>> stvdsbase = tgis.STVDSBase(ident="soil@PERMANENT")
- >>> str3dsbase = tgis.STR3DSBase(ident="soil@PERMANENT")
- (C) 2011-2013 by the GRASS Development Team
- This program is free software under the GNU General Public
- License (>=v2). Read the file COPYING that comes with GRASS
- for details.
- :author: Soeren Gebbert
- """
- from __future__ import print_function
- from datetime import datetime
- from .core import (
- get_tgis_message_interface,
- get_tgis_dbmi_paramstyle,
- SQLDatabaseInterfaceConnection,
- )
- ###############################################################################
- class DictSQLSerializer(object):
- def __init__(self):
- self.D = {}
- self.dbmi_paramstyle = get_tgis_dbmi_paramstyle()
- def serialize(self, type, table, where=None):
- """Convert the internal dictionary into a string of semicolon
- separated SQL statements The keys are the column names and
- the values are the row entries
- Usage:
- .. code-block:: python
- >>> init()
- >>> t = DictSQLSerializer()
- >>> t.D["id"] = "soil@PERMANENT"
- >>> t.D["name"] = "soil"
- >>> t.D["mapset"] = "PERMANENT"
- >>> t.D["creator"] = "soeren"
- >>> t.D["creation_time"] = datetime(2001,1,1)
- >>> t.D["modification_time"] = datetime(2001,1,1)
- >>> t.serialize(type="SELECT", table="raster_base")
- ('SELECT name , creator , creation_time , modification_time , mapset , id FROM raster_base ;\\n', ())
- >>> t.serialize(type="INSERT", table="raster_base")
- ('INSERT INTO raster_base ( name ,creator ,creation_time ,modification_time ,mapset ,id ) VALUES (? ,? ,? ,? ,? ,?) ;\\n', ('soil', 'soeren', datetime.datetime(2001, 1, 1, 0, 0), datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil@PERMANENT'))
- >>> t.serialize(type="UPDATE", table="raster_base")
- ('UPDATE raster_base SET name = ? ,creator = ? ,creation_time = ? ,modification_time = ? ,mapset = ? ,id = ? ;\\n', ('soil', 'soeren', datetime.datetime(2001, 1, 1, 0, 0), datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil@PERMANENT'))
- >>> t.serialize(type="UPDATE ALL", table="raster_base")
- ('UPDATE raster_base SET name = ? ,creator = ? ,creation_time = ? ,modification_time = ? ,mapset = ? ,id = ? ;\\n', ('soil', 'soeren', datetime.datetime(2001, 1, 1, 0, 0), datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil@PERMANENT'))
- :param type: must be SELECT. INSERT, UPDATE
- :param table: The name of the table to select, insert or update
- :param where: The optional where statement
- :return: a tuple containing the SQL string and the arguments
- """
- sql = ""
- args = []
- # Create ordered select statement
- if type == "SELECT":
- sql += "SELECT "
- count = 0
- for key in self.D.keys():
- if count == 0:
- sql += " %s " % key
- else:
- sql += " , %s " % key
- count += 1
- sql += " FROM " + table + " "
- if where:
- sql += where
- sql += ";\n"
- # Create insert statement
- if type == "INSERT":
- count = 0
- sql += "INSERT INTO " + table + " ("
- for key in self.D.keys():
- if count == 0:
- sql += " %s " % key
- else:
- sql += " ,%s " % key
- count += 1
- count = 0
- sql += ") VALUES ("
- for key in self.D.keys():
- if count == 0:
- if self.dbmi_paramstyle == "qmark":
- sql += "?"
- else:
- sql += "%s"
- else:
- if self.dbmi_paramstyle == "qmark":
- sql += " ,?"
- else:
- sql += " ,%s"
- count += 1
- args.append(self.D[key])
- sql += ") "
- if where:
- sql += where
- sql += ";\n"
- # Create update statement for existing entries
- if type == "UPDATE":
- count = 0
- sql += "UPDATE " + table + " SET "
- for key in self.D.keys():
- # Update only entries which are not None
- if self.D[key] is not None:
- if count == 0:
- if self.dbmi_paramstyle == "qmark":
- sql += " %s = ? " % key
- else:
- sql += " %s " % key
- sql += "= %s "
- else:
- if self.dbmi_paramstyle == "qmark":
- sql += " ,%s = ? " % key
- else:
- sql += " ,%s " % key
- sql += "= %s "
- count += 1
- args.append(self.D[key])
- if where:
- sql += where
- sql += ";\n"
- # Create update statement for all entries
- if type == "UPDATE ALL":
- count = 0
- sql += "UPDATE " + table + " SET "
- for key in self.D.keys():
- if count == 0:
- if self.dbmi_paramstyle == "qmark":
- sql += " %s = ? " % key
- else:
- sql += " %s " % key
- sql += "= %s "
- else:
- if self.dbmi_paramstyle == "qmark":
- sql += " ,%s = ? " % key
- else:
- sql += " ,%s " % key
- sql += "= %s "
- count += 1
- args.append(self.D[key])
- if where:
- sql += where
- sql += ";\n"
- return sql, tuple(args)
- def deserialize(self, row):
- """Convert the content of the dbmi dictionary like row into the
- internal dictionary
- :param row: The dictionary like row to store in the internal dict
- """
- self.D = {}
- for key in row.keys():
- self.D[key] = row[key]
- def clear(self):
- """Initialize the internal storage"""
- self.D = {}
- def print_self(self):
- """Print the content of the internal dictionary to stdout"""
- print(self.D)
- ###############################################################################
- class SQLDatabaseInterface(DictSQLSerializer):
- """This class represents the SQL database interface
- Functions to insert, select and update the internal
- structure of this class in the temporal database are implemented.
- This is the base class for raster, raster3d, vector and
- space time datasets data management classes:
- - Identification information (base)
- - Spatial extent
- - Temporal extent
- - Metadata
- Usage:
- .. code-block:: python
- >>> init()
- >>> t = SQLDatabaseInterface("raster", "soil@PERMANENT")
- >>> t.mapset = get_current_mapset()
- >>> t.D["name"] = "soil"
- >>> t.D["mapset"] = "PERMANENT"
- >>> t.D["creator"] = "soeren"
- >>> t.D["creation_time"] = datetime(2001,1,1)
- >>> t.get_delete_statement()
- "DELETE FROM raster WHERE id = 'soil@PERMANENT';\\n"
- >>> t.get_is_in_db_statement()
- "SELECT id FROM raster WHERE id = 'soil@PERMANENT';\\n"
- >>> t.get_select_statement()
- ("SELECT creation_time , mapset , name , creator FROM raster WHERE id = 'soil@PERMANENT';\\n", ())
- >>> t.get_select_statement_mogrified()
- "SELECT creation_time , mapset , name , creator FROM raster WHERE id = 'soil@PERMANENT';\\n"
- >>> t.get_insert_statement()
- ('INSERT INTO raster ( creation_time ,mapset ,name ,creator ) VALUES (? ,? ,? ,?) ;\\n', (datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil', 'soeren'))
- >>> t.get_insert_statement_mogrified()
- "INSERT INTO raster ( creation_time ,mapset ,name ,creator ) VALUES ('2001-01-01 00:00:00' ,'PERMANENT' ,'soil' ,'soeren') ;\\n"
- >>> t.get_update_statement()
- ("UPDATE raster SET creation_time = ? ,mapset = ? ,name = ? ,creator = ? WHERE id = 'soil@PERMANENT';\\n", (datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil', 'soeren'))
- >>> t.get_update_statement_mogrified()
- "UPDATE raster SET creation_time = '2001-01-01 00:00:00' ,mapset = 'PERMANENT' ,name = 'soil' ,creator = 'soeren' WHERE id = 'soil@PERMANENT';\\n"
- >>> t.get_update_all_statement()
- ("UPDATE raster SET creation_time = ? ,mapset = ? ,name = ? ,creator = ? WHERE id = 'soil@PERMANENT';\\n", (datetime.datetime(2001, 1, 1, 0, 0), 'PERMANENT', 'soil', 'soeren'))
- >>> t.get_update_all_statement_mogrified()
- "UPDATE raster SET creation_time = '2001-01-01 00:00:00' ,mapset = 'PERMANENT' ,name = 'soil' ,creator = 'soeren' WHERE id = 'soil@PERMANENT';\\n"
- """
- def __init__(self, table=None, ident=None):
- """Constructor of this class
- :param table: The name of the table
- :param ident: The identifier (primary key) of this
- object in the database table
- """
- DictSQLSerializer.__init__(self)
- self.table = table # Name of the table, set in the subclass
- self.ident = ident
- self.msgr = get_tgis_message_interface()
- if self.ident and self.ident.find("@") >= 0:
- self.mapset = self.ident.split("@" "")[1]
- else:
- self.mapset = None
- def get_table_name(self):
- """Return the name of the table in which the internal
- data are inserted, updated or selected
- :return: The name of the table
- """
- return self.table
- def get_delete_statement(self):
- """Return the delete string
- :return: The DELETE string
- """
- return (
- "DELETE FROM "
- + self.get_table_name()
- + " WHERE id = '"
- + str(self.ident)
- + "';\n"
- )
- def delete(self, dbif=None):
- """Delete the entry of this object from the temporal database
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- """
- sql = self.get_delete_statement()
- # print(sql)
- if dbif:
- dbif.execute(sql, mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- dbif.execute(sql, mapset=self.mapset)
- dbif.close()
- def get_is_in_db_statement(self):
- """Return the selection string that checks if this object is registered in the
- temporal database
- :return: The SELECT string
- """
- return (
- "SELECT id FROM "
- + self.get_table_name()
- + " WHERE id = '"
- + str(self.ident)
- + "';\n"
- )
- def is_in_db(self, dbif=None):
- """Check if this object is present in the temporal database
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :return: True if this object is present in the temporal database,
- False otherwise
- """
- sql = self.get_is_in_db_statement()
- if dbif:
- dbif.execute(sql, mapset=self.mapset)
- row = dbif.fetchone(mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- dbif.execute(sql, mapset=self.mapset)
- row = dbif.fetchone(mapset=self.mapset)
- dbif.close()
- # Nothing found
- if row is None:
- return False
- return True
- def get_select_statement(self):
- """Return the sql statement and the argument list in
- database specific style
- :return: The SELECT string
- """
- return self.serialize(
- "SELECT", self.get_table_name(), "WHERE id = '" + str(self.ident) + "'"
- )
- def get_select_statement_mogrified(self, dbif=None):
- """Return the select statement as mogrified string
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :return: The SELECT string
- """
- if not dbif:
- dbif = SQLDatabaseInterfaceConnection()
- return dbif.mogrify_sql_statement(
- self.get_select_statement(), mapset=self.mapset
- )
- def select(self, dbif=None):
- """Select the content from the temporal database and store it
- in the internal dictionary structure
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- """
- sql, args = self.get_select_statement()
- # print(sql)
- # print(args)
- if dbif:
- if len(args) == 0:
- dbif.execute(sql, mapset=self.mapset)
- else:
- dbif.execute(sql, args, mapset=self.mapset)
- row = dbif.fetchone(mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- if len(args) == 0:
- dbif.execute(sql, mapset=self.mapset)
- else:
- dbif.execute(sql, args, mapset=self.mapset)
- row = dbif.fetchone(mapset=self.mapset)
- dbif.close()
- # Nothing found
- if row is None:
- return False
- if len(row) > 0:
- self.deserialize(row)
- else:
- self.msgr.fatal(_("Object not found in the temporal database"))
- return True
- def get_insert_statement(self):
- """Return the sql statement and the argument
- list in database specific style
- :return: The INSERT string"""
- return self.serialize("INSERT", self.get_table_name())
- def get_insert_statement_mogrified(self, dbif=None):
- """Return the insert statement as mogrified string
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :return: The INSERT string
- """
- if not dbif:
- dbif = SQLDatabaseInterfaceConnection()
- return dbif.mogrify_sql_statement(
- self.get_insert_statement(), mapset=self.mapset
- )
- def insert(self, dbif=None):
- """Serialize the content of this object and store it in the temporal
- database using the internal identifier
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- """
- sql, args = self.get_insert_statement()
- # print(sql)
- # print(args)
- if dbif:
- dbif.execute(sql, args, mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- dbif.execute(sql, args, mapset=self.mapset)
- dbif.close()
- def get_update_statement(self, ident=None):
- """Return the sql statement and the argument list
- in database specific style
- :param ident: The identifier to be updated, useful for renaming
- :return: The UPDATE string
- """
- if ident:
- return self.serialize(
- "UPDATE", self.get_table_name(), "WHERE id = '" + str(ident) + "'"
- )
- else:
- return self.serialize(
- "UPDATE", self.get_table_name(), "WHERE id = '" + str(self.ident) + "'"
- )
- def get_update_statement_mogrified(self, dbif=None, ident=None):
- """Return the update statement as mogrified string
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :param ident: The identifier to be updated, useful for renaming
- :return: The UPDATE string
- """
- if not dbif:
- dbif = SQLDatabaseInterfaceConnection()
- return dbif.mogrify_sql_statement(
- self.get_update_statement(ident), mapset=self.mapset
- )
- def update(self, dbif=None, ident=None):
- """Serialize the content of this object and update it in the temporal
- database using the internal identifier
- Only object entries which are exists (not None) are updated
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :param ident: The identifier to be updated, useful for renaming
- """
- if self.ident is None:
- self.msgr.fatal(_("Missing identifier"))
- sql, args = self.get_update_statement(ident)
- # print(sql)
- # print(args)
- if dbif:
- dbif.execute(sql, args, mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- dbif.execute(sql, args, mapset=self.mapset)
- dbif.close()
- def get_update_all_statement(self, ident=None):
- """Return the sql statement and the argument
- list in database specific style
- :param ident: The identifier to be updated, useful for renaming
- :return: The UPDATE string
- """
- if ident:
- return self.serialize(
- "UPDATE ALL", self.get_table_name(), "WHERE id = '" + str(ident) + "'"
- )
- else:
- return self.serialize(
- "UPDATE ALL",
- self.get_table_name(),
- "WHERE id = '" + str(self.ident) + "'",
- )
- def get_update_all_statement_mogrified(self, dbif=None, ident=None):
- """Return the update all statement as mogrified string
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :param ident: The identifier to be updated, useful for renaming
- :return: The UPDATE string
- """
- if not dbif:
- dbif = SQLDatabaseInterfaceConnection()
- return dbif.mogrify_sql_statement(
- self.get_update_all_statement(ident), mapset=self.mapset
- )
- def update_all(self, dbif=None, ident=None):
- """Serialize the content of this object, including None objects,
- and update it in the temporal database using the internal identifier
- :param dbif: The database interface to be used,
- if None a temporary connection will be established
- :param ident: The identifier to be updated, useful for renaming
- """
- if self.ident is None:
- self.msgr.fatal(_("Missing identifier"))
- sql, args = self.get_update_all_statement(ident)
- # print(sql)
- # print(args)
- if dbif:
- dbif.execute(sql, args, mapset=self.mapset)
- else:
- dbif = SQLDatabaseInterfaceConnection()
- dbif.connect()
- dbif.execute(sql, args, mapset=self.mapset)
- dbif.close()
- ###############################################################################
- class DatasetBase(SQLDatabaseInterface):
- """This is the base class for all maps and spacetime datasets storing
- basic identification information
- Usage:
- .. code-block:: python
- >>> init()
- >>> t = DatasetBase("raster", "soil@PERMANENT", creator="soeren", ctime=datetime(2001,1,1), ttype="absolute")
- >>> t.id
- 'soil@PERMANENT'
- >>> t.name
- 'soil'
- >>> t.mapset
- 'PERMANENT'
- >>> t.creator
- 'soeren'
- >>> t.ctime
- datetime.datetime(2001, 1, 1, 0, 0)
- >>> t.ttype
- 'absolute'
- >>> t.print_info()
- +-------------------- Basic information -------------------------------------+
- | Id: ........................ soil@PERMANENT
- | Name: ...................... soil
- | Mapset: .................... PERMANENT
- | Creator: ................... soeren
- | Temporal type: ............. absolute
- | Creation time: ............. 2001-01-01 00:00:00
- >>> t.print_shell_info()
- id=soil@PERMANENT
- name=soil
- mapset=PERMANENT
- creator=soeren
- temporal_type=absolute
- creation_time='2001-01-01 00:00:00'
- """
- def __init__(
- self,
- table=None,
- ident=None,
- name=None,
- mapset=None,
- creator=None,
- ctime=None,
- ttype=None,
- ):
- """Constructor
- :param table: The name of the temporal database table
- that should be used to store the values
- :param ident: The unique identifier must be a combination of
- the dataset name, layer name and the mapset
- "name@mapset" or "name:layer@mapset"
- used as as primary key in the temporal database
- :param name: The name of the map or dataset
- :param mapset: The name of the mapset
- :param creator: The name of the creator
- :param ctime: The creation datetime object
- :param ttype: The temporal type
- - "absolute" Identifier for absolute time
- - "relative" Identifier for relative time
- """
- SQLDatabaseInterface.__init__(self, table, ident)
- self.set_id(ident)
- if ident is not None and name is None and mapset is None:
- if ident.find("@") >= 0:
- name, mapset = ident.split("@")
- if name.find(":") >= 0:
- name, layer = ident.split(":")
- self.set_name(name)
- self.set_mapset(mapset)
- self.set_creator(creator)
- self.set_ctime(ctime)
- self.set_ttype(ttype)
- def set_id(self, ident):
- """Convenient method to set the unique identifier (primary key)
- :param ident: The unique identifier must be a combination
- of the dataset name, layer name and the mapset
- "name@mapset" or "name:layer@mapset"
- """
- self.ident = ident
- self.D["id"] = ident
- name = ""
- if ident is not None:
- if ident.find("@") >= 0:
- name, mapset = ident.split("@")
- self.set_mapset(mapset)
- self.set_name(name)
- else:
- self.msgr.fatal(_("Wrong identifier, the mapset is missing"))
- if name.find(":") >= 0:
- name, layer = ident.split(":")
- self.set_layer(layer)
- self.set_name(name)
- def set_name(self, name):
- """Set the name of the dataset
- :param name: The name of the dataset
- """
- self.D["name"] = name
- def set_mapset(self, mapset):
- """Set the mapset of the dataset
- :param mapset: The name of the mapset in which this dataset is stored
- """
- self.D["mapset"] = mapset
- def set_layer(self, layer):
- """Convenient method to set the layer of the map (part of primary key)
- Layer are supported for vector maps
- :param layer: The layer of the map
- """
- self.D["layer"] = layer
- def set_creator(self, creator):
- """Set the creator of the dataset
- :param creator: The name of the creator
- """
- self.D["creator"] = creator
- def set_ctime(self, ctime=None):
- """Set the creation time of the dataset,
- if nothing set the current time is used
- :param ctime: The current time of type datetime
- """
- if ctime is None:
- self.D["creation_time"] = datetime.today()
- else:
- self.D["creation_time"] = ctime
- def set_ttype(self, ttype):
- """Set the temporal type of the dataset: absolute or relative,
- if nothing set absolute time will assumed
- :param ttype: The temporal type of the dataset "absolute or relative"
- """
- if ttype is None or (ttype != "absolute" and ttype != "relative"):
- self.D["temporal_type"] = "absolute"
- else:
- self.D["temporal_type"] = ttype
- def get_id(self):
- """Convenient method to get the unique identifier (primary key)
- :return: None if not found
- """
- if "id" in self.D:
- return self.D["id"]
- else:
- return None
- def get_map_id(self):
- """Convenient method to get the unique map identifier
- without layer information
- :return: the name of the vector map as "name@mapset"
- or None in case the id was not set
- """
- if self.id:
- if self.id.find(":") >= 0:
- # Remove the layer identifier from the id
- return self.id.split("@")[0].split(":")[0] + "@" + self.id.split("@")[1]
- else:
- return self.id
- else:
- return None
- def get_layer(self):
- """Convenient method to get the layer of the map (part of primary key)
- Layer are currently supported for vector maps
- :return: None if not found
- """
- if "layer" in self.D:
- return self.D["layer"]
- else:
- return None
- def get_name(self):
- """Get the name of the dataset
- :return: None if not found"""
- if "name" in self.D:
- return self.D["name"]
- else:
- return None
- def get_mapset(self):
- """Get the name of mapset of this dataset
- :return: None if not found"""
- if "mapset" in self.D:
- return self.D["mapset"]
- else:
- return None
- def get_creator(self):
- """Get the creator of the dataset
- :return: None if not found"""
- if "creator" in self.D:
- return self.D["creator"]
- else:
- return None
- def get_ctime(self):
- """Get the creation time of the dataset, datatype is datetime
- :return: None if not found"""
- if "creation_time" in self.D:
- return self.D["creation_time"]
- else:
- return None
- def get_ttype(self):
- """Get the temporal type of the map
- :return: None if not found"""
- if "temporal_type" in self.D:
- return self.D["temporal_type"]
- else:
- return None
- # Properties of this class
- id = property(fget=get_id, fset=set_id)
- map_id = property(fget=get_map_id, fset=None)
- name = property(fget=get_name, fset=set_name)
- mapset = property(fget=get_mapset, fset=set_mapset)
- ctime = property(fget=get_ctime, fset=set_ctime)
- ttype = property(fget=get_ttype, fset=set_ttype)
- creator = property(fget=get_creator, fset=set_creator)
- def print_info(self):
- """Print information about this class in human readable style"""
- # 0123456789012345678901234567890
- print(
- " +-------------------- Basic information -------------------------------------+"
- )
- print(" | Id: ........................ " + str(self.get_id()))
- print(" | Name: ...................... " + str(self.get_name()))
- print(" | Mapset: .................... " + str(self.get_mapset()))
- if self.get_layer():
- print(" | Layer:...................... " + str(self.get_layer()))
- print(" | Creator: ................... " + str(self.get_creator()))
- print(" | Temporal type: ............. " + str(self.get_ttype()))
- print(" | Creation time: ............. " + str(self.get_ctime()))
- def print_shell_info(self):
- """Print information about this class in shell style"""
- print("id=" + str(self.get_id()))
- print("name=" + str(self.get_name()))
- print("mapset=" + str(self.get_mapset()))
- if self.get_layer():
- print("layer=" + str(self.get_layer()))
- print("creator=" + str(self.get_creator()))
- print("temporal_type=" + str(self.get_ttype()))
- print("creation_time='{}'".format(str(self.get_ctime())))
- ###############################################################################
- class RasterBase(DatasetBase):
- """Time stamped raster map base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- creator=None,
- creation_time=None,
- temporal_type=None,
- ):
- DatasetBase.__init__(
- self,
- "raster_base",
- ident,
- name,
- mapset,
- creator,
- creation_time,
- temporal_type,
- )
- class Raster3DBase(DatasetBase):
- """Time stamped 3D raster map base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- creator=None,
- creation_time=None,
- temporal_type=None,
- ):
- DatasetBase.__init__(
- self,
- "raster3d_base",
- ident,
- name,
- mapset,
- creator,
- creation_time,
- temporal_type,
- )
- class VectorBase(DatasetBase):
- """Time stamped vector map base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- layer=None,
- creator=None,
- creation_time=None,
- temporal_type=None,
- ):
- DatasetBase.__init__(
- self,
- "vector_base",
- ident,
- name,
- mapset,
- creator,
- creation_time,
- temporal_type,
- )
- self.set_id(ident)
- if ident is not None and name is None and mapset is None:
- if ident.find("@") >= 0:
- name, mapset = ident.split("@")
- if layer is None:
- if name.find(":") >= 0:
- name, layer = name.split(":")
- self.set_name(name)
- self.set_mapset(mapset)
- # Layer currently only in use by vector maps
- self.set_layer(layer)
- ###############################################################################
- class STDSBase(DatasetBase):
- """Base class for space time datasets
- This class adds the semantic type member variable to the dataset
- base class.
- Usage:
- .. code-block:: python
- >>> init()
- >>> t = STDSBase("stds", "soil@PERMANENT", semantic_type="average", creator="soeren", ctime=datetime(2001,1,1), ttype="absolute", mtime=datetime(2001,1,1))
- >>> t.semantic_type
- 'average'
- >>> t.print_info()
- +-------------------- Basic information -------------------------------------+
- | Id: ........................ soil@PERMANENT
- | Name: ...................... soil
- | Mapset: .................... PERMANENT
- | Creator: ................... soeren
- | Temporal type: ............. absolute
- | Creation time: ............. 2001-01-01 00:00:00
- | Modification time:.......... 2001-01-01 00:00:00
- | Semantic type:.............. average
- >>> t.print_shell_info()
- id=soil@PERMANENT
- name=soil
- mapset=PERMANENT
- creator=soeren
- temporal_type=absolute
- creation_time='2001-01-01 00:00:00'
- modification_time='2001-01-01 00:00:00'
- semantic_type=average
- """
- def __init__(
- self,
- table=None,
- ident=None,
- name=None,
- mapset=None,
- semantic_type=None,
- creator=None,
- ctime=None,
- ttype=None,
- mtime=None,
- ):
- DatasetBase.__init__(self, table, ident, name, mapset, creator, ctime, ttype)
- self.set_semantic_type(semantic_type)
- self.set_mtime(mtime)
- def set_semantic_type(self, semantic_type):
- """Set the semantic type of the space time dataset"""
- self.D["semantic_type"] = semantic_type
- def set_mtime(self, mtime=None):
- """Set the modification time of the space time dataset, if nothing set
- the current time is used
- """
- if mtime is None:
- self.D["modification_time"] = datetime.now()
- else:
- self.D["modification_time"] = mtime
- def get_semantic_type(self):
- """Get the semantic type of the space time dataset
- :return: None if not found
- """
- if "semantic_type" in self.D:
- return self.D["semantic_type"]
- else:
- return None
- def get_mtime(self):
- """Get the modification time of the space time dataset, datatype is
- datetime
- :return: None if not found
- """
- if "modification_time" in self.D:
- return self.D["modification_time"]
- else:
- return None
- semantic_type = property(fget=get_semantic_type, fset=set_semantic_type)
- def print_info(self):
- """Print information about this class in human readable style"""
- DatasetBase.print_info(self)
- # 0123456789012345678901234567890
- print(" | Modification time:.......... " + str(self.get_mtime()))
- print(" | Semantic type:.............. " + str(self.get_semantic_type()))
- def print_shell_info(self):
- """Print information about this class in shell style"""
- DatasetBase.print_shell_info(self)
- print("modification_time='{}'".format(str(self.get_mtime())))
- print("semantic_type=" + str(self.get_semantic_type()))
- ###############################################################################
- class STRDSBase(STDSBase):
- """Space time raster dataset base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- semantic_type=None,
- creator=None,
- ctime=None,
- ttype=None,
- ):
- STDSBase.__init__(
- self,
- "strds_base",
- ident,
- name,
- mapset,
- semantic_type,
- creator,
- ctime,
- ttype,
- )
- class STR3DSBase(STDSBase):
- """Space time 3D raster dataset base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- semantic_type=None,
- creator=None,
- ctime=None,
- ttype=None,
- ):
- STDSBase.__init__(
- self,
- "str3ds_base",
- ident,
- name,
- mapset,
- semantic_type,
- creator,
- ctime,
- ttype,
- )
- class STVDSBase(STDSBase):
- """Space time vector dataset base information class"""
- def __init__(
- self,
- ident=None,
- name=None,
- mapset=None,
- semantic_type=None,
- creator=None,
- ctime=None,
- ttype=None,
- ):
- STDSBase.__init__(
- self,
- "stvds_base",
- ident,
- name,
- mapset,
- semantic_type,
- creator,
- ctime,
- ttype,
- )
- ###############################################################################
- class AbstractSTDSRegister(SQLDatabaseInterface):
- """This is the base class for all maps to store the space time datasets
- as comma separated string in which they are registered
- Usage:
- .. code-block:: python
- >>> init()
- >>> t = AbstractSTDSRegister("raster", "soil@PERMANENT", "A@P,B@P,C@P")
- >>> t.id
- 'soil@PERMANENT'
- >>> t.registered_stds
- 'A@P,B@P,C@P'
- """
- def __init__(self, table=None, ident=None, registered_stds=None):
- """Constructor
- :param table: The name of the temporal database table
- that should be used to store the values
- :param ident: The unique identifier must be a combination of
- the dataset name, layer name and the mapset
- "name@mapset" or "name:layer@mapset"
- used as as primary key in the temporal database
- :param stds: A comma separated list of space time dataset ids
- """
- SQLDatabaseInterface.__init__(self, table, ident)
- self.set_id(ident)
- self.set_registered_stds(registered_stds)
- def set_id(self, ident):
- """Convenient method to set the unique identifier (primary key)
- :param ident: The unique identifier must be a combination
- of the dataset name, layer name and the mapset
- "name@mapset" or "name:layer@mapset"
- """
- self.ident = ident
- self.D["id"] = ident
- def set_registered_stds(self, registered_stds):
- """Get the comma separated list of space time datasets ids
- in which this map is registered
- :param registered_stds: A comma separated list of space time
- dataset ids in which this map is registered
- """
- self.D["registered_stds"] = registered_stds
- def get_id(self):
- """Convenient method to get the unique identifier (primary key)
- :return: None if not found
- """
- if "id" in self.D:
- return self.D["id"]
- else:
- return None
- def get_registered_stds(self):
- """Get the comma separated list of space time datasets ids
- in which this map is registered
- :return: None if not found
- """
- if "registered_stds" in self.D:
- return self.D["registered_stds"]
- else:
- return None
- # Properties of this class
- id = property(fget=get_id, fset=set_id)
- registered_stds = property(fget=get_registered_stds, fset=set_registered_stds)
- ###############################################################################
- class RasterSTDSRegister(AbstractSTDSRegister):
- """Time stamped raster map base information class"""
- def __init__(self, ident=None, registered_stds=None):
- AbstractSTDSRegister.__init__(
- self, "raster_stds_register", ident, registered_stds
- )
- class Raster3DSTDSRegister(AbstractSTDSRegister):
- """Time stamped 3D raster map base information class"""
- def __init__(self, ident=None, registered_stds=None):
- AbstractSTDSRegister.__init__(
- self, "raster3d_stds_register", ident, registered_stds
- )
- class VectorSTDSRegister(AbstractSTDSRegister):
- """Time stamped vector map base information class"""
- def __init__(self, ident=None, registered_stds=None):
- AbstractSTDSRegister.__init__(
- self, "vector_stds_register", ident, registered_stds
- )
- ###############################################################################
- if __name__ == "__main__":
- import doctest
- doctest.testmod()
|