Ted
Ted

Reputation: 7251

Setting string to be sql type of "varchar" instead of "nvarchar"

I have the following mapping:

public class LogEntryMap
{
    public LogEntryMap()
    {
        Map.Id(x => x.Id).GeneratedBy.Identity();
        Map(x => x.Context).CustomSqlType("varchar").Length(512);
    }
}

However, using SchemaExport to generate the database in SQL Server 2008, the script generated ignores the length so in effect it ends up being a varchar with length of 1:

create table OV_SAC.dbo.[LogEntry] (
    Id BIGINT IDENTITY NOT NULL,
   Context varchar null,
   primary key (Id)
)

.CustomSqlType("varchar 512") throws an exception. And without defining the CustomSqlType, strings are mapped to nvarchar (which does respect the Length property).

Any suggestions?

Upvotes: 13

Views: 9874

Answers (4)

Szymon Pobiega
Szymon Pobiega

Reputation: 3376

Use .CustomType("AnsiString") instead of default "String" and NHibernate will use varchar instead of nvarchar.

Upvotes: 23

Joel WZ
Joel WZ

Reputation: 100

We found using the "CustomType("AnsiString")" option does prevent it from using the nvarchar, however, it sets the field length of 8000 for a column that is specified as varchar(30). The 8000 varchar is much faster than 4000 nvarchar, but it is still causing huge problems with sql server overhead.

Upvotes: 0

Jonathan Moffatt
Jonathan Moffatt

Reputation: 13457

If you wanted all of your strings to be mapped to varchar instead of nvarchar you could consider using a convention:

/// <summary>
/// Ensures that all of our strings are stored as varchar instead of nvarchar.
/// </summary>
public class OurStringPropertyConvention : IPropertyConvention
{
    public void Apply(IPropertyInstance instance)
    {
        if (instance.Property.PropertyType == typeof (string))
            instance.CustomType("AnsiString");
    }
}

You mappings could then go back to a simple mapping:

Map(x => x.Context);

Just make sure you remember to tell Fluent NH to use the convention:

        var configuration = new Configuration();
        configuration.Configure();
        Fluently
            .Configure(configuration)
            .Mappings(m => m.FluentMappings
                .AddFromAssemblyOf<Widget>()
                .Conventions.Add<OurStringPropertyConvention>()
                )
            .BuildSessionFactory();

Upvotes: 17

Ted
Ted

Reputation: 7251

Doh.

Map(x => x.Context).CustomSqlType("varchar (512)");

create table OV_SAC.dbo.[LogEntry] (
    Id BIGINT IDENTITY NOT NULL,
   Context varchar (512) null,
   primary key (Id)
)

Upvotes: 8

Related Questions