⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 atlrt.cpp

📁 Vc.Net入门与提高源码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// atlrt.cpp : Defines the entry point for the DLL application.
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
// This source code is only intended as a supplement to the
// Microsoft Classes Reference and related electronic
// documentation provided with the library.
// See these sources for detailed information regarding the
// Microsoft C++ Libraries products.

#include "stdafx.h"
// For custom assert and trace handling with WebDbg.exe
#ifdef _DEBUG
CDebugReportHook g_ReportHook;
#endif

#include "atlrt.h"
[ module(name="atlrt", type="dll") ];
[ emitidl(restricted) ];

#include "atlrtextension.h"

HTTP_CODE CATLRTHandler::ValidateAndExchange()
{			
	Trace::TraceMsg("CATLRTHandler ValidateAndExchange");

	// Get the IMemoryCache service from the ISAPI extension
	if (FAILED(m_spServiceProvider->QueryService(__uuidof(IMemoryCache), 
					__uuidof(IMemoryCache), (void **)&m_spBinaryCache)))
		return HTTP_FAIL;

	// Get the IDataSourceCache service from the ISAPI extension
	if (FAILED(m_spServiceProvider->QueryService(__uuidof(IDataSourceCache), 
					__uuidof(IDataSourceCache), (void **)&m_spDataSrcCache)))
		return HTTP_FAIL;

	// get or create our variable map	
	HCACHEITEM cacheHandle;
	HRESULT hr = m_spBinaryCache->LookupEntry(VARIABLE_MAP, &cacheHandle);
	if (FAILED(hr))
	{
		// we need to create a variable map
		m_variableMap = new StringMap();		
		hr = m_spBinaryCache->Add(VARIABLE_MAP, 
								  (void*)m_variableMap,
								  sizeof(StringMap),
								  NULL,
								  NULL,
								  NULL,
								  NULL);
		if (FAILED(hr))
		{
			Trace::TraceMsg("CATLRTHandler ValidateAndExchange can't create variable map!");
			return hr;
		}
	}
	else
	{
		// get the variable map pointer from the cache
		DWORD dwSize = 0;	
		hr = m_spBinaryCache->GetData(cacheHandle, (void**)&m_variableMap, &dwSize);
		
		if (FAILED(hr) || !m_variableMap)
		{
			Trace::TraceMsg("CATLRTHandler ValidateAndExchange can't get variable map!");
			return hr;
		}
	}	

	// get or create our connection time	
	hr = m_spBinaryCache->LookupEntry(CONNECTION_MAP, &cacheHandle);
	if (FAILED(hr))
	{
		// we need to create a variable map
		m_connectionMap = new StringMap();		
		hr = m_spBinaryCache->Add(CONNECTION_MAP, 
								  (void*)m_connectionMap,
								  sizeof(StringMap),
								  NULL,
								  NULL,
								  NULL,
								  NULL);
		if (FAILED(hr))
		{
			Trace::TraceMsg("CATLRTHandler ValidateAndExchange can't create connection map!");
			return hr;
		}
	}
	else
	{
		// get the variable map pointer from the cache
		DWORD dwSize = 0;	
		hr = m_spBinaryCache->GetData(cacheHandle, (void**)&m_connectionMap, &dwSize);
		
		if (FAILED(hr) || !m_connectionMap)
		{
			Trace::TraceMsg("CATLRTHandler ValidateAndExchange can't get connection map!");
			return hr;
		}
	}
	CloseHandle(cacheHandle);

	return HTTP_SUCCESS;
}
 
HTTP_CODE CATLRTHandler::Uninitialize(HTTP_CODE hcError) throw( )
{
	Trace::TraceMsg("CATLRTHandler Uninitialize");
	
	return HTTP_SUCCESS;
}

/////////////////////////////////////////////////////////////////////
// Variable Map Operations
/////////////////////////////////////////////////////////////////////	
HTTP_CODE CATLRTHandler::OnGetValue(TCHAR *szVariableName)
{	
	ASSERT(szVariableName);
	if (szVariableName == NULL) 
		return HTTP_SUCCESS;

	LPCSTR szValue = NULL;

	// try to find the variable value in our variable map or in the request parameters
	szValue = _GetValue(CStringA(szVariableName));

	// if we got a value from either place, output it
	if (szValue != NULL)
	{
		m_HttpResponse << szValue;				
	}

	return HTTP_SUCCESS;
}

HTTP_CODE CATLRTHandler::OnCopyValue(TCHAR *szArgs)
{
	ASSERT(szArgs);
	if (!szArgs)
		return HTTP_SUCCESS;

	ArgParser parser;

	if (!parser.Parse(szArgs))
		return HTTP_SUCCESS;

	// need 'source' and 'dest' attributes
	CStringA source;
	CStringA dest;
	
	if (parser.GetAttribute("source", source) != 1)
		return HTTP_SUCCESS;

	if (parser.GetAttribute("dest", dest) != 1)
		return HTTP_SUCCESS;

	// get the value specified by source
	LPCSTR szSourceValue = _GetValue(source);

	if (!szSourceValue)
		return HTTP_SUCCESS;

	// insert this value into the destination name	
	m_variableMap->SetAt(dest, szSourceValue);

	return HTTP_SUCCESS;
}

HTTP_CODE CATLRTHandler::OnContainsValue(TCHAR *szName)
{	
	if (!szName)
		return HTTP_S_FALSE;

	if (!_GetValue(CStringA(szName)))
		return HTTP_S_FALSE;
	else
		return HTTP_SUCCESS;	
}

HTTP_CODE CATLRTHandler::OnCompareValue(TCHAR *szArgs)
{
	if (!szArgs)
		return HTTP_S_FALSE;

	ArgParser parser;

	if (!parser.Parse(szArgs))
		return HTTP_S_FALSE;

	// get the 'name' and 'value' attributes, both are required
	CStringA name;
	CStringA value;

	if (parser.GetAttribute("name", name) != 1)
		return HTTP_S_FALSE;

	if (parser.GetAttribute("value", value) != 1)
		return HTTP_S_FALSE;

	// get the value specified by 'name1'
	LPCSTR szValue1 = _GetValue(name);
	
	if (!szValue1)
		return HTTP_S_FALSE;

	// compare the values	
	if (strcmp(szValue1, value) != 0)
	{	
		return HTTP_S_FALSE;
	}
	else
	{
		return HTTP_SUCCESS;
	}
}

HTTP_CODE CATLRTHandler::OnMaintainValue(TCHAR *szArgs)
{	
	if (!szArgs)
		return HTTP_SUCCESS;

	ArgParser parser;

	CStringA var_name;
	CStringA state_name;

	// see if we have an arg list (ie. a=b;c=d)
	if (!parser.Parse(szArgs)) // if we don't, use the whole CStringA as the name
	{		
		var_name = szArgs;
		state_name = szArgs;
	}
	else // if we do, parse out the values
	{		
		if (parser.GetAttribute("name", var_name) != 1)
			return HTTP_SUCCESS;

		if (parser.GetAttribute("save_as", state_name) != 1)
			return HTTP_SUCCESS;
	}

	// get the value specified by var_name
	LPCSTR szValue = _GetValue(var_name);

	if (!szValue)
		return HTTP_SUCCESS;

	// save this value as a hidden input field
	CStringA hiddenField;
	hiddenField.Format("<input type=\"hidden\" value=\"%s\" name=\"%s\">", szValue, state_name);
	
	m_HttpResponse << hiddenField;

	return HTTP_SUCCESS;
}

/////////////////////////////////////////////////////////////////////
// Database Operations
/////////////////////////////////////////////////////////////////////
HTTP_CODE CATLRTHandler::OnSetConnection(TCHAR *szArgs)
{
	if (!szArgs)
	{
		m_HttpResponse << "ERROR: missing argument CStringA";			
		m_HttpResponse << USEAGE_SETCONNECTION;

		return HTTP_SUCCESS;
	}
	ArgParser parser;

	// look for server, 
	CStringA name;
	CStringA conn;

	if (!parser.Parse(szArgs))
	{
		name = DEFAULT_CONNECTION;

		// we have to treat this string carefully, if there are enclosing quotes, then 
		// these quotes have to be removed		
		if (*szArgs == '\"')
		{			
			int length = strlen(szArgs);

			// we don't want the first and last characters in szArgs, which are "'s
			for (int i = 1; i < length - 1; i++)
			{	
				conn += szArgs[i];
			}	
		}
		else
		{
			conn = szArgs;		
		}
	}
	else
	{
		if (parser.GetAttribute("name", name) != 1)
		{
			m_HttpResponse << "ERROR: missing name attribute";			
			m_HttpResponse << USEAGE_SETCONNECTION;

			return HTTP_SUCCESS;
		}
		if (parser.GetAttribute("conn", conn) != 1)
		{
			m_HttpResponse << "ERROR: missing conn attribute";
			m_HttpResponse << USEAGE_SETCONNECTION;

			return HTTP_SUCCESS;
		}
	}

	// put the connection CStringA into our map
	m_connectionMap->SetAt(name, conn);

	return HTTP_SUCCESS;
}

HTTP_CODE CATLRTHandler::OnExecute(TCHAR *szArgs)
{
	if (!szArgs)
		return HTTP_S_FALSE;

	// look for:
	// cmd (required)
	// conn (optional, default to 'default_connection'
	// results (optional, default to 'default_result'
	// input_params (optional)
	// output_params (optional)
	
	ArgParser parser;

	if (!parser.Parse(szArgs))
		return HTTP_S_FALSE;

	CStringA cmd;
	if (parser.GetAttribute("cmd", cmd) != 1)
		return HTTP_S_FALSE;

	CStringA conn;
	if (parser.GetAttribute("conn", conn) != 1)
		conn = DEFAULT_CONNECTION;

	// we could have multiple result names or none at all
	StringList resultNames;
	parser.GetAttribute("results", resultNames);

	// set a default value if we don't have any result names
	if (resultNames.GetCount() == 0)
		resultNames.AddTail(DEFAULT_RESULTS);

	// we could have multiple input parameter names or none at all
	Params inputParamNames;
	StringList inputParams;
	parser.GetAttribute("params", inputParamNames);
		
	int inputParamCount = inputParamNames.GetCount();
	if (inputParamCount > 0)
	{
		// resolve our parameter values
		if (_ResolveParameters(inputParamNames, inputParams) <= 0)
		{
			// just get out of here, _ResolveParameters has already outputted
			// an error message
			// return HTTP_S_FALSE to stop processing so we don't crash
			// on calls that depend on this function succeeding
			return HTTP_S_FALSE;
		}
	}

	// we could have multiple output parameter names or none at all
	StringList outputParams;
	parser.GetAttribute("output_params", outputParams);

	// create a builder to add to our cmd results map
	ResultSetBuilder builder(&resultNames, &outputParams, m_variableMap);

	// create a data connection factory that will hide all the 
	// data cache pooling and creation details
	DataConnectionFactory dataConnectionFactory(m_spDataSrcCache);

	// create a cmd info factory that will hide all the details
	// involving getting information about a stored procedure
	CmdInfoFactory cmdInfoFactory(m_spBinaryCache);

	// execute our command	
	DBCommand command(&builder, &dataConnectionFactory, &cmdInfoFactory);

	HRESULT hr;
	if (FAILED((hr = command.Execute(	cmd,
										(*m_connectionMap)[conn],
										inputParams))))
	{
		// we could not execute the stored proc, tell the user and
		// get out of here
		m_HttpResponse << "execute command: " << cmd << " failed" << " " << hr;

		// return HTTP_S_FALSE to stop processing so we don't crash
		// on calls that depend on this function succeeding
		return HTTP_S_FALSE;
	}
	
	// if we succeeded, get the results
	builder.GetResults(m_resultsMap);

	return HTTP_SUCCESS;
}

HTTP_CODE CATLRTHandler::OnMoveNextRow(TCHAR *szArgs)
{	
	CStringA resultsName;

	if (!szArgs)
	{
		// if we get a NULL argument, use 'DEFAULT_RESULTS' as the results name		
		resultsName = DEFAULT_RESULTS;
	}
	else
	{
		// otherwise, take the whole argument string as the result name
		resultsName = szArgs;		
	}

	// if we get here, then we have a valid results name, either the default or
	// the one the user specified
	// see if we have a CmdResult using this results name as the key

	if (!_CheckForResults(resultsName))
	{
		// getting here means we have no results for the specified name, _CheckForResults
		// has already sent an error message so we can just return

		return HTTP_S_FALSE;
	}
	
	// otherwise, move the result set along
	if (m_resultsMap[resultsName].MoveNextRow())		
	{
		return HTTP_SUCCESS;
	}
	else
	{
		// MoveNextRow will be used in a loop, so returning HTTP_S_FALSE will stop
		// the loop
		return HTTP_S_FALSE;
	}
}

HTTP_CODE CATLRTHandler::OnMoveNextColumn(TCHAR *szArgs)
{
	CStringA resultsName;

	if (!szArgs)
	{
		// if we get a NULL argument, use 'DEFAULT_RESULTS' as the results name		
		resultsName = DEFAULT_RESULTS;
	}
	else
	{
		// otherwise, take the whole argument string as the result name
		resultsName = szArgs;		
	}

	// if we get here, then we have a valid results name, either the default or
	// the one the user specified
	// see if we have a CmdResult using this results name as the key

	if (!_CheckForResults(resultsName))
	{
		// getting here means we have no results for the specified name, _CheckForResults
		// has already sent an error message so we can just return

		return HTTP_S_FALSE;
	}
	
	// otherwise, move the result set along
	if (m_resultsMap[resultsName].MoveNextColumn())		
	{
		return HTTP_SUCCESS;
	}
	else
	{
		// MoveNextColumn will be used in a loop, so returning HTTP_S_FALSE will stop
		// the loop
		return HTTP_S_FALSE;
	}
}


HTTP_CODE CATLRTHandler::OnGetColumnValue(TCHAR *szArgs)
{
	// szArgs has 4 possiblities, look for each one in the following code:
	// 1. szArgs == NULL -  this means we'll use the default result name and the current column
	//						value stored for that result
	// 2. szArgs == "name=value;" - this means we'll use the specified result name and the current
	//								value stored for that result
	// 3. szArgs == "name=value;column=col" - this means we'll use the specified result name and the
	//										  specified column value.
	// 4. szArgs == "column index" - this means we'll use the default result name and the specified column
	//								 value
	
	CStringA resultsName;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -