internal EntityListItemsCollection(DataContext dataContext, SPCList list)
 {
     this.m_list                    = list;
     this.m_DataContext             = dataContext;
     m_DerivedTypes                 = typeof(TEntity).GetDerivedTypes();
     m_EntityPropertiesDictionary   = new Dictionary <string, Dictionary <string, StorageItem> >();
     m_ListItemPropertiesDictionary = new Dictionary <string, StorageItemsList>();
     foreach (var _typeidx in m_DerivedTypes)
     {
         StorageItemsList _si = StorageItem.CreateStorageDescription(_typeidx.Value, true);
         m_EntityPropertiesDictionary.Add(_typeidx.Key, _si.Values.ToDictionary <StorageItem, string>(storageItem => storageItem.PropertyName));
         m_ListItemPropertiesDictionary.Add(_typeidx.Key, _si);
     }
 }
        private static void Synchronize <TSQL, TSP>(Table <TSQL> sqlTable, EntityList <TSP> spList, ProgressChangedEventHandler progressChanged, Dictionary <string, string> mapping, bool port2210)
            where TSQL : class, SharePoint.Client.Link2SQL.IItem, INotifyPropertyChanged, new()
            where TSP : Linq.Item, ITrackEntityState, ITrackOriginalValues, INotifyPropertyChanged, INotifyPropertyChanging, new()
        {
            progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Reading the table {0} from SharePoint website.", typeof(TSP).Name)));
            List <TSP> _scrList = spList.ToList <TSP>();

            progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Reading the table {0} from SQL database.", typeof(TSQL).Name)));
            Dictionary <int, IItem> _dictinary = sqlTable.Where <TSQL>(x => !x.OnlySQL).ToDictionary <TSQL, int, IItem>(x => x.ID, y => (SharePoint.Client.Link2SQL.IItem)y);

            progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Synchronization {0} elements in the SharePoint source tables with the {1} element in the SQL table.", _scrList.Count, _dictinary.Count)));
            //create descriptors using reflection
            Dictionary <string, StorageItemsList> _spDscrpt  = StorageItem.CreateStorageDescription(typeof(TSP));
            Dictionary <string, SQLStorageItem>   _sqlDscrpt = SQLStorageItem.CreateStorageDescription(typeof(TSQL), mapping);
            int           _archivalCount    = 0;
            int           _archivalCountOld = 0;
            int           _counter          = 0;
            int           _counterOld       = 0;
            int           _itemChanges      = 0;
            int           _itemChangesOld   = 0;
            bool          _itemChanged;
            Action <TSP>  _port    = x => { };
            List <string> _changes = new List <string>();

            if (port2210 && typeof(IArchival).IsAssignableFrom(typeof(TSP)))
            {
                _port = x => { ((IArchival)x).Archival = false; _archivalCount++; };
                progressChanged(1, new ProgressChangedEventArgs(1, "The table will be updated new software version"));
            }
            int _loopCounter = 0;

            foreach (TSP _spItem in _scrList)
            {
                _port(_spItem);
                SharePoint.Client.Link2SQL.IItem _sqlItem = default(SharePoint.Client.Link2SQL.IItem);
                if (!_dictinary.TryGetValue(_spItem.Id.Value, out _sqlItem))
                {
                    _sqlItem         = new TSQL();
                    _sqlItem.OnlySQL = false;
                    _dictinary.Add(_spItem.Id.Value, _sqlItem);
                    sqlTable.InsertOnSubmit((TSQL)_sqlItem);
                }
                Microsoft.SharePoint.Linq.ContentTypeAttribute _attr = _spItem.GetType().GetContentType();
                _itemChanged = false;
                Synchronize <TSQL, TSP>(
                    (TSQL)_sqlItem,
                    _spItem, _spDscrpt[_attr.Id],
                    _sqlDscrpt, progressChanged,
                    spList.DataContext,
                    (x, y) =>
                {
                    _counter++;
                    _changes.Add(y.PropertyName);
                    _itemChanged = true;
                });
                if (_itemChanged)
                {
                    _itemChanges++;
                }
                _loopCounter++;
                if (_loopCounter > 10000)
                {
                    progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Intermediate: submitting {0} changes on {1} list rows to SQL database", _counter - _counterOld, _itemChanges - _itemChangesOld)));
                    sqlTable.Context.SubmitChanges();
                    if (_archivalCount > 0)
                    {
                        progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Intermediate: update to Rel 2.10 Submitting {0} Archival bit changes", _archivalCount - _archivalCountOld)));
                        spList.DataContext.SubmitChanges();
                    }
                    _loopCounter    = 0;
                    _counterOld     = _counter;
                    _itemChangesOld = _itemChanges;
                }
            }
            progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Submitting total {0} changes on {1} list rows to SQL database", _counter, _itemChanges)));
            sqlTable.Context.SubmitChanges();
            if (_archivalCount > 0)
            {
                progressChanged(1, new ProgressChangedEventArgs(1, String.Format("Update to Rel 2.10 Submitting total {0} Archival bit changes", _archivalCount)));
                spList.DataContext.SubmitChanges();
            }
        }