Hi,
I've solved the issue with few tweaks, I'm sure theses tweaks are weak since I'm not used to the best practices in nhibernate code structure and have done them in hurry:
in ~/NHibernate/Dialect/Oracle9Dialect.cs
Replace
RegisterColumnType(DbType.Guid, "CHAR(38)");
With
RegisterColumnType(DbType.Guid, "RAW(16)");
also have modified ~/NHibernate/Type/GuidType.cs but I'm unsure now if it's required (it helped me handling Guid in oracle and sqlite and others) and that's BAD HACK:
Code:
public override object Get(IDataReader rs, int index)
{
System.Type type = rs.GetFieldType(index);
byte[] buffer;
if(type == typeof(Guid)){
buffer = ((Guid)rs[index]).ToByteArray();
} else
if(type == typeof(byte[])){
buffer = (byte[]) rs[index];
} else if (type == typeof(string)) {
buffer = (new Guid((string)rs[index])).ToByteArray();
} else {
return null; // ouch
}
return new Guid(buffer);
}
public override void Set(IDbCommand cmd, object value, int index) {
IDataParameter parm = cmd.Parameters[index] as IDataParameter;
#if SQLITE || MSSQL
parm.Value = ((Guid)value);
#else
parm.Value = ((Guid)value).ToByteArray(); // oracle provider won't convert Guid to binary :(
#endif
}
It seems obvious to me that Guid should be mapped as binary by default, but it doesn't seems to be the case in the NHibernate codebase and across drivers implementation.
I don't know if there is better way (using IUserType or such thing?) that does not require to change MapType which should stay implicit when using System.Guid
Any guidance on this topic would help because I'm worried to "maintain" such hacks in the NHibernate codebase and a nicer way should be implemented.