August 2003 - Posts
Today I came across some ThoughtWorkers who have some very interesting blogs. Check them out:
Chris Stevenson states that the NUnit ExpectedException Attribute is an AntiPattern. In his post he talks about how the ExpectedException attribute doesn't allow us to truely test that an exception is being thrown by the individual peice of code we expect it to. To steal from Chris's example, Code Snippet #1 does not allow us to ensure that the callSomethingThatThrowsTheException() is the method throwing the exception. If the doSomeSetup() method unexpectedly throws a “ExceptionType“ exception our test will still pass even though in actuality it is failing. To work around this problem Chris recommends implementing the test as shown in Code Snippet #2. Opinions?
// Code Snippet #1
[Test]
[ExpectedException(ExceptionType)]
public void ExceptionThrownByVerifier() {
doSomeSetup();
doSomeProcessing();
callSomethingThatThrowsTheException();
}
// Code Snippet #2
[Test]
public void ExceptionThrownByVerifier() {
doSomeSetup();
doSomeProcessing();
try {
callSomethingThatThrowsTheException();
fail("Expected Exception");
}
catch (ExceptionType e) {
//expected
}
}
Chris Stevenson states that the NUnit ExpectedException Attribute is an AntiPattern. In his post he talks about how the ExpectedException attribute doesn't allow us to truely test that an exception is being thrown by the individual peice of code we expect it to. To steal from Chris's example, Code Snippet #1 does not allow us to ensure that the callSomethingThatThrowsTheException() is the method throwing the exception. If the doSomeSetup() method unexpectedly throws a “ExceptionType“ exception our test will still pass even though in actuality it is failing. To work around this problem Chris recommends implementing the test as shown in Code Snippet #2. Opinions?
// Code Snippet #1
[Test]
[ExpectedException(ExceptionType)]
public void ExceptionThrownByVerifier() {
doSomeSetup();
doSomeProcessing();
callSomethingThatThrowsTheException();
}
// Code Snippet #2
[Test]
public void ExceptionThrownByVerifier() {
doSomeSetup();
doSomeProcessing();
try {
callSomethingThatThrowsTheException();
fail("Expected Exception");
}
catch (ExceptionType e) {
//expected
}
}
Man what a cheesy title!
Today I was reading a post from Mike Roberts about why he doesn't like the GAC. It brought back memories from my most recent project. To make a long story short we were developing a web application that required some heavy duty processing to take place. To handle the processing we created a Windows Service that monitored a message queue for new requests. During our deployment planning we decided that rather then have a copy of the core dll in the web application directory and the windows service directory we would just place the core assemblies in the GAC. At the time I didn't think much about the implications of this decision. The decision to place the dll's in the GAC has caused us several headaches during the initial deployment as well as during a couple of the code “refreshes.“ I think Mike states it best:
“... libraries shouldn't be in the GAC unless they are part of, or an extension of, the .NET runtime itself.“
Well rather then complain about the lack of a main feed for http://blogs.gotdotnet.com/ I decided to code up a little app to create a feed. The current feed only includes the blogs running BlogX so guys like Don Box are currently not included. I'll write more about how I created the main feed as well as release the source for the feed creator in a later post. For the time being point your aggregators over to http://www.emxtechnologies.com/gotdotnet-blogs/mainfeed.xml and let me know what you think!
I've found a ton of excellent content over on the blogs at:
http://blogs.gotdotnet.com/. What I would love to see is a main feed for all the Microsoft peeps blogging over there. Since the blog engine is
BlogX it might be a little harder to aggregate the feeds into a single listing, however, considering the intellect of the people blogging I'm sure it could be done in pretty short order. If worst comes to worst we can just convert them to
.Text! I haven't tried this
BlogX to .Text import tool yet but it could be just what we need.
One of the things that often comes up while writing stored procedures is the
need to SELECT a set of results from another stored procedure. While it is
not possible to SELECT a, b, c FROM (EXEC ap_Sproc) it is possible to use a
temporary table to achieve the desired result. The example below
shows how the results of the ap_GetCustomers stored procedure can be selected
from in the ap_CustomerSearch stored procedure. As always leave questions,
comments, and suggestions in the comments for this entry.
CREATE PROCEDURE ap_CustomerSearch
(
@BeginsWith varchar(10)
)
as
SET NOCOUNT
ON
CREATE TABLE #tmpCustomers
(
CustomerID varchar(10),
CompanyName varchar(100),
ContactName
varchar(100),
ContactTitle varchar(100)
)
INSERT INTO #tmpCustomers
EXEC ap_GetCustomers
-- ap_GetCustomers must return the same number of columns as
#tmpCustomers defines
SELECT
* FROM #tmpCustomers WHERE CompanyName LIKE @BeginsWith + '%'
DROP TABLE
#tmpCustomers
CREATE PROCEDURE
ap_GetCustomers
as
SET NOCOUNT
ON
SELECT
CustomerID,
CompanyName,
ContactName,
ContactTitle
FROM Customers
Over the last year I have been very lucky with the projects I've been put
on. The last 4 projects I've worked on have used C#,
ASP.NET, SQL Server, and a bunch of other
miscellaneous technologies. What I didn't realize over the course of
the last year is how spoiled I've been to work almost exclusively with
.NET. My most recent project has come to an end. Although I had
hoped that a really cool .NET project would be waiting for me I was preparing
myself for the letdown that a return to classic ASP would bring. Over the
last week I've had to slowly remember how to program without all the excellence
that the .NET environment brings. Forget inheritence, forget server
controls, forget curly braces and semi-colons. Remember to set objects to
nothing, loop over record sets, and everything else I had forgotten about the
NON .NET world. I hope my stay isn't too long in this unmanaged
world. Its dark, gloomy, and I don't like it.
Do you use an entity framework to help speed the development of your
applications? How do you reduce the amount of time spent on writing the
redundant CRUD operations for your objects?
Over the last couple of months I've posted a couple times in regards to some
work I'm doing with my "Entity Framework". I've come across a good number
of frameworks that provide similar functionality. Has anyone used any of
these frameworks? What was the deciding factor when you made your
decision? Have you developed your own framework? If anyone has used
any of the frameworks below, or implemented their own I would love to hear your
experiences, as well as your likes and dislikes. What would your ideal
framework look like?
NEO
Entity Broker
ObjectSpaces
Note: I'm interested particularly in frameworks and not necessarily pure
code generators.
Persistence
Frameworks on SharpToolBox
One of the things that myself and several other members of the technology
department have been trying to figure out is how to best share knowledge with
the members of the "Tech Team". We've considered setting up the ASP.NET
Forums, I've thought about trying to encourage some internal blogs, and
yesterday during my review my manager talked about writing papers. Over
the past 3 years I've tried a couple of things to share knowledge but haven't
been as aggressive with making sure the department as a whole is growing and
learning from each other. I would love to hear from others in the
community about how you facilitate the sharing of knowledge among your
team. Additionally if you have any insights into things that don't work I
would love to hear them as well!
Eric Sink provides an excellent insight into
how to
make your career outstanding by doing some simple Career Calculus. I
couldn't agree more with what Eric states in this entry.
Tonight I was continuing some work on my new and improved "Entity
Framework." As part of the conversion I'm updating a recent project to use
the new implementation. Not only does this help me to see where and how
things could be simplified and cleaned up but it also provides me with a whole
set of unit tests for different aspects of the application that could be
affected by the changes.
As I ran through the Unit tests this evening I noticed a couple broken tests
that I thought should be working. One of the tests was for an object using
the .ToXml and .FromXml methods supplied by the base EntityObject class. I
had a couple other tests that were using these methods that were showing green
so I was curious to see what the error was for the test. The error and
stack trace being returned is shown below:
MyProject.Core.Test.EntityObjects.UserTest.ToFromXml :
System.IO.FileNotFoundException : File or assembly name kbrbyhzh.dll, or one of
its dependencies, was not found.
at System.Reflection.Assembly.nLoad(AssemblyName
fileName, String codeBase, Boolean isStringized, Evidence assemblySecurity,
Boolean throwOnFileNotFound, Assembly locationHint, StackCrawlMark&
stackMark)
at
System.Reflection.Assembly.InternalLoad(AssemblyName assemblyRef, Boolean
stringized, Evidence assemblySecurity, StackCrawlMark&
stackMark)
at System.Reflection.Assembly.Load(AssemblyName
assemblyRef, Evidence assemblySecurity)
at
System.CodeDom.Compiler.CompilerResults.get_CompiledAssembly()
at
System.CodeDom.Compiler.CompilerResults.get_CompiledAssembly()
at System.Xml.Serialization.Compiler.Compile()
at
System.Xml.Serialization.TempAssembly..ctor(XmlMapping[]
xmlMappings)
at
System.Xml.Serialization.XmlSerializer..ctor(Type type, String
defaultNamespace)
at
System.Xml.Serialization.XmlSerializer..ctor(Type type)
at
emxTechnologies.Core.EntityObjects.EntityObject.ToXml() in
c:\development\emx\emxtechnologies.core.v2\entityobjects\entityobject.cs:line
489
at MyProject.Core.Test.EntityObjects.UserTest.
To make a long story short I was able to track the error to a property
on one of my objects. The property was providing a new implementation of
the UserType property and was being defined as so:
CustomUser.cs
public class
CustomUser : User
{
public new string UserType
{
get { ... }
}
}
In the base User class the UserType property was being defined
as so:
User.cs
public class
User : EntityObject
{
public string UserType
{
get { return _userType; }
set { _userType =
value; }
}
}
I'm sure many of you are
wondering why the new keyword was being used rather then having the
UserType on the base User class defined as virtual and overriding it in
the CustomUser class. Unfortuntely I don't have an answer at the moment
since I wasn't the author of the classes. However, the interesting thing
to note is that changing the User class to define the UserType property as
virtual and then adding the override keyword to the UserType property in the
CustomUser class fixed the strange serialization problem. Apparently the
XmlSerializer doesn't like properties with the new keyword. While
it isn't a problem in the example provided I do use the new keyword
(well not actually but its possible at some point that I might) in other
places to redefine the implemention of a property/method. I'm wondering if
I'll run into the same strange problems, I guess its time to go find
out!
If anyone happens to know why the
new keyword causes the XmlSerializer to bomb please share in the
comments for this entry.
One of the principles of Extreme Programming (XP) that I've struggled with is
the idea that you should only think about the immediate needs of the applciation
and not consider all the future requirements or uses of the application.
While I understand the principle, I've always had a hard time actually following
it. I usually spend a good amount of time considering how my application
will evolve and what requirements they *might* need to fullfill in the
future. At times I spend too much time thinking and not enough time
doing.
Today Jimmy
Nillson pointed to an article by Andy Hunt and Dave
Thomas called "The Tip-Packing Dilemma." The article describes some of
the problems the YAGNI (you aren't going to need it) principle can
cause. In the article Andy and Dave say that they have had a lot
of success by not following the YAGNI principle, but instead
following the DOGBITE (do it, or get bitten in the end) principle. Its
nice to hear that I'm not alone in my thinking. I've been meaning to pick
up The Pragmattic Programmer, perhaps the fact that I've found
some common ground with Andy and Dave will be the thing that brings me over to
amazon for a purchase. If only I had more time in the
day!
I came across an article on eWeek about Don Box's talk at
the XML Web Services One
Conference on object-oriented programming giving way
to service-oriented architectures. It reminded me about some things I read
a while back on X#, has anyone heard anything about whether or not it actually
exists, and if so when MS is hoping to release it?
The following query will provide a "dependency report" in the following
format:
table name
dependent
object dependent
object
type
Categories
dbo.Alphabetical list of products
view
Categories
dbo.Product Sales for
1997
view
Categories
dbo.Products by
Category
view
Categories
dbo.Sales by
Category
view
Categories
dbo.SalesByCategory
stored procedure
create table #tableDependencies
(
tableName varchar(100),
dependency
varchar(200),
type varchar(100)
)
create table #depends
(
dependency varchar(200),
type
varchar(100)
)
declare @tableName varchar(255)
declare tableCur cursor
for
select
name from sysobjects where type = 'u' order by name
open tableCur
while 1 = 1
begin
fetch next
from tableCur into @tableName
if
@@fetch_status <> 0
break
insert into #depends
exec ('sp_depends ''' +
@tableName + '''')
insert into #tableDependencies
select @tableName,
dependency, type from #depends
delete from #depends
end
close tableCur
deallocate tableCur
select * from
#tableDependencies
drop table #tableDependencies
drop table #depends
Today one of my colleagues asked if I had a proc to list all the tables in a database along with a count of the total records. A quick memory scan brought back 0 matches so I decided to write a script to provide the desired information. I didn't look to see if there is any system procedures to do this so if their is an easier way please share it!
create table
#t
(
tableName varchar(100),
tableRowCount int
)
declare
@TmpName varchar(255)
declare tmpCur cursor for
select name from sysobjects where type = 'u' order by name
open
tmpCur
while 1 = 1 begin
fetch next from tmpCur into @TmpName
if @@fetch_status <> 0
break
insert into #t (tableName, tableRowCount)
exec ('select ''' + @TmpName + ''', count(*) from [' + @TmpName + '] WITH (NOLOCK)')
end
close tmpCur
deallocate tmpCur
select * from #t order by tableRowCount desc
drop table #t
Example output from Northwind database:
Order Details 2155
Orders 830
Customers 91
Products 77
Territories 53
EmployeeTerritories 49
Suppliers 29
Employees 9
Categories 8
Region 4
Shippers 3
CustomerCustomerDemo 0
CustomerDemographics 0
dtproperties 0
Peter Provost has a
nice write up in response to my post on
Creating a dynamic asssembly using System.CodeDOM. Peter shows
how to use the code generating capabilities of CodeSmith to provide a very nice
alternative to the StringBuilder.Append and StringBuilder.AppendFormat calls I
was using to generate my code. I downloaded
CodeSmith last
night to give his method a whirl! Thanks Peter!
After working with the CodeDOM classes this week I added
the above static method to one of the helper classes in my project. I've
ommitted some custom code and exception handling to keep the posting from
getting too long, but hopefully the snippet shows how easy it is to use the
CodeDOM classes to create dynamic assemblies.
public static Assembly CreateAssembly(string[] referencedAssemblies, string source)
{
// compile the
code
CSharpCodeProvider prov = new
CSharpCodeProvider();
ICodeCompiler comp =
prov.CreateCompiler();\
CompilerParameters p = new
CompilerParameters();
p.GenerateInMemory = true;
// setup
references
p.ReferencedAssemblies.Add("System.dll");
if(referencedAssemblies != null){
foreach(string assemblyName in referencedAssemblies)\
{
p.ReferencedAssemblies.Add(assemblyName);
}
}
CompilerResults res = comp.CompileAssemblyFromSource(p,
source);
return
res.CompiledAssembly;
}
And a quick code snippet showing how the above method may be used.
StringBuilder sourceCode = new StringBuilder();
// create C#
code for the EntityLoader with string Builder (omitted)
Assembly assembly
= AssemblyGenerator.CreateAssembly(new string[] {"System.Data.dll" },
sourceCode.ToString());
EntityLoader loader = (EntityLoader)
assembly.CreateInstance(assembly.GetTypes()[0].FullName);
return loader;
Six months ago while working on a framework for a project I decided to
leverage the Reflection.Emit classes for dynamically generating
assemblies. Before I decided on Reflection.Emit I took a quick look at
what functionality System.CodeDOM provided and what advantages and disadvantages
I would realize by going with each option. The samples I came across for
System.CodeDOM showed how to use the CodeDOM classes for genearting source files
in multiple languages. After a quick review I decided to use the
Reflection.Emit class for genearting my dynamic assembly, since I wasn't really
concerned with generating source files, or outputting them in a variety of
languages. All I was interested in was generating an assembly in
memory.
This past week while working on a re-write of the framework that prompted the
initial evaluation of Emit vs. CodeDOM I decided to revisit the debate.
After "thumbing" my way through the documentation of the CodeDOM classes I came
across the ICodeCompiler.CompileAssemblyFromSource() method. Rather then
emitting OpCodes I decided to create a couple of templates for my code and use
the ICodeCompiler to genearte an in memory assembly. While I did miss the
process of pushing things onto the call stack using OpCodes, I realized how much
more productive I was creating "C# templates" for my code and compiling them
with the CodeDOM classes.
I don't regret the decision of using the Reflection.Emit classes the first
time around. By working with the Emit class and learning about the
different OpCodes necessary for emitting an assembly I learned a lot about what
goes on behind the scenes when my code is compiled to IL. With that said,
I'm not sure I'll go back to working with OpCodes and Reflection.Emit. The
CodeDOM classes provide a quick and easy way to generate the same output in much
less time.
To help reduce the amount of finder code necessary in my custom collections I
set out to create a factory object for creating finder methods "on the
fly". To give you an idea of what I'm trying to simplify let me show a
quick sample:
CustomerCollection.cs
public Customer
GetByCustomerCode(string customerCode)
{
for(int i = 0; i < this.Count;
i++)
{
if(this[i].CustomerCode ==
customerCode)
return this[i];
}
return null;
}
Now imagine a couple different variations of the above code in all of your
collections. Rather then being forced to write this code (albeit simple)
for each property lookup I wanted to allow a more simplistic mechanism.
Something like this:
public Customer
GetByCustomerCode(string customerCode)
{
return (Customer)
FindByPropertyValue(typeof(Customer), "CustomerCode",
customerCode);
}
or even simpler use the FindByPropertyValue directly from the
client code like so...
Customer customer =
myCustomerCollection.FindByPropertyValue(typeof(Customer), "CustomerCode", "ABC");
In order to accomplish my goal I leveraged the
dynamic compilation capabilities made available by the System.CodeDOM
namespace. I was able to quickly create a template for the finder class,
implement an interface, and bring it all together with the wonderful CodeDOM
classes. The FindByPropertyValue in my base collection class ended up
looking like so:
public EntityCollection
FindByPropertyValue(Type entityType, string
propertyName, object propertyValue)
{
return
DynamicCollectionFinderFactory.Instance.GetFinder(entityType,
propertyName).Find(this, propertyValue);
}
The real work for all of this is done
in the DynamicCollectionFinderFactory object. Rather then make this post
super long with all the code let me briefly explain what is happening within the
object. The first thing the object does is look in its internal cache
(hashtable) to see if it has already created a finder for the object/property
combination. If it has it prompty returns it to the FindByPropertyValue
method so the Find can be executed. If, however, the finder factory does
not have an object in its internal cache for the object/property combination it
plugs in the necessary information into the template and uses the CodeDOM
objects to compile the template and create an in memory assembly. The
assembly is then returned and an instance of the finder is created using the
CreateInstance() method of the dynamically generated
assembly.
So...by levearging the capabilities of the CodeDom objects I was
able to simplify the code required to find objects within my
collections.
Am I supposed to have this much fun coding? at night? off
the clock? yes 
In response to Eric Kepes question about whether a CASE statement can be used in a WHERE
clause I put together this inpractical example....
CREATE PROCEDURE ap_SortedCustomers
(
@SortBy varchar(50)
)
as
SET NOCOUNT ON
SELECT * FROM Customers
WHERE CASE WHEN @SortBy = 'CustomerID' THEN CustomerID
ELSE 'WOLZA' END = 'WOLZA'
ORDER BY
CASE
WHEN @SortBy = 'CustomerID'
THEN CustomerID
WHEN @SortBy = 'CompanyName' THEN
CompanyName
WHEN @SortBy = 'ContactName' THEN ContactName
WHEN @SortBy = 'ContactTitle' THEN
ContactTitle
WHEN @SortBy = 'Address' THEN Address
WHEN @SortBy = 'PostalCode' THEN
PostalCode
END
GO
The above query will sort by the necessary column using the @SortBy
parameter you specify and if your sorting by 'CustomerID' it will only show
records with a Customer ID equal to the 'WOLZA' string. Obviously this
isn't a very practical example but I think you get the idea. Oh the fun we
can have with that handy CASE statement!
Almost all of the applications that I write use stored procedures for all
database interactions. While there are advantages to this approach, there
are times when I long for the flexibility of dynamic SQL. One
example of when it would be nice to fall back on writing dynamic SQL is when we
need to dynamically set the ORDER BY for a SELECT statement. In
the project I'm currently working on this is one of the requirements. The
page displaying the results is using custom paging done on the database so
unfortuntely handling the sorting in the page, or writing a custom IComparer
class for our collections won't give us the desired results. To show an
example of how I handled the requirement look at the following stored procedure
that I wrote for the Northwind database:
CREATE PROCEDURE ap_SortedCustomers
(
@SortBy varchar(50)
)
as
SET NOCOUNT ON
SELECT * FROM Customers
ORDER
BY
CASE
WHEN @SortBy = 'CustomerID'
THEN CustomerID
WHEN @SortBy = 'CompanyName' THEN
CompanyName
WHEN @SortBy = 'ContactName' THEN ContactName
WHEN @SortBy = 'ContactTitle' THEN
ContactTitle
WHEN @SortBy = 'Address' THEN Address
WHEN @SortBy = 'PostalCode' THEN
PostalCode
END
GO
The stored procedure will use the @SortBy parameter to properly ORDER the
results retrieved from the Customers table. One minor caveat to the above
procedure is that it doesn't support toggling the sort order to either ASC or
DESC. The only way I've found to do this is by branching the code and
creating two seperate selects with the DESC select appending 'DESC' onto the end
of the case statement. Feel free to share your own methods for achieving
the desired results in the comments for this post!
Darren Neimke's recent post on what is the best path to Microsoft made me
think about what I really want in a job. While I think Microsoft would be
an awesome place to work I have about a 0% chance of ever talking my wife into
moving to Seattle. So with that said, what is it that I really want?
I want to work somewhere that makes me think, learn, and grow. I want
challenges, and difficult problems. I want to work with people smarter
then me. I want my brain to hurt!
I'm not sure if a mid-size or large company is more likely to give me these
things. Perhaps being an independent consultant would be the most
likely.
A couple of months back I worked on a project for an international
client. The project involved web enabling one of the clients "legacy"
applications. One of the requirements for the web application was that it
needed to support English and French locales. As I begun desiging the
architecture for the application and particularly the localization I evaluated
several alternatives.
- Use the so called "built-in" features of the .NET framework.
- Create a custom RDBMS backed localization engine.
- Find a 3rd party component to handle the localization.
When it came time to make a decision I ended up going with #2. The
major reason was flexibility. By building my own custom solution I knew I
wouldn't tie myself down with any limitations. The finished localization
system ended up as follows:
- Tables in the database to store supported locales, strings to be
localized, and localized strings for each supported locale.
- A set of business objects for retrieving localized strings from the
database.
- A set of localized server controls.
- LocalizedButton
- LocalizedLabel
- LocalizedHyperLink
- LocalizedRequiredFieldValidator
- The server controls had a LocalizeKey property that was used to lookup the
localized text for the text displayed by the control.
- The localized strings for the different locales where cached using the
Cache object.
- A configuration setting allowed all localized strings to be retrieved (and
cached) at the application onStart or one at a time as they were
requested.
Ever since making the decision to go with the custom solution I have
wondered what kind of experience I would have had if I used the localization
within the .NET Framework. Is it any good? Does it work in a web
scenario? How would the custom solution I developed compare?
Advantages? Disadvantages?