ConfluenceWrapper
-----------------

Overview:

ConfluenceWrapper.dll provides a wrapper layer between the C# code generated by the .NET
WSDL tool and the unmanaged C++ of ReportGen. It exposes the following methods:

Usage:

bool ConfLogin( const char* const username, const char* const password, char* const authToken, const int iMaxLen )
Login to confluence and return an authentication token in the string pointed to by authToken. Confluence authentication
tokens are generally short (< 10 characters) but adding some overhead for safety is worthwhile. This authentication
token will be passed to other methods and is essentially a session ID.

void ConfLogout( const char* const authToken )
Logout and end the session pointed to by authToken.

bool ConfGetPage( const char* const authToken, const char* const space, const char* const page, ConfluencePage& remotePage )
This function retrieves a page from Confluence identified by the space name (space) and page name (page). A ConfluencePage
structure must be allocated by the caller but the fields within are allocated and managed by the DLL. Unfortunately this
was the cleanest way of passing data back and forth across the DLL boundary and between unmanaged and managed C++.

void ConfFreePage( ConfluencePage* page )
This function frees the members contained within the ConfluencePage structure but not the structure itself, which is owned
by the caller as described above. This should be used to clean up any page returned from ConfGetPage once it is finished
with.

bool ConfAttachFile( const char* const authToken, const char* const filename, const char* const shortFilename, const char* const title, const char* const mimeType, const unsigned char* pData, const unsigned int uDataSize, LONG64 pageId )
This method is used to attach a file to a page described by pageId (which can be retrieved from within a ConfluencePage
structure. Filename and shortFilename are the full and relative path to the file, shortFilename should uniquely identify
the attachment within its parent Confluence page. mimeType is a string describing the MIME type of the file and must be
set correctly in order to view the attachment correctly with Confluence. Finally pData and uDataSize point to the full
contents of the file to be uploaded.
In addition to uploading the page this function will also verify that it was uploaded correctly and then introduce a delay
to prevent corruption issues that can occur if files are uploaded too rapidly.

Binding to ConfluenceWrapper:

Unfortunately dynamic binding must be used with .NET class libraries. The ConfluenceStubs structure is provided for this
purpose. An example of binding ConfluenceWrapper, as used in ReportGen is given below:

bool InitialiseConfluence( void )
{
	if ( g_hConfluence == NULL )
	{
		const HMODULE g_hConfluence = LoadLibraryA( "ConfluenceWrapper.dll" );
		if ( g_hConfluence == NULL )
		{
			const DWORD error = GetLastError();
			fprintf( stderr, "Failed to load ConfluenceWrapper.dll (%i)\n", error );
			return false;
		}
	
		g_Conf.pfnLogin = (ConfLogin*)GetProcAddress( g_hConfluence, "Login" );
		g_Conf.pfnLogout = (ConfLogout*)GetProcAddress( g_hConfluence, "Logout" );
		g_Conf.pfnGetPage = (ConfGetPage*)GetProcAddress( g_hConfluence, "GetPage" );
		g_Conf.pfnFreePage = (ConfFreePage*)GetProcAddress( g_hConfluence, "FreePage" );
		g_Conf.pfnAttachFile = (ConfAttachFile*)GetProcAddress( g_hConfluence, "AttachFile" );
	}
	return true;
}

bool ShutdownConfluence( void )
{
	if ( g_hConfluence != NULL )
	{
		FreeLibrary( g_hConfluence );
		g_hConfluence = NULL;
	
		g_Conf.pfnLogin = NULL;
		g_Conf.pfnLogout = NULL;
		g_Conf.pfnGetPage = NULL;
		g_Conf.pfnFreePage = NULL;
		g_Conf.pfnAttachFile = NULL;
	}
	return true;
}
