Wednesday, November 29, 2006

Development: Empty strings in Oracle and MySQL

Today I was testing some code I've written, on a client's QA environment. These tests revealed, that if your tests succeed locally on a MySQL server environment this doesn't necessarily mean the tests will succeed on an Oracle server. I was having problems with Oracle's interpretation of an empty string. It seems that if you're executing the following statement:

insert into MyTable (c1,c2) values ('val1','');

this is the same as executing:

insert into MyTable (c1,c2) values ('val1',null);

IMHO this is plain wrong. '' does not equal NULL from a programmer's point of view.
Inserting an empty string (or '') can be convenient to make your prepared statements easier.
Suppose, in the above example, c2 is an optional parameter. When c2 is not available you insert ''. In this case a prepared statement to select records from MyTable could be:

select * from MyTable where c1 = ? and c2 = ?

After substitution the resulting statement for MySQL will be:

select * from MyTable where c1 = 'example' and c2 = ''

And for Oracle:

select * from MyTable where c1 = 'example' and c2 = null

Which is wrong.
So, if Oracle replaces my empty string with null, the prepared statement should be:

select * from MyTable where c1 = ? and coalesce(c2,'dontcare') = coalesce(?,'dontcare')

(please see also this link)
This works for both MySQL and Oracle ... of course.

Monday, November 13, 2006

Linux: Fixing authentication in Apache 2, after doing an upgrade

This is the second post on upgrading my Debian box to testing. Obviously everything was b0rken, even authentication mechanisms put in place for Apache2. Apache2 is using the local LDAP server for authenticating users on a subversion repository. Apparently, the people of Apache did some "refactoring" on the naming of their authentication modules. They renamed auth_ldap to authnz_ldap. Enabling this module instead of the outdated on, did not do the trick. I got the following error instead:

[Thu Nov 02 19:07:26 2006] [crit] [client] configuration error: couldn't check user. No user file?: /svn/configs/!svn/act/ed8028d3-8254-bd4c-bc94-c3b93f8b97bb
[Thu Nov 02 19:07:44 2006] [crit] [client] configuration error: couldn't check user. No user file?: /svn/configs/!svn/act/b2296e68-a114-8e49-aea6-bebfe78947bf
[Thu Nov 02 19:14:57 2006] [notice] caught SIGTERM, shutting down

I did some more reading and found this presentation very useful: TH21 - Using LDAP Authentication in Apache 2.2.ppt (I want to post a link, but the site seems down)
After updating my config, authentication started working again. Here it is:

<Location /svn/configs/>
<LimitExcept GET PROPFIND OPTIONS REPORT>
AuthType Basic
AuthName "svn"
AuthBasicProvider ldap
AuthLDAPURL ldap://localhost:389/ou=Users,dc=MyDomain?uid
AuthzLDAPAuthoritative off
require valid-user
</LimitExcept>
</Location>

That wasn't that bad ... was it ;)

Monday, November 06, 2006

Development: Convert your code to html

If you want to cut and paste code into an html page, you will find the following tools very handy:

Makes blogging and publishing code easier ;)

Sunday, November 05, 2006

Linux: Upgrading Debian woes (1)

So I decided to give my server, running Debian testing, an upgrade. Normally this works like a breeze. I have never encountered any problems during an upgrade, even though I am following testing.
This time was different and things were very b0rken. This is about fixing my first issue: LDAP + libnss + udev.

LDAP

During the upgrade, the script didn't manage to create a decent backup of the running LDAP server. This LDAP is serving users for my home network and is also the backend for my Samba domain controller. So the LDAP was very b0rken. The only fix I could see was repopulating the entire tree, starting from a fresh, empty LDAP. To help me with this, I found this a very interesting and thorough guide. Since the LDAP is also my Samba backend I am using smbldap-tools to maintain users and such. So repopulating the LDAP wasn't such a big task.
Lucky.

udev

What is udev?
udev works entirely in userspace, using hotplug events the kernel sends whenever a device is added or removed from the kernel. Details about the devices are exported by the kernel to the sysfs filesystem at /sys All device naming policy permission control and event handling is done in userspace. devfs is operated from within the kernel.
(read).
This thing is started way before my LDAP boots. Why? Because this thing is necessary to build the /dev tree and modprobing drivers, such as drivers for my network card. So udev starts very early in the boot process looking for users and groups to assign. E.g. /dev/audio is assigned to the audio group.
If a user or group is not found local, it tries to search the LDAP, which is ... not there. Before the upgrade udev tried a few times to reach the LDAP, and finally gave up. Now it didn't. It just kept trying to reach the damn LDAP. This link describes the problem I was having (bug #375077). The solution to this problem was to change the bind_policy so it only tries to reach the LDAP 3 times (or less if you want):

bind_policy hard
nss_reconnect_tries 3
nss_reconnect_sleeptime 1
nss_reconnect_maxconntries 3


Libnss

After messing around a little, I suddenly got the following error:

ldap-nss.c:1323: do_init: Assertion `cfg->ldc_uris[__session.ls_current_uri] != ((void *)0)' failed.

Now that's what I call a decent error ;) This happened when trying to log in with a user known in the LDAP, but not on the system. After pulling my hair a little and googling a while, I discovered I accidentally messed up the libnss-ldap.conf. This configuration file is necessary for the name switch service to be able to access the ldap. This file contains the root DN and credentials to access/search the LDAP. Therefore this file should be:

  • readable by everyone;

  • or readable by root only, but then you'll need the nscd (name switch caching daemon).


Since I must be able to add and change users on this particular machine, the file contains administrator credentials and is readable for root only. So I need the nscd running which was throwing the above error while asking the name switch service for a user existing in the LDAP. Reverting the libnss-ldap.conf to its original state solved my problems. If you store your /etc in a subversion repository, this is easy ;)
In a next post I will be discussing my next problem: "Fixing authentication in Apache 2, after doing an upgrade"

Monday, October 16, 2006

Linux: Problems in Ubuntu, icons do not appear when inserting removable device 2 (the solution!)

Seems I was still having problems with devices not being automounted. Very frustrating knowing "it should" automount plugged in devices ... but it just doesn't. So tonight I decided to google some more and finally I found the solution. I had to put

session optional pam_foreground.so

Near the end of /etc/pam.d/common-session. Since I am authenticating users against an LDAP, I have a sneaky suspicion why my problem occured:
- step 1. Installed Hoary a long time ago
- step 2. Make sure Hoary is able to talk to an LDAP to retrieve its users
- step 3. Upgrade to Breezy (also long time ago). During the upgrade the installer asks: "Dude! someone changed /etc/pam.d/common.session do you want to overwrite the file with the maintainer's version?" Hell no ... I spent a reasonable amount of time configuring pam.d to use pam_ldap (btw: this is an interesting read on how to setup LDAP and stuff) ... and that's when all my problems started.
- step 4. Upgrade to Dapper ... still b0rken but now I finally managed to fix it.

Thursday, August 03, 2006

Solaris: Change action behind browser icon in CDE

So I inherited a Sun Enterprise 450, dual CPU, 2GB RAM and a dozen of disks. I’ve been busy wiping disks on this machine and on another Sun Enterprise 250 using this link. Next, I’ve been installing Solaris 10, which was a pretty “next -> next -> finish” install. I’m not running Gnome, because I just love the CDE environment (don’t ask why, I’m a geek). I decided not to install the mozilla browser provided with the set of installation CD-ROMs, instead I used the software service from blastwave to install firefox. It wasn’t very easy to make CDE look for firefox instead of mozilla, when pressing the “world” icon in the front panel. Ok, I admit, after Reading The Funky Advanced CDE Guide, I found all I needed to do is to tweak sdtwebclient file, found in /usr/dt/bin. Change the follwing lines:

PATH=/usr/bin:${PATH}:/usr/sfw/bin:/opt/NSCPcom
COMMAND=`basename $0`
DEFAULT_BROWSER_LIST="mozilla netscape sun_netscape netscape6"

To:

PATH=/usr/bin:${PATH}:/usr/sfw/bin:/opt/NSCPcom:/opt/csw/bin
COMMAND=`basename $0`
DEFAULT_BROWSER_LIST="mozilla netscape sun_netscape netscape6 firefox"

And firefox will appear when pressing the world icon.
BTW, CDE rules ;)

Monday, February 27, 2006

Linux: Testing your iptables firewall

I have an old Pentium II running Debian Testing to protect my internal network from the Internet. Yesterday, I decided to test this firewall using a site that performs a portscan. I came accross http://www.testmyfirewall.com/ that did exactly what I wanted. This site claimed my internal address (the address of the computer sitting behind the firewall) was exposed to the outside. Yeah, right. After some digging I came accross this post from a guy having the same "problem". It seems that testmyfirewall starts an applet displaying the address of the computer running the applet, which is indeed the one sitting behind the firewall.
So this site does not test your firewall, it only tests your browser which is a different thing.
Just be aware of sites that claim to test your firewall, they're not allways right.

Monday, February 13, 2006

Java: Extending classpath in Tomcat 5.5.x

According to the documentation you can add locations/jars to your classpath using the CLASSPATH system variable in windows. I have discovered another way to do this. Just open the catalina.properties file in the conf directory. This should read:
shared.loader=${catalina.base}/shared/classes,${catalina.base}/shared/lib/*.jar
Changing the line to:
shared.loader=${catalina.base}/shared/classes,${catalina.base}/shared/lib/*.jar,c:/test/foo.jar
Will extend the shared classpath with foo.jar.

Thursday, February 09, 2006

Biztalk 2004: Issue you might encounter when you refactor

So I decided to split a project that contained 4 orchestration. I now have
- 1 project containing a receive pipeline
- 4 other projects containing the orchestrations, referencing the above project
Apart from splitting the project, I decided to clean up the namespaces for the schema’s and property schema files. “Easy enough”, I thought, “Edit the schemas and property schemas using notepad or some other XML editor and we’re done”. Better think again. When deploying the “split” DLLs I encountered the following error in our test environment:

errors:
Property "ns0:Something"
(msgType="http://foo#bar ")
not found in Configuration database.

The solution for this problem is not to edit your property schema files, but generate them again, if you’re refactoring namespaces or types. Reason for this is the fact that properties have their GUIDs and these have to be unique. Should you change the namespace and not the GUID for this property, uniqueness is not maintained.
So, in short, refactoring Biztalk projects is a pain, better think twice (or more) before starting to implement ;-)

Wednesday, February 01, 2006

Linux: Problems in Ubuntu, icons do not appear when inserting removable device

In my setup, users on my Ubuntu box are authenticated against an LDAP running on Debian. This is working very nicely, but since I upgraded from Hoary to Breezy, my icons for auto-mounted removable devices were not showing any more. This is, of course, very annoying.
After googling a bit, I came accross this bug. But none of the suggestions worked for me.
So I decided to create a real local user (i.e. a user not available in the LDAP) and see if this one still had the icons showing when auto-mounting happens. It did ;) So I guessed the local user was member of some local groups, my LDAP user wasn't member of. My guess was correct. Seems that the LDAP users have to be member of the local “users” group as well, which was the one I missed out. Below is the output of the id command for an LDAP user:

uid=1002(ldapuser) gid=513(Domain Users) groups=24(cdrom),25(floppy),29(audio),46(plugdev),100(users),109(admin),513(Domain Users)

Thursday, January 12, 2006

Devlopment: Hungarian Notation Sucks ...

Don't you just hate people using the so called Hungarian Notation in their C#/Java code. Well, I do. Here's an interesting read on this matter.

Monday, January 09, 2006

Linux: New chapter in DGP

Dr. Salus is back from holiday and released a new chapter in his series on "The Daemon, the GNU and the Penguin". Read it here.