Web Q&A

ANSI Chars in XML, E-commerce Architecture, and More

Edited by Nancy Michell

Q I am writing some code that writes strings from Registry keys, value names, and value data strings into an XML document that I operate on programmatically and sometimes display in an HTML report. I also sometimes need to regenerate the original data string from the XML document. My problem is that there are valid ANSI characters such as 0x07 (BEL) that appear in these Registry strings which are not valid XML characters and, according to the specification, are not valid to escape.

Q I am writing some code that writes strings from Registry keys, value names, and value data strings into an XML document that I operate on programmatically and sometimes display in an HTML report. I also sometimes need to regenerate the original data string from the XML document. My problem is that there are valid ANSI characters such as 0x07 (BEL) that appear in these Registry strings which are not valid XML characters and, according to the specification, are not valid to escape.

I am considering using a Base64 encoding of these strings, but this makes rendering the data in an XML page difficult. How can I automatically decode and display the Base64 string with the invalid character?

Another approach would be to use the rules for XML escaping to double encode these strings using "&x07;" notation. However, I then need to write my XML encoder (because it seems that these characters are invalid, so a standard encoder may not consistently encode them as I expect) and build a decoder that I can run on the strings twice to convert the final escaped sequence into the string as needed. However, both of these solutions seem like a hack to me. There must be enough of these legacy strings around that others have faced this problem as well.

A Escaping the characters would still be incorrect; they are disallowed for well-formed XML regardless of whether they are escaped or not. The only correct way to store bytes like 0x07 in XML is to use BinHex or Base64.

A Escaping the characters would still be incorrect; they are disallowed for well-formed XML regardless of whether they are escaped or not. The only correct way to store bytes like 0x07 in XML is to use BinHex or Base64.

On the other hand, you are correct that this is a relatively common problem. SQL Server™ varchar columns, for example, and messages in Microsoft® Exchange Server both allow such characters. Support for these characters has been proposed for the XML 1.1 specification, but you should not make plans based on that. A workaround would be to use your own escaping mechanism (not XML's ""). Of course, you could write the characters out using XmlTextWriter and the invalid XML will load in Microsoft Internet Explorer (which supports these invalid characters for legacy reasons), but this is strongly discouraged because your XML will break in most other parsers.

Q My company sells tickets for events. Popular events produce heavy traffic on our ASP.NET system. We have six Web servers load balanced using hardware and an Oracle back-end database. During heavy load on the system, the Oracle Query/Lock manager pegs the memory and processor. Through testing, I found that if I can use a separate queue, I can alleviate the immediate problem.

Q My company sells tickets for events. Popular events produce heavy traffic on our ASP.NET system. We have six Web servers load balanced using hardware and an Oracle back-end database. During heavy load on the system, the Oracle Query/Lock manager pegs the memory and processor. Through testing, I found that if I can use a separate queue, I can alleviate the immediate problem.

I am considering the following architecture to solve the problem. First, I want to create two local Microsoft Message Queue Server (MSMQ) queues on each of the six Web servers. Let's call these queues ProcessQueue and ResponseQueue. Each Web server will have a custom .NET service. When a request comes in, the ASP.NET page will put a message in the ProcessQueue and then get into a loop to continuously read the ResponseQueue until a message is found or a predefined timeout occurs.

The service will read the message (which will be comprised of the data I need to run the stored procedure in Oracle) and call the Oracle stored procedure. This will be a synchronous process. So from the perspective of the Oracle database there will be only five requests in the queue at any one point in time, thus minimizing the load on the database server. The service can be made smart enough to spawn off multiple threads, providing the ability to find a sweet spot where the database is neither overloaded nor underutilized. Once the stored procedure is completed, the service will put a message in ResponseQueue for the ASP.NET request to pick it up. Will this architecture solve the problem?

A Does the long-running transaction have to be synchronous to the user? In other words, for asynchronous tracking, you can just drop a message on the queue, give the user a tracking ID so that they can manually track the result, and then send them a success or failure e-mail, as many e-commerce sites such as Amazon.com and Barnes & Noble.com do.

A Does the long-running transaction have to be synchronous to the user? In other words, for asynchronous tracking, you can just drop a message on the queue, give the user a tracking ID so that they can manually track the result, and then send them a success or failure e-mail, as many e-commerce sites such as Amazon.com and Barnes & Noble.com do.

In this scenario, you drop a message on the queue and return to the user immediately. The user gets a tracking ID. The service pulls the message off the queue and sends the request to the database when it has the opportunity. When it gets the success or failure result from the database, it sends an e-mail indicating so. If it was a failure, the user is prompted to return to the site, enter a new credit card number, choose different seats, and so on. If it was a success, the mail just gives the customer a final confirmation number, expected ship dates, a link to print up tickets, and so on.

Q Does Microsoft have any solution for securing my network from people who walk into the office, plug in a laptop, and boot on the network? I know about Remote Access with Windows Server™ 2003, but is there any way besides physical security to secure the internal network from visitors and customers just plugging in and using the network? I want to avoid viruses that come in via portable devices.

Q Does Microsoft have any solution for securing my network from people who walk into the office, plug in a laptop, and boot on the network? I know about Remote Access with Windows Server™ 2003, but is there any way besides physical security to secure the internal network from visitors and customers just plugging in and using the network? I want to avoid viruses that come in via portable devices.

A If you implement 802.1x for wired networks, it's possible to secure your internal network. But this solution can be costly because you need network hardware that supports it. You could use 802.1x certificate-based authentication with RADIUS server, but if you do not have Active Directory® (autoenrollment) and Windows Server, you'll incur an additional cost as well as facing a programming challenge.

A If you implement 802.1x for wired networks, it's possible to secure your internal network. But this solution can be costly because you need network hardware that supports it. You could use 802.1x certificate-based authentication with RADIUS server, but if you do not have Active Directory® (autoenrollment) and Windows Server, you'll incur an additional cost as well as facing a programming challenge.

Without Active Directory fully deployed, you might want to create a Web site where users can request a certificate. Once they get this certificate, it will direct them to the RADIUS server at which point you'll do your mandatory checks and put them in quarantine. So, how do you force all clients to get a certificate? You can refuse to route their IP traffic based on either their machine access code (MAC) or current IP (MAC would be better since it does not change as often). They will then be forced to call your help desk where you can direct them to the correct procedure. The beauty of this solution is that it works for wireless, too.

You can require MAC address reservations for ports on switches. But using MAC address or IP address restrictions does not scale well and is not secure, as both are easily spoofed. Plus, using MAC filtering in the switches means that every time someone gets a new PC, another human will have to update the switch table.

802.1x or IPSec are the recommended technologies to use here. 802.1x requires Windows® XP on all clients as well as a public key infrastructure (PKI) and RADIUS. IPSec works with Windows 2000 clients and doesn't require RADIUS, but it does require a PKI (please don't use pre-shared keys).

In addition, if you want to use a technology like Enterasys, which allows for blocking devices at the port level, you should go to https://www.enterasys.com/solutions/secure-networks to take a look at their User Personalized Network (UPN) offering.

There's also a great article on this exact topic by the IPSec team at Microsoft which describes how to configure IPSec for Windows 2000 and Windows XP to help secure an internal corporate network server against network-based attacks from untrusted computers. This paper describes the security threats to and the benefits of using IPSec on an internal corporate network server and uses a scenario to describe the process of IPSec policy design for an internal corporate network. Although the focus of this paper is IPSec for Windows 2000 and Windows XP, it also provides information about IPSec functionality enhancements in Windows 2000 service packs and in the Windows Server 2003 family. Microsoft and Foundstone Strategic Strategy coauthored "Using Microsoft Windows IPSec to Help Secure an Internal Corporate Network Server.".

IPSec is a good solution, but if you are implementing 802.1x for your wireless networks anyway, then using it as a starting point to a wired solution may make sense.

Q I'm looking for documentation to help me design an offline scenario in a traditional three-tier application. If the network connection becomes unavailable, what are the best practices for continuing work until the connection becomes available again?

Q I'm looking for documentation to help me design an offline scenario in a traditional three-tier application. If the network connection becomes unavailable, what are the best practices for continuing work until the connection becomes available again?

Here's some background. Currently, I use a centralized database on the back end. There are clients at many different locations and multiple clients at each location. We're using COM+ for the COM components in the middle tier, and ADO and ODBC.

A There's a good tutorial on this subject—"Northwind Unplugged: Build a Semi-Connected Application in Visual Basic .NET". It's a .NET-compatible application and will give you some good ideas on how to handle the "sometimes-offline" scenario. It shows how to build a semi-connected application using Visual Basic® .NET. The application bases its behavior on the connection state. When working offline, changes to data are cached, and later, when reconnected, the data is automatically synchronized with the server.

A There's a good tutorial on this subject—"Northwind Unplugged: Build a Semi-Connected Application in Visual Basic .NET". It's a .NET-compatible application and will give you some good ideas on how to handle the "sometimes-offline" scenario. It shows how to build a semi-connected application using Visual Basic® .NET. The application bases its behavior on the connection state. When working offline, changes to data are cached, and later, when reconnected, the data is automatically synchronized with the server.

Q I need to install IIS and some of its components in an unattended mode on more than 30 machines running domain controllers in order to run Microsoft Software Update Services (SUS). Is there a way to perform the installation outside of the Add/Remove programs console?

Q I need to install IIS and some of its components in an unattended mode on more than 30 machines running domain controllers in order to run Microsoft Software Update Services (SUS). Is there a way to perform the installation outside of the Add/Remove programs console?

A Create a file named iis.txt containing the code shown in Figure 1 . Then copy the file to drive A, and issue the following command from the command line while you are on A:

sysocmgr /i:%windir%\inf\sysoc.inf /u:a:\ iis.txt

You'll need to tweak the iis.txt file according to your environment and your particular needs.

A Create a file named iis.txt containing the code shown in Figure 1 . Then copy the file to drive A, and issue the following command from the command line while you are on A:

sysocmgr /i:%windir%\inf\sysoc.inf /u:a:\ iis.txt

You'll need to tweak the iis.txt file according to your environment and your particular needs.

Figure 1 iis.txt

[Components]
Iis_common = On
Iis_ftp = Off
Iis_nntp = Off
Iis_webdav = Off
Iis_serversideincludes = Off
Iis_smtp = Off
iis_asp =Off
Iis_inetmgr = On
iis_www=on
iis_webadmin=off
TSWebClient=off
indexsrv_system=Off
Aspnet = On
rootautoupdate = Off
[InternetServer]
PathWWWRoot = E:\WebSite 

Q I need to search all files and folders on a test machine and have it look for a certain file or file type. How can I do this in script?

Q I need to search all files and folders on a test machine and have it look for a certain file or file type. How can I do this in script?

A That's easy—take a look at Figure 2. Just replace the following line with whatever thing you want to do to the file based on its path:

WScript.Echo File.Path 

This recursively descends the C disk—it would be easy to make it enumerate the local disks and recursively descend each one.

A That's easy—take a look at Figure 2. Just replace the following line with whatever thing you want to do to the file based on its path:

WScript.Echo File.Path 

This recursively descends the C disk—it would be easy to make it enumerate the local disks and recursively descend each one.

Figure 2 Recursive Descent

Option Explicit
Dim FSO
Set FSO = CreateObject("Scripting.FileSystemObject")
DoDir FSO.GetFolder("c:\")
Sub DoDir(Folder)
    On Error Resume Next
    Dim File, SubFolder
    For Each File In Folder.Files
        WScript.Echo File.Path
    Next
    For Each SubFolder in Folder.SubFolders
        DoDir SubFolder
    Next
End Sub

 

Got a question? Send questions and comments to  webqa@microsoft.com.

Thanks to the following Microsoft developers for their technical expertise: Joshua Allen, Rhett Attwood, Jerry Carlson, Samuel Cavaliere, Len Childers, Mark Cleary, Brad Daniels, Scott Deacon, Joseph Elalouf, Murat Erenturk, Les Gainous, Denis Hawkins, Chris Hollander, Larry Kuhn, Eric Lippert, Maurizio Macagno, Richard Macdonald, Steve Riley (SBU), Taufiq Shamim, Jamie Sharp, Robert Steele, Chad Verbowski