Friday, July 6, 2007

How to move a Typed Dataset to its own Project and Namespace

This is "Part 1" of a 2 part adventure. Please do not alter any of your code before reading part 1 & part 2.

In today’s adventure I dared to travel into an area that I have feared greatly for many months. For the betterment of our software I decided today was the day that I finally broke all of the typed datasets out of our web project’s App_Code directory and into their own project. After all, nobody wants to read boring “adventures!”

First of all, I have seen many people asking, “How do you add a namespace to a typed dataset?” The answer is “Don’t bother.” It can be done quite simply by just renaming the .xsd file but like I said, “Don’t bother.” Here is why, having all these XSDs embedded in their web projects makes them completely useless to any other application (unless you create web services to expose them but web services can add an extra layer to an application that most applications do not need). So, all that namespacing work is just going to need to be removed when you finally realize that these files should have been in a totally separate project from the beginning. Once the XSDs have been moved to a separate project then they will fall within the root namespace of the project. If you need to add further namespacing in addition to the project root namespace you can accomplish that by renaming the .xsd file.

So, rather than asking, “How do you add a namespace to an XSD” you should be asking “How do I get all of these XSDs out of my ASP.Net project?”

Here is how I did it.

1) Make a copy of all of your XSD files to a separate directory outside of your web project. Let’s say c:\Temp\XSDs.

2) Make all of the .xsd files editable by removing their Read-Only property.

3) Create a new class library project wherever it is appropriate, e.g. c:\CompanyName\SolutionName\SolutionName.DAL\

4) Add a reference to System.Configuration in your project.

5) Create an app.config in your new project. Based on my experience in part 2 this is not a necessary step in the long run but it may be needed to get your project to initially compile. Make sure to read part 2 to see how to make the DAL project run against a runtime database that may differ from your development database.

6) Make sure to set the root namespace of your project (Project Properties Application tab). At my company, we name our projects “SolutionName.DAL” but the root namespace for our projects is “CompanyName.SolutionName.DAL”. You want to get this set correctly before continuing.

7) Create a new XSD in your new project and create some simple query this will accomplish getting a valid connectionString into app.config. This connectionString ends up being a little different than what you may have expected so I think it is better to let the XSD wizards create it for you. Here is approximately what mine looked like. As you can see by the providerName I use Oracle so your connectionString may differ quite a bit. Therefore, I recommend letting the wizard do the work for you. Note this connectionstring is only used by the designer at design time. At runtime it will use the connectionstring named “ConnectionString” from the app.config of the main executable (or ASP.Net site).

<add name="CompanyName.ProjectName.DAL.My.MySettings.ConnectionString" connectionString="Data Source=Something;Persist Security Info=True;User ID=SomeUser;Password=SomePassword; " providerName="System.Data.OracleClient" />

8) Download Notepad++ if you have not already done so. This is a great free text editor.

9) Because Notepad++ is an MDI application it will allow you to open all of the .xsd files at once. So, select all the .xsd files, right click and choose “Edit with Notepad++.”

10) Do a find and replace (ctrl+h) using the following:
a. Find this: web.config
b. Replace it with this: MySettings
c. Hit the “Replace all in all opened documents” button. That’s nice!

11) Save all your files.

12) Next you will need to replace the following section from each .xsd file.
a. Find this:
b. Replace it with the following. Make sure to change where it says “CompanyName.ProjectName.DAL” to the root namespace of your project. This value should also match the name of the connectionString in your app.config file:

c. Hit the “Replace all in all opened documents” button.

13) Save the file.

14) Copy the file (and its child files with the same name and different extensions, e.g. any .vb, .xss files) to your new DAL project. You can simply choose “copy” in Windows Explorer and select the project in Visual Studio’s Solution Explore and choose “paste” and the file will be added to the project and placed in the project’s working directory.

15) Cross your fingers. Stand back from your computer. Try to build your DAL project. If it builds you might be in the clear!

16) Before you get too excited and edit and import all the other XSD files (you adventurer!) take a moment to create another project, perhaps a unit test project, within your solution. Within this other project add a reference to your DAL project.

17) See if you can write some functioning code against the datasets exposed by your DAL project. This will give you a chance to make sure your DAL project is truly working and that you have the namespaces right. Remember, getting the correct namespaces is the whole reason you wanted to do this in the first place! Believe it or not your DAL project can compile but not expose any of the datasets to outside projects if you have an error in your app.config within the DAL project.

18) If you do not like your namespaces change them by changing the project root namespace (Project Properties Application tab) and/or change the file name of the .xsd file. Continue tweaking the namespace and rebuilding the project and testing the project from your test project. Keep in mind that if you make changes now to the root namespace, you may have to synchronize these changes with the settings in the App.Config and the XSD files.

19) Check everything into your source control software before you break something in the next step. It is only good to be adventurous if you live to tell about your adventure.

20) Once you are comfortable with your namespace strategy go back and edit all of the remaining .xsd files in Notepad++ and copy all of the remaining files into your DAL project. Although I love adventure as much as the next person I would recommend that you do this 1 file at a time just to make sure if something breaks it is easy to identify what file won’t compile. After all, you are manually editing the complex .xsd files in a text editor. Something is bound to go wrong sooner or later. Be scientific and limit your variables by being a little patient and importing one file at a time. Don’t forget to write a unit test for each XSD (or at least doing a “Preview Data” within each XSD) too. You really never know if these things are working until you have a working test. Be careful. If you make a mistake you may end up getting this message:
Unable to find connection 'ConnectionString (MySettings)1' for object 'MySettings'. The connection string could not be found in application settings, or the data provider associated with the connection string could not be loaded.

Which will probably lead you here

I hope this has helped someone. I know I will sleep better at night knowing that all of these datasets are now available for use by other projects and the business logic layer that I also had to painstakingly pull out of App_Code today.

Thanks for joining me on this adventure. I hope you did not get too many bumps and bruises.


JKK said...

Good Article ... :)

mrP said...

Where is the Read Only property? I don't know where do change that, can you elobrate?


Dragoljub Ćurčić said...

Helpful article! I knew some of that stuff already, but the Notepad++ tip was excellent! It saved me a lot of time. In 23 datasets, 217 connection string references fixed with one click! :)