|
|
//========= Copyright � 1996-2004, Valve LLC, All rights reserved. ============
//
// Purpose:
//
// $NoKeywords: $
//=============================================================================
#ifndef GCSCHEMAFULL_H
#define GCSCHEMAFULL_H
#ifdef _WIN32
#pragma once
#endif
namespace GCSDK {
//-----------------------------------------------------------------------------
// SerSchemaFull
// This defines the binary serialization format for a CSchemaFull
//-----------------------------------------------------------------------------
struct SerSchemaFull_t { enum EVersion { k_ECurrentVersion = 1, };
int32 m_nVersion; // version of serialization format
int32 m_cSchema; // # of schema we contain
};
//-----------------------------------------------------------------------------
// CFTSCatalogInfo
// information about a full text search catalog object in our schema
//-----------------------------------------------------------------------------
class CFTSCatalogInfo { public: enum ESchemaCatalog m_eCatalog; const char *m_pstrName; int m_nFileGroup;
CFTSCatalogInfo() : m_pstrName( NULL ), m_eCatalog( k_ESchemaCatalogInvalid ) { }
~CFTSCatalogInfo() { free( (void*) m_pstrName); }
CFTSCatalogInfo( const CFTSCatalogInfo &refOther ) { m_eCatalog = refOther.m_eCatalog; m_nFileGroup = refOther.m_nFileGroup; if ( refOther.m_pstrName != NULL ) m_pstrName = strdup( refOther.m_pstrName ); else m_pstrName = NULL; }
#ifdef DBGFLAG_VALIDATE
void Validate( CValidator &validator, const char *pchName ) // Validate our internal structures
{ validator.ClaimMemory( (void *) m_pstrName ); } #endif
};
//-----------------------------------------------------------------------------
// SchemaFull conversion instructions
// These specify various operations that can be performed when converting
// from one SchemaFull to another.
//-----------------------------------------------------------------------------
struct DeleteTable_t { char m_rgchTableName[k_cSQLObjectNameMax]; // Name of the table to delete
};
struct RenameTable_t { char m_rgchTableNameOld[k_cSQLObjectNameMax]; // Rename a table with this name
int m_iTableDst; // to this table
};
enum ETriggerType { k_ETriggerType_Invalid, k_ETriggerType_After_Insert, k_ETriggerType_InsteadOf_Insert, k_ETriggerType_After_Delete, k_ETriggerType_InsteadOf_Delete, k_ETriggerType_After_Update, k_ETriggerType_InsteadOf_Update, };
class CTriggerInfo { public: CTriggerInfo() : m_eTriggerType( k_ETriggerType_Invalid ), m_bMatched( false ) { }
// are these equal for identity?
bool operator==( const CTriggerInfo& refOther ) const { if ( 0 != Q_stricmp( m_szTriggerTableName, refOther.m_szTriggerTableName ) ) return false; if ( 0 != Q_stricmp( m_szTriggerName, refOther.m_szTriggerName ) ) return false;
// they're equal!
return true; }
// if the identity is the same, this will tell if text or type differs
bool IsDifferent( const CTriggerInfo& refOther ) const { if ( m_eTriggerType != refOther.m_eTriggerType ) return false; if ( m_strText != refOther.m_strText ) return false;
// they're equal!
return true; }
const char* GetTriggerTypeString() const { const char *pstrSQL = "~~ unknown trigger type syntax error ~~";
switch ( m_eTriggerType ) { case k_ETriggerType_After_Insert: pstrSQL = "AFTER INSERT"; break; case k_ETriggerType_InsteadOf_Insert: pstrSQL = "INSTEAD OF INSERT"; break; case k_ETriggerType_After_Delete: pstrSQL = "AFTER DELETE"; break; case k_ETriggerType_InsteadOf_Delete: pstrSQL = "INSTEAD OF DELETE"; break; case k_ETriggerType_After_Update: pstrSQL = "AFTER UPDATE"; break; case k_ETriggerType_InsteadOf_Update: pstrSQL = "INSTEAD OF UPDATE"; break;
default: case k_ETriggerType_Invalid: /* initialize is fine, thanks */ break; }
return pstrSQL; }
bool m_bMatched; // got matched during schema convert
ETriggerType m_eTriggerType; // what kinda trigger is this?
ESchemaCatalog m_eSchemaCatalog; // catalog where this trigger lives
char m_szTriggerName[k_cSQLObjectNameMax]; // name of the trigger object
char m_szTriggerTableName[k_cSQLObjectNameMax]; // name of the table hosting this trigger
CUtlString m_strText; // text of the trigger
// Validate our internal structures
#ifdef DBGFLAG_VALIDATE
void Validate( CValidator &validator, const char *pchName ) { m_strText.Validate( validator, pchName ); } #endif
};
//-----------------------------------------------------------------------------
// CSchemaFull
// This defines the schema for the entire data store. It's essentially just
// a collection of CSchema, which define the schema for individual tables.
//-----------------------------------------------------------------------------
class CSchemaFull { public: // Constructors & destructors
CSchemaFull(); ~CSchemaFull();
void Uninit();
// add a new schema and return its pointer.
CSchema *AddNewSchema( int iTable, ESchemaCatalog eCatalog, const char *pstrName ) { CSchema &refNewSchema = m_VecSchema[m_VecSchema.AddToTail()]; refNewSchema.SetName( pstrName ); refNewSchema.SetESchemaCatalog( eCatalog ); SetITable( &refNewSchema, iTable ); return &refNewSchema; }
// Accessors
int GetCSchema() const { return m_VecSchema.Count(); } CSchema &GetSchema( int iSchema ) { return m_VecSchema[iSchema]; } uint32 GetCheckSum() const { return m_unCheckSum; }
uint8 *GetPubScratchBuffer( ); uint32 GetCubScratchBuffer() const { return m_cubScratchBuffer; }
// Makes sure that a generated intrinsic schema is consistent
void CheckSchema( CSchema *pSchema, int cField, uint32 cubRecord );
// Find the table with a given name (returns -1 if not found)
int FindITable( const char *pchName ); const char *PchTableFromITable( int iTable );
// Helper functions for recording schema conversion operations
void AddDeleteTable( const char *pchTableName ); void AddRenameTable( const char *pchTableNameOld, const char *pchTableNameNew ); void AddDeleteField( const char *pchTableName, const char *pchFieldName ); void AddRenameField( const char *pchTableName, const char *pchFieldNameOld, const char *pchFieldNameNew ); void AddAlterField( const char *pchTableName, const char *pchFieldNameOld, const char *pchFieldNameNew, PfnAlterField_t pfnAlterField );
// declare that a trigger is on a table
void AddTrigger( ESchemaCatalog eCatalog, const char *pchTableName, const char *pchTriggerName, ETriggerType eTriggerType, const char *pchTriggerText );
// Schema conversion helper: figure out what table to map a table from a different schema to
bool BCanConvertTable( const char *pchTableSrc, int *piTableDst );
// full text catalogs
void AddFullTextCatalog( enum ESchemaCatalog eCatalog, const char *pstrCatalogName, int nFileGroup ); int GetFTSCatalogByName( enum ESchemaCatalog eCatalog, const char *pstrCatalogName ); void EnableFTS( enum ESchemaCatalog eCatalog ); int GetCFTSCatalogs() const { return m_vecFTSCatalogs.Count(); } const CFTSCatalogInfo & GetFTSCatalogInfo( int nIndex ) const { return m_vecFTSCatalogs[nIndex]; }
const CUtlVector< CTriggerInfo> & GetTriggerInfos( ) const { return m_VecTriggers; }
// is the given schema catalog FTS enabled?
bool GetFTSEnabled( enum ESchemaCatalog eCatalog );
void Validate( CValidator &validator, const char *pchName ); // Validate our internal structures
// sets tableID on CSchema, checking that it is not a duplicate
void SetITable( CSchema* pSchema, int iTable ); void FinishInit(); // Recalculates some internal fields
private:
CUtlVector< CSchema > m_VecSchema; // Schema for tables in all catalogs
CUtlVector< CTriggerInfo > m_VecTriggers; // list of triggers in all catalogs
// which schema catalogs have FTS enabled?
CUtlMap< ESchemaCatalog, bool > m_mapFTSEnabled;
// list of catalogs; each is marked with the schema where it lives.
CUtlVector< CFTSCatalogInfo > m_vecFTSCatalogs;
uint32 m_unCheckSum; // A simple checksum of our contents
// SchemaFull conversion instructions
CUtlVector<DeleteTable_t> m_VecDeleteTable; CUtlVector<RenameTable_t> m_VecRenameTable;
uint8 *m_pubScratchBuffer; // Big enough to hold any record or sparse record in this schemafull
uint32 m_cubScratchBuffer; // Size of the scratch buffer
};
extern CSchemaFull & GSchemaFull();
} // namespace GCSDK
#endif // GCSCHEMAFULL_H
|