1069,1072c1069,1072
< 		if ($wgDBtype === 'postgres') {
< 			$this->reportProgress("Sorry, Postgres is currently not supported. Please contact the\ndevelopers if you wish to help fixing this.\n",$verbose);
< 			return;
< 		}
---
> //		if ($wgDBtype === 'postgres') {
> //			$this->reportProgress("Sorry, Postgres is currently not supported. Please contact the\ndevelopers if you wish to help fixing this.\n",$verbose);
> //			return;
> //		}
1079,1083c1079,1083
< 		              array('smw_id'        => 'INT(8) UNSIGNED NOT NULL KEY AUTO_INCREMENT',
< 		                    'smw_namespace' => 'INT(11) NOT NULL',
< 		                    'smw_title'     => 'VARCHAR(255) binary NOT NULL',
< 		                    'smw_iw'        => 'CHAR(32)',
< 		                    'smw_sortkey'   => 'VARCHAR(255) binary NOT NULL'
---
> 		              array('smw_id'        => ($wgDBtype=='postgres'?'SERIAL NOT NULL PRIMARY KEY':'INT(8) UNSIGNED NOT NULL KEY AUTO_INCREMENT'),
> 		                    'smw_namespace' => ($wgDBtype=='postgres'?'BIGINT':'INT(11)').' NOT NULL',
> 		                    'smw_title'     => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL',
> 		                    'smw_iw'        => ($wgDBtype=='postgres'?'TEXT':'CHAR(32)'),
> 		                    'smw_sortkey'   => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL'
1104,1106c1104,1106
< 		              array('s_title'     => 'VARCHAR(255) binary NOT NULL',
< 		                    's_namespace' => 'INT(11) NOT NULL',
< 		                    'o_id'        => 'INT(8) UNSIGNED NOT NULL',), $db, $verbose);
---
> 		              array('s_title'     => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL',
> 		                    's_namespace' => ($wgDBtype=='postgres'?'BIGINT':'INT(11)').' NOT NULL',
> 		                    'o_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',), $db, $verbose);
1110,1112c1110,1112
< 		              array('s_id' => 'INT(8) UNSIGNED NOT NULL',
< 		                    'p_id' => 'INT(8) UNSIGNED NOT NULL',
< 		                    'o_id' => 'INT(8) UNSIGNED NOT NULL'), $db, $verbose);
---
> 		              array('s_id' => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'p_id' => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'o_id' => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL'), $db, $verbose);
1116,1120c1116,1120
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'p_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'value_unit'        => 'VARCHAR(63) binary',
< 		                    'value_xsd'         => 'VARCHAR(255) binary NOT NULL',
< 		                    'value_num'         => 'DOUBLE'), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'p_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'value_unit'        => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(63) binary'),
> 		                    'value_xsd'         => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL',
> 		                    'value_num'         => ($wgDBtype=='postgres'?'DOUBLE PRECISION':'DOUBLE')), $db, $verbose);
1124,1126c1124,1126
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'p_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'value_blob'        => 'MEDIUMBLOB'), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'p_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'value_blob'        => ($wgDBtype=='postgres'?'BYTEA':'MEDIUMBLOB')), $db, $verbose);
1131c1131,1135
< 			$db->query("ALTER TABLE $smw_spec2 CHANGE `sp_id` `p_id` INT(8) UNSIGNED NOT NULL", 'SMWSQLStore2::setup');
---
> 			$db->query(
> 			(($wgDBtype=='postgres')?
> 			 ("ALTER TABLE $smw_spec2 ALTER COLUMN sp_id RENAME TO p_id")
> 			 : ("ALTER TABLE $smw_spec2 CHANGE `sp_id` `p_id` INT(8) UNSIGNED NOT NULL")
> 			), 'SMWSQLStore2::setup');
1134,1136c1138,1140
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'p_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'value_string'      => 'VARCHAR(255) binary NOT NULL'), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'p_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'value_string'      => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL'), $db, $verbose);
1140,1141c1144,1145
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'o_id'        => 'INT(8) UNSIGNED NOT NULL',), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'TEXT':'VARCHAR(255) binary').' NOT NULL',
> 		                    'o_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED'),), $db, $verbose);
1145,1146c1149,1150
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'o_id'        => 'INT(8) UNSIGNED NOT NULL',), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'o_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',), $db, $verbose);
1150,1157c1154,1161
< 		              array('s_id'             => 'INT(8) UNSIGNED NOT NULL KEY',
< 		                    'concept_txt'      => 'MEDIUMBLOB',
< 		                    'concept_docu'     => 'MEDIUMBLOB',
< 		                    'concept_features' => 'INT(8)',
< 		                    'concept_size'     => 'INT(8)',
< 		                    'concept_depth'    => 'INT(8)',
< 		                    'cache_date'       => 'INT(8) UNSIGNED',
< 		                    'cache_count'      => 'INT(8) UNSIGNED' ), $db, $verbose);
---
> 		              array('s_id'             => ($wgDBtype=='postgres'?'INTEGER NOT NULL PRIMARY KEY':'INT(8) UNSIGNED NOT NULL KEY'),
> 		                    'concept_txt'      => ($wgDBtype=='postgres'?'BYTEA':'MEDIUMBLOB'),
> 		                    'concept_docu'     => ($wgDBtype=='postgres'?'BYTEA':'MEDIUMBLOB'),
> 		                    'concept_features' => ($wgDBtype=='postgres'?'INTEGER':'INT(8)'),
> 		                    'concept_size'     => ($wgDBtype=='postgres'?'INTEGER':'INT(8)'),
> 		                    'concept_depth'    => ($wgDBtype=='postgres'?'INTEGER':'INT(8)'),
> 		                    'cache_date'       => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED'),
> 		                    'cache_count'      => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED'), ), $db, $verbose);
1161,1162c1165,1166
< 		              array('s_id'        => 'INT(8) UNSIGNED NOT NULL',
< 		                    'o_id'        => 'INT(8) UNSIGNED NOT NULL'), $db, $verbose);
---
> 		              array('s_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL',
> 		                    'o_id'        => ($wgDBtype=='postgres'?'INTEGER':'INT(8) UNSIGNED').' NOT NULL'), $db, $verbose);
1186c1190,1191
< 			$db->replace('smw_ids', array(), array('smw_id' => $id, 'smw_title' => $p->getXSDValue(), 'smw_namespace' => SMW_NS_PROPERTY, 'smw_iw' => $this->getPropertyInterwiki($p), 'smw_sortkey' => $p->getXSDValue()), 'SMW::setup');
---
> //			$db->replace('smw_ids', array(), array('smw_id' => $id, 'smw_title' => $p->getXSDValue(), 'smw_namespace' => SMW_NS_PROPERTY, 'smw_iw' => $this->getPropertyInterwiki($p), 'smw_sortkey' => $p->getXSDValue()), 'SMW::setup');
> 			$db->replace('smw_ids', array('smw_id'), array('smw_id' => $id, 'smw_title' => $p->getXSDValue(), 'smw_namespace' => SMW_NS_PROPERTY, 'smw_iw' => $this->getPropertyInterwiki($p), 'smw_sortkey' => $p->getXSDValue()), 'SMW::setup');
1200c1205,1207
< 			$db->query("DROP TABLE IF EXISTS $name", 'SMWSQLStore2::drop');
---
> 			$db->query(
> 			           (($wgDBtype=='postgres')?"DROP TABLE":"DROP TABLE IF EXISTS"). $name
> 			           , 'SMWSQLStore2::drop');
1494c1501,1504
< 		global $wgDBname;
---
> 		global $wgDBname, $wgDBtype;
> 
> 		$DBdelim = ($wgDBtype=="postgres"?"\"":"`");
> 
1497c1507
< 			$sql = 'CREATE TABLE `' . $wgDBname . '`.' . $table . ' (';
---
> 			$sql = 'CREATE TABLE ' . ($wgDBtype=='postgres'?'': $DBdelim . $wgDBname . $DBdelim) . $table . ' (';
1507c1517,1518
< 			$sql .= ') TYPE=innodb';
---
> 			$sql .= ') ' . ($wgDBtype=='postgres'?'':'TYPE=innodb');
> //			$this->reportProgress($sql,$verbose);
1513c1524,1553
< 			$res = $db->query( 'DESCRIBE ' . $table, 'SMWSQLStore2::setupTable' );
---
> 			$sql =
> 			 ($wgDBtype=='postgres')
> // use the data dictionary in postgresql to get an output comparable to DESCRIBE
> // To find out what kind of magic takes place here (and to remove the bugs included), simply use:
> // psql
> // \set ECHO_HIDDEN
> // \d <tablename>
> 			 ? (
> 			  	'SELECT a.attname as "Field", '
> 				.' upper(pg_catalog.format_type(a.atttypid, a.atttypmod)) as "Type", '
> 				.' (SELECT substring(pg_catalog.pg_get_expr(d.adbin, d.adrelid) for 128) '
> 				.'  FROM pg_catalog.pg_attrdef d '
> 			        .'  WHERE d.adrelid = a.attrelid AND d.adnum = a.attnum AND a.atthasdef) as "Extra", '
> 				.'  case when a.attnotnull THEN \'NO\'::text else \'YES\'::text END as "Null", a.attnum '
> 				.' FROM pg_catalog.pg_attribute a '
> 				.' WHERE a.attrelid = ('
> 				.'    SELECT c.oid '
> 				.'    FROM pg_catalog.pg_class c '
> 				.'    LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace '
> 				.'    WHERE c.relname ~ \'^(' . $table . ')$\' '
> 				.'    AND pg_catalog.pg_table_is_visible(c.oid) '
> 				.'    LIMIT 1 '
> 				.' ) AND a.attnum > 0 AND NOT a.attisdropped '
> 				.' ORDER BY a.attnum'			  
> 			    ) 
> 			 : ('DESCRIBE ' . $table)
> 			;			 
> //			$this->reportProgress($sql,$verbose);
> 			$res = $db->query($sql, 'SMWSQLStore2::setupTable');
> //			$this->reportProgress("SQL done",$verbose);
1517,1518c1557,1570
< 				$type = strtoupper($row->Type);
< 				if (substr($type,0,8) == 'VARCHAR(') {
---
> //				$this->reportProgress("<br />checking ".$row->Field.':'.$row->Null.':'.$row->Extra,$verbose);
> 
> 				$type = $row->Type;
> 
> 				if ($wgDBtype=='postgres') {
> 					if (eregi('^nextval\\(.+\\)$',$row->Extra)) {
> 						$type = 'SERIAL NOT NULL';
> 					}  else {
> 						if ($row->Null != 'YES') {
> 							$type .= ' NOT NULL';
> 						}
> 					}
> 				} 
> 				if (($wgDBtype!='postgres')&&(substr($type,0,8) == 'VARCHAR(')) {
1521,1524c1573,1579
< 				if ($row->Null != 'YES') {
< 					$type .= ' NOT NULL';
< 				}
< 				if ($row->Key == 'PRI') { /// FIXME: updating "KEY" is not possible, the below query will fail in this case.
---
> 				if ($wgDBtype!='postgres') {
> 					if ($row->Null != 'YES') {
> 						$type .= ' NOT NULL';
> 					}
> 				}		
> 				if ($wgDBtype!='postgres') {
> 					if ($row->Key == 'PRI') { /// FIXME: updating "KEY" is not possible, the below query will fail in this case.
1526,1528c1581,1586
< 				}
< 				if ($row->Extra == 'auto_increment') {
< 					$type .= ' AUTO_INCREMENT';
---
> 					}
> 				}	
> 				if ($wgDBtype!='postgres') {
> 					if ($row->Extra == 'auto_increment') {
> 						$type .= ' AUTO_INCREMENT';
> 					}	
1530a1589
> //				$this->reportProgress("<br /> type for ".$row->Field.": ".$type,$verbose);
1532,1533c1591,1630
< 			$position = 'FIRST';
< 			foreach ($fields as $name => $type) {
---
> 
> 			if ($wgDBtype=='postgres') {
> 			  foreach ($fields as $name => $type) {
> 			  	$keypos = strpos($type,' PRIMARY KEY');
> 			  	if ($keypos > 0) {
> 			  	  $type=substr($type,0,$keypos);			  	
> 			  	};
> 				if ( !array_key_exists($name,$curfields) ) {
> 					$this->reportProgress("   ... creating column $name ... ",$verbose);
> 					$db->query("ALTER TABLE $table ADD \"" . $name . "\" $type", 'SMWSQLStore2::setupTable');
> 					$result[$name] = 'new';
> 					$this->reportProgress("done \n",$verbose);
> 				} elseif ($curfields[$name] != $type) {
> 					$this->reportProgress("   ... changing type of column $name from '$curfields[$name]' to '$type' ... ",$verbose);
> 					$notnullposnew = strpos($type,' NOT NULL');
> 					if ($notnullposnew > 0) $type=substr($type,0,$notnullposnew);
> 					$notnullposold = strpos($curfields[$name],' NOT NULL');
> 					$typeold = ($notnullposold > 0)?substr($curfields[$name],0,$notnullposold):$curfields[$name];
> 					if ($typeold!=$type) $db->query("ALTER TABLE \"".$table."\" ALTER COLUMN \"".$name."\" TYPE " . $type, 'SMWSQLStore2::setupTable');
> 					if ($notnullposold!=$notnullposnew) 
> 					  $db->query("ALTER TABLE \"". $table . "\" ALTER COLUMN \"".$name."\" ".($notnullposnew>0?'SET':'DROP'). " NOT NULL", 'SMWSQLStore2::setupTable');
> 					$result[$name] = 'up';
> 					$curfields[$name] = false;
> 					$this->reportProgress("done.\n",$verbose);
> 				} else {
> 					$this->reportProgress("   ... column $name is fine\n",$verbose);
> 					$curfields[$name] = false;
> 				}
> 			  };
> 			  foreach ($curfields as $name => $value) {
> 			  	if ($value !== false) {
> 					$this->reportProgress("   ... deleting obsolete column $name ... ",$verbose);
> 					$db->query("ALTER TABLE \"". $table . "\" DROP COLUMN \"" . $name . "\"", 'SMWSQLStore2::setupTable');
> 					$result[$name] = 'del';
> 					$this->reportProgress("done.\n",$verbose);
> 			  	}
> 			  }
> 			} else {
> 			  $position = 'FIRST';
> 			  foreach ($fields as $name => $type) {
1550,1551c1647,1648
< 			}
< 			foreach ($curfields as $name => $value) {
---
> 			  }
> 			  foreach ($curfields as $name => $value) {
1557a1655
> 			  }
1558a1657
> 			
1569c1668,1702
< 		$table = $db->tableName($table);
---
> 	   global $wgDBtype,$verbose;
> 	   $table = $db->tableName($table);
> 
> 	   if ($wgDBtype=='postgres') {
> 
> 		$sql= "SELECT  i.relname AS indexname,"
> 	           ." pg_get_indexdef(i.oid) AS indexdef, "
> 	           ." replace(substring(pg_get_indexdef(i.oid) from '\\\\((.*)\\\\)'),' ','') AS indexcolumns"
> 		   ." FROM pg_index x"
> 		   ." JOIN pg_class c ON c.oid = x.indrelid"
> 		   ." JOIN pg_class i ON i.oid = x.indexrelid"
> 	           ." LEFT JOIN pg_namespace n ON n.oid = c.relnamespace"
> 	           ." LEFT JOIN pg_tablespace t ON t.oid = i.reltablespace"
> 		   ." WHERE c.relkind = 'r'::\"char\" AND i.relkind = 'i'::\"char\"" 
> 		   ." AND c.relname = '" . $table . "'"
> 		   ." AND NOT pg_get_indexdef(i.oid) ~ '^CREATE UNIQUE INDEX'";		
> 		$res = $db->query($sql,'SMW::SetupIndex');
> 		if ( !$res ) {
> 			return false;
> 		}
> 		$indexes = array();
> 		while ( $row = $db->fetchObject( $res ) ) {
> // remove unneeded indexes, let indexes alone that already exist in the correct fashion
> 			if (array_key_exists($row->indexcolumns,$columns)) {
> 			   $columns[$row->indexcolumns]=false;
> 			} else {
> 			   $db->query('DROP INDEX IF EXISTS ' . $row->indexname, 'SMW::SetupIndex');
> 			};
> 		};
> 		foreach ($columns as $key => $column) { // add remaining indexes
> 			if ($column != false) {
> 				$db->query("CREATE INDEX " . $table . "_index" . $key . " ON " . $table . " USING btree(" . $column . ")", 'SMW::SetupIndex'); 			
> 			}
> 		}
> 	   } else {
1595c1728,1729
< 		return true;
---
> 	   };		
> 	   return true;
