#c# #.net #entity-framework #linq-to-entities
#c# #.net #entity-framework #linq-to-entities
Вопрос:
Я столкнулся с проблемой, когда существует отношение «один ко многим», и я пытаюсь обновить данные в одной из таблиц и таблице ссылок.
- У меня есть две таблицы (User, роли) и одна таблица ссылок (UserRoles).
- У пользователя много ролей.
- Роли предопределены, и есть только 3 строки, как показано ниже.
Я хочу обновить пользователя с помощью ролей. Я не могу выполнить следующий код. Пожалуйста, поделитесь своими вводными данными.
Original
User : John
Roles : Admin, User
Update to
User : John
Roles : User
Это структура таблицы
User
UserID : Pk
Name
Roles //Data is not added in this table, Data already exists in this table
RoleID : Pk
Name
RoleID Name
1 Admin
2 User
3 None
UserRoles
UserID : PK
RoleID : Pk
Соответствующие объекты
User
UserId
Name
EntityCollection<Role> Roles
Role
RoleId
Name
EntityCollection<User> Users
Я попытался со следующим кодом
public void update(int userId, string newusername, list<int> roleList)
{
using (DBEntites context = new DBEntites())
{
User objUserInDb = new User();
objUserInDb.UserID = userId;
Context.Users.Attach(objUserInDb);
objUserInDb.Name = newusername;
objUserInDb.Roles.Clear();
// TRIED TO USE The remove method objUserInDb.Roles.Remove(entity),
// is returning false
foreach (long pkIDToAdd in roleList)
{
Role objRoleInDb = new Role();
objRoleInDb.RoleId = pkIDToAdd;
// GIVES EXCEPTION
//An object with the same key already exists in the ObjectStateManager.
//The ObjectStateManager cannot track multiple objects with the same
//
context.Roles.Attach(objRoleInDb);
objUserInDb.Roles.Add(objRoleInDb);
}
}
}
Ответ №1:
Исключение связано с тем, что некоторые роли уже загружены в контекст. Вы можете сделать так,
foreach (long pkIDToAdd in roleList)
{
var role= context.RiskTypes.FirstOrDefault(r=>r.id==pkIDToAdd );
objUserInDb.Roles.Add(role);
}
Комментарии:
1. Спасибо, Джаянта. На самом деле я пытаюсь избежать вызова базы данных, используя метод FirstOrDefault и, следовательно, используя метод Attach . Я попытался использовать метод TryGetObjectByKey с вновь созданным типом риска, используя Role objRole = new Role(); objRole . RoleId = 1; но я вижу, что ключ объекта для objRole равен нулю, а EntityState отсоединен. когда я пытаюсь использовать метод Attach, он выдает исключение объекта с ключом, который уже существует. Я хочу избежать использования жестко запрограммированной строки для создания нового ключа объекта и проверки его наличия. Надеюсь, я понял
2. Да, я понял. Вы можете проверить
context.Entry(role).State
, и если этоDetached
так, вы можете прикрепить его снова.