2

私のエンティティと NHibernate の間の関係をどうするかをよりよく理解するのを手伝ってくれませんか?

どの操作を手動で行う必要があるか、NHibernate がどの操作を行うか (または行わないか) を理解するのが難しい場合があります。

私はこれらの2つのエンティティを持っています:

public class Position : BaseEntity<int, Position>
{
    private IList<Player> allPlayers = new List<Player>();

    public Position()
    {

    }

    public Position(string name, int number)
        : this()
    {
        Name = name;
        Number = number;
    }

    public string Name { get; set; }
    public int Number { get; set; }
}

public class Player : BaseEntity<int, Player>
{
    public Player()
    {
        Visible = true;
    }

    public Player(string firstName, string lastName, int defaultNumber, Sex sex = Sex.Male, Position defaultPosition = null)
        : this()
    {
        FirstName = firstName;
        LastName = lastName;
        DefaultNumber = defaultNumber;
        Sex = sex;
        DefaultPosition = defaultPosition;
    }

    public string FirstName { get; set; }
    public string LastName { get; set; }
    public Position DefaultPosition { get; set; }
}

流暢なマッピングは次のとおりです。

public class PositionMap : ClassMap<Position>
{
    public PositionMap()
    {
        Id(pp => pp.Id)
            .GeneratedBy.Increment();

        Map(pp => pp.Name)
            .Not.Nullable();

        Map(pp => pp.Number)
            .Not.Nullable();

        HasMany<Player>(Reveal.Member<Position>("allPlayers"))
            .Access.CamelCaseField();
    }
}

public class PlayerMap : ClassMap<Player>
{
    public PlayerMap()
    {
        Table("Players");

        Id(p => p.Id)
            .GeneratedBy.Increment();

        Map(p => p.FirstName)
            .Not.Nullable()
            .UniqueKey("Players_Unique_FirstName_LastName");

        Map(p => p.LastName)
            .Not.Nullable()
            .UniqueKey("Players_Unique_FirstName_LastName");

        References(p => p.DefaultPosition);
    }
}

ご覧のとおり、1 人のプレイヤーは 1 つのポジションを持ちますが、ポジションを持たない場合もあります (つまり、DefaultPosition は null 可能です)。

ここに私の質問があります:

  1. ポジションをプレイヤーの DefaultPosition に関連付けるとき、Position のヘルパー メソッドを介してこれを行う必要がありますか? (AddPlayer、DeletePlayer など)

ポジションを削除するとき、このポジションを持つすべてのプレーヤーが代わりに null DefaultPosition を持つようにしたいと思います。

  1. 位置のフィールド allPlayers を手動でクリアし、関連するすべてのプレーヤーの DefaultPosition に null を手動で設定する必要がありますか?

  2. NHibernate がDELETE FROM Positions WHERE Id...のみを実行し、関係するプレイヤーのフィールド DefaultPOsition を更新しないのはなぜですか? PositionMap の HasMany に Cascade.Delete を追加しようとしましたが、何も変わりません。それを行うカスタムクエリを実行する必要がありますか?

前もって感謝します

4

1 に答える 1

2

Q1 Players on Position のプロパティを追加する場合、それらのヘルパー メソッドは必要ありません。

public class Position : BaseEntity<int, Position>
{
    private IList<Player> allPlayers = new List<Player>();

    //read only
    public IList<Player> Players { get { return allPlayers;} }

    //... rest of class omitted
}

次に、次のように呼び出します。

var position = new Position();
position.Players.Add(new Player());

Q2、Q3 単純化するヘルパー メソッドを配置できます。

何かのようなもの:

public class Position : BaseEntity<int, Position>
{
    public void RemoveAll()
    {
       // null out the position on players
       foreach(var player in allPlayers)
       {
           player.Position = null; // SETS PositionId FIELD IN PLAYER TABLE TO NULL
       }
       allPlayers.Clear();
    }

    // ... rest of class omitted
}

次のような呼び出しで:

using(var session = SessionFactory.GetCurrentSession())
{
   using(var tx = session.BeginTransaction())
   {
      position.RemoveAll();
      position.Delete();
      tx.Commit();
   }
}

プレイヤーはポジションを超えて存続しますが、ポジションが削除されるため、カスケードは使用したくないでしょう。Cascade は削除用であり、実際には ID の更新用ではありません。たとえば、オーダーを削除して、そのすべての広告申込情報をカスケードします。

于 2010-06-29T17:51:51.813 に答える