This project has moved and is read-only. For the latest updates, please go here.

Fixed sized string fields

Apr 23, 2013 at 12:41 PM
Edited Apr 23, 2013 at 12:46 PM
Hi,

i have:

myEntity.Items

I have added some items. When, in a test, i do

myEntitity.Items.Where(...).ToList()

it result in 0 items in the list.
I'm sure that there should be 1 item.

If i write

myEntity.Items.ToList().Where(...).ToList()

then i obtain the result i excpected, one item.

why i must add the ToList() before the where ? That seem a bug, and i can't do a toList to the whole table ;)...

Thank You
Vincenzo
Apr 23, 2013 at 12:49 PM
Hello!

It is possible that this is caused by a bug.

Please tell me a bit more about your schema and Where expression.
Apr 23, 2013 at 1:11 PM
The query is:
List<string> codes = new List<string> { "CODE1" };

var oldMatricules = _entities.Matricole.Where(m => codes.Contains(m.CodiceMatricola)).ToList();
Before this i have added to _entities.Matricole an object with CodiceMatricola = "CODE1". Then i have do SaveChanges().
Then i excpet that in oldMatricules there is at least 1 matricule, but it return 0 matricuels.
If i add a ToList() after Matricole
var oldMatricules = _entities.Matricole.ToList().Where(m => codes.Contains(m.CodiceMatricola)).ToList();
in oldMatricules there is 1 item.

For working with Effort i use this construct:
        var entityConnection = EntityConnectionFactory.CreateTransient(ConfigurationManager.ConnectionStrings["FashionEntities"].ConnectionString);

        _entities = new FashionEntities(entityConnection);
Because in the others way it throw exceptions about keys , schema ecc. ecc.



Thank You
Apr 23, 2013 at 1:29 PM
I just tried this kind of query, and it worked for me.

How did you add the data? Haven't you forgotten to call SaveChanges?
Apr 23, 2013 at 1:39 PM
Edited Apr 23, 2013 at 1:39 PM
I have done SaveChanges.

I have just tried to do the where with a condition on another property:

var oldMatricules = _entities.Matricole.Where(m => m.OrdineTaglia == 40).ToList();

and this work well!

The property OrdineTaglia is a numeric, while CodiceMatricola is string...

Have you tried with a string property ?
Apr 23, 2013 at 1:40 PM
I add the data in this mode:
            var matricolaOld = new Matricole {CodiceMatricola = code, OrdineTaglia = Byte.Parse(ordineTaglia)};

            entities.Matricole.Add( matricolaOld );

            entities.SaveChanges();
Apr 23, 2013 at 1:48 PM
Edited Apr 23, 2013 at 2:12 PM
I think the problem is that CodiceMatricola is a fixed sized string field, try to initialize the collection with aprropriately sized strings, for example:
List<string> codes = new List<string> { "CODE1    " };
Nonetheless, correct handling of fixed sized strings should be implemented.
Apr 23, 2013 at 2:05 PM
Ok, i have fixed (my mind...) CodiceMatricola is mapped with fixed-length char(16), but i have matched with a 15-long string....
Excuse me ... and thank you
Vincenzo
Apr 23, 2013 at 2:07 PM
good!, you get it without seeing the code;)
Apr 23, 2013 at 2:25 PM
Edited Apr 23, 2013 at 2:26 PM
No problem. Effort does not do it right, it should definitely do trimmed comparison.

For now, please try to use appropriately sized strings.
Apr 23, 2013 at 4:18 PM
Edited Apr 23, 2013 at 4:18 PM
Ok, and what about table names with spaces ? Effort throw exception because it crop the string at first space, ..example:

if i have a table name : 'ABC DEF', in EF it will renamed as 'ABC__DEF'.

if i have 2 tables : 'ABC DEF' and 'ABC 123', when effort create EntityConnection and try to add second table, throw that there is a table with that name.... because, i think, it get only ABC..
Apr 23, 2013 at 4:25 PM
Precisely, the exception happen in this point:
            schema.RegisterTable(
                new DbTableInformation(
                    entityType.Name,
                    entityType,
                    primaryKeyFields.ToArray(),
                    identityFields.SingleOrDefault(),
                    properties.ToArray(),
                    constraint.ToArray(),
                    primaryKeyInfo));
in 'DbSchemaFactory.cs'

entityType.Name is not correctly setted.
Apr 23, 2013 at 4:40 PM
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
   modelBuilder.Entity<Foo>().ToTable("ABC DEF");
   modelBuilder.Entity<Foo2>().ToTable("ABC 123");
}
This seems to be working.

How did you name the tables?
Apr 23, 2013 at 5:00 PM
Edited Apr 23, 2013 at 5:01 PM
Ok, i have cloned the repository, try add this tables:

'{Foo China$Whse. Activity Hdr. Interface}' [entityType.Name = ' Interface']
'{Foo China$Whse. Activity Lines Interface}' [entityType.Name = ' Activity Lines Interface']
'{Foo Corporation$Whse. Activity Hdr. Interface}' [entityType.Name = ' Interface']


the third table throw exception because entityType.Name is ' Interface' that its the same of first table.

The problem is the second point i think.
Apr 23, 2013 at 5:04 PM
Edited Apr 23, 2013 at 5:05 PM
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Foo>().ToTable("Foo China$Whse. Activity Hdr. Interface");
modelBuilder.Entity<Foo>().ToTable("Foo China$Whse. Activity Lines Interface");
modelBuilder.Entity<Foo>().ToTable("Foo Corporation$Whse. Activity Hdr. Interface");
}
Apr 25, 2013 at 10:37 PM
Edited Apr 25, 2013 at 10:37 PM
Okey, the confusion comes from the period characters. EF interprets the string before the last period as the schema. To overcome this, you should use explicit schema definition:
modelBuilder.Entity<Foo>().ToTable("Foo China$Whse. Activity Hdr. Interface", "");
modelBuilder.Entity<Foo>().ToTable("Foo China$Whse. Activity Lines Interface", "");
modelBuilder.Entity<Foo>().ToTable("Foo Corporation$Whse. Activity Hdr. Interface", "");
Furthermore Effort had a bug that caused name collisions, but i have fixed it. Thank you for reporting this issue.
Apr 29, 2013 at 11:22 AM
Ok, thank you, i've resolved, but i think that this
line:
        return name.Replace("_", "__").Replace(".", "_");

may cause some problems with tablenames with one underscore, i have changed that line with this:
        return name.Replace(".", "_");
Now work with all my tables.


TY
Apr 29, 2013 at 11:31 AM
.Replace("_", "__")
This code was added to prevent name collisions of tables named like "Tab_le" and "Tab.le". What kind of problem did you encounter exactly?
Apr 29, 2013 at 1:20 PM
But if i have this table 'ABC_DEF', it will be registered as 'ABC__DEF'..
This is the exception throwed in my test, when i try to create FakeEntity:

Test method TestProject.GetMatriculeTest.Get_CdmRowConMatricolaSbagliataDoceId_Eccezione threw exception:
System.Collections.Generic.KeyNotFoundException: The given key was not present in the dictionary.
at System.Collections.Generic.Dictionary`2.get_Item(TKey key)
at Effort.Internal.DbManagement.Schema.DbSchemaFactory.CreateDbSchema(StoreItemCollection edmStoreSchema) in c:\Users*\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\DbManagement\Schema\DbSchemaFactory.cs: line 219
at Effort.Internal.DbManagement.DbContainer.<Initialize>b__0(StoreItemCollection sic) in c:\Users*
\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\DbManagement\DbContainer.cs: line 135
at Effort.Internal.Caching.DbSchemaStore.<>c__DisplayClass1.<GetDbSchema>b__0() in c:\Users*\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\Caching\DbSchemaStore.cs: line 84
at System.Lazy1.CreateValue()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Lazy
1.get_Value()
at Effort.Internal.Caching.ConcurrentCache2.Get(TKey key, Func1 factory) in c:\Users*\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\Caching\ConcurrentCache2.cs: line 76
at Effort.Internal.Caching.DbSchemaStore.GetDbSchema(StoreItemCollection metadata, Func
2 schemaFactoryMethod) in c:\Users*
\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\Caching\DbSchemaStore.cs: line 82
at Effort.Internal.DbManagement.DbContainer.Initialize(StoreItemCollection edmStoreSchema) in c:\Users*
\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Internal\DbManagement\DbContainer.cs: line 132
at Effort.Provider.EffortProviderServices.DbCreateDatabase(DbConnection connection, Nullable`1 commandTimeout, StoreItemCollection storeItemCollection) in c:\Users*\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\Provider\EffortProviderServices.cs: line 176
at System.Data.Objects.ObjectContext.CreateDatabase()
at Effort.EntityConnectionFactory.CreateEntityConnection(MetadataWorkspace metadata, DbConnection connection) in c:\Users*
\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\EntityConnectionFactory.cs: line 281
at Effort.EntityConnectionFactory.CreateTransient(String entityConnectionString, IDataLoader dataLoader) in c:\Users*\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\EntityConnectionFactory.cs: line 145
at Effort.EntityConnectionFactory.CreateTransient(String entityConnectionString) in c:\Users*
\Documents\Visual Studio 2012\Projects\effort\Main\Source\Effort\EntityConnectionFactory.cs: line 164
at TestProject.Common.GetFakeFashionEntity() in Common.cs: line 13
at TestProject.GetMatriculeTest.Get_CdmRowConMatricolaSbagliataDoceId_Eccezione() in GetMatriculeTest.cs: line 77
Apr 29, 2013 at 2:59 PM
Edited Apr 29, 2013 at 4:27 PM
I think I fixed this. However, I will do some deeper analysis in the future.