0

コンテキスト: http://docs.orchardproject.net/Documentation/Creating-1-n-and-nn-relations

これが私のトラックパーツのモデルです:

    public class TrackPartRecord : ContentPartRecord
    {
        public virtual IList<TrackInformationRecord> Tracks { get; set; }
    }

    public class TrackPart : ContentPart<TrackPartRecord>
    {
        public IList<TrackInformationRecord> Tracks
        {
            get { return Record.Tracks; }
        }
    }

    public class TrackInformationRecord
    {
        public virtual int Id { get; set; }
        public virtual int TrackPartId { get; set; }
        public virtual string Title { get; set; }
        public virtual string Description { get; set; }
        public virtual bool IsDeleted { get; set; }

        public virtual IList<SessionInformationRecord> Sessions { get; set; }
   }

    public class SessionInformationRecord
    {
        public virtual int Id { get; set; }
        public virtual int TrackId { get; set; }
        public virtual string Title { get; set; }
        public virtual string Description { get; set; }
        public virtual DateTime Timeslot { get; set; }
        public virtual bool HasEvaluation { get; set; }
        public virtual bool IsDeleted { get; set; }
    }

そして、ここに 3 つのテーブル (2 つの情報レコードと 1 つの部分レコード) を作成するための移行があります。

    // Creating table TrackInformationRecord
    SchemaBuilder.CreateTable("TrackInformationRecord", table => table
        .Column("Id", DbType.Int32, column => column.PrimaryKey().Identity())
        .Column("TrackPartId", DbType.Int32)
        .Column("Title", DbType.String)
        .Column("Description", DbType.String)
        .Column("IsDeleted", DbType.Boolean)
    );

    // Creating table TrackPartRecord
    SchemaBuilder.CreateTable("TrackPartRecord", table => table
        .ContentPartRecord()
    );

    ContentDefinitionManager.AlterPartDefinition("TrackPart", builder => builder.Attachable());

    // Creating table SessionInformationRecord
    SchemaBuilder.CreateTable("SessionInformationRecord", table => table
        .Column("Id", DbType.Int32, column => column.PrimaryKey().Identity())
        .Column("TrackId", DbType.Int32)
        .Column("Title", DbType.String)
        .Column("Description", DbType.String)
        .Column("Timeslot", DbType.DateTime)
        .Column("HasEvaluation", DbType.Boolean)
        .Column("IsDeleted", DbType.Boolean)
    );

コンテンツ アイテムはトラック パーツ (1 対 n の関係を形成する) を添付し、トラック レコードにはセッション レコードのリストがあります。

問題は、トラックを追加するときに始まります。最初に追加されたトラックが追加されます。最初の更新 (最初のトラックの追加、まだセッションはありません) の後、コンテンツ アイテムで何も更新できなくなりました。コードを実行しても、エラーや例外は発生しません (おそらく、Orchard の奥深くに埋もれているため、直接目に見えるものは何もスローされません)。

データベースに直接アクセスして、コンテンツ アイテムに関連するトラック レコードを削除すると、すべてをもう一度更新できます。

ログを確認したところ、次のことがわかりました。

2013-08-14 14:15:00,882 [30] NHibernate.AdoNet.AbstractBatcher - Could not execute command: UPDATE Ignite_EventsAgenda_SessionInformationRecord SET TrackInformationRecord_id = null WHERE TrackInformationRecord_id = @p0
System.Data.SqlServerCe.SqlCeException (0x80004005): The column name is not valid. [ Node name (if any) = ,Column name = TrackInformationRecord_id ]
   at System.Data.SqlServerCe.SqlCeCommand.ProcessResults(Int32 hr)
   at System.Data.SqlServerCe.SqlCeCommand.CompileQueryPlan()
   at System.Data.SqlServerCe.SqlCeCommand.ExecuteCommand(CommandBehavior behavior, String method, ResultSetOptions options)
   at System.Data.SqlServerCe.SqlCeCommand.ExecuteNonQuery()
   at NHibernate.AdoNet.AbstractBatcher.ExecuteNonQuery(IDbCommand cmd)
2013-08-14 14:15:00,888 [30] NHibernate.Util.ADOExceptionReporter - System.Data.SqlServerCe.SqlCeException (0x80004005): The column name is not valid. [ Node name (if any) = ,Column name = TrackInformationRecord_id ]
   at System.Data.SqlServerCe.SqlCeCommand.ProcessResults(Int32 hr)
   at System.Data.SqlServerCe.SqlCeCommand.CompileQueryPlan()
   at System.Data.SqlServerCe.SqlCeCommand.ExecuteCommand(CommandBehavior behavior, String method, ResultSetOptions options)
   at System.Data.SqlServerCe.SqlCeCommand.ExecuteNonQuery()
   at NHibernate.AdoNet.AbstractBatcher.ExecuteNonQuery(IDbCommand cmd)
   at NHibernate.Persister.Collection.AbstractCollectionPersister.Remove(Object id, ISessionImplementor session)
2013-08-14 14:15:00,891 [30] NHibernate.Util.ADOExceptionReporter - The column name is not valid. [ Node name (if any) = ,Column name = TrackInformationRecord_id ]
2013-08-14 14:15:00,894 [30] NHibernate.Event.Default.AbstractFlushingEventListener - Could not synchronize database state with session
NHibernate.Exceptions.GenericADOException: could not delete collection: [Ignite.EventsAgenda.Models.TrackInformationRecord.Sessions#1][SQL: UPDATE Ignite_EventsAgenda_SessionInformationRecord SET TrackInformationRecord_id = null WHERE TrackInformationRecord_id = @p0] ---> System.Data.SqlServerCe.SqlCeException: The column name is not valid. [ Node name (if any) = ,Column name = TrackInformationRecord_id ]

まず、「列名が無効です」という問題が発生する理由がわかりません。

次に、次の行がわかりません: UPDATE Ignite_EventsAgenda_SessionInformationRecord SET TrackInformationRecord_id = null WHERE TrackInformationRecord_id = @p0

列名 TrackInformationRecord_id はどこで取得しましたか?

ヘルプやアドバイスをいただければ幸いです。

4

3 に答える 3

0
public class TrackInformationRecord
{
    public virtual IList<SessionInformationRecord> Sessions { get; set; }
}

TrackInformationRecord... 親には多くの子がいると言いますSessions。Orchard は、裏で Fluent NHibernate の自動マッピングを使用して NHibernate マッピングを生成していると推測しています。1 対多の関係に対する FluentNH のデフォルトの列名は です{classNameOfParent}_id。したがってTrackInformationRecord_id、したがってエラー-その名前の列を作成したことはありません。

私は Orchard に詳しくないので、この動作をカスタマイズする方法が提供されているかどうかはわかりません。FluentNH は方法 ( https://github.com/jagregory/fluent-nhibernate/wiki/Auto-mapping#overrides ) を提供しますが、Orchard がその機能を公開しているかどうかはわかりません。マッピングのオーバーライドを配置する場所が見つかった場合は、次のように機能するはずです。

public class TrackInformationRecordOverride
    : IAutoMappingOverride<TrackInformationRecord>
{
    public void Override(AutoMapping<TrackInformationRecord> mapping)
    {
        mapping.HasMany(x => x.Sessions)
            .KeyColumn("TrackId"); // ... assuming TrackId is the column you wanted.
    }
}
于 2013-08-15T23:11:44.707 に答える