Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Getting list of Ids from collection throws Unable to cast object of type 'LiteDB.ObjectId' to type 'System.String' #2527

Open
ssteiner opened this issue Jul 29, 2024 · 4 comments
Labels

Comments

@ssteiner
Copy link

Version
LiteDb 5.0.21 on Win11 2023H2 on .NET 8.0.7

Describe the bug

Here's my object model:

public class PhoneBookCategory
{
    public string Id { get; set; }

    public string Name { get; set; }
}

Then I populate my DB as follows:

PhoneBookCategory category1 = new()
{
    Id = ObjectId.NewObjectId().ToString(),
    Name = "Category1"
};
PhoneBookCategory category2 = new()
{
    Id = ObjectId.NewObjectId().ToString(),
    Name = "Category2"
};
PhoneBookCategory category3 = new()
{
    Id = ObjectId.NewObjectId().ToString(),
    Name = "special Subcategory3"
};

database.GetCollection<PhoneBookCategory>().Insert(category1);
database.GetCollection<PhoneBookCategory>().Insert(category2);
database.GetCollection<PhoneBookCategory>().Insert(category3);

And I'm trying to fetch the list of Ids

var accessibleObjects = database.GetCollection().Query().Select(x => x.Id).ToList();

When I run this, it throws

Unable to cast object of type 'LiteDB.ObjectId' to type 'System.String'. at at LiteDB.LiteQueryable1.<ToEnumerable>b__27_1(BsonValue x) at System.Linq.Enumerable.SelectEnumerableIterator2.ToList()
at LiteDB.LiteQueryable1.ToList() at LiteDbTest.LiteDbContext.<>c__DisplayClass21_01.b__0(LiteDatabaseContext context)
at LiteDbTest.LiteDbContext.PerformDatabaseOperation[T](Func`2 myFunc, IUserInformation userInfo, String methodName)

What I would expect is to get a List containing all Ids in my database.

If I remove the ToList(), it runs fine. If I replace ToList() with .FirstOrDefault(), it runs fine.

@ssteiner ssteiner added the bug label Jul 29, 2024
@Vernizze
Copy link

Hi! I have a same problem in a same environment configuration of ssteiner, but not in cast to string but to long.

My stack trace:

Unable to cast object of type 'LiteDB.ObjectId' to type 'System.Int64'.- at lambda_method168(Closure, Object, Object) at LiteDB.BsonMapper.DeserializeObject(EntityMapper entity, Object obj, BsonDocument value) at LiteDB.BsonMapper.Deserialize(Type type, BsonValue value) at LiteDB.LiteQueryable 1.<ToEnumerable>b__27_2(BsonDocument x) at System.Linq.Enumerable.SelectEnumerableIterator 2.MoveNext() at System.Linq.Enumerable.<Any>g__WithEnumerator|36_0[TSource](IEnumerable 1 source) at System.Linq.Enumerable.Any[TSource](IEnumerable 1 source)

@ssteiner
Copy link
Author

@Vernizze : did you ever look in the database directly? I had the lingering feeling that in my case, I had a messed up value in the database. And since the IEnumerable only gets evaluated when I access the data, that would explain why it threw on ToList()

As I was using exclusive DB access mode, I never looked at the data.

@Joy-less
Copy link
Contributor

I run this code in the upstream repository and it works fine:

using Xunit;

namespace LiteDB.Tests.Issues;

public class Issue2527_Tests
{
    [Fact]
    public void Test() 
    {
        using LiteDatabase database = new(new ConnectionString()
        {
            Filename = "Demo.db",
        });

        PhoneBookCategory category1 = new()
        {
            Id = ObjectId.NewObjectId().ToString(),
            Name = "Category1"
        };
        PhoneBookCategory category2 = new()
        {
            Id = ObjectId.NewObjectId().ToString(),
            Name = "Category2"
        };
        PhoneBookCategory category3 = new()
        {
            Id = ObjectId.NewObjectId().ToString(),
            Name = "special Subcategory3"
        };

        database.GetCollection<PhoneBookCategory>().Insert(category1);
        database.GetCollection<PhoneBookCategory>().Insert(category2);
        database.GetCollection<PhoneBookCategory>().Insert(category3);

        var accessibleObjects = database.GetCollection<PhoneBookCategory>().Query().Select(x => x.Id).ToList();
    }

    public class PhoneBookCategory
    {
        public string Id { get; set; }
        public string Name { get; set; }
    }
}

Changing string to long also works. Maybe your database IDs are corrupted or the issue got fixed. Please send more info if you still have the issue @ssteiner @Vernizze.

@ssteiner
Copy link
Author

I wasn't able to create a repro sample that you could run - as I said in my previous post, I suspect I had some data corruption somewhere.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants