C
C#•9mo ago
Elio

SQLITE EFcore saving value

Hi, i'm working on a project which have a SQLITE database. I'm using EFcore to managed it. I want to know if there is a way to automatically add/remove/update by tracking or idk all the variable in my list Widths. Basically i want to call a methods Save that will add thickness if not added or add/remove/update elements in width a if thickness i already in the database.
public class Thickness
{
#region Properties
[Key]
public long Id { get; set; }

[Required]
public long MaterialId { get; set; }

[Required]
public double Value { get; set; }

public List<Width> Widths { get; set; } = new List<Width>();
}
public class Thickness
{
#region Properties
[Key]
public long Id { get; set; }

[Required]
public long MaterialId { get; set; }

[Required]
public double Value { get; set; }

public List<Width> Widths { get; set; } = new List<Width>();
}
[Table("Width")]
public class Width
{
#region Properties
[Key]
public long Id { get; set; }

[Required]
public long ThicknessId { get; set; }

[Required]
public double Value { get; set; }
}
[Table("Width")]
public class Width
{
#region Properties
[Key]
public long Id { get; set; }

[Required]
public long ThicknessId { get; set; }

[Required]
public double Value { get; set; }
}
38 Replies
Pobiega
Pobiega•9mo ago
Nothing is persisted in your database until you call context.SaveChangesAsync (or the non-async version), but otherwise EF already does this, if I have understood your question correctly ie, if you do
var thickness = await context.Thicknesses.FindAsync(5);
thickness.Widths.Add(new Width(43.5));
await context.SaveChangesAsync();
var thickness = await context.Thicknesses.FindAsync(5);
thickness.Widths.Add(new Width(43.5));
await context.SaveChangesAsync();
it will associate that width with that thickness if you modify any item in thickness.Widths before calling SaveChanges, it will also be updated accordingly.
Elio
ElioOP•9mo ago
i wanted more something like this :
var thickness = new thickness();
thickness.widths.add(new width());
Save(thickness); // this automatically add/reamode/update all the stuff in Widths
var thickness = new thickness();
thickness.widths.add(new width());
Save(thickness); // this automatically add/reamode/update all the stuff in Widths
Angius
Angius•9mo ago
What "stuff in widths"?
Elio
ElioOP•9mo ago
all the variable in my list widths
Angius
Angius•9mo ago
A width has: 1. An ID, which gets generated automatically anyway 2. FK to a width, which will be set using Pobiega's method 3. A value that you want to give some default value to, I guess?
var thickness = new Thickness {
// ...
Widths = [
new Width { Value = 10 },
new Width { Value = 24 },
new Width { Value = 114 },
]
}
_context.Thicknesses.Add(thickness);
await _context.SaveChangesAsync();
var thickness = new Thickness {
// ...
Widths = [
new Width { Value = 10 },
new Width { Value = 24 },
new Width { Value = 114 },
]
}
_context.Thicknesses.Add(thickness);
await _context.SaveChangesAsync();
is what you want?
Elio
ElioOP•9mo ago
not exactly because i allready use that king of method i will explain how my app is stuctured
Angius
Angius•9mo ago
Or
public class Width
{
public long Id { get; set; }
public long ThicknessId { get; set; }
public double Value { get; set; } = 123.45;
}
public class Width
{
public long Id { get; set; }
public long ThicknessId { get; set; }
public double Value { get; set; } = 123.45;
}
var thickness = new Thickness {
// ...
Widths = [new(), new(), new()]
}
_context.Thicknesses.Add(thickness);
await _context.SaveChangesAsync();
var thickness = new Thickness {
// ...
Widths = [new(), new(), new()]
}
_context.Thicknesses.Add(thickness);
await _context.SaveChangesAsync();
?
Elio
ElioOP•9mo ago
in fact my app load all the database, then i do my stuff like adding removing or even updating Width after that i want to call Save that will automattically track all the new item or removed items in Widths
Angius
Angius•9mo ago
EF tracks all additions, changes, and deletions And await _context.SaveChangesAsync(); persists them
Elio
ElioOP•9mo ago
i need to use _context.Thicknesses.Add(thickness); if i want him to track this right ? because i i do this thicknesses.Add(thickness); then save async it won't know that i have change stuff ?
Angius
Angius•9mo ago
Depends what is thicknesses
Elio
ElioOP•9mo ago
here is how i load my thicknesses :
public async Task<IEnumerable<Thickness>> GetAllWithData(Material material)
{
using(AppDbContext context = _dbContextFactory.CreateDbContext())
{
IEnumerable<Thickness> thicknesses = await context.Thicknesses.
Where(thickness => thickness.MaterialId == material.Id).
Include(thickness => thickness.Widths)
ToListAsync();
if(thicknesses == null)
throw new NullDbObjectException(material.Id);

return thicknesses;
}
}
public async Task<IEnumerable<Thickness>> GetAllWithData(Material material)
{
using(AppDbContext context = _dbContextFactory.CreateDbContext())
{
IEnumerable<Thickness> thicknesses = await context.Thicknesses.
Where(thickness => thickness.MaterialId == material.Id).
Include(thickness => thickness.Widths)
ToListAsync();
if(thicknesses == null)
throw new NullDbObjectException(material.Id);

return thicknesses;
}
}
Pobiega
Pobiega•9mo ago
nope thats a filtered copy of your thicknesses
Angius
Angius•9mo ago
What's this formatting 💀 First time I see someone place dots at the end of line lol
Pobiega
Pobiega•9mo ago
you need to add it to the DbSet if its a new entity to be tracked
Angius
Angius•9mo ago
And, yeah. Each individual thickness will be tracked, but the list as a whole is not a reflection of the dbset
Pobiega
Pobiega•9mo ago
also this. Please put the . on the new line :d oh and the context is disposed after the list is fetched
Elio
ElioOP•9mo ago
i will i promise i will search how to do it ahah
Angius
Angius•9mo ago
Just... do Instead of
foo.
Bar();
foo.
Bar();
write
foo
.Bar();
foo
.Bar();
Or use $prettycode shortcuts
MODiX
MODiX•9mo ago
To format your code in Visual Studio, Visual Studio Code, Rider, use the following shortcut:
Visual Studio CTRL + K + D
Rider / Resharper CTRL + ALT + L
Visual Studio Code SHIFT + ALT + F
Visual Studio CTRL + K + D
Rider / Resharper CTRL + ALT + L
Visual Studio Code SHIFT + ALT + F
NOTE: the first key must be held while doing it. https://cdn.discordapp.com/attachments/569261465463160900/899513918567890944/2021-10-18_01-26-35.gif
Pobiega
Pobiega•9mo ago
var x = context.Something
.Where()
.Include()
.ToListAsync();
var x = context.Something
.Where()
.Include()
.ToListAsync();
Elio
ElioOP•9mo ago
this copy the list to right ?
Pobiega
Pobiega•9mo ago
yeah this isnt a fix to your problem it was just an example of proper formatting
Elio
ElioOP•9mo ago
oh ok i will correct that i'm using codderush to format all king of stuff i'm looking to it
Pobiega
Pobiega•9mo ago
your problem is fixed by having a database context available when you plan to insert data into your database 😛
Elio
ElioOP•9mo ago
so i should keep a database context open the moment i load my items ?
Pobiega
Pobiega•9mo ago
$itdepends
Pobiega
Pobiega•9mo ago
Impossible to answer You need a context available at the time where you insert new data into your database thats a hard fact should it be the same context? Depends on how your application is made.
Elio
ElioOP•9mo ago
so if i'm copying the thickness, in fact it keep the id right ? can i track it when opening the context and then saving it ? EFcore will be able to add/remove/update all the item in thickness no ?
Pobiega
Pobiega•9mo ago
yeah, anything you fetch from the context will have the correct IDs however, if you fetch it in one context, then try to save it on another context, you will need to let the new context know about the item as tracking is per-context
Elio
ElioOP•9mo ago
ok so to achieve my goal i will have to create a save function that will track all the change made in order to update thickness and widths in my db
Pobiega
Pobiega•9mo ago
"track all the changes" is a bit much just add the thickness to the tracker
Elio
ElioOP•9mo ago
ok i think i've understand i'll try some test by my side, if i'm right by tracking thickness it should also track the width in it and i will be able to save all the changes made in it like all the removed/added width item there it is i've updated my formatting 😉 :
public async Task<IEnumerable<Thickness>> GetAllWithData
(Material material)
{
using(AppDbContext context = _dbContextFactory.CreateDbContext())
{
IEnumerable<Thickness> thicknesses = await context.Thicknesses
.Where(thickness => thickness.MaterialId == material.Id)
.Include(thickness => thickness.Widths)
.ThenInclude(width => width.SymmetricRolls)
.Include(thickness => thickness.Widths)
.ThenInclude(width => width.AsymmetricRolls)
.ToListAsync();
if(thicknesses == null)
throw new NullDbObjectException(material.Id);

return thicknesses;
}
}
public async Task<IEnumerable<Thickness>> GetAllWithData
(Material material)
{
using(AppDbContext context = _dbContextFactory.CreateDbContext())
{
IEnumerable<Thickness> thicknesses = await context.Thicknesses
.Where(thickness => thickness.MaterialId == material.Id)
.Include(thickness => thickness.Widths)
.ThenInclude(width => width.SymmetricRolls)
.Include(thickness => thickness.Widths)
.ThenInclude(width => width.AsymmetricRolls)
.ToListAsync();
if(thicknesses == null)
throw new NullDbObjectException(material.Id);

return thicknesses;
}
}
Pobiega
Pobiega•9mo ago
I'd argue your data has a weird shape for a relational database
Elio
ElioOP•9mo ago
what do you mean by weird shape ?
Elio
ElioOP•9mo ago
No description
Elio
ElioOP•9mo ago
i've tried to dissociate the app from the database to be able to modify my item freely without breaking my db with wrong manipulation. And if i'm done to update/add/remove item then i call save to interact with the db and confirm all the changes made.
Want results from more Discord servers?
Add your server