Beispiel #1
0
        /// <summary>
        /// Parses a term key string and returns a term describing it. All terms are created here.
        /// The main caller is TypeCache.MakeTerm, but it's also called from places that use a
        /// dynamic domain (processors).
        /// </summary>
        public Term Parse(Type resource, string key, string componentSeparator, TermBindingRule bindingRule, ICollection <string> dynDomain)
        {
            var term = new Term(componentSeparator);

            Property propertyMaker(string str)
            {
                if (string.IsNullOrWhiteSpace(str))
                {
                    throw new InvalidSyntax(ErrorCodes.InvalidConditionSyntax, $"Invalid condition '{str}'");
                }
                if (dynDomain?.Contains(str, StringComparer.OrdinalIgnoreCase) == true)
                {
                    return(DynamicProperty.Parse(str));
                }

                Property make(Type type)
                {
                    switch (bindingRule)
                    {
                    case TermBindingRule.DeclaredWithDynamicFallback:
                        try
                        {
                            return(TypeCache.FindDeclaredProperty(type, str));
                        }
                        catch (UnknownProperty)
                        {
                            return(DynamicProperty.Parse(str));
                        }

                    case TermBindingRule.DynamicWithDeclaredFallback: return(DynamicProperty.Parse(str, true));

                    case TermBindingRule.OnlyDeclared:
                        try
                        {
                            return(TypeCache.FindDeclaredProperty(type, str));
                        }
                        catch (UnknownProperty)
                        {
                            if (type.GetSubclasses().Any(subClass => TypeCache.TryFindDeclaredProperty(subClass, str, out _)))
                            {
                                return(DynamicProperty.Parse(str));
                            }
                            throw;
                        }

                    default: throw new Exception();
                    }
                }

                return(term.LastOrDefault() switch
                {
                    null => make(resource),
                    DeclaredProperty declared => make(declared.Type),
                    _ => DynamicProperty.Parse(str)
                });
            }
Beispiel #2
0
        /// <summary>
        /// Converts all properties in this term to dynamic properties
        /// </summary>
        private static Term MakeDynamic(Term term)
        {
            if (term.IsDynamic)
            {
                return(term);
            }
            var newTerm = new Term(term.ComponentSeparator);

            newTerm.Store.AddRange(term.Store.Select(prop => prop switch
            {
                DynamicProperty _ => prop,
                DeclaredProperty _ => DynamicProperty.Parse(prop.Name),
                _ => throw new ArgumentOutOfRangeException()
            }));