Ошибки: Как сохранить отношения многие ко многим в Castle Active Record? - PullRequest
2 голосов
/ 12 мая 2009

Я часами пытался получить отношения многих ко многим, чтобы сохранить с помощью Castle ActiveRecord. Что я делаю неправильно? Я не могу найти ничего в документации или в Google. В базе данных есть данные.

Курсы имеют много-много отношений с Книгами.

Тестовый код.

Database.Course c = new Database.Course();
c.Number = "CS 433";
c.Name = "Databases";
c.Size = 34;
c.Books = Database.Book.FindAll();
c.Save();

Также не работает

foreach(Database.Book b in Database.Book.FindAll()){
    c.Books.Add(b);
}

База данных классов

[ActiveRecord]
public class Course : ActiveRecordValidationBase<Course>
{
    private int? id;
    private string number;
    private string name;
    private string description;
    private int size; //number of students in class

    //references
    private IList books = new ArrayList();


    public override string ToString()
    {
        return FormattedName;
    }

    public string FormattedName
    {
        get
        {
            return string.Format("{0} - {1}", Number, Name);
        }
    }

    [PrimaryKey]
    public int? Id
    {
        get { return id; }
        set { id = value; }
    }

    [Property, ValidateNonEmpty]
    public string Number
    {
        get { return number; }
        set { number = value; }
    }

    [Property, ValidateNonEmpty]
    public string Name
    {
        get { return name; }
        set { name = value; }
    }

    [Property(ColumnType="StringClob")]
    public string Description
    {
        get { return description; }
        set { description = value; }
    }

    [Property]
    public int Size
    {
        get { return size; }
        set { size = value; }
    }

    [HasAndBelongsToMany(typeof(Book),
    Table = "BookCourse", ColumnKey = "course_id", ColumnRef = "book_id", Inverse = true)]
    public IList Books
    {
        get { return books; }
        set { books = value; }
    }
}

[ActiveRecord]
public class Book : ActiveRecordValidationBase<Book>
{
    private int? id;
    private string title;
    private string edition;
    private string isbn;
    private bool is_available_for_order;
    //relations
    private IList authors = new ArrayList();
    private IList bookordercount = new ArrayList();
    private IList courses = new ArrayList();
    private Inventory inventory;

    public override string ToString()
    {
        return FormattedName;
    }

    public string FormattedName
    {
        //*
        get {
            string str;
            if (Edition == null || Edition == "")
                str = Title;
            else
                str = string.Format("{0} ({1})", Title, Edition);

            if (Authors.Count != 0)
            {
                return string.Format("{0} by {1}", str, FormattedAuthors);
            }
            else
            {
                return str;
            }
        }
        /*/
        get
        {
            return Title;
        }
        //*/
    }

    public string FormattedAuthors
    {
        get
        {
            if (Authors.Count == 0) return "";

            StringBuilder sb = new StringBuilder();
            int i = 0, end = Authors.Count;
            foreach (Author a in Authors)
            {
                i++;
                sb.Append(a.FormattedName);
                if (i != end) sb.Append("; ");
            }
            return sb.ToString();
        }
    }


    [PrimaryKey]
    public int? Id
    {
        get { return id; }
        set { id = value; }
    }

    [Property, ValidateNonEmpty]
    public string Title
    {
        get { return title; }
        set { title = value; }
    }

    [Property]
    public string Edition
    {
        get { return edition; }
        set { edition = value; }
    }

    [Property, ValidateNonEmpty]
    public string Isbn
    {
        get { return isbn; }
        set { isbn = value; }
    }

    [Property]
    public bool IsAvailableForOrder
    {
        get { return is_available_for_order; }
        set { is_available_for_order = value; }
    }

    //relations

    [HasAndBelongsToMany(typeof(Author),
    Table = "BookAuthor", ColumnKey = "book_id", ColumnRef = "author_id")]
    public IList Authors
    {
        get { return authors; }
        set { authors = value; }
    }

    [HasMany(typeof(BookOrderCount), Table = "BookOrderCounts", ColumnKey = "BookId")]
    public IList BookOrderCount
    {
        get { return bookordercount; }
        set { bookordercount = value; }
    }

    [HasAndBelongsToMany(typeof(Course),
   Table = "BookCourse", ColumnKey = "book_id", ColumnRef = "course_id")]
    public IList Courses
    {
        get { return courses; }
        set { courses = value; }
    }

    [OneToOne]
    public Inventory Inventory
    {
        get { return inventory; }
        set { inventory = value; }
    }
}

1 Ответ

3 голосов
/ 12 мая 2009

Убедитесь, что вы положили Inverse = true, где вы хотите. Из Замка AR документы ,

Целесообразно выбрать одну из сторон отношение как владелец. Обратная сторона, не для записи, нужно использовать Обратные = верно.

Поместите значение Inverse = true на другую сторону отношений, например:

[HasAndBelongsToMany(typeof(Book),
    Table = "BookCourse", ColumnKey = "course_id", ColumnRef = "book_id")]
    public IList<Book> Books

[HasAndBelongsToMany(typeof(Course),
   Table = "BookCourse", ColumnKey = "book_id", ColumnRef = "course_id", Inverse = true)]
    public IList<Course> Courses

Вы также должны добавить атрибуты в начало обоих классов - в данный момент они не знают, на какие таблицы они отображаются. В настоящее время у вас есть это:

public class Course : ActiveRecordBase<Course>

Добавьте это (где «курс» - название таблицы вашего курса):

[ActiveRecord("course")]
public class Course : ActiveRecordBase<Course>
...