Пример #1
0
        /// <summary>
        /// Reads the latest attribute value using the priority Target -> PreImage -> PostImage
        /// </summary>
        /// <typeparam name="TValue">The type of the attribute value to read</typeparam>
        /// <param name="readProperty">The delegate that defines the property to read</param>
        /// <param name="exceptionMessage">The message to appear in the exception message when the value is not available on either target or image</param>
        /// <returns>The value read from the prioritised entities</returns>
        public TValue ReadValue <TValue>(Func <TEntity, TValue> readProperty, string exceptionMessage = null)
        {
            var target = _context.LoadTarget <TEntity>(false);
            var image  = _context.LoadPreImage <TEntity>() ?? _context.LoadPostImage <TEntity>();
            var result = readProperty(target ?? image);

            //Resharper warnings/recommendations...
            //Cannot use Null Coalescing Expression due to not being able to apply class OR nullable constraint
            //Value type null compare won't occur as all CRM value types are nullable
            if (result == null && !string.IsNullOrEmpty(exceptionMessage))
            {
                throw new InvalidPluginExecutionException(exceptionMessage);
            }
            return(result);
        }
Пример #2
0
        /// <summary>
        /// Helper method for plugins for reading the property defined
        /// on the <paramref name="readProperty"/> callback from either the <paramref name="target"/>
        /// or <paramref name="image"/> (pre/post) depending on whichever is populated.  So if it is an update triggering
        /// the plugin it will always read the latest value, regardless of whether the attribute being read was one of the
        /// triggering attributes.
        /// </summary>
        /// <typeparam name="T">The type for the return value (referencee type only)</typeparam>
        /// <typeparam name="TE">The entity types for target and image</typeparam>
        /// <param name="readProperty">The callback to determine which property on the entity to be read</param>
        /// <param name="propertyDisplayName">Friendly display name for the property if an exception is thrown</param>
        /// <returns>The value off either the target if it exists or the image</returns>
        /// <exception cref="NullReferenceException"></exception>
        public static T Read <T, TE>(this IPluginExecutionContext context, Func <TE, T> readProperty,
                                     string propertyDisplayName = "Value")
            where T : class
            where TE : Entity
        {
            var image = context.LoadPreImage <TE>() ?? context.LoadPostImage <TE>();

            var result = readProperty(context.LoadTarget <TE>()) ?? readProperty(image);

            if (result == null)
            {
                throw new NullReferenceException(propertyDisplayName + " has not been defined.");
            }
            return(result);
        }