📄 ch26.htm
字号:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
<HTML>
<HEAD>
<META HTTP-EQUIV="Content-Type" CONTENT="text/html;CHARSET=iso-8859-1">
<META NAME="Author" Content="Steph Mineart">
<TITLE>Ch 26 -- Extending an Internet Server with ISAPI</TITLE>
</HEAD>
<BODY BACKGROUND="bg1.gif" tppabs="http://pbs.mcp.com/ebooks/0672310228/buttonart/bg1.gif" BGCOLOR="#FFFFFF">
<P ALIGN="CENTER"><IMG SRC="sams.gif" tppabs="http://pbs.mcp.com/ebooks/0672310228/buttonart/sams.gif" WIDTH="75" HEIGHT="24" ALIGN="BOTTOM"
BORDER="0"><BR>
<BR>
<A HREF="index-3.htm" tppabs="http://pbs.mcp.com/ebooks/0672310228/index.htm"><IMG SRC="toc.gif" tppabs="http://pbs.mcp.com/ebooks/0672310228/buttonart/toc.gif" WIDTH="40" HEIGHT="40"
ALIGN="BOTTOM"
ALT="TOC" BORDER="0" NAME="toc4"></A><A HREF="ch25.htm" tppabs="http://pbs.mcp.com/ebooks/0672310228/ch25.htm"><IMG SRC="back-1.gif" tppabs="http://pbs.mcp.com/ebooks/0672310228/buttonart/back.gif"
WIDTH="40" HEIGHT="40" ALIGN="BOTTOM" ALT="BACK" BORDER="0" NAME="toc1"></A><A HREF="ch27.htm" tppabs="http://pbs.mcp.com/ebooks/0672310228/ch27.htm"><IMG
SRC="forward.gif" tppabs="http://pbs.mcp.com/ebooks/0672310228/buttonart/forward.gif" WIDTH="40" HEIGHT="40"
ALIGN="BOTTOM" ALT="FORWARD" BORDER="0"
NAME="toc2"></A></P>
<H2 ALIGN="CENTER"><FONT COLOR="#000077">Charlie Calvert's C++ Builder Unleashed</FONT></H2>
<P>
<H2 ALIGN="CENTER"><A NAME="Heading1"></A><FONT COLOR="#000077">- 26 -</FONT></H2>
<H2
ALIGN="CENTER"><A NAME="Heading2"></A><FONT COLOR="#000077">Extending an Internet
Server with ISAPI</FONT></H2>
<P>
<H3><A NAME="Heading3"></A><FONT COLOR="#000077">Overview</FONT></H3>
<P>This chapter examines the ISAPI and CGI technologies. You can
use CGI to create
applications that extend a Web server, and you can use ISAPI to create DLLs that
extend a Web server. In particular, ISAPI allows you to write scripts and filters
and to interact dynamically with a user of your browser.</P>
<P>ISAPI
technology is specific to the Internet Information Server that ships with
Windows NT and to the Personal Web Server that ships with Microsoft FrontPage. It
is, however, merely a specification, and other servers could conform to it if they
wish.
Several different vendors, including Borland, have created technology that
allows ISAPI-based technology to be used in conjunction with NSAPI, which is a similar
technology to ISAPI. (The NSAPI/ISAPI bridge is available in Delphi 3.0, for
example.)</P>
<P>ISAPI programming is very similar to CGI programming. The only major difference
is that you're creating a DLL instead of an executable. DLLs are advantageous because
they can be loaded into the address space of the Web server. This
capability gives
them a leg up over CGI when you're considering performance. CGI, on the other hand,
is a very simple specification to use, and it adapts itself easily to database applications.</P>
<P>ISAPI's reliance on the Windows platform might be
a serious limitation in some
other context, but because C++Builder also relies on Windows, discussing the topic
at length in this book makes sense. Another feature to recommend ISAPI is its extreme
simplicity. Friendly, powerful, easy-to-use APIs are
the bread and butter of this
book, and ISAPI fits the bill beautifully. Writing BCB database applications with
ISAPI is, however, a bit tricky.</P>
<P>The first half of this chapter deals with ISAPI, and the second half deals with
CGI. I will show how
to retrieve data from both ISAPI DLLs and CGI applications,
though my treatment of the subject is more complete in the section on CGI. If you
are interested primarily in ISAPI, you should also take the time to read about the
CGI database applications
in the second half of this chapter.</P>
<P>The C++ code in this chapter relies on the presence of several HTML files that
are quoted in full in this chapter and that are also available on the CD that ships
with this book. However, the C++ code will
not function properly unless the HTML
files quoted in this chapter are in the correct location on your hard drive. See
the <TT>README.TXT</TT> file that comes with the CD for additional information on
setting up your system correctly to run this code.
Some of these files are located
in the root of the <TT>Chap26</TT> directory on the CD. You will also need to use
several databases' aliases described in the readme file.
<H3><A NAME="Heading4"></A><FONT COLOR="#000077">Hardware and Software
Requirements</FONT></H3>
<P>As I implied in the "Overview" section for this chapter, the code discussed
here requires one of the following:
<UL>
<LI>A copy of Microsoft Windows NT 3.51 Server or NT 4.0 or later server with the
Internet
Information Server loaded
<P>
<LI>Windows 95 and a copy of the Personal Web Server that ships with FrontPage
</UL>
<P>At the time of this writing, it is not clear whether the Personal Web Server (PWS)
will be available from other sources besides
FrontPage. I downloaded the beta copy
I used while writing this book directly from Microsoft's Web site. Checking to see
if this copy is still available in that form is probably worthwhile.</P>
<P>You should also check to see if the Netscape or
WebSite servers are now supporting
the ISAPI API. An unfortunate and rather unseemly economic battle between Microsoft
and its various competitors may slow down or even halt the spread of ISAPI as a standard,
but checking to see if the battle has
cooled somewhat is still worthwhile.</P>
<P>At any rate, the PWS is a useful piece of software for home users to explore.
It will turn any Windows 95 machine into a Web server. I'm not sure how robust it
will be under the strain of more than a few
contiguous users. However, it is ideal
if you want to set up a Web server in your home or in a small office. WebSite, from
O'Reilly, is another fine product to turn to, particularly if you want to select
a well-tested, robust server that can carry a
heavy load.</P>
<P>You should also have a second computer equipped with a Web browser. This second
computer can be running any operating system and can use virtually any software that
supports Web browsing. I can think of no reason why you can't test
most of this code
on a single machine running a server, of course, but you will hardly get into the
spirit of this enterprise if you're limited to that kind of setup.</P>
<P>I assume that most readers working in a business setting will have an
intranet
setup that will allow them to experiment with this technology. If you're working
at home, I cannot stress too often the incredible value of setting up a network in
your house. Network cards are very inexpensive these days. One of the ones I
use
in my home cost about $30 new. Network cable is also inexpensive, and both Windows
95 and Windows NT come equipped with all the software you need to set up a network
that supports both file browsing with Windows Explorer and also TCP/IP.</P>
<P>When I first set up a network in my home, I thought I was pushing the extreme
edge of modern technology. Now I simply take it for granted and can't understand
how in the world I ever got along without it. Old computers don't have to die; they
can
just become Web servers. Small hard drives are extended easily by sharing storage
space across multiple machines. After all, you don't need a separate copy of every
application or every file on each machine. You can just share drives back and forth
between machines, thereby saving a tremendous amount of space.</P>
<P>Most importantly, you can study and experiment with your network at your leisure
and then apply that knowledge at work. A home network is an ideal place to educate
yourself
regarding this valuable technology.
<H3><A NAME="Heading5"></A><FONT COLOR="#000077">Getting More Information on ISAPI</FONT></H3>
<P>The best place to go for information on ISAPI is the Microsoft MSDN or the Microsoft
Internet SDK. These two sources
provide most of the information you need that can't
be found in this book.</P>
<P>Here's a place you can go on the Web if you want to find out more about the ISAPI
specification:</P>
<PRE><A HREF="javascript:if(confirm('http://www.microsoft.com/win32dev/apiext/isalegal.htm \n\nThis file was not retrieved by Teleport Pro, because it is addressed on a domain or path outside the boundaries set for its Starting Address. \n\nDo you want to open it from the server?'))window.location='http://www.microsoft.com/win32dev/apiext/isalegal.htm'" tppabs="http://www.microsoft.com/win32dev/apiext/isalegal.htm">http://www.microsoft.com/win32dev/apiext/isalegal.htm
</A></PRE>
<P>Of course, I can't guarantee that this Web page will still be in existence when
you read this book. However, two relatively stable sites on the Web that should serve
as links to
this spot are</P>
<PRE><A HREF="javascript:if(confirm('http://www.microsoft.com/intdev/ \n\nThis file was not retrieved by Teleport Pro, because it is addressed on a domain or path outside the boundaries set for its Starting Address. \n\nDo you want to open it from the server?'))window.location='http://www.microsoft.com/intdev/'" tppabs="http://www.microsoft.com/intdev/">http://www.microsoft.com/intdev/
</A><A HREF="javascript:if(confirm('http://www.microsoft.com/win32dev/ \n\nThis file was not retrieved by Teleport Pro, because it is addressed on a domain or path outside the boundaries set for its Starting Address. \n\nDo you want to open it from the server?'))window.location='http://www.microsoft.com/win32dev/'" tppabs="http://www.microsoft.com/win32dev/">http://www.microsoft.com/win32dev/
</A></PRE>
<P>Check in at both these sites on fairly regular
intervals to get updates on Win32
and Internet technology.
<H3><A NAME="Heading6"></A><FONT COLOR="#000077">ISAPI</FONT></H3>
<P>As stated in the Microsoft documentation, ISAPI allows you to "Write server-side
scripts and filters to extend the
capabilities of Microsoft Internet Information
Server and other ISAPI Web servers."</P>
<P>ISAPI is a very easy-to-use yet extremely powerful technology that allows you
to extend the reach of the Internet Information Server or the Personal Web
Server.
This tool allows you to make your Web site do pretty much whatever you want it to
do. For example, it provides a means for you to
<UL>
<LI>Set up interactive responses to user input
<P>
<LI>Provide database browsing and updating
<P>
<LI>Filter input to your browser to track who signs on and where he or she goes
</UL>
<P>In the past, the best way to extend a Web server was to create CGI applications.
These powerful tools were limited by their executable format. When you sent in a
CGI-based request from a browser to a server, the CGI application in question usually
had to be loaded into memory, which took a long time. Also, the CGI technology could
be a bit awkward to use under some circumstances.</P>
<P>ISAPI is a method of
writing DLLs that replace CGI applications. You can also
write filters with ISAPI, though this subject is not covered in this book. ISAPI
has the advantage of being easier to use than CGI, plus it can be much faster and
make much better use of system
resources. In particular, the following points help
explain why ISAPI DLLs are better than CGI applications:
<UL>
<LI>ISAPI DLLs live in the same address space as the HTTP server. They can therefore
directly access the HTTP services available from
the server. They load into memory
more quickly and have much less overhead when it comes to making a call from the
server. These capabilities can be particularly helpful if you're working under a
heavy load.
<P>
<LI>You can control when the DLL
is loaded or unloaded. For example, you can preload
DLLs for fast access on the first try or unload the ISAPI applications DLLs that
are not being used to free system resources. You can do the same thing with the CGI
executable, but the executable
format was not really designed for this kind of manipulation,
although this is part of the native capability of DLLs.
</UL>
<P>In this chapter, I will concentrate on writing DLLs that return datasets or that
simply communicate with the user who is
running a browser. I will not explore filters
at all. For information on filters, you should go to the Microsoft Web site or browse
the MSDN.
<H3><A NAME="Heading7"></A><FONT COLOR="#000077">ISAPI Basics</FONT></H3>
<P>The file <TT>Httpext.h</TT>
contains the key declarations used with ISAPI. This
file should ship with C++Builder and is available with versions of the Microsoft
SDK dated later than July 1996. It should also appear in the <TT>\include\vcl</TT>
directory as <TT>ISAPI.HPP</TT>.
Because it is a Windows 95- or Windows NT-based
technology, you must be using a 32-bit compiler to access this technology. You can't
use it from a 16-bit compiler, nor is it available on Windows 3.1.</P>
<P><TT>Httpext.h</TT> contains the interface to
the ISAPI technology created by Microsoft.
At the time of this writing, C++Builder has no custom interface for ISAPI, and I
will describe only how to use Microsoft's existing technology. However, ISAPI is
extremely easy to use, and the addition of a
custom object is not necessary for most
users.</P>
<P>Three functions can serve as entry points to ISAPI DLLs. The first two listed
here are mandatory, whereas the third is optional:
<UL>
<LI><TT>GetExtensionVersion</TT>: This function just does
minimal version checking.
<P>
<LI><TT>HttpExtensionProc</TT>: This function is the entry point of the DLL, like
the main <TT>begin..end</TT> block in a Delphi application.
<P>
<LI><TT>TerminateExtension</TT>: This optional routine can be used to
clean up threads
of other memory allocations.
</UL>
<P>When you're creating an ISAPI DLL, you must export the first two of the three
preceding functions. Implementing these two functions is the key to all ISAPI programming.</P>
<P>In C++Builder, DEF
files are frowned upon. You should therefore make sure that
<TT>Httpext.h</TT> has been modified to export both of these functions with <TT>__declspec(dllexport)</TT>:</P>
<PRE><FONT COLOR="#0066FF">BOOL WINAPI __declspec(dllexport)
GetExtensionVersion(HSE_VERSION_INFO *pVer);
DWORD
WINAPI
__declspec(dllexport) HttpExtensionProc(EXTENSION_CONTROL_BLOCK *pECB);
</FONT></PRE>
<P><TT>TerminateExtension</TT> is new in ISAPI 2.0. Its declaration looks like this:</P>
<PRE><FONT
COLOR="#0066FF">BOOL WINAPI TerminateExtension( DWORD dwFlags );
</FONT></PRE>
<P><TT>TerminateExtension</TT> is called just before a connection is broken. It provides
a place for you to deallocate memory allocated inside your DLL.</P>
<P>These
three routines all contain the word <TT>Extension</TT>. This term is used
because ISAPI DLLs extend the Internet Information Server or the Personal Web Server.
(Remember, the Internet Information Server is Microsoft's Web server. If you want
to turn
an NT Server into a Web server, you use this tool. It ships with NT 4.0 and
is installed automatically during the setup of that operating system.)
<H3><A NAME="Heading8"></A><FONT COLOR="#000077">Using GetExtensionVersion</FONT></H3>
<P>The
<TT>GetExtensionVersion</TT> function must be exported from your DLL; otherwise,
the server will not load your DLL. The only job of this function is to report the
version of ISAPI that you expect to support.</P>
<P>You can always just cut and paste
the <TT>GetExtensionVersion</TT> code into your
DLLs. You need to change the function only slightly when you want to change the description
passed in the <TT>lpszExtensionDesc</TT> field of the <TT>HSE_VERSION_INFO </TT>struct:</P>
<PRE><FONT
COLOR="#0066FF">BOOL WINAPI GetExtensionVersion(HSE_VERSION_INFO *pVer)
{
pVer->dwExtensionVersion = MAKELONG(HSE_VERSION_MINOR, HSE_VERSION_MAJOR);
strcpy(pVer->lpszExtensionDesc, "C++ Builder ISAPI DLL");
return (TRUE);
};
</FONT></PRE>
<P>The parameter passed to this function is declared in <TT>Httpext.h</TT> as follows:</P>
<PRE><FONT COLOR="#0066FF">typedef struct _HSE_VERSION_INFO {
DWORD dwExtensionVersion; // Version info
CHAR lpszExtensionDesc[HSE_MAX_EXT_DLL_NAME_LEN]; // Description
} HSE_VERSION_INFO, *LPHSE_VERSION_INFO;
</FONT></PRE>
<P>The two fields of the record are self-explanatory, with the first containing the
ISAPI version number and the second
holding a user-defined string describing the
purpose of the DLL. The following are some constants declared in the DLL that are
used in the preceding code:</P>
<PRE><FONT COLOR="#0066FF">#define HSE_MAX_EXT_DLL_NAME_LEN 256
#define
HSE_VERSION_MAJOR 1 // major version of this spec
#define HSE_VERSION_MINOR 0 // minor version of this spec
</FONT></PRE>
<P>That's all you need to do to set up the first of the two mandatory functions in
an ISAPI
DLL. The next step, using <TT>HttpExtensionProc</TT>, is a bit more complex,
so I will treat it in its own section.
<H3><A NAME="Heading9"></A><FONT COLOR="#000077">Working with the HttpExtensionProc</FONT></H3>
<P>The <TT>HttpExtensionProc</TT>
routine is the entry point for the DLL. It serves
the same purpose that the <TT>main()</TT> routine does in a C program, or that the
<TT>main begin..end</TT> pair does in a Delphi program.</P>
<P>Here is a very simple example of an
<TT>HttpExtensionProc</TT> routine:</P>
<PRE><FONT COLOR="#0066FF">DWORD WINAPI HttpExtensionProc(EXTENSION_CONTROL_BLOCK *pECB)
{
char ResultString[500];
DWORD resultLen;
char *IsapiLogText = "ISAPI1 - Simple ISAPI Extension DLL";
strcpy(pECB->lpszLogData, IsapiLogText);
pECB->dwHttpStatusCode = 200;
char *HtmlInfo =
"<HTML>"
"<HEAD><TITLE>C++ Builder ISAPI DLL </TITLE></HEAD>"
"<H1>ISAPI1
Test Results</H1>"
"<BODY bgcolor=\"#0000FF\" text=\"#00FFFF\">"
"Hello from a C++ Builder ISAPI DLL!<BR></BODY>"
"</HTML>";
sprintf(ResultString,
"HTTP/1.0 200 OK\nContent-Type: text/html\n"
"Content-Length: %d\nContent:\n\n %s", 500, HtmlInfo);
resultLen = lstrlen(ResultString);
fprintf(out, ResultString);
pECB->WriteClient(pECB->ConnID, ResultString,
&resultLen, 0);
return (HSE_STATUS_SUCCESS);
}
</FONT></PRE>
<P>If you queried a DLL containing this function from a browser, you would get a
page back with this message:</P>
<PRE><FONT COLOR="#0066FF">ISAPI1 Test Results
Hello from a C++
Builder ISAPI DLL!
</FONT></PRE>
<P>In the next few paragraphs, I will describe the key points of the code shown here.
However, I'll help you develop a complete understanding of this routine slowly in
the next few sections of the chapter.</P>
<P>The
HTML code for querying the DLL might look something like this:</P>
<PRE><FONT COLOR="#0066FF"><a href="/scripts/isapi1.dll">ISAPI1 Example</a>
</FONT></PRE>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -