private bool SetUnversionedField(CustomSqlItemData targetItem, SqlItemFieldValue currentField, int version, string language)
        {
            // check for corruption in SQL server tables (field values in wrong table) - an unversioned field should have a version less than 1 (SQL sends -1 back for unversioned) and a language
            if (version >= 1)
            {
                Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {currentField.FieldId} (unversioned) had a value in the versioned fields table. The field value will be ignored.", this);
                return(false);
            }

            if (string.IsNullOrEmpty(language))
            {
                Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {currentField.FieldId} (unversioned) had a value in the shared fields table. The field value will be ignored.", this);
                return(false);
            }

            foreach (var languageFields in targetItem.RawUnversionedFields)
            {
                if (languageFields.Language.Name.Equals(language, StringComparison.Ordinal))
                {
                    languageFields.RawFields.Add(currentField);
                    return(true);
                }
            }

            var newLanguage = new SqlItemLanguage();

            newLanguage.Language = new CultureInfo(language);
            newLanguage.RawFields.Add(currentField);

            targetItem.RawUnversionedFields.Add(newLanguage);

            return(true);
        }
        private bool SetSharedField(CustomSqlItemData targetItem, SqlItemFieldValue currentField, int version, string language)
        {
            // check for corruption in SQL server tables (field values in wrong table) - shared field should have neither language nor version one or greater (SQL sends version -1 for shared)
            if (version >= 1)
            {
                Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {{{currentField.FieldId}}} (shared) had a value in the versioned fields table. The field value will be ignored.", this);
                return(false);
            }

            if (!string.IsNullOrEmpty(language))
            {
                Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {currentField.FieldId} (shared) had a value in the unversioned fields table. The field value will be ignored.", this);
                return(false);
            }

            targetItem.RawSharedFields.Add(currentField);

            return(true);
        }
        private bool SetVersionedField(CustomSqlItemData targetItem, string language, int version, SqlItemFieldValue currentField)
        {
            // check for corruption in SQL server tables (field values in wrong table) - a versioned field should have both a language and a version that's one or greater
            if (version < 1)
            {
                if (string.IsNullOrEmpty(language))
                {
                    Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {currentField.FieldId} (versioned) had a value in the shared fields table. The field value will be ignored.", this);
                }
                else
                {
                    Log.Error($"[Dilithium] Data corruption in {targetItem.DatabaseName}://{{{targetItem.Id}}}! Field {currentField.FieldId} (versioned) had a value in the unversioned fields table. The field value will be ignored.", this);
                }
                return(false);
            }

            foreach (var versionFields in targetItem.RawVersions)
            {
                if (versionFields.Language.Name.Equals(language, StringComparison.Ordinal) && versionFields.VersionNumber == version)
                {
                    versionFields.RawFields.Add(currentField);
                    return(true);
                }
            }

            var newVersion = new SqlItemVersion
            {
                Language      = new CultureInfo(language),
                VersionNumber = version
            };

            newVersion.RawFields.Add(currentField);

            targetItem.RawVersions.Add(newVersion);

            return(true);
        }
        private void IngestItemData(SqlDataReader reader, string rootParentItemPath)
        {
            // 8087 = prime. Lots of items will load in so we start with a large capacity to minimize expansions.
            // Dictionary expands using primes, hence our choice.
            var results = new Dictionary <Guid, CustomSqlItemData>(8087);

            while (reader.Read())
            {
                var currentItem = new CustomSqlItemData
                {
                    Id           = reader.GetGuid(0),
                    Name         = reader.GetString(1),
                    TemplateId   = reader.GetGuid(2),
                    BranchId     = reader.GetGuid(3),
                    ParentId     = reader.GetGuid(4),
                    Path         = rootParentItemPath + reader.GetString(5),
                    DatabaseName = Database.Name
                };

                results.Add(currentItem.Id, currentItem);
            }

            _itemsById = results;
        }