当我添加新的“多对多”对象时,旧记录中的某些关系字段值将设置为null或0(参考:图像1)。
还会删除一些先前的中间表记录(参考:图像2)。
以下是代码:
型号:
public class ModelBase
{
[PrimaryKey, AutoIncrement]
public int Id {set; get;}
}
[Table(nameof(Quoter))]
public class Quoter : ModelBase
{
[Unique, MaxLength(30)]
public string Name {set; get;}
[ManyToMany(typeof(QuoterProfession), CascadeOperations = CascadeOperation.CascadeInsert | CascadeOperation.CascadeRead)]
public List<Profession> Professions {set; get;}
[OneToMany(CascadeOperations = CascadeOperation.All)]
public List<Quote> Quotes {set; get;}
}
[Table(nameof(Quote))]
public class Quote : ModelBase
{
public string Statement {set; get;}
[ForeignKey(typeof(Quoter))]
public int QuoterId { get; set; }
[ManyToOne(CascadeOperations = CascadeOperation.CascadeInsert | CascadeOperation.CascadeRead)]
public Quoter Quoter {set; get;}
[ForeignKey(typeof(Profession))]
public int ProfessionId { get; set; }
[ManyToOne(CascadeOperations = CascadeOperation.CascadeInsert | CascadeOperation.CascadeRead)]
public Profession Profession {set; get;}
}
[Table(nameof(Profession))]
public class Profession : ModelBase
{
[Unique, MaxLength(20)]
public string Name {set; get;}
[ManyToMany(typeof(QuoterProfession), CascadeOperations = CascadeOperation.CascadeInsert | CascadeOperation.CascadeRead)]
public List<Quoter> Quoters {set; get;}
[OneToMany(CascadeOperations = CascadeOperation.CascadeInsert | CascadeOperation.CascadeRead)]
public List<Quote> Quotes {set; get;}
}
[Table(nameof(QuoterProfession))]
class QuoterProfession : ModelBase
{
[ForeignKey(typeof(Quoter))]
public int QuoterId { get; set; }
[ForeignKey(typeof(Profession))]
public int ProfessionId { get; set; }
}
视图模型:
public class AddQuoterPageVm
{
public Quoter Quoter { get; set; }
public List<Profession> Professions { get; set; }
public ObservableCollection<Profession> QuoterProfessions { get; set; }
public Profession QuoterProfession { get; set; }
public Profession QuoteProfession { get; set; }
public Quote Quote { get; set; }
public ObservableCollection<Quote> Quotes { get; set; }
public void SaveQuoter() // Add a new Quoter with all his properties & Save
{
Quoter = new Quoter {Name = "QuoterN"};
asyncConnection.InsertWithChildrenAsync(Quoter).Wait(); // Adds a new Quoter to database
AddProfessions(); // Add profession to database
Professions = asyncConnection.GetAllWithChildrenAsync<Profession>().Result;
// Add QuoterN's profession
QuoterProfessions = new ObservableCollection<Profession>{ Professions[0], Professions[1] };
Quoter.Professions = new List<Profession>(QuoterProfessions);
Quotes = new ObservableCollection<Quote>
{
new Quote {Statement = "q1 q1", Profession = Professions[0]},
new Quote {Statement = "q1 q2", Profession = Professions[1]}
};
Quoter.Quotes = new List<Quote>(Quotes); // Add QuoterN's quotes
Quotes = null;
// Update QuoterN in database after adding additional properties
asyncConnection.InsertOrReplaceWithChildrenAsync(Quoter, true);
}
private void AddProfessions() // Adds professions to database
{
asyncConnection.GetAllWithChildrenAsync()
.ContinueWith(professionListTask =>
{
if (professionListTask.Result.Any()) return;
var professions = new List<Profession>
{
new Profession {Name = "Profession1"},
new Profession {Name = "Profession2"},
new Profession {Name = "Profession3"},
new Profession {Name = "Profession4"},
new Profession {Name = "Profession5"},
new Profession {Name = "Profession6"},
new Profession {Name = "Profession7"}
};
asyncConnection.InsertAllWithChildrenAsync(professions);
});
}
}
如何在不影响(不合需要)以前的记录的情况下添加Quoter?
答案 0 :(得分:0)
可能在两端递归所有关系都会导致问题,因为您只设置其中一个而另一端可能不一致。由于您没有使用递归插入操作,我建议您从所有关系中删除CascadeOperation.CascadeInsert
,或将反向关系标记为ReadOnly
。
我不确定等待这样的异步操作是否会导致问题,所以我也试着修复它。尝试等待异步操作并返回Task
而不是void
来返回结果任务:
public async Task SaveQuoter() {
Quoter = new Quoter {Name = "QuoterN"};
await asyncConnection.InsertWithChildrenAsync(Quoter);
await AddProfessions();
Professions = await asyncConnection.GetAllWithChildrenAsync<Profession>();
...
}
您可以查看来源中包含的IntegrationTests
project中的示例代码。
答案 1 :(得分:0)
我使用asyncConnection.UpdateWithChildren(Quoter)
更新了Quoter。使用此旧记录后不会被删除。
之前我使用的是asyncConnection.InsertOrReplaceWithChildrenAsync(Quoter, true)
。