예제 #1
0
wxString pgTablespace::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		sql = wxT("-- Tablespace: ") + GetName() + wxT("\n\n");
		if (location.IsEmpty())
			sql += wxT("-- System Tablespace\n");
		else
			sql += wxT("-- DROP TABLESPACE ") + GetQuotedIdentifier()
			       +  wxT("\n\nCREATE TABLESPACE ") + GetQuotedIdentifier()
			       +  wxT("\n  OWNER ") + qtIdent(GetOwner())
			       +  wxT("\n  LOCATION ") + qtDbString(location)
			       +  wxT(";\n");
		sql += GetCommentSql();

		size_t i;
		for (i = 0 ; i < variables.GetCount() ; i++)
			sql += wxT("ALTER TABLESPACE ") + GetQuotedFullIdentifier()
			       +  wxT(" SET (") + variables.Item(i) + wxT(");\n");

		if (GetConnection()->BackendMinimumVersion(9, 2))
			sql += GetSeqLabelsSql();
	}
	return sql;
}
예제 #2
0
wxString pgSequence::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		UpdateValues();
		sql = wxT("-- Sequence: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP SEQUENCE ") + GetQuotedFullIdentifier() + wxT(";")
		      + wxT("\n\nCREATE SEQUENCE ") + GetQuotedFullIdentifier()
		      + wxT("\n  INCREMENT ") + GetIncrement().ToString()
		      + wxT("\n  MINVALUE ") + GetMinValue().ToString()
		      + wxT("\n  MAXVALUE ") + GetMaxValue().ToString()
		      + wxT("\n  START ") + GetLastValue().ToString()
		      + wxT("\n  CACHE ") + GetCacheValue().ToString();
		if (GetCycled())
			sql += wxT("\n  CYCLE");
		sql += wxT(";\n")
		       + GetOwnerSql(7, 3, wxT("TABLE ") + GetQuotedFullIdentifier());

		if (!GetConnection()->BackendMinimumVersion(8, 2))
			sql += GetGrant(wxT("arwdRxt"), wxT("TABLE ") + GetQuotedFullIdentifier());
		else
			sql += GetGrant(wxT("rwU"), wxT("TABLE ") + GetQuotedFullIdentifier());

		sql += GetCommentSql();

		if (GetConnection()->BackendMinimumVersion(9, 1))
			sql += GetSeqLabelsSql();
	}

	return sql;
}
예제 #3
0
wxString pgSchemaBase::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		wxString strName = qtIdent(GetName());
		if (GetMetaType() == PGM_CATALOG)
			sql = wxT("-- Catalog: ") + GetName() + wxT("\n\n");
		else
			sql = wxT("-- Schema: ") + GetName() + wxT("\n\n");

		sql += wxT("-- DROP SCHEMA ") + GetQuotedFullIdentifier() + wxT(";")
		       + wxT("\n\nCREATE SCHEMA ") + strName
		       + wxT("\n  AUTHORIZATION ") + qtIdent(GetOwner());
		sql += wxT(";\n\n");

		sql += GetGrant(wxT("UC"), wxT("SCHEMA ") + GetQuotedFullIdentifier())
		       + GetCommentSql();

		sql += wxT("\n") + pgDatabase::GetDefaultPrivileges('r', m_defPrivsOnTables, strName);
		sql += pgDatabase::GetDefaultPrivileges('S', m_defPrivsOnSeqs, strName);
		sql += pgDatabase::GetDefaultPrivileges('f', m_defPrivsOnFuncs, strName);

		if (GetConnection()->BackendMinimumVersion(9, 1))
			sql += GetSeqLabelsSql();
	}
	return sql;
}
예제 #4
0
wxString pgView::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		sql = wxT("-- View: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP VIEW ") + GetQuotedFullIdentifier() + wxT(";")
		      + wxT("\n\nCREATE OR REPLACE VIEW ") + GetQuotedFullIdentifier();
		if (GetConnection()->BackendMinimumVersion(9, 2) && GetSecurityBarrier().Length() > 0)
			sql += wxT(" WITH (security_barrier=") + GetSecurityBarrier() + wxT(")");
		sql += wxT(" AS \n")
		       + GetFormattedDefinition()
		       + wxT("\n\n")
		       + GetOwnerSql(7, 3, wxT("TABLE ") + GetQuotedFullIdentifier());

		if (GetConnection()->BackendMinimumVersion(8, 2))
			sql += GetGrant(wxT("arwdxt"), wxT("TABLE ") + GetQuotedFullIdentifier());
		else
			sql += GetGrant(wxT("arwdRxt"), wxT("TABLE ") + GetQuotedFullIdentifier());

		sql += GetCommentSql()
		       + wxT("\n");

		pgCollection *columns = browser->FindCollection(columnFactory, GetId());
		if (columns)
		{
			wxString defaults, comments;
			columns->ShowTreeDetail(browser);
			treeObjectIterator colIt(browser, columns);

			pgColumn *column;
			while ((column = (pgColumn *)colIt.GetNextObject()) != 0)
			{
				column->ShowTreeDetail(browser);
				if (column->GetColNumber() > 0)
				{
					if (!column->GetDefault().IsEmpty())
					{
						defaults += wxT("ALTER TABLE ") + GetQuotedFullIdentifier()
						            +  wxT(" ALTER COLUMN ") + column->GetQuotedIdentifier()
						            +  wxT(" SET DEFAULT ") + column->GetDefault()
						            + wxT(";\n");
					}
					comments += column->GetCommentSql();
				}
			}
			if (!defaults.IsEmpty())
				sql += defaults + wxT("\n");

			if (!comments.IsEmpty())
				sql += comments + wxT("\n");

			if (GetConnection()->BackendMinimumVersion(9, 1))
				sql += GetSeqLabelsSql();
		}

		AppendStuff(sql, browser, ruleFactory);
		AppendStuff(sql, browser, triggerFactory);
	}
	return sql;
}
예제 #5
0
wxString pgType::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		sql = wxT("-- Type: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP TYPE ") + GetQuotedFullIdentifier() + wxT(";")
		      + wxT("\n\nCREATE TYPE ") + GetQuotedFullIdentifier();
		if (GetTypeClass() == TYPE_COMPOSITE)
		{
			sql += wxT(" AS\n   (");
			sql += GetQuotedTypesList();
		}
		else if (GetTypeClass() == TYPE_ENUM)
		{
			sql += wxT(" AS ENUM\n   (");
			sql += GetQuotedLabelList();
		}
		else
		{
			sql += wxT("\n   (INPUT=") + qtIdent(GetInputFunction())
			       + wxT(", OUTPUT=") + qtIdent(GetOutputFunction());
			AppendIfFilled(sql, wxT(", DEFAULT="), qtDbString(GetDefault()));
			if (!GetElement().IsNull())
			{
				sql += wxT(",\n       ELEMENT=") + GetElement()
				       + wxT(", DELIMITER='") + GetDelimiter() + wxT("'");
			}
			sql += wxT(",\n       INTERNALLENGTH=") + NumToStr(GetInternalLength())
			       + wxT(", ALIGNMENT=" + GetAlignment()
			             + wxT(", STORAGE=") + GetStorage());
			if (GetConnection()->BackendMinimumVersion(8, 3))
			{
				if (GetTypmodinFunction() != wxEmptyString && GetTypmodoutFunction() != wxEmptyString)
				{
					sql += wxT(",\n       TYPMOD_IN=") + GetTypmodinFunction()
					       + wxT(", TYPMOD_OUT=") + GetTypmodoutFunction();
				}
				else if (GetTypmodinFunction() != wxEmptyString)
					sql += wxT(",\n       TYPMOD_IN=") + GetTypmodinFunction();
				else if (GetTypmodoutFunction() != wxEmptyString)
					sql += wxT(",\n       TYPMOD_OUT=") + GetTypmodoutFunction();
			}
			if (GetConnection()->BackendMinimumVersion(9, 1) && GetCollatable())
			{
				sql += wxT(",\n       COLLATABLE=true");
			}
		}
		sql += wxT(");\n")
		       + GetOwnerSql(8, 0)
		       + GetCommentSql();

		if (GetConnection()->BackendMinimumVersion(9, 1))
			sql += GetSeqLabelsSql();
	}

	return sql;
}
예제 #6
0
wxString pgDomain::GetSql(ctlTree *browser)
{
    if (sql.IsNull())
    {
        sql = wxT("-- Domain: ") + GetQuotedFullIdentifier() + wxT("\n\n")
              + wxT("-- DROP DOMAIN ") + GetQuotedFullIdentifier() + wxT(";")
              + wxT("\n\nCREATE DOMAIN ") + GetQuotedFullIdentifier()
              + wxT("\n  AS ") + GetQuotedBasetype();
        if (GetCollationOid() > 0)
            sql += wxT("\n  COLLATE ") + GetQuotedCollation();
        AppendIfFilled(sql, wxT("\n  DEFAULT "), GetDefault());
        // CONSTRAINT Name Dont know where it's stored, may be omitted anyway
        if (notNull)
            sql += wxT("\n  NOT NULL");

        // Get a count of the constraints.
        int consCount = 0;
        pgCollection *constraints = browser->FindCollection(checkFactory, GetId());
        if (constraints)
        {
            constraints->ShowTreeDetail(browser);
            treeObjectIterator consIt(browser, constraints);

            pgObject *data;

            while ((data = consIt.GetNextObject()) != 0)
            {
                data->ShowTreeDetail(browser);

                sql += wxT("\n  CONSTRAINT ") + data->GetQuotedIdentifier()
                       + wxT(" ") + data->GetTypeName().Upper()
                       + wxT(" ") ;

                switch (data->GetMetaType())
                {
                case PGM_CHECK:
                    sql += wxT("(") + ((pgCheck *)data)->GetDefinition() + wxT(")");
                    if (GetDatabase()->BackendMinimumVersion(9, 2) && !((pgCheck *)data)->GetValid())
                        sql += wxT(" NOT VALID");
                    break;
                }
            }
        }

        sql += wxT(";\n")
               + GetOwnerSql(7, 4)
               + GetCommentSql();

        if (GetConnection()->BackendMinimumVersion(9, 1))
            sql += GetSeqLabelsSql();
    }

    return sql;
}
예제 #7
0
wxString pgForeignTable::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		sql = wxT("-- Foreign Table: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP FOREIGN TABLE ") + GetQuotedFullIdentifier() + wxT(";")
		      + wxT("\n\nCREATE FOREIGN TABLE ") + GetQuotedFullIdentifier()
		      + wxT("\n   (") + GetQuotedTypesList()
		      + wxT(")\n   SERVER ") + GetForeignServer();

		if (!GetOptionsList().IsEmpty())
			sql += wxT("\n   OPTIONS (") + GetOptionsList() + wxT(")");

		sql += wxT(";\n")
		       + GetOwnerSql(9, 1)
		       + GetCommentSql();

		if (GetConnection()->BackendMinimumVersion(9, 1))
			sql += GetSeqLabelsSql();
	}

	return sql;
}
예제 #8
0
파일: pgType.cpp 프로젝트: Joe-xXx/pgadmin3
wxString pgType::GetSql(ctlTree *browser)
{
	if (sql.IsNull())
	{
		sql = wxT("-- Type: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP TYPE ") + GetQuotedFullIdentifier() + wxT(";")
		      + wxT("\n\nCREATE TYPE ") + GetQuotedFullIdentifier();
		if (GetTypeClass() == TYPE_COMPOSITE)
		{
			sql += wxT(" AS\n   (");
			sql += GetQuotedTypesList();
		}
		else if (GetTypeClass() == TYPE_ENUM)
		{
			sql += wxT(" AS ENUM\n   (");
			sql += GetQuotedLabelList();
		}
		else if (GetTypeClass() == TYPE_RANGE)
		{
			sql += wxT(" AS RANGE\n   (")
			       wxT("SUBTYPE=") + rngsubtypestr;
			if (!rngsubopcstr.IsEmpty())
				sql += wxT(",\n    SUBTYPE_OPCLASS=") + rngsubopcstr;
			if (!rngcollationstr.IsEmpty())
				sql += wxT(",\n    COLLATION=") + rngcollationstr;
			if (!rngcanonical.IsEmpty())
				sql += wxT(",\n    CANONICAL=") + rngcanonical;
			if (!rngsubdiff.IsEmpty())
				sql += wxT(",\n    SUBTYPE_DIFF=") + rngsubdiff;
		}
		else
		{
			sql += wxT("\n   (INPUT=") + qtIdent(GetInputFunction())
			       + wxT(",\n       OUTPUT=") + qtIdent(GetOutputFunction());
			if (GetConnection()->BackendMinimumVersion(7, 4))
			{
				if (!GetReceiveFunction().IsEmpty())
				{
					sql += wxT(",\n       RECEIVE=") + GetReceiveFunction();
				}
				if (!GetSendFunction().IsEmpty())
				{
					sql += wxT(",\n       SEND=") + GetSendFunction();
				}
			}
			if (GetConnection()->BackendMinimumVersion(8, 3))
			{
				if (!GetTypmodinFunction().IsEmpty())
					sql += wxT(",\n       TYPMOD_IN=") + GetTypmodinFunction();
				if (!GetTypmodoutFunction().IsEmpty())
					sql += wxT(",\n       TYPMOD_OUT=") + GetTypmodoutFunction();
				if (GetAnalyzeFunction() != wxEmptyString)
					sql += wxT(",\n       ANALYZE=") + GetAnalyzeFunction();
			}
			if (GetConnection()->BackendMinimumVersion(8, 4))
			{
				sql += wxT(",\n       CATEGORY=") + qtDbString(GetCategory());
				if (GetPrefered())
					sql += wxT(",\n       PREFERRED=true");
			}
			if (GetPassedByValue())
				sql += wxT(",\n    PASSEDBYVALUE");
			AppendIfFilled(sql, wxT(", DEFAULT="), qtDbString(GetDefault()));
			if (!GetElement().IsNull())
			{
				sql += wxT(",\n       ELEMENT=") + GetElement()
				       + wxT(", DELIMITER='") + GetDelimiter() + wxT("'");
			}
			sql += wxT(",\n       INTERNALLENGTH=") + NumToStr(GetInternalLength())
			       + wxT(", ALIGNMENT=" + GetAlignment()
			             + wxT(", STORAGE=") + GetStorage());
			if (GetConnection()->BackendMinimumVersion(9, 1) && GetCollatable())
			{
				sql += wxT(",\n       COLLATABLE=true");
			}
			if (GetConnection()->BackendMinimumVersion(9, 1) && GetCollatable())
			{
				sql += wxT(",\n       COLLATABLE=true");
			}
		}
		sql += wxT(");\n")
		       + GetOwnerSql(8, 0)
		       + GetCommentSql();

		if (GetConnection()->BackendMinimumVersion(9, 1))
			sql += GetSeqLabelsSql();
	}

	return sql;
}
예제 #9
0
wxString pgDatabase::GetSql(ctlTree *browser)
{
	if (sql.IsEmpty())
	{
		// If we can't connect to this database, use the maintenance DB
		pgConn *myConn = GetConnection();
		if (!myConn)
			myConn = GetServer()->GetConnection();

		sql = wxT("-- Database: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP DATABASE ") + GetQuotedIdentifier() + wxT(";")
		      + wxT("\n\nCREATE DATABASE ") + GetQuotedIdentifier()
		      + wxT("\n  WITH OWNER = ") + qtIdent(GetOwner())
		      + wxT("\n       ENCODING = ") + qtDbString(GetEncoding());
		if (!GetTablespace().IsEmpty())
			sql += wxT("\n       TABLESPACE = ") + qtIdent(GetTablespace());
		if (myConn && myConn->BackendMinimumVersion(8, 4))
		{
			sql += wxT("\n       LC_COLLATE = ") + qtDbString(GetCollate());
			sql += wxT("\n       LC_CTYPE = ") + qtDbString(GetCType());
		}
		if (myConn && myConn->BackendMinimumVersion(8, 1))
		{
			sql += wxT("\n       CONNECTION LIMIT = ");
			sql << GetConnectionLimit();
		}
		sql += wxT(";\n");

		size_t i;
		wxString username;
		wxString varname;
		wxString varvalue;
		for (i = 0 ; i < variables.GetCount() ; i++)
		{
			wxStringTokenizer tkz(variables.Item(i), wxT("="));
			while (tkz.HasMoreTokens())
			{
				username = tkz.GetNextToken();
				varname = tkz.GetNextToken();
				varvalue = tkz.GetNextToken();
			}

			if (username.Length() == 0)
			{
				sql += wxT("ALTER DATABASE ") + GetQuotedFullIdentifier();
			}
			else
			{
				sql += wxT("ALTER ROLE ") + username + wxT(" IN DATABASE ") + GetQuotedFullIdentifier();
			}
			if (varname != wxT("search_path") && varname != wxT("temp_tablespaces"))
				sql += wxT(" SET ") + varname + wxT("='") + varvalue + wxT("';\n");
			else
				sql += wxT(" SET ") + varname + wxT("=") + varvalue + wxT(";\n");
		}

		if (myConn)
		{
			if (!myConn->BackendMinimumVersion(8, 2))
				sql += GetGrant(wxT("CT"));
			else
				sql += GetGrant(wxT("CTc"));
		}

		sql += wxT("\n") + pgDatabase::GetDefaultPrivileges('r', m_defPrivsOnTables, wxT(""));
		sql += pgDatabase::GetDefaultPrivileges('S', m_defPrivsOnSeqs, wxT(""));
		sql += pgDatabase::GetDefaultPrivileges('f', m_defPrivsOnFuncs, wxT(""));

		sql += GetCommentSql();

		if (myConn->BackendMinimumVersion(9, 2))
			sql += GetSeqLabelsSql();
	}
	return sql;
}
예제 #10
0
wxString gpExtTable::GetSql(ctlTree *browser)
{
	wxString colDetails;
	wxString prevComment;
	wxString q;

	if (sql.IsNull())
	{
		sql = wxT("-- External Table: ") + GetQuotedFullIdentifier() + wxT("\n\n")
		      + wxT("-- DROP EXTERNAL TABLE ") + GetQuotedFullIdentifier() + wxT(";\n\n");
		/* Now get required information from pg_exttable */
		if (GetDatabase()->BackendMinimumVersion(8, 2, 5))
		{
			q += wxT(
			         "SELECT x.location, x.fmttype, x.fmtopts, x.command, ")
			     wxT("x.rejectlimit, x.rejectlimittype,")
			     wxT("(SELECT relname ")
			     wxT("FROM pg_class ")
			     wxT("WHERE Oid=x.fmterrtbl) AS errtblname, ")
			     wxT("pg_catalog.pg_encoding_to_char(x.encoding) ")
			     wxT("FROM pg_catalog.pg_exttable x, pg_catalog.pg_class c ")
			     wxT("WHERE x.reloid = c.oid AND c.oid = ") + GetOidStr();
		}
		else
		{
			/* not SREH and encoding colums yet */
			q += wxT(
			         "SELECT x.location, x.fmttype, x.fmtopts, x.command, ")
			     wxT("-1 as rejectlimit, null as rejectlimittype,")
			     wxT("null as errtblname, ")
			     wxT("null as encoding ")
			     wxT("FROM pg_catalog.pg_exttable x, pg_catalog.pg_class c ")
			     wxT("WHERE x.reloid = c.oid AND c.oid = ") + GetOidStr();

		}

		pgSet *extTable = GetDatabase()->ExecuteSet(q);

		wxString locations = extTable->GetVal(0);
		wxString fmttype = extTable->GetVal(1);
		wxString fmtopts = extTable->GetVal(2);
		wxString command = extTable->GetVal(3);
		wxString rejlim = extTable->GetVal(4);
		wxString rejlimtype = extTable->GetVal(5);
		wxString errtblname = extTable->GetVal(6);
		wxString extencoding = extTable->GetVal(7);


		if ((command.Length() > 0) ||
		        (locations.Mid(1, 4) ==  wxT("http")))
		{
			sql += wxT("CREATE EXTERNAL WEB TABLE ") +
			       GetQuotedFullIdentifier() + wxT("\n(\n");
		}
		else
		{
			sql += wxT("CREATE EXTERNAL TABLE ") +
			       GetQuotedFullIdentifier() + wxT("\n(\n");
		}

		// Get the columns
		pgCollection *columns = browser->FindCollection(columnFactory, GetId());
		if (columns)
		{
			columns->ShowTreeDetail(browser);
			treeObjectIterator colIt1(browser, columns);
			treeObjectIterator colIt2(browser, columns);


			int lastRealCol = 0;
			int currentCol = 0;
			pgColumn *column;

			// Iterate the columns to find the last 'real' one
			while ((column = (pgColumn *)colIt1.GetNextObject()) != 0)
			{
				currentCol++;

				if (column->GetInheritedCount() == 0)
					lastRealCol = currentCol;
			}

			// Now build the actual column list
			int colCount = 0;
			while ((column = (pgColumn *)colIt2.GetNextObject()) != 0)
			{
				column->ShowTreeDetail(browser);
				if (column->GetColNumber() > 0)
				{
					if (colCount)
					{
						// Only add a comma if this isn't the last 'real' column
						if (colCount != lastRealCol)
							sql += wxT(",");
						if (!prevComment.IsEmpty())
							sql += wxT(" -- ") + firstLineOnly(prevComment);

						sql += wxT("\n");
					}

					/* if (column->GetInheritedCount() > 0)
					 {
					     if (!column->GetIsLocal())
					         sql += wxString::Format(wxT("-- %s "), _("Inherited"))
					             + wxT("from table ") +  column->GetInheritedTableName() + wxT(":");
					 }*/

					sql += wxT("  ") + column->GetQuotedIdentifier() + wxT(" ")
					       + column->GetDefinition();

					prevComment = column->GetComment();

					// Whilst we are looping round the columns, grab their comments as well.
					// Perhaps we should also get storage types here?
					colDetails += column->GetCommentSql();
					if (colDetails.Length() > 0)
						if (colDetails.Last() != '\n') colDetails += wxT("\n");

					colCount++;
				}
			}
		}
		if (!prevComment.IsEmpty())
			sql += wxT(" -- ") + firstLineOnly(prevComment);

		sql += wxT("\n)\n");

		if(command.Length() > 0)
		{

			wxString on_clause = locations;

			/* remove curly braces */
			on_clause = locations.Mid(1, locations.Length() - 2);


			/* add EXECUTE clause */
			sql += wxT(" EXECUTE E'");
			for (size_t i = 0; i < command.Length(); i++)
			{
				if (command[i] == wxT('\\')) sql += wxT('\\');
				if (command[i] == wxT('\'')) sql += wxT('\'');
				sql +=	command[i];
			}
			sql += wxT("' ");


			/* add ON clause */
			wxString temp;

			if(on_clause.StartsWith(wxT("HOST:"), &temp))
			{
				sql += wxT("ON HOST '") + temp + wxT("'");
			}
			else if(on_clause.StartsWith(wxT("PER_HOST"), &temp))
				sql += wxT("ON HOST ");
			else if(on_clause.StartsWith(wxT("MASTER_ONLY"), &temp))
				sql += wxT("ON MASTER ");
			else if(on_clause.StartsWith(wxT("SEGMENT_ID:"), &temp))
				sql += wxT("ON SEGMENT ") + temp + wxT(" ");
			else if(on_clause.StartsWith(wxT("TOTAL_SEGS:"), &temp))
				sql += wxT("ON  ") + temp + wxT(" ");
			else if(on_clause.StartsWith(wxT("ALL_SEGMENTS"), &temp))
				sql += wxT("ON ALL ");
			else
				sql += on_clause;

			sql += wxT("\n ");

		}
		else
		{

			/* add LOCATION clause */

			locations = locations.Mid(1, locations.Length() - 2);
			wxStringTokenizer locs(locations, wxT(","));
			wxString token;
			token = locs.GetNextToken();
			sql += wxT(" LOCATION (\n    '");
			sql += token;
			sql += wxT("'");
			while (locs.HasMoreTokens())
			{
				sql += wxT(",\n    '");
				sql += locs.GetNextToken();
				sql += wxT("'");
			}
			sql += wxT("\n)\n ");

		}

		/* add FORMAT clause */
		sql += wxT("FORMAT '");
		sql +=	fmttype[0] == 't' ? wxT("text") : wxT("csv");
		sql += wxT("'");
		sql += wxT(" (");
		for (size_t i = 0; i < fmtopts.Length(); i++)
		{
			if (fmtopts[i] == wxT('\\')) sql += wxT('\\');
			sql +=	fmtopts[i];
		}
		sql += wxT(")\n");

		if (GetDatabase()->BackendMinimumVersion(8, 2))
		{
			/* add ENCODING clause */
			sql += wxT("ENCODING '");
			sql += extencoding ;
			sql += wxT("'");

			/* add Single Row Error Handling clause (if any) */
			if(rejlim.Length() > 0)
			{
				sql += wxT("\n");

				/*
				* NOTE: error tables get automatically generated if don't exist.
				* therefore we must be sure that this statment will be dumped after
				* the error relation CREATE is dumped, so that we won't try to
				* create it twice. For now we rely on the fact that we pick dumpable
				* objects sorted by OID, and error table oid *should* always be less
				* than its external table oid (could that not be true sometimes?)
				*/
				if(errtblname.Length() > 0)
				{
					sql += wxT("LOG ERRORS INTO ");
					sql += errtblname;
					sql += wxT(" ");
				}

				/* reject limit */
				sql += wxT("SEGMENT REJECT LIMIT ");
				sql += rejlim;

				/* reject limit type */
				if(rejlimtype[0] == 'r')
					sql += wxT(" ROWS");
				else
					sql += wxT(" PERCENT");
			}
		}

		sql += wxT(";\n")
		       + GetOwnerSql(7, 3, wxEmptyString, wxT("TABLE"));


		sql += GetGrant(wxT("r"), wxT("TABLE ") + GetQuotedFullIdentifier());

		sql += GetCommentSql()
		       + wxT("\n");

		// Column/constraint comments
		if (!colDetails.IsEmpty())
			sql += colDetails + wxT("\n");

	}
	return sql;
}