ASP.Net Core frente a MySQL
La tabla Student y la tabla Course se unen con la tabla de unión StudentCourse:
Student StudentCourse Course ========= ============ ======= PK | ID FK | StudentID PK | ID | Name FK | CourseID | NameUn estudiante cambia su curso, por lo que el administrador debe cambiar CourseID en la tabla de unión StudentCourse.
Pero no tengo acceso directo a la tabla de unión debido a:
public class AppDbContext { public DbSet<CourseModel> CourseModels { get; set; } public DbSet<StudentModel> StudentModels { get; set; } protected override void OnModelCreating(ModelBuilder builder) { base.OnModelCreating(builder); builder.Entity<StudentCourse>() .HasKey(t => new { t.StudentId, t.CourseId }); builder.Entity<StudentCourse>() .HasOne(sc => sc.Student) .WithMany(s => s.StudentCourse) .HasForeignKey(sc => sc.StudentId); builder.Entity<StudentCourse>() .HasOne(sc => sc.Course) .WithMany(s => s.StudentCourse) .HasForeignKey(sc => sc.CourseId); } }Entonces no puedo ejecutar este comando SQL directamente:
UPDATE StudentCourse SET CourseId = '9A414E30-DA37-48ED-105E-08D8129A967A' WHERE StudentId = 'A1F38C12-AE65-464C-C489-08D814F4CDDC'Creo que tengo que usar Inner Join. Mi lógica es:
[HttpGet] public IActionResult ChangeCourse(Guid id) { IQueryable<CourseModel> courses = courseModel.GetCourses(); ViewBag.Courses = new SelectList(courses, "Id", "Name"); var course = courseModel.GetCourseById(id); return View(course); } [HttpPost] public IActionResult ChangeCourse(CourseModel newCourse) { // I know student's id, so I can get his old course id Guid oldCourseId = (from ... in ...).SingleOrDefault(); // Then just change and save oldCourseId = newCourse.Id; context.SaveChanges(); return RedirectToAction(); }Tengo el comando SQL para obtener una identificación de curso anterior:
SELECT CourseId FROM StudentModels L INNER JOIN StudentCourse R ON L.Id = R.StudentId WHERE L.Id = 'A1F38C12-AE65-464C-C489-08D814F4CDDC'Entonces las preguntas son:
Intenté esto pero obtuve la lista de ID:
from student in context.StudentModels join cours in context.CourseModels on student.Id equals studentId select cours.IdTodavía no soy bueno en LINQ. Por favor ayuda.
Parece haber una relación de muchos a muchos entre Estudiantes y Cursos. Cada Estudiante sigue cero o más Cursos, y cada Curso es seguido por cero o más Estudiantes. Por eso necesitas una mesa de unión.
Tu escribiste:
Un estudiante cambia de curso.
Bueno, como los Estudiantes pueden seguir varios Cursos, no se puede decir que un Estudiante cambia de curso. Puede decir que un estudiante sigue un nuevo curso y/o deja de seguir otro curso.
Si ha seguido las convenciones del marco de la entidad, tendrá clases similares a las siguientes:
class Student { public int Id {get; set;} ... // Every Student follows zero or more Courses (many-to-many) public virtual ICollection<Course> Courses {get; set;} } class Course { public int Id {get; set;} ... // Every Course is followed by zero or more Courses (many-to-many) public virtual ICollection<Student> Students {get; set;} }Esto es todo lo que el marco de la entidad necesita saber para detectar su relación de muchos a muchos. Creará automáticamente una tabla de unión para usted y la usará cuando sea necesario.
Si desea cambiar cualquier elemento en el marco de la entidad, deberá obtener el elemento completo y usar Include para las colecciones relacionadas.
Para dejar de seguir un curso y comenzar a seguir un nuevo curso:
int studentId = ... int courseIdToStop = ... int courseIdToAttend = ... // get the student to change; include his courses Student studentToChange = dbContext.Students .Include(student => student.Courses) .Where(student => student.Id == studentId) .FirstOrDefault(); // Stop the course Course courseToStop = studentToChange.Courses .Where(course => course.Id == courseIdToStop) .FirstOrDefault(); if (courseToStop != null) { // This Student follows this cours; stop it: studentToChange.Courses.Remove(courseToStop); } Course courseToStart = dbContext.Courses .Where(course => course.Id == courseIdToStart) .FirstOrDefault(); // only start the course if course exists and not already following if (courseToStart != null && !studentToChange.Courses.Contains(courseToStart)) { studentToChange.Courses.Add(courseToStart); } dbContext.SaveChanges();