// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved. See License.txt in the project root for license information.

namespace System.Data.Entity.Core.Query.PlanCompiler
{
    using System.Data.Entity.Core.Query.InternalTrees;

    // <summary>
    // Additional information for a "Table" node
    // AugmentedTableNode - the augmentedTableNode is a subclass of AugmentedNode,
    // and represents a ScanTable node. In addition to the information above, this
    // class keeps track of all join edges that this node participates in,
    // whether this table has been eliminated, and finally, how high in the tree
    // this node is visible
    // </summary>
    internal sealed class AugmentedTableNode : AugmentedNode
    {
        #region private state

        private readonly Table m_table;

        // The replacement table 
        private AugmentedTableNode m_replacementTable;

        // Is this table being moved
        private int m_newLocationId;

        // List of columns of this table that are nullable (and must have nulls pruned out)

        #endregion

        #region constructors

        // <summary>
        // Basic constructor
        // </summary>
        // <param name="id"> node id </param>
        // <param name="node"> scan table node </param>
        internal AugmentedTableNode(int id, Node node)
            : base(id, node)
        {
            var scanTableOp = (ScanTableOp)node.Op;
            m_table = scanTableOp.Table;
            LastVisibleId = id;
            m_replacementTable = this;
            m_newLocationId = id;
        }

        #endregion

        #region public properties

        // <summary>
        // The Table
        // </summary>
        internal Table Table
        {
            get { return m_table; }
        }

        // <summary>
        // The highest node (id) at which this table is visible
        // </summary>
        internal int LastVisibleId { get; set; }

        // <summary>
        // Has this table been eliminated
        // </summary>
        internal bool IsEliminated
        {
            get { return m_replacementTable != this; }
        }

        // <summary>
        // The replacement table (if any) for this table
        // </summary>
        internal AugmentedTableNode ReplacementTable
        {
            get { return m_replacementTable; }
            set { m_replacementTable = value; }
        }

        // <summary>
        // New location for this table
        // </summary>
        internal int NewLocationId
        {
            get { return m_newLocationId; }
            set { m_newLocationId = value; }
        }

        // <summary>
        // Has this table "moved" ?
        // </summary>
        internal bool IsMoved
        {
            get { return m_newLocationId != Id; }
        }

        // <summary>
        // Get the list of nullable columns (that require special handling)
        // </summary>
        internal VarVec NullableColumns { get; set; }

        #endregion
    }
}
