我正在尝试实现与我们在 SO - 标记系统上的功能非常相似的功能。我输入标签,它会查看它们是否存在 - 如果不存在,则会通过连接表(多对多)创建与帖子相关联的标签。
它的工作原理如下:用户在“,”-分隔值(TagList)中输入标签。我用 RegEx 拆分 TagList 以提取不同的标签 - 我尝试在数据库中查找标签。如果它不存在,我创建它。
到目前为止,这就是我所拥有的:
食谱.cs
public class Recipe
{
[Key]
public int RecipeId { get; set; }
[Required]
public string Name { get; set; }
public string Subtitle { get; set; }
public int Serving { get; set; }
public string Instructions { get; set; }
public int PrepTime { get; set;}
public int CookingTime { get; set; }
public IList<Wine> Wines { get; set; }
public IList<Pairing> Pairings { get; set; }
public ICollection<UsedIngredient> UsedIngredients { get; set; }
[NotMapped]
public string TagList { get; set; }
public IList<Tag> Tags { get; set; }
}
标签.cs
public class Tag
{
public int TagId { get; set; }
public string Name { get; set; }
public ICollection<Recipe> Recipes { get; set; }
}
连接表
创建表(
"dbo.TagRecipes",
c => new
{
Tag_TagId = c.Int(nullable: false),
Recipe_RecipeId = c.Int(nullable: false),
})
.PrimaryKey(t => new { t.Tag_TagId, t.Recipe_RecipeId })
.ForeignKey("dbo.Tags", t => t.Tag_TagId, cascadeDelete: true)
.ForeignKey("dbo.Recipes", t => t.Recipe_RecipeId, cascadeDelete: true)
.Index(t => t.Tag_TagId)
.Index(t => t.Recipe_RecipeId);
TagRepo - FindOrCreate 方法
public Tag FindOrCreateTag(string tagName)
{
Tag tag = context.Tags.Where(t => t.Name == tagName).Include("Recipes").FirstOrDefault();
if (tag == null)
{
tag = new Tag
{
Name = tagName,
Recipes = new List<Recipe>()
};
context.Tags.Add(tag);
}
return tag;
}
RecipeRepo - GetTagList
private IList<String> GetTagList(string tagString)
{
IList<string> tagList = new List<string>(Regex.Split(tagString, @"\,\s*"));
return tagList;
}
RecipeRepo - 分配标签
public void AssignTags(Recipe recipe, string tagString)
{
if (recipe.Tags == null)
recipe.Tags = new List<Tag>();
IList<string> tags = GetTagList(tagString);
foreach (string tagName in tags)
{
Tag tag = tagRepository.FindOrCreateTag(tagName);
if (tag.Recipes == null)
tag.Recipes = new List<Recipe>();
if (!tag.Recipes.Any(r => r.RecipeId == recipe.RecipeId))
tag.Recipes.Add(recipe);
if (recipe.Tags.All(t => t.TagId != tag.TagId))
recipe.Tags.Add(tag);
}
}
最后,我打电话给这个。
RecipeRepo - 更新
public bool Update(Recipe recipe)
{
if (recipe.TagList != null)
AssignTags(recipe, recipe.TagList);
Recipe dbEnt = context.Recipes.Find(recipe.RecipeId);
context.Entry(dbEnt).CurrentValues.SetValues(recipe);
return Save();
}
发生的事情是 - 它需要字符串,正确地拆分它 - 但在那之后,事情似乎有点南下。它不是简单地分配新标签,而是复制配方对象。
是什么,我失踪了?