Thursday, October 15, 2009
Windows 7 is satisfactory
I won't state anything profound or even moderately interesting in this post. I've been using various flavors of Windows 7 RTM for almost two months now and can report no problems. A friend of mine thought that I should have a more enthusiastic view of Windows 7. My response: "It's an OS. I've seen them come and go." But don't take my lack of excitement for a negative viewpoint. In fact, lack of excitement is a good thing when it comes to an operating system. I want something stable that allows me to get my work done. I want an OS that doesn't annoy or frustrate me whether it is at home or work. Windows 7 fulfills those requirements. It is pleasingly adequate.
Monday, October 5, 2009
When "Copy Local" doesn't copy locally
There are days when software development is fun, challenging, rewarding. Then there are days like today when frustration makes me want to hurl my monitors against the wall and generally destroy my office like Keith Moon.
The day started innocently enough as I tried to wrap up some final release details by executing my stable old deployment scripts. By 'stable' and 'old' I mean they haven't had to change in over a year and have staged several successful releases. One of the scripts reported that it couldn't find Oracle.DataAccess.dll. That's odd, I thought, and proceeded to waste 2 hours investigating why my reference wasn't copying locally. Because the scripts had been so seemingly reliable for so long, I had forgotten their flow. I couldn't remember who was responsible for copying Oracle.DataAccess.dll to the proper deployment location so I had to take a trip down memory lane and get reacquainted.
The bottom line is that though the reference is set to "Copy Local", its presence in the GAC causes MSBuild to not copy it to the output directory. Here's a great description of the problem and solution. And here's a second post on the subject.
I don't know how long the build and deployment system has had this problem. Probably a long time. There are a few key files, such as Oracle.DataAccess.dll, that get injected into the build process. The deployment scripts package everything and were probably obscuring the issue so that it didn't surface until now. Ultimately the problem is mine since I am the de facto build engineer here. I think that the best course of action is to rebuild the build and deployment environments after this release. There could be other lurking problems like this one that would be discovered by a fresh build server.
The day started innocently enough as I tried to wrap up some final release details by executing my stable old deployment scripts. By 'stable' and 'old' I mean they haven't had to change in over a year and have staged several successful releases. One of the scripts reported that it couldn't find Oracle.DataAccess.dll. That's odd, I thought, and proceeded to waste 2 hours investigating why my reference wasn't copying locally. Because the scripts had been so seemingly reliable for so long, I had forgotten their flow. I couldn't remember who was responsible for copying Oracle.DataAccess.dll to the proper deployment location so I had to take a trip down memory lane and get reacquainted.
The bottom line is that though the reference is set to "Copy Local", its presence in the GAC causes MSBuild to not copy it to the output directory. Here's a great description of the problem and solution. And here's a second post on the subject.
I don't know how long the build and deployment system has had this problem. Probably a long time. There are a few key files, such as Oracle.DataAccess.dll, that get injected into the build process. The deployment scripts package everything and were probably obscuring the issue so that it didn't surface until now. Ultimately the problem is mine since I am the de facto build engineer here. I think that the best course of action is to rebuild the build and deployment environments after this release. There could be other lurking problems like this one that would be discovered by a fresh build server.
Monday, September 28, 2009
Dumbing down work environments
Our LOB application has a couple of different codelines. Occasionally two will be in use simultaneously for a short period of time. This requires developers to think about where they are working. The TFS task that is assigned contains all relevant information, such as the codeline in which the developer should be working, but there are a couple of people who just always pick the wrong one.
Maybe I need to dumb down the work environment. Right now we've got separate VS2008 solution and project files for the codeline. We've got separate databases related to each codeline. And the multitude of reports are also similarly segregated by codeline. I suppose that I could spend time getting the codeline name somehow worked into all object names, but this feel unnecessarily infantile to the other developers who are able to consistently pick the right place to work.
We have no junior developers on staff. No one is new to our organization either, so it's not like our software development processes are novel to anyone. Maybe I'm being too hard, but my expectation is that if your title is 'Senior Software Engineer' then you should be able to successfully analyze and execute work assignments. Knowing the personalities of the individuals involved I don't think that this behavior is intentional. That leads me to the conclusion that this is either apathy or sloppiness. Or both.
I suppose that this is a sore spot for me because I resent spending so much time merging and synchronizing. When someone works in the wrong place I've got to spend even more time sorting it all out. And then I also feel really petty when I have to scold someone who is a highly skilled, highly compensated professional for making such a rookie mistake. Again.
Maybe I need to dumb down the work environment. Right now we've got separate VS2008 solution and project files for the codeline. We've got separate databases related to each codeline. And the multitude of reports are also similarly segregated by codeline. I suppose that I could spend time getting the codeline name somehow worked into all object names, but this feel unnecessarily infantile to the other developers who are able to consistently pick the right place to work.
We have no junior developers on staff. No one is new to our organization either, so it's not like our software development processes are novel to anyone. Maybe I'm being too hard, but my expectation is that if your title is 'Senior Software Engineer' then you should be able to successfully analyze and execute work assignments. Knowing the personalities of the individuals involved I don't think that this behavior is intentional. That leads me to the conclusion that this is either apathy or sloppiness. Or both.
I suppose that this is a sore spot for me because I resent spending so much time merging and synchronizing. When someone works in the wrong place I've got to spend even more time sorting it all out. And then I also feel really petty when I have to scold someone who is a highly skilled, highly compensated professional for making such a rookie mistake. Again.
Friday, September 4, 2009
Windows 7 x64, Toad 9.7.2.5, Oracle 11g ODAC
After too much time and frustration, I finally got Toad (version 9.7.2.5) and Oracle Data Access Components to work on Windows 7 Professional x64.
For hours Toad wouldn't even acknowledge that an Oracle client was installed. I tried the 11g x86, Instant Client, 10g Oracle x64, finally Oracle 11g ODAC and Oracle Developer Tools for Visual Studio AKA ODTwithODAC1110621.zip started to work. At one point while trying to get Instant Client to work I manually set the ORACLE_HOME, TNS_ADMIN, and PATH environment variables. I don't know if that had any effect on my success. I'm too scared to remove them to find out considering the fragility of the Toad / Oracle client interaction. For now I'm just happy that my Dell Latitude E6500 can play any role other than netbook.
For hours Toad wouldn't even acknowledge that an Oracle client was installed. I tried the 11g x86, Instant Client, 10g Oracle x64, finally Oracle 11g ODAC and Oracle Developer Tools for Visual Studio AKA ODTwithODAC1110621.zip started to work. At one point while trying to get Instant Client to work I manually set the ORACLE_HOME, TNS_ADMIN, and PATH environment variables. I don't know if that had any effect on my success. I'm too scared to remove them to find out considering the fragility of the Toad / Oracle client interaction. For now I'm just happy that my Dell Latitude E6500 can play any role other than netbook.
Wednesday, August 19, 2009
Corrupt TNSNAMES.ORA file
I just spent three hours troubleshooting this error: "ORA-12154: TNS:could not resolve the connect identifier specified." I had three TNSNAMES.ORA files with identical information. Oracle.DataAccess interaction with two of the three resulted in the ORA-12154 error. After scouring Google, I finally came across this nugget of wisdom:
Just a note, sometimes the TNSNAMES.ORA will get messed up. Nothing will jump out but it will not work and you cannot see the file though the net config. Just re-create it using notepad or [s]omething.
I replaced the two misbehaving files with the 'good' file and guess what? ORA-12154 magically went away.
Just a note, sometimes the TNSNAMES.ORA will get messed up. Nothing will jump out but it will not work and you cannot see the file though the net config. Just re-create it using notepad or [s]omething.
I replaced the two misbehaving files with the 'good' file and guess what? ORA-12154 magically went away.
Wednesday, August 5, 2009
ClickOnce and NHibernate
I've been working on a WPF MVVM intranet application that uses NHibernate for data access. As I expected, the initial ClickOnce deployment failed due to a missing configuration file and Castle assemblies. My View project used a Post-build event to get the required NHibernate files so that everything would run smoothly. Here's what that command line looks like:
C:\Windows\Microsoft.NET\Framework\v3.5\MSBuild.exe
"$(ProjectDir)DeploymentUtil\CopyNHibernateStuff.xml"
"/p:TargetCompileDirectory=$(TargetDir);TargetProjectDirectory=$(ProjectDir)"
Originally it just used the $(TargetDir) macro as an input to an MSBuild project file to copy the NHibernate files to the bin\Debug directory. In consideration of ClickOnce I modified it to also use the $(ProjectDir) macro to copy the files to the View project's root directory. Here's the contents of the CopyNHibernateStuff.xml file:
<?xml version="1.0" encoding="utf-8"?>
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<TargetCompileDirectory>.</TargetCompileDirectory>
<TargetProjectDirectory>.</TargetProjectDirectory>
<HibernateCfgPath>C:\SourceTfs\Patient Safety Organization\Eligibility Manager\PsorgEligibilityData\hibernate.cfg.xml</HibernateCfgPath>
</PropertyGroup>
<ItemGroup>
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\Castle.Core.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\Castle.DynamicProxy2.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\NHibernate.ByteCode.Castle.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\NHibernate.ByteCode.Castle.pdb" />
<NHFiles Include="$(HibernateCfgPath)" />
</ItemGroup>
<Target Name="CopyNH">
<Message Text="NHFiles: @(NHFiles)" />
<Message Text="TargetCompileDirectory: $(TargetCompileDirectory)" />
<Copy SourceFiles="@(NHFiles)" DestinationFolder="$(TargetCompileDirectory)" />
<!-- Now copy files (again) to project directory so that they can be referenced as a publishable file by ClickOnce. -->
<Copy SourceFiles="@(NHFiles)" DestinationFolder="$(TargetProjectDirectory)" />
</Target>
</Project>
I did some spelunking in the View project file to determine how items appeared in the Application Files dialog on the Publish tab. I figured out that I could manually add my required NHibernate references in the following manner and they would be available to ClickOnce for publishing.
<ItemGroup>
<Content Include="hibernate.cfg.xml" />
<Reference Include="Castle.Core.dll" />
<Reference Include="Castle.DynamicProxy2.dll" />
<Reference Include="NHibernate.ByteCode.Castle.dll" />
</ItemGroup>
Of course after I did all of this work I discovered this post which described my process in detail. At least it confirmed that I wasn't terribly abusing MSBuild.
C:\Windows\Microsoft.NET\Framework\v3.5\MSBuild.exe
"$(ProjectDir)DeploymentUtil\CopyNHibernateStuff.xml"
"/p:TargetCompileDirectory=$(TargetDir);TargetProjectDirectory=$(ProjectDir)"
Originally it just used the $(TargetDir) macro as an input to an MSBuild project file to copy the NHibernate files to the bin\Debug directory. In consideration of ClickOnce I modified it to also use the $(ProjectDir) macro to copy the files to the View project's root directory. Here's the contents of the CopyNHibernateStuff.xml file:
<?xml version="1.0" encoding="utf-8"?>
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<TargetCompileDirectory>.</TargetCompileDirectory>
<TargetProjectDirectory>.</TargetProjectDirectory>
<HibernateCfgPath>C:\SourceTfs\Patient Safety Organization\Eligibility Manager\PsorgEligibilityData\hibernate.cfg.xml</HibernateCfgPath>
</PropertyGroup>
<ItemGroup>
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\Castle.Core.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\Castle.DynamicProxy2.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\NHibernate.ByteCode.Castle.dll" />
<NHFiles Include="C:\Program Files\NHibernate\Required_For_LazyLoading\Castle\NHibernate.ByteCode.Castle.pdb" />
<NHFiles Include="$(HibernateCfgPath)" />
</ItemGroup>
<Target Name="CopyNH">
<Message Text="NHFiles: @(NHFiles)" />
<Message Text="TargetCompileDirectory: $(TargetCompileDirectory)" />
<Copy SourceFiles="@(NHFiles)" DestinationFolder="$(TargetCompileDirectory)" />
<!-- Now copy files (again) to project directory so that they can be referenced as a publishable file by ClickOnce. -->
<Copy SourceFiles="@(NHFiles)" DestinationFolder="$(TargetProjectDirectory)" />
</Target>
</Project>
I did some spelunking in the View project file to determine how items appeared in the Application Files dialog on the Publish tab. I figured out that I could manually add my required NHibernate references in the following manner and they would be available to ClickOnce for publishing.
<ItemGroup>
<Content Include="hibernate.cfg.xml" />
<Reference Include="Castle.Core.dll" />
<Reference Include="Castle.DynamicProxy2.dll" />
<Reference Include="NHibernate.ByteCode.Castle.dll" />
</ItemGroup>
Of course after I did all of this work I discovered this post which described my process in detail. At least it confirmed that I wasn't terribly abusing MSBuild.
Monday, July 20, 2009
NHibernate and Oracle 9i
Spent 1.5 hours troubleshooting the following error when using NHibernate 2.1:
"NHibernate.HibernateException: Could not instantiate dialect class NHibernate.Dialect.Oracle9Dialect ---> System.TypeLoadException: Could not load type NHibernate.Dialect.Oracle9Dialect. Possible cause: no assembly name specified."
I was looking at outdated documentation. The correct dialect is "NHibernate.Dialect.Oracle9iDialect" (emphasis mine). "NHibernate.Dialect.Oracle10gDialect" is also valid.
"NHibernate.HibernateException: Could not instantiate dialect class NHibernate.Dialect.Oracle9Dialect ---> System.TypeLoadException: Could not load type NHibernate.Dialect.Oracle9Dialect. Possible cause: no assembly name specified."
I was looking at outdated documentation. The correct dialect is "NHibernate.Dialect.Oracle9iDialect" (emphasis mine). "NHibernate.Dialect.Oracle10gDialect" is also valid.
Subscribe to:
Posts (Atom)