예제 #1
0
 public void MetadataCache_Test2b()
 {
     using (var verify = new Verify())
     {
         verify.ArgumentNullException("type", () => MetadataCache.GetMetadata((TypeInfo)null));
     }
 }
예제 #2
0
        public void MetadataCache_MakeNullable_Object()
        {
            var x = MetadataCache.GetMetadata(typeof(object));
            var y = x.MakeNullable().TypeInfo;

            Assert.AreEqual(typeof(object), y);
        }
예제 #3
0
        public void MetadataCache_MakeNullable_Nullable_Int()
        {
            var x = MetadataCache.GetMetadata(typeof(int?));
            var y = x.MakeNullable().TypeInfo;

            Assert.AreEqual(typeof(int?), y);
        }
예제 #4
0
        public void MetadataCache_IsNullable_Object()
        {
            var x = MetadataCache.GetMetadata(typeof(object));
            var y = x.IsNullable;

            Assert.AreEqual(true, y);
        }
예제 #5
0
        public static void CheckForOverlaps(object?firstObject, object?secondObject, string errorFormat)
        {
            if (firstObject == null)
            {
                return;
            }
            if (secondObject == null)
            {
                return;
            }

            var leftList  = MetadataCache.GetMetadata(firstObject.GetType()).Properties;
            var rightList = MetadataCache.GetMetadata(secondObject.GetType()).Properties;

            foreach (var property1 in leftList)
            {
                foreach (var property2 in rightList)
                {
                    if (property1.Name.Equals(property2.Name, StringComparison.OrdinalIgnoreCase))
                    {
                        throw new InvalidOperationException(string.Format(CultureInfo.InvariantCulture, errorFormat, property1.Name));
                    }
                }
            }
        }
예제 #6
0
        public void FakeCorLib()
        {
            using (MetadataCache.LockAndClean())
            {
                var assemblies = MetadataTestHelpers.GetSymbolsForReferences(new[] { TestReferences.SymbolsTests.CorLibrary.FakeMsCorLib.dll });

                MetadataOrSourceAssemblySymbol msCorLibRef = (MetadataOrSourceAssemblySymbol)assemblies[0];

                for (int i = 1; i <= (int)SpecialType.Count; i++)
                {
                    Assert.True(msCorLibRef.KeepLookingForDeclaredSpecialTypes);
                    var t = msCorLibRef.GetSpecialType((SpecialType)i);
                    Assert.Equal((SpecialType)i, t.SpecialType);

                    if (t.SpecialType == SpecialType.System_Object)
                    {
                        Assert.NotEqual(TypeKind.Error, t.TypeKind);
                    }
                    else
                    {
                        Assert.Equal(TypeKind.Error, t.TypeKind);
                        Assert.Same(msCorLibRef, t.ContainingAssembly);
                    }

                    Assert.Same(msCorLibRef, t.ContainingAssembly);
                }

                Assert.False(msCorLibRef.KeepLookingForDeclaredSpecialTypes);
            }
        }
예제 #7
0
        /// <summary>
        /// Writes the rows with the specified write options.
        /// </summary>
        /// <typeparam name="TInfluxRow"></typeparam>
        /// <param name="db"></param>
        /// <param name="measurementName"></param>
        /// <param name="rows"></param>
        /// <param name="options"></param>
        /// <returns></returns>
        public Task WriteAsync <TInfluxRow>(string db, string measurementName, IEnumerable <TInfluxRow> rows, InfluxWriteOptions options)
            where TInfluxRow : new()
        {
            List <HttpContent> contents = new List <HttpContent>();

            foreach (var groupOfRows in rows.GroupBy(x => x.GetType()))
            {
                var info = MetadataCache.GetOrCreate(groupOfRows.Key);

                var c = info.CreateHttpContentFor(this, groupOfRows, measurementName, options);
                contents.Add(c);
            }

            if (contents.Count == 0)
            {
                return(TaskHelpers.CompletedTask);
            }
            var content = contents.Count == 1 ? contents[0] : new MultiContent(contents);


            if (options.UseGzip)
            {
                content = new GzipContent(content);
            }
            return(PostInternalIgnoreResultAsync(CreateWriteUrl(db, options), content));
        }
예제 #8
0
        public void GetMetadata_ReplacesCache_IfFileTimestampChanged()
        {
            // Arrange
            var directory        = _testAssetsManager.CreateTestDirectory();
            var metadataCache    = new MetadataCache();
            var assemblyFilePath = LoaderTestResources.Delta.WriteToFile(directory.Path, "Delta.dll");

            // Act 1
            var result = metadataCache.GetMetadata(assemblyFilePath);

            // Assert 1
            Assert.NotNull(result);
            var entry = Assert.Single(metadataCache.Cache.TestingEnumerable);

            Assert.Same(result, entry.Value.Metadata);

            // Act 2
            // Update the timestamp of the file
            File.SetLastWriteTimeUtc(assemblyFilePath, File.GetLastWriteTimeUtc(assemblyFilePath).AddSeconds(1));
            var cacheResult = metadataCache.GetMetadata(assemblyFilePath);

            // Assert 2
            Assert.NotSame(result, cacheResult);
            entry = Assert.Single(metadataCache.Cache.TestingEnumerable);
            Assert.Same(cacheResult, entry.Value.Metadata);
        }
예제 #9
0
        internal static void WriteCustomPropertyFile(MetadataCache mdc,
                                                     string pathRoot,
                                                     string record)
        {
            // Theory has it that the fwdata file is all sorted.
            var cpElement = DataSortingService.SortCustomPropertiesRecord(record);
            // Not this one, since it leaves out the temporary "key' attr. var cpElement = XElement.Parse(SharedConstants.Utf8.GetString(record));
            // Add custom property info to MDC, since it may need to be sorted in the data files.
            var hasCustomProperties = false;

            foreach (var propElement in cpElement.Elements(SharedConstants.CustomField))
            {
                hasCustomProperties = true;
                var className         = propElement.Attribute(SharedConstants.Class).Value;
                var propName          = propElement.Attribute(SharedConstants.Name).Value;
                var typeAttr          = propElement.Attribute("type");
                var adjustedTypeValue = MetadataCache.AdjustedPropertyType(typeAttr.Value);
                if (adjustedTypeValue != typeAttr.Value)
                {
                    typeAttr.Value = adjustedTypeValue;
                }
                var customProp = new FdoPropertyInfo(
                    propName,
                    typeAttr.Value,
                    true);
                mdc.AddCustomPropInfo(
                    className,
                    customProp);
            }
            if (hasCustomProperties)
            {
                mdc.ResetCaches();
            }
            WriteCustomPropertyFile(Path.Combine(pathRoot, SharedConstants.CustomPropertiesFilename), cpElement);
        }
예제 #10
0
 public ModuleMetadata(Stream byteStream, MetadataCache<AssemblyMetadata> assemblyCache)
     : base(byteStream)
 {
     FilePath = byteStream.DeserializeString();
     AssemblyId = byteStream.DeserializeUint32();
     Assembly = assemblyCache[AssemblyId];
 }
예제 #11
0
        public KeyJoinAppender(ILink <Tuple <List <T1>, List <T2> > > previousLink, Func <T1, TKey> primaryKeyExpression, Func <T2, TKey> foreignKeyExpression, string targetCollectionName, JoinOptions joinOptions) : base(previousLink)
        {
            if (previousLink == null)
            {
                throw new ArgumentNullException("previousLink", "previousLink is null.");
            }
            if (primaryKeyExpression == null)
            {
                throw new ArgumentNullException("primaryKeyExpression", "primaryKeyExpression is null.");
            }
            if (foreignKeyExpression == null)
            {
                throw new ArgumentNullException("foreignKeyExpression", "foreignKeyExpression is null.");
            }
            if (string.IsNullOrEmpty(targetCollectionName))
            {
                throw new ArgumentException("targetCollectionName is null or empty.", "targetCollectionName");
            }

            var targetPropertyStub = MetadataCache.GetMetadata(typeof(T1)).Properties[targetCollectionName]; //don't inline this variable.

            m_TargetCollectionExpression = (p) => (ICollection <T2>)targetPropertyStub.InvokeGet(p);


            m_ForeignKeyExpression = foreignKeyExpression;
            m_PrimaryKeyExpression = primaryKeyExpression;
            m_JoinOptions          = joinOptions;
        }
        /// <summary>
        /// Validate a CmObject instance, as represented by an XElement.
        ///
        /// A CmObject may, or may not, contain nested CmObjects.
        /// </summary>
        /// <returns>a String with the first problem found in the CmObject, or null, if no problems were found.</returns>
        /// <exception cref="ArgumentNullException">Thrown is either <paramref name="mdc"/> of <paramref name="obj"/> are null.</exception>
        internal static string ValidateObject(MetadataCache mdc, XElement obj)
        {
            Guard.AgainstNull(mdc, "mdc");
            Guard.AgainstNull(obj, "obj");

            return ValidateObject(mdc, obj, "");
        }
        private void InitializeProperties(JadeSoftware.Joob.Client.JoobConnection connection)
        {
            MetadataCache <JoobGeometryMetadata> .LoadData(null);

            metaClass    = new JadeSoftware.Joob.ClassMetadata(connection, typeof(StateByGeomRTree), "StateByGeomRTree", "RootSchema.JoobSpatialDemoSchema", JadeSoftware.Joob.DuplicationOption.NotAllowed);
            this.GeomKey = metaClass.CheckMemberKey(typeof(StateByGeomRTree), typeof(State), "geom", typeof(JoobGeometry), JadeSoftware.Joob.CaseSensitivityOption.Sensitive, JadeSoftware.Joob.KeyOrderOption.Ascending);
        }
예제 #14
0
        /// <inheritdoc />
        public Task <AddOrGetContentHashListResult> AddOrGetContentHashListAsync(Context context, StrongFingerprint strongFingerprint, ContentHashListWithDeterminism contentHashListWithDeterminism, CancellationToken cts, UrgencyHint urgencyHint)
        {
            return(WithOperationContext(
                       context,
                       cts,
                       operationContext =>
            {
                return operationContext.PerformOperationAsync(
                    DistributedTracer,
                    async() =>
                {
                    // Metadata cache assumes no guarantees about the fingerprints added, hence invalidate the cache and serve the request using backing store
                    var cacheResult = await MetadataCache.DeleteFingerprintAsync(context, strongFingerprint);
                    if (!cacheResult.Succeeded)
                    {
                        context.Error($"Error while removing fingerprint {strongFingerprint} from metadata cache. Result: {cacheResult}.");
                    }

                    return await _innerCacheSession.AddOrGetContentHashListAsync(context, strongFingerprint, contentHashListWithDeterminism, cts, urgencyHint);
                },
                    traceOperationStarted: true,
                    extraStartMessage: $"StrongFingerprint=({strongFingerprint}) {contentHashListWithDeterminism.ToTraceString()}",
                    extraEndMessage: _ => $"StrongFingerprint=({strongFingerprint}) {contentHashListWithDeterminism.ToTraceString()}");
            }));
        }
예제 #15
0
 public void SetUp()
 {
     _mocks = new MockRepository();
     _enumeratedTypeReflectorMock = _mocks.StrictMock <IEnumerationReflector> ();
     _statePropertyReflector      = new StatePropertyReflector(_enumeratedTypeReflectorMock);
     _cache = new MetadataCache();
 }
예제 #16
0
        private static bool EnsureBasicValueTypePropertyElementsExist(MetadataCache mdc, FdoClassInfo classInfo, XElement element, IEnumerable <string> basicPropertyNames, out string result)
        {
            result = null;

            if (mdc.ModelVersion < 7000066)
            {
                return(true);                // The value type data types are only required at DM 7000066, and higher.
            }
            foreach (var basicPropertyName in basicPropertyNames)
            {
                var currentPropName  = basicPropertyName;
                var isCustomProperty = classInfo.GetProperty(basicPropertyName).IsCustomProperty;
                var propertyElement  = isCustomProperty
                                        ? element.Elements("Custom").FirstOrDefault(propElement => propElement.Attribute(SharedConstants.Name).Value == currentPropName)
                                        : element.Element(currentPropName);
                if (propertyElement != null)
                {
                    continue;
                }

                result = string.Format("Required basic property element '{0}' of class '{1}' is missing.", currentPropName, classInfo.ClassName);
                return(false);
            }
            return(true);
        }
        static StreamingObjectConstructor()
        {
            var methodType = typeof(StreamingObjectConstructor <T>).GetMethods(BindingFlags.NonPublic | BindingFlags.Static).Where(m => m.Name == "CreateMappedProperty_Helper").Single();

            var mappedProperties     = new List <MappedProperty <T> >();
            var decomposedProperties = new List <MappedProperty <T> >();

            foreach (var property in MetadataCache.GetMetadata(typeof(T)).Properties)
            {
                if (property.MappedColumnName != null)
                {
                    if (property.CanWrite)
                    {
                        var genericMethod = methodType.MakeGenericMethod(property.PropertyType);
                        var mapper        = (MappedProperty <T>)genericMethod.Invoke(null, new object[] { property.MappedColumnName, property });

                        mappedProperties.Add(mapper);
                    }

                    if (property.Decompose)
                    {
                        decomposedProperties.Add(new MappedProperty <T>(property.MappedColumnName, property));
                    }
                }
            }

            s_AllMappedProperties  = mappedProperties.ToImmutableArray();
            s_DecomposedProperties = decomposedProperties.ToImmutableArray();
        }
 public void SetUp()
 {
     _mocks = new MockRepository();
     _enumeratedTypeReflectorMock = _mocks.StrictMock <IEnumerationReflector> ();
     _abstractRoleReflector       = new AbstractRoleReflector(_enumeratedTypeReflectorMock);
     _cache = new MetadataCache();
 }
 public SamplingCallTreeElem(
     Stream byteStream,
     ICallTreeElemFactory <SamplingCallTreeElem> callTreeElemFactory,
     MetadataCache <MethodMetadata> methodCache)
     : base(byteStream, callTreeElemFactory, methodCache)
 {
 }
예제 #20
0
        public void ConvertAndSave_LocalizedStateName()
        {
            CultureInfo[] cultures = CreateCultureInfos("de", "en");
            LocalizingMetadataConverter converter = new LocalizingMetadataConverter(_localizationConverter, cultures);
            string               filename         = "metadata.xml";
            MetadataCache        cache            = new MetadataCache();
            List <EnumValueInfo> states           = new List <EnumValueInfo> ();

            states.Add(new EnumValueInfo("Remotion.Security.UnitTests.TestDomain.FileState", "Archived", 2));
            StatePropertyInfo propertyInfo = AddStatePropertyInfo(cache, typeof(PaperFile), "State", "00000000-0000-0000-0002-000000000001", states);

            string stateDescription = propertyInfo.Description + "|Archived";

            LocalizedName[] expectedGermanNames = new LocalizedName[] {
                CreateLocalizedName(propertyInfo),
                CreateLocalizedName(propertyInfo, 0, stateDescription)
            };

            _localizationConverter.ConvertAndSave(expectedGermanNames, cultures[0], filename);

            LocalizedName[] expectedEnglishNames = new LocalizedName[] {
                CreateLocalizedName(propertyInfo),
                CreateLocalizedName(propertyInfo, 0, stateDescription)
            };
            _localizationConverter.ConvertAndSave(expectedEnglishNames, cultures[1], filename);
            _mocks.ReplayAll();

            converter.ConvertAndSave(cache, filename);

            _mocks.VerifyAll();
        }
예제 #21
0
        public StreamingObjectConstructor(DbDataReader source, IReadOnlyList <Type> constructorSignature)
        {
            m_Source   = source;
            m_Ordinals = new Dictionary <string, int>(source.FieldCount, StringComparer.OrdinalIgnoreCase);
            for (var i = 0; i < source.FieldCount; i++)
            {
                m_Ordinals.Add(source.GetName(i), i);
            }

            constructorSignature = constructorSignature ?? s_DefaultConstructor;

            var desiredType = typeof(T);

            m_Constructor = MetadataCache.GetMetadata(desiredType).Constructors.Find(constructorSignature);

            if (m_Constructor == null)
            {
                var types = string.Join(", ", constructorSignature.Select(t => t.Name));
                throw new MappingException($"Cannot find a constructor on {desiredType.Name} with the types [{types}]");
            }

            var constructorParameters = m_Constructor.ParameterNames;

            for (var i = 0; i < constructorParameters.Length; i++)
            {
                if (!m_Ordinals.ContainsKey(constructorParameters[i]))
                {
                    throw new MappingException($"Cannot find a column that matches the parameter {constructorParameters[i]}");
                }
            }

            m_PopulateComplexObject = constructorSignature.Count == 0;
            m_Dictionary            = new StreamingObjectConstructorDictionary(this);
        }
예제 #22
0
        public SamplingCallTree GetCallTree(Stream byteStream, MetadataCache <MethodMetadata> methodCache)
        {
            var samplingCallTreeElemFactory = new SamplingCallTreeElemFactory();
            var samplingCallTree            = new SamplingCallTree(byteStream, samplingCallTreeElemFactory, methodCache);

            return(samplingCallTree);
        }
예제 #23
0
        public TracingCallTree GetCallTree(Stream byteStream, MetadataCache <MethodMetadata> methodCache)
        {
            var tracingCallTreeElemFactory = new TracingCallTreeElemFactory();
            var tracingCallTree            = new TracingCallTree(byteStream, tracingCallTreeElemFactory, methodCache);

            return(tracingCallTree);
        }
예제 #24
0
        private static void WriteOptionalCustomProperties(XmlWriter writer, string pathRoot)
        {
            // Write out optional custom property data to the fwdata file.
            // The foo.CustomProperties file will exist, even if it has nothing in it, but the "AdditionalFields" root element.
            var optionalCustomPropFile = Path.Combine(pathRoot, SharedConstants.CustomPropertiesFilename);
            var doc = XDocument.Load(optionalCustomPropFile);
            var customFieldElements = doc.Root.Elements(SharedConstants.CustomField).ToList();

            if (!customFieldElements.Any())
            {
                return;
            }

            var mdc = MetadataCache.MdCache;

            foreach (var cf in customFieldElements)
            {
                // Remove 'key' attribute from CustomField elements, before writing to main file.
                cf.Attribute("key").Remove();
                // Restore type attr for object values.
                var propType = cf.Attribute("type").Value;
                cf.Attribute("type").Value = MetadataCache.RestoreAdjustedTypeValue(propType);

                mdc.GetClassInfo(cf.Attribute(SharedConstants.Class).Value).AddProperty(
                    new FdoPropertyInfo(cf.Attribute(SharedConstants.Name).Value, propType, true));
            }
            mdc.ResetCaches();
            FileWriterService.WriteElement(writer, doc.Root);
        }
예제 #25
0
        public async Task <ActionResult <MetadataValidationResponse> > GenerateCode()
        {
            if (!_permissionService.IsAllowed(new ActionRequestInfo(HttpContext, _implementationContainer, null, ActionTypeEnum.ManageMetadata)))
            {
                return(Unauthorized());
            }
            var bundle = await MetadataBundle.FromDbWithoutNavigations(_dbContext
                                                                       , _implementationContainer.InstanceInfo.AppTypeId, _implementationContainer.InstanceInfo.AppInstanceId);

            bundle.FixupRelationships();
            var metadataCache = new MetadataCache(bundle);
            var errorList     = await GenerateCodeValidation();

            var result = new MetadataValidationResponse();

            if (errorList.Value?.Success != true)
            {
                return(errorList);
            }

            var(succeeded, diagnostics) = await _assemblyGenerator.GenerateAssembly(metadataCache, _implementationContainer.InstanceInfo
                                                                                    , _globalConfiguration.ImplementationsDirectory, _implementationContainer.InstanceInfo.InstanceName);

            if (!succeeded)
            {
                result.Errors.AddRange(diagnostics.Select(x => x.Message));
                result.Success = false;
                return(result);
            }
            result.Success = true;
            return(result);
        }
예제 #26
0
        /// <summary>
        /// Initializes a new instance of the <see cref="VerboseReporterMessageHandler" /> class.
        /// </summary>
        /// <param name="logger">The logger used to report messages</param>
        public VerboseReporterMessageHandler(IRunnerLogger logger)
            : base(logger)
        {
            Execution.TestStartingEvent += args =>
            {
                Guard.ArgumentNotNull(args);

                Logger.LogMessage($"    {Escape(args.Message.TestDisplayName)} [STARTING]");
            };

            Execution.TestFinishedEvent += args =>
            {
                Guard.ArgumentNotNull(args);

                var metadata = MetadataCache.TryGetTestMetadata(args.Message);
                if (metadata != null)
                {
                    Logger.LogMessage($"    {Escape(metadata.TestDisplayName)} [FINISHED] Time: {args.Message.ExecutionTime}s");
                }
                else
                {
                    Logger.LogMessage($"    <unknown test> [FINISHED] Time: {args.Message.ExecutionTime}s");
                }
            };
        }
예제 #27
0
        public KeyJoinAppender(ILink <Tuple <List <T1>, List <T2> > > previousLink, string primaryKeyName, string foreignKeyName, string targetCollectionName, JoinOptions joinOptions) : base(previousLink)
        {
            if (string.IsNullOrEmpty(primaryKeyName))
            {
                throw new ArgumentException($"{nameof(primaryKeyName)} is null or empty.", nameof(primaryKeyName));
            }

            if (string.IsNullOrEmpty(foreignKeyName))
            {
                throw new ArgumentException($"{nameof(foreignKeyName)} is null or empty.", nameof(foreignKeyName));
            }

            if (string.IsNullOrEmpty(targetCollectionName))
            {
                throw new ArgumentException($"{nameof(targetCollectionName)} is null or empty.", nameof(targetCollectionName));
            }

            var primaryKeyStub = MetadataCache.GetMetadata(typeof(T1)).Properties[primaryKeyName]; //don't inline this variable.

            m_PrimaryKeyExpression = (p) => (TKey)primaryKeyStub.InvokeGet(p !);

            var foreignKeyStub = MetadataCache.GetMetadata(typeof(T1)).Properties[foreignKeyName]; //don't inline this variable.

            m_ForeignKeyExpression = (p) => (TKey)foreignKeyStub.InvokeGet(p !);

            var targetPropertyStub = MetadataCache.GetMetadata(typeof(T1)).Properties[targetCollectionName]; //don't inline this variable.

            m_TargetCollectionExpression = (p) => (ICollection <T2>)targetPropertyStub.InvokeGet(p !);

            m_JoinOptions = joinOptions;
        }
예제 #28
0
        static internal T ConstructObject <T>(IReadOnlyDictionary <string, object> source, IReadOnlyList <Type> constructorSignature, bool?populateComplexObject = null)
        {
            if (source == null || source.Count == 0)
            {
                throw new ArgumentException($"{nameof(source)} is null or empty.", nameof(source));
            }

            constructorSignature = constructorSignature ?? s_EmptyTypeList;

            if (!populateComplexObject.HasValue)
            {
                populateComplexObject = constructorSignature.Count == 0;
            }

            var desiredType = typeof(T);
            var constructor = MetadataCache.GetMetadata(desiredType).Constructors.Find(constructorSignature);

            if (constructor == null)
            {
                var types = string.Join(", ", constructorSignature.Select(t => t.Name));
                throw new MappingException($"Cannot find a constructor on {desiredType.Name} with the types [{types}]");
            }

            var constructorParameters = constructor.ParameterNames;

            for (var i = 0; i < constructorParameters.Length; i++)
            {
                if (!source.ContainsKey(constructorParameters[i]))
                {
                    throw new MappingException($"Cannot find a column that matches the parameter {constructorParameters[i]}");
                }
            }

            return(ConstructObject <T>(source, constructor));
        }
예제 #29
0
        internal static Task <InfluxResultSet <TInfluxRow> > CreateAsync <TInfluxRow>(
            InfluxClient client,
            IEnumerable <QueryResult> queryResult,
            string db,
            bool allowMetadataQuerying,
            InfluxQueryOptions options,
            CancellationToken cancellationToken = default)
            where TInfluxRow : new()
        {
            var propertyMap   = MetadataCache.GetOrCreate <TInfluxRow>();
            var timestampType = propertyMap.GetTimestampType();

            if (propertyMap.IsBasedOnInterface())
            {
                var createBasedOnInterfaceAsync = CreateBasedOnInterfaceAsyncMethod.MakeGenericMethod(new[] { typeof(TInfluxRow), timestampType });
                return((Task <InfluxResultSet <TInfluxRow> >)createBasedOnInterfaceAsync.Invoke(
                           null,
                           new object[] { client, queryResult, db, allowMetadataQuerying, propertyMap, options, cancellationToken }));
            }
            else
            {
                var createBasedOnAttributes = CreateBasedOnAttributesMethod.MakeGenericMethod(new[] { typeof(TInfluxRow), timestampType });
                return(Task.FromResult((InfluxResultSet <TInfluxRow>)createBasedOnAttributes.Invoke(null, new object[] { client, queryResult, options, propertyMap })));
            }
        }
예제 #30
0
        /// <summary>
        /// Validate a CmObject instance, as represented by an XElement.
        ///
        /// A CmObject may, or may not, contain nested CmObjects.
        /// </summary>
        /// <returns>a String with the first problem found in the CmObject, or null, if no problems were found.</returns>
        /// <exception cref="ArgumentNullException">Thrown is either <paramref name="mdc"/> of <paramref name="obj"/> are null.</exception>
        internal static string ValidateObject(MetadataCache mdc, XElement obj)
        {
            Guard.AgainstNull(mdc, "mdc");
            Guard.AgainstNull(obj, "obj");

            return(ValidateObject(mdc, obj, ""));
        }
예제 #31
0
        internal IEnumerable <KeyValuePair <Row, T> > ToObjectsWithEcho_Core <T>(IReadOnlyList <Type> constructorSignature)
        {
            var desiredType = typeof(T);
            var constructor = MetadataCache.GetMetadata(desiredType).Constructors.Find(constructorSignature);

            if (constructor == null)
            {
                var types = string.Join(", ", constructorSignature.Select(t => t.Name));
                throw new MappingException($"Cannot find a constructor on {desiredType.Name} with the types [{types}]");
            }

            var constructorParameters = constructor.ParameterNames;

            for (var i = 0; i < constructorParameters.Length; i++)
            {
                if (!ColumnNames.Any(p => p.Equals(constructorParameters[i], StringComparison.OrdinalIgnoreCase)))
                {
                    throw new MappingException($"Cannot find a column that matches the parameter {constructorParameters[i]}");
                }
            }

            foreach (var item in Rows)
            {
                var parameters = new object[constructorParameters.Length];
                for (var i = 0; i < constructorParameters.Length; i++)
                {
                    parameters[i] = item[constructorParameters[i]];
                }
                var result = constructor.ConstructorInfo.Invoke(parameters);
                yield return(new KeyValuePair <Row, T>(item, (T)result));
            }
        }
예제 #32
0
        public async Task FindEntryNuGetV2MultiThreadWithDelays()
        {
            int    taskCount = 100;
            Random random    = new Random();

            MetadataCache.Clear();

            var tasks = new List <Task>();

            metadataCalls = 0;

            for (var i = 0; i < taskCount; i++)
            {
                if (random.NextDouble() < 0.25)
                {
                    await Task.Delay(random.Next(1, 250));
                }

                tasks.Add(FindEntryNuGetV2());
            }

            await Task.WhenAll(tasks);

            Assert.Equal(1, metadataCalls);
        }
예제 #33
0
 public void Initialize(TypeSystem system, ITypeSystemController controller)
 {
     TypeSystem = system;
     Controller = controller;
     Cache = new MetadataCache();
     Loader = new MetadataLoader(this);
     Resolver = new MetadataResolver(this);
 }
예제 #34
0
 public ClassMetadata(Stream byteStream, MetadataCache<ModuleMetadata> moduleCache)
     : base(byteStream)
 {
     Contract.Ensures(moduleCache != null);
     Name = byteStream.DeserializeString();
     IsGeneric = byteStream.DeserializeBool();
     ModuleId = byteStream.DeserializeUint32();
     Module = moduleCache[ModuleId];
 }
 public void SetUp()
 {
     _methodCache = new MetadataCache<MethodMetadata>();
     _classCache = new MetadataCache<ClassMetadata>();
     _moduleCache = new MetadataCache<ModuleMetadata>();
     _assemblyCache = new MetadataCache<AssemblyMetadata>();
     var mockSourceLocatorFaktory = new Mock<ISourceLocatorFactory>(MockBehavior.Strict);
     _srcLocatorMockupFkt = mockSourceLocatorFaktory.Object;
 }
		public void Do3WayMerge(MetadataCache mdc, MergeOrder mergeOrder)
		{
			var merger = new XmlMerger(mergeOrder.MergeSituation)
				{
					EventListener = mergeOrder.EventListener
				};
			CustomLayoutMergeStrategiesMethod.AddElementStrategies(merger.MergeStrategies);
			CustomLayoutMergeService.DoMerge(mergeOrder, merger);
		}
 internal static XmlMerger CreateXmlMergerForFieldWorksData(MergeOrder mergeOrder, MetadataCache mdc)
 {
     var merger = new XmlMerger(mergeOrder.MergeSituation)
         {
             EventListener = mergeOrder.EventListener
         };
     BootstrapSystem(mdc, merger);
     return merger;
 }
		/// <summary>
		/// All callers merging FieldWorks data need to pass 'true', so the MDC will know about  any custom properties for their classes.
		///
		/// Non-object callers (currently only the merge of the custom property definitions themselves) shoudl pass 'false'.
		/// </summary>
		internal static void Do3WayMerge(MergeOrder mergeOrder, MetadataCache mdc, bool addcustomPropertyInformation)
		{
			// Skip doing this for the Custom property definiton file, since it has no real need for the custom prop definitions,
			// which are being merged (when 'false' is provided).
			if (addcustomPropertyInformation)
				mdc.AddCustomPropInfo(mergeOrder); // NB: Must be done before FieldWorksCommonMergeStrategy is created. since it used the MDC.

			var merger = FieldWorksMergeServices.CreateXmlMergerForFieldWorksData(mergeOrder, mdc);
			merger.EventListener = mergeOrder.EventListener;
			var mergeResults = merger.MergeFiles(mergeOrder.pathToOurs, mergeOrder.pathToTheirs, mergeOrder.pathToCommonAncestor);
			// Write out merged data.
			FileWriterService.WriteNestedFile(mergeOrder.pathToOurs, mergeResults.MergedNode);
		}
 public MetadataDeserializer(
     MetadataCache<MethodMetadata> methodCache,
     MetadataCache<ClassMetadata> classCache,
     MetadataCache<ModuleMetadata> moduleCache,
     MetadataCache<AssemblyMetadata> assemblyCache,
     ISourceLocatorFactory sourceLocatorFactory)
 {
     _methodCache = methodCache;
     _classCache = classCache;
     _moduleCache = moduleCache;
     _assemblyCache = assemblyCache;
     _sourceLocatorFactory = sourceLocatorFactory;
 }
예제 #40
0
		/// <summary>
		/// Bootstrap a merger for the new-styled (nested) files.
		/// </summary>
		/// <remarks>
		/// 1. A generic 'header' element will be handled, although it may not appear in the file.
		/// 2. All classes will be included.
		/// 3. Merge strategies for class properties (regular or custom) will have keys of "classname+propname" to make them unique, system-wide.
		/// </remarks>
		private static void BootstrapSystem(MetadataCache metadataCache, XmlMerger merger)
		{
			merger.MergeStrategies.ElementToMergeStrategyKeyMapper = new FieldWorksElementToMergeStrategyKeyMapper();

			var sharedElementStrategies = new Dictionary<string, ElementStrategy>();
			CreateSharedElementStrategies(sharedElementStrategies);

			var strategiesForMerger = merger.MergeStrategies;
			ContextGen.MergeStrategies = strategiesForMerger;

			foreach (var sharedKvp in sharedElementStrategies)
				strategiesForMerger.SetStrategy(sharedKvp.Key, sharedKvp.Value);

			var customPropDefnStrat = new ElementStrategy(false)
							{
								MergePartnerFinder = new FindByMultipleKeyAttributes(new List<string> { SharedConstants.Name, SharedConstants.Class }),
								ContextDescriptorGenerator = new FieldWorksCustomPropertyContextGenerator(),
								IsAtomic = true,
								NumberOfChildren = NumberOfChildrenAllowed.Zero
							};
			strategiesForMerger.SetStrategy(SharedConstants.CustomField, customPropDefnStrat);

			var headerStrategy = CreateSingletonElementType(false);
			headerStrategy.ContextDescriptorGenerator = ContextGen;
			strategiesForMerger.SetStrategy(SharedConstants.Header, headerStrategy);

			// There are two abstract class names used: CmAnnotation and DsChart.
			// Chorus knows how to find the matching element for these, as they use <CmAnnotation class='concreteClassname'.
			// So, add a keyed strategy for each of them.
			var keyedStrat = ElementStrategy.CreateForKeyedElement(SharedConstants.GuidStr, false);
			keyedStrat.AttributesToIgnoreForMerging.Add(SharedConstants.Class);
			keyedStrat.AttributesToIgnoreForMerging.Add(SharedConstants.GuidStr);
			strategiesForMerger.SetStrategy(SharedConstants.CmAnnotation, keyedStrat);

			keyedStrat = ElementStrategy.CreateForKeyedElement(SharedConstants.GuidStr, false);
			keyedStrat.AttributesToIgnoreForMerging.Add(SharedConstants.Class);
			keyedStrat.AttributesToIgnoreForMerging.Add(SharedConstants.GuidStr);
			strategiesForMerger.SetStrategy(SharedConstants.DsChart, keyedStrat);

			foreach (var classInfo in metadataCache.AllConcreteClasses)
			{
				MakeClassStrategy(strategiesForMerger, classInfo, ContextGen);
				AddPropertyStrategiesForClass(strategiesForMerger, classInfo);
			}
		}
		public void Do3WayMerge(MetadataCache mdc, MergeOrder mergeOrder)
		{
			// NB: Doesn't need the mdc updated with custom props.
			if (mergeOrder.EventListener is NullMergeEventListener)
				mergeOrder.EventListener = new ChangeAndConflictAccumulator();

			// The bigger model number wins, no matter if it came in ours or theirs.
			var commonData = File.ReadAllText(mergeOrder.pathToCommonAncestor);
			var commonNumber = Int32.Parse(SplitData(commonData)[1]);

			var ourData = File.ReadAllText(mergeOrder.pathToOurs);
			var ourNumber = Int32.Parse(SplitData(ourData)[1]);

			var theirData = File.ReadAllText(mergeOrder.pathToTheirs);
			var theirNumber = Int32.Parse(SplitData(theirData)[1]);

			if (commonNumber == ourNumber && commonNumber == theirNumber)
				return; // No changes.

			if (ourNumber < commonNumber || theirNumber < commonNumber)
				throw new InvalidOperationException("Downgrade in model version number.");

			var mergedNumber = ourNumber;
			var listener = mergeOrder.EventListener;
			if (ourNumber > theirNumber)
			{
				listener.ChangeOccurred(new FieldWorksModelVersionUpdatedReport(mergeOrder.pathToOurs, commonNumber, ourNumber));
			}
			else
			{
				mergedNumber = theirNumber;
				// Put their number in our file. {"modelversion": #####}
				var newFileContents = "{\"modelversion\": " + theirNumber + "}";
				File.WriteAllText(mergeOrder.pathToOurs, newFileContents);
				listener.ChangeOccurred(new FieldWorksModelVersionUpdatedReport(mergeOrder.pathToTheirs, commonNumber, theirNumber));
			}

			mdc.UpgradeToVersion(mergedNumber);
		}
        public void SetUp()
        {
            _memoryStream = _metadataBytes.ConvertToMemoryStream();
            _methodCache = new MetadataCache<MethodMetadata>();
            _classCache = new MetadataCache<ClassMetadata>();
            _moduleCache = new MetadataCache<ModuleMetadata>();
            _assemblyCache = new MetadataCache<AssemblyMetadata>();

            var mockSourceLocatorFaktory = new Mock<ISourceLocatorFactory>(MockBehavior.Strict);
            var metadataDeserializer = new MetadataDeserializer(
                _methodCache,
                _classCache,
                _moduleCache,
                _assemblyCache,
                mockSourceLocatorFaktory.Object);
            metadataDeserializer.DeserializeAllMetadataAndCacheIt(_memoryStream);
        }
 private static string ValidateOwningCollectionProperty(MetadataCache mdc, bool isCustomProperty, XElement propertyElement, string indentation)
 {
     if (propertyElement == null)
         return null;
     if (!isCustomProperty && propertyElement.HasAttributes)
         return "Has unrecognized attribute(s)";
     if (!propertyElement.HasElements)
         return null;
     return propertyElement.Elements().Select(ownedElement => ValidateObject(mdc, ownedElement, indentation)).FirstOrDefault(result => result != null);
 }
        /// <summary>
        /// Validate a CmObject instance, as represented by an XElement.
        ///
        /// A CmObject may, or may not, contain nested CmObjects.
        /// </summary>
        /// <returns>a String with the first problem found in the CmObject, or null, if no problems were found.</returns>
        /// <exception cref="ArgumentNullException">Thrown is either <paramref name="mdc"/> of <paramref name="obj"/> are null.</exception>
        private static string ValidateObject(MetadataCache mdc, XElement obj, string indentation)
        {
            try
            {
                var attribute = obj.Attribute(SharedConstants.GuidStr);

                string result;
                var className = GetClassName(obj, out result);
                if (attribute == null)
                    return GetFormattedResult(indentation, null, null, className ?? "", null, "Reports error: ", "No guid attribute");
                var guid = new Guid(attribute.Value); // Will throw if not a guid.
                if (result != null)
                    return GetFormattedResult(indentation, null, null, className ?? "", guid, result);
                var classInfo = mdc.GetClassInfo(className);
                if (classInfo == null)
                    return GetFormattedResult(indentation, null, null, className, guid, "No recognized class");
                if (classInfo.IsAbstract)
                    return GetFormattedResult(indentation, null, null, className, guid, "Abstract class");

                attribute = obj.Attribute(SharedConstants.OwnerGuid);
                if (attribute != null)
                    return GetFormattedResult(indentation, null, null, className, guid, "Has 'ownerguid' attribute");

                // Check each property
                var allProperties = classInfo.AllProperties.ToList();
                var allPropertyNames = new HashSet<string>(from prop in allProperties select prop.PropertyName);
                var allValueTypeProperties = new HashSet<string>(from prop in allProperties
                                                                 where DataTypesForValueTypeData.Contains(prop.DataType)
                                                                 select prop.PropertyName);
                if (allValueTypeProperties.Count == 0 && !obj.HasElements)
                    return null; // It is fine for objects that have no value type data props to not have any other properties.

                foreach (var propertyElement in obj.Elements())
                {
                    if (propertyElement.NodeType != XmlNodeType.Element)
                        return GetFormattedResult(indentation, null, propertyElement.Name.LocalName, className, guid, "Not a property element child");

                    // Deal with custom properties.
                    var isCustomProperty = propertyElement.Name.LocalName == SharedConstants.Custom;
                    var propertyName = isCustomProperty ? propertyElement.Attribute(SharedConstants.Name).Value : propertyElement.Name.LocalName;

                    if (!allPropertyNames.Contains(propertyName))
                        return GetFormattedResult(indentation, null, propertyName, className, guid, "Not a property element child");

                    var currentPropertyinfo = (allProperties.Where(pi => pi.PropertyName == propertyName)).First();
                    var nextIndentationLevel = indentation + "\t";
                    var nextOwningLevel = Environment.NewLine + indentation;
                    var nextPropertyLevel = Environment.NewLine + nextIndentationLevel;
                    switch (currentPropertyinfo.DataType)
                    {
                        case DataType.OwningCollection:
                            result = ValidateOwningCollectionProperty(mdc, isCustomProperty, propertyElement, nextIndentationLevel);
                            if (result != null)
                                return GetFormattedResult(nextOwningLevel, "Collection Owning", propertyName, className, guid, "in:", result);
                            break;
                        case DataType.OwningSequence:
                            result = ValidateOwningSequenceProperty(mdc, isCustomProperty, propertyElement, nextIndentationLevel);
                            if (result != null)
                                return GetFormattedResult(nextOwningLevel, "Sequence Owning", propertyName, className, guid, "in:", result);
                            break;
                        case DataType.OwningAtomic:
                            result = ValidateOwningAtomicProperty(mdc, isCustomProperty, propertyElement, nextIndentationLevel);
                            if (result != null)
                                return GetFormattedResult(nextOwningLevel, "Atomic Owning", propertyName, className, guid, "in:", result);
                            break;

                        case DataType.ReferenceCollection:
                            result = ValidateReferenceCollectionProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "Collection Reference", propertyName, className, guid, result);
                            break;
                        case DataType.ReferenceSequence:
                            result = ValidateReferenceSequenceProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "Sequence Reference", propertyName, className, guid, result);
                            break;
                        case DataType.ReferenceAtomic:
                            result = ValidateReferenceAtomicProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "Atomic Reference", propertyName, className, guid, result);
                            break;

                        case DataType.MultiUnicode:
                            result = ValidateMultiUnicodeProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "MultiUnicode", propertyName, className, guid, result);
                            break;
                        case DataType.MultiString:
                            result = ValidateMultiStringProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "MultiString", propertyName, className, guid, result);
                            break;
                        case DataType.Unicode:
                            result = ValidateUnicodeProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "Unicode", propertyName, className, guid, result);
                            break;
                        case DataType.String:
                            result = ValidateStringProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "String (TsString)", propertyName, className, guid, result);
                            break;
                        case DataType.Binary:
                            result = ValidateBinaryProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "Binary", propertyName, className, guid, result);
                            break;
                        case DataType.TextPropBinary:
                            result = ValidateTextPropBinaryProperty(isCustomProperty, propertyElement);
                            if (result != null)
                                return GetFormattedResult(nextPropertyLevel, "TextPropBinary", propertyName, className, guid, result);
                            break;

                        case DataType.Integer:
                            if (BasicValueTypeAttributeCheckIsValid(propertyElement, isCustomProperty, out result))
                            {
                                Int32.Parse(result);
                                result = null;
                            }
                            else
                            {
                                return GetFormattedResult(nextPropertyLevel, "Integer", propertyName, className, guid, result);
                            }
                            break;
                        case DataType.Boolean:
                            if (BasicValueTypeAttributeCheckIsValid(propertyElement, isCustomProperty, out result))
                            {
                                bool.Parse(result);
                                result = null;
                            }
                            else
                            {
                                return GetFormattedResult(nextPropertyLevel, "Boolean", propertyName, className, guid, result);
                            }
                            break;
                        case DataType.Time:
                            if (BasicValueTypeAttributeCheckIsValid(propertyElement, isCustomProperty, out result))
                            {
                                DateTime.Parse(result);
                                result = null;
                            }
                            else
                            {
                                return GetFormattedResult(nextPropertyLevel, "Time (DateTime)", propertyName, className, guid, result);
                            }
                            break;
                        case DataType.GenDate:
                            if (BasicValueTypeAttributeCheckIsValid(propertyElement, isCustomProperty, out result))
                            {
                                // What is a GenDate?
                                //var dateTimeAttrVal = DateTime.Parse(element.Attribute(SharedConstants.Val).Value);
                                // string.Format("{0}{1:0000}{2:00}{3:00}{4}", dataProperty.IsAD ? "" : "-", dataProperty.Year,
                                //		dataProperty.Month, dataProperty.Day, (int)dataProperty.Precision)
                                // TODO: Check internals of the GenDate.
                                result = null;
                            }
                            else
                            {
                                return GetFormattedResult(nextPropertyLevel, "GenDate", propertyName, className, guid, result);
                            }
                            break;
                        case DataType.Guid:
                            if (BasicValueTypeAttributeCheckIsValid(propertyElement, isCustomProperty, out result))
                            {
                                new Guid(result);
                                result = null;
                            }
                            else
                            {
                                return GetFormattedResult(nextPropertyLevel, "Guid", propertyName, className, guid, result);
                            }
                            break;
                    }
                }

                // Ensure that all value type data property elements exist.
                if (!EnsureBasicValueTypePropertyElementsExist(mdc, classInfo, obj, allValueTypeProperties, out result))
                {
                    return GetFormattedResult(indentation, null, null, className, guid, result);
                }
            }
            catch (Exception err)
            {
                return err.Message;
            }

            return null;
        }
        private static bool EnsureBasicValueTypePropertyElementsExist(MetadataCache mdc, FdoClassInfo classInfo, XElement element, IEnumerable<string> basicPropertyNames, out string result)
        {
            result = null;

            if (mdc.ModelVersion < 7000066)
                return true; // The value type data types are only required at DM 7000066, and higher.

            foreach (var basicPropertyName in basicPropertyNames)
            {
                var currentPropName = basicPropertyName;
                var isCustomProperty = classInfo.GetProperty(basicPropertyName).IsCustomProperty;
                var propertyElement = isCustomProperty
                    ? element.Elements("Custom").FirstOrDefault(propElement => propElement.Attribute(SharedConstants.Name).Value == currentPropName)
                    : element.Element(currentPropName);
                if (propertyElement != null)
                    continue;

                result = string.Format("Required basic property element '{0}' of class '{1}' is missing.", currentPropName, classInfo.ClassName);
                return false;
            }
            return true;
        }
 public void Do3WayMerge(MetadataCache mdc, MergeOrder mergeOrder)
 {
     FieldWorksCommonFileHandler.Do3WayMerge(mergeOrder, mdc, true);
 }
 private static string ValidateOwningAtomicProperty(MetadataCache mdc, bool isCustomProperty, XElement propertyElement, string indentation)
 {
     if (propertyElement == null)
         return null;
     if (!isCustomProperty && propertyElement.HasAttributes)
         return "Has unrecognized attribute(s)";
     var children = propertyElement.Elements().ToList();
     return (children.Count > 1)
             ? "Has too many child elements"
             : ((children.Count == 0)
                 ? null
                 : ValidateObject(mdc, children[0], indentation));
 }
 public void Do3WayMerge(MetadataCache mdc, MergeOrder mergeOrder)
 {
     FieldWorksCommonFileHandler.Do3WayMerge(mergeOrder, mdc,
         false); // We don't want (or even need) the custom properties to be added to the MDC, while merging the custom props file itself.
                 // We won't even know what they are until after the merge is done.
 }
		private static string ChangeGuids(MetadataCache mdc, FdoClassInfo classInfo, XElement element)
		{
			var newGuid = Guid.NewGuid().ToString().ToLowerInvariant();

			element.Attribute(SharedConstants.GuidStr).Value = newGuid;

			// Recurse down through everything that is owned and change those guids.
			foreach (var owningPropInfo in classInfo.AllOwningProperties)
			{
				var isCustomProp = owningPropInfo.IsCustomProperty;
				var owningPropElement = isCustomProp
											? (element.Elements(SharedConstants.Custom).Where(customProp => customProp.Attribute(SharedConstants.Name).Value == owningPropInfo.PropertyName)).FirstOrDefault()
											: element.Element(owningPropInfo.PropertyName);
				if (owningPropElement == null || !owningPropElement.HasElements)
					continue;
				foreach (var ownedElement in owningPropElement.Elements())
				{
					FdoClassInfo ownedClassInfo;
					string className;
					GetClassInfoFromElement(mdc, element, out ownedClassInfo, out className);
					ChangeGuids(mdc, ownedClassInfo, ownedElement);
				}
			}

			return newGuid;
		}
        internal static void WriteCustomPropertyFile(MetadataCache mdc,
													 string pathRoot,
													 byte[] record)
        {
            WriteCustomPropertyFile(mdc, pathRoot, SharedConstants.Utf8.GetString(record));
        }
        internal static void WriteCustomPropertyFile(MetadataCache mdc,
													 string pathRoot,
													 string record)
        {
            // Theory has it that the fwdata file is all sorted.
            var cpElement = DataSortingService.SortCustomPropertiesRecord(record);
            // Not this one, since it leaves out the temporary "key' attr. var cpElement = XElement.Parse(SharedConstants.Utf8.GetString(record));
            // Add custom property info to MDC, since it may need to be sorted in the data files.
            var hasCustomProperties = false;
            foreach (var propElement in cpElement.Elements(SharedConstants.CustomField))
            {
                hasCustomProperties = true;
                var className = propElement.Attribute(SharedConstants.Class).Value;
                var propName = propElement.Attribute(SharedConstants.Name).Value;
                var typeAttr = propElement.Attribute("type");
                var adjustedTypeValue = MetadataCache.AdjustedPropertyType(typeAttr.Value);
                if (adjustedTypeValue != typeAttr.Value)
                    typeAttr.Value = adjustedTypeValue;
                var customProp = new FdoPropertyInfo(
                    propName,
                    typeAttr.Value,
                    true);
                mdc.AddCustomPropInfo(
                    className,
                    customProp);
            }
            if (hasCustomProperties)
                mdc.ResetCaches();
            WriteCustomPropertyFile(Path.Combine(pathRoot, SharedConstants.CustomPropertiesFilename), cpElement);
        }
 public void Do3WayMerge(MetadataCache mdc, MergeOrder mergeOrder)
 {
     throw new NotSupportedException("'Do3WayMerge' method is not supported for unknown file types.");
 }
        private static string ValidateOwningSequenceProperty(MetadataCache mdc, bool isCustomProperty, XElement propertyElement, string indentation)
        {
            if (propertyElement == null)
                return null;
            if (!isCustomProperty && propertyElement.HasAttributes)
                return "Has unrecognized attribute(s)";
            if (!propertyElement.HasElements)
                return null; // No children.
            // ownseq
            var ownseqChildElements = propertyElement.Elements().Where(childElement => childElement.Name.LocalName == SharedConstants.Ownseq).ToList();
            if (ownseqChildElements.Count != propertyElement.Elements().Count())
                return "Contains unrecognized child elements";

            return ownseqChildElements.Select(ownseqChildElement => ValidateObject(mdc, ownseqChildElement, indentation)).FirstOrDefault(result => result != null);
        }
		private static bool GetClassInfoFromElement(MetadataCache mdc, XElement element, out FdoClassInfo classInfo,
													out string className)
		{
			var isOwnSeqNode = element.Name.LocalName == SharedConstants.Ownseq;
			className = isOwnSeqNode ? element.Attribute(SharedConstants.Class).Value : element.Name.LocalName;
			classInfo = mdc.GetClassInfo(className);
			return isOwnSeqNode;
		}