コード例 #1
0
        private bool HasAdminPrivileges()
        {
            var contentMap    = AdxstudioCrmConfigurationManager.CreateContentMapProvider();
            var webSiteEntity = PortalContext.Current.Website;

            if (webSiteEntity == null)
            {
                return(false);
            }

            WebsiteNode webSite = null;

            contentMap.Using(map => map.TryGetValue(webSiteEntity, out webSite));

            if (webSite == null)
            {
                return(false);
            }

            // Get names of current user roles
            var roleNames = Roles.GetRolesForUser();

            // Select these role nodes
            var userRoles = webSite.WebRoles.Where(role => roleNames.Contains(role.Name));

            // Select web site access permissions
            var permissions = userRoles.SelectMany(role => role.WebsiteAccesses);

            // Check if there is permission with all options active
            var hasAcccess =
                permissions.Any(p => p.ManageContentSnippets.Value && p.ManageSiteMarkers.Value &&
                                p.ManageWebLinkSets.Value && p.PreviewUnpublishedEntities.Value);

            return(hasAcccess);
        }
コード例 #2
0
        /// <summary>
        /// Constructor
        /// </summary>
        public SubgridViewLayout(ViewConfiguration configuration, EntityReference source, Relationship relationship, string viewEntityLogicalName,
                                 EntityView view  = null, string portalName = null,
                                 int languageCode = 0, bool addSelectColumn = false, bool addActionsColumn = false, string selectColumnHeaderText = "")
            : base(configuration, view, portalName, languageCode, addSelectColumn, addActionsColumn, selectColumnHeaderText)
        {
            if (source == null)
            {
                throw new ArgumentNullException("source");
            }

            if (relationship == null)
            {
                throw new ArgumentNullException("relationship");
            }

            if (string.IsNullOrWhiteSpace(viewEntityLogicalName))
            {
                throw new ArgumentNullException("viewEntityLogicalName");
            }

            Source       = source;
            Relationship = relationship;

            if ((configuration.EnableEntityPermissions && AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled) &&
                configuration.AssociateActionLink.Enabled)
            {
                var serviceContext = PortalCrmConfigurationManager.CreateServiceContext(configuration.PortalName);
                var crmEntityPermissionProvider = new CrmEntityPermissionProvider(configuration.PortalName);

                configuration.AssociateActionLink.Enabled =
                    crmEntityPermissionProvider.TryAssert(serviceContext, CrmEntityPermissionRight.AppendTo,
                                                          Retrieve(serviceContext, source)) &&
                    crmEntityPermissionProvider.TryAssert(serviceContext, CrmEntityPermissionRight.Append, viewEntityLogicalName);
            }
        }
コード例 #3
0
        private IWebsiteAccessPermissionProvider GetWebsiteAccessPermissionProvider()
        {
            var portalContext      = CreatePortalContext();
            var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(PortalName);

            return(new RequestCachingWebsiteAccessPermissionProvider(new WebsiteAccessPermissionProvider(portalContext.Website, contentMapProvider), portalContext.Website.ToEntityReference()));
        }
コード例 #4
0
        public FetchXmlIndexDocumentFactory(ICrmEntityIndex index, FetchXml fetchXml, string titleAttributeLogicalName, FetchXmlLocaleConfig localeConfig)
        {
            if (index == null)
            {
                throw new ArgumentNullException("index");
            }

            if (fetchXml == null)
            {
                throw new ArgumentNullException("fetchXml");
            }

            if (titleAttributeLogicalName == null)
            {
                throw new ArgumentNullException("titleAttributeLogicalName");
            }

            if (localeConfig == null)
            {
                throw new ArgumentNullException("localeConfig");
            }

            _index = index;
            _contentMapProvider        = AdxstudioCrmConfigurationManager.CreateContentMapProvider();
            _fetchXml                  = fetchXml;
            _titleAttributeLogicalName = titleAttributeLogicalName;
            _localeConfig              = localeConfig;

            _dataContext = _index.DataContext;
        }
コード例 #5
0
        private static void LoadOutputCache(object sender, EventArgs e)
        {
            var name = AdxstudioCrmConfigurationManager.GetCrmSection().OutputObjectCacheName;
            var keys = HttpSingleton <OutputCacheKeyCollection> .GetInstance(name, () => new OutputCacheKeyCollection());

            HttpContext.Current.Response.AddCacheItemDependencies(keys.ToArray());
        }
コード例 #6
0
        public override void Initialize(string name, NameValueCollection config)
        {
            OutputObjectCacheName = config["outputObjectCacheName"]
                                    ?? AdxstudioCrmConfigurationManager.GetCrmSection().OutputObjectCacheName;

            base.Initialize(name, config);
        }
コード例 #7
0
        private static void Initialize()
        {
            if (_initialized)
            {
                return;
            }

            lock (_initializeLock)
            {
                if (_initialized)
                {
                    return;
                }

                OnInitializing();

                var searchElement = AdxstudioCrmConfigurationManager.GetCrmSection().Search;

                _enabled = searchElement.Enabled;

                if (_enabled.GetValueOrDefault(false))
                {
                    _providers = new ProviderCollection <SearchProvider>();

                    foreach (ProviderSettings providerSettings in searchElement.Providers)
                    {
                        _providers.Add(InstantiateProvider <SearchProvider>(providerSettings));
                    }

                    _providers.SetReadOnly();

                    if (searchElement.DefaultProvider == null)
                    {
                        throw new ProviderException("Specify a default search provider.");
                    }

                    try
                    {
                        _provider = _providers[searchElement.DefaultProvider];
                    }
                    catch {}

                    if (_provider == null)
                    {
                        var defaultProviderPropertyInformation = searchElement.ElementInformation.Properties["defaultProvider"];

                        const string message = "Default Search Provider could not be found.";

                        throw defaultProviderPropertyInformation == null
                                                        ? (Exception) new ProviderException(message)
                                                        : new ConfigurationErrorsException(message, defaultProviderPropertyInformation.Source, defaultProviderPropertyInformation.LineNumber);
                    }
                }

                _initialized = true;
            }
        }
コード例 #8
0
        private EntityReference GetExistingParent(EntityReference child)
        {
            var contentMapProvider      = AdxstudioCrmConfigurationManager.CreateContentMapProvider();
            var dataAdapterDependencies = new PortalConfigurationDataAdapterDependencies(requestContext: Request.RequestContext);

            return(contentMapProvider == null
                                ? GetExistingParent(child, dataAdapterDependencies)
                                : contentMapProvider.Using(map => GetExistingParent(child, dataAdapterDependencies, map)));
        }
コード例 #9
0
        private IFileSystem CreateFileSystem()
        {
            var contentMapProvider      = AdxstudioCrmConfigurationManager.CreateContentMapProvider();
            var contentMapUrlProvider   = PortalCrmConfigurationManager.CreateDependencyProvider().GetDependency <IContentMapEntityUrlProvider>();
            var dataAdapterDependencies = new PortalConfigurationDataAdapterDependencies(requestContext: Request.RequestContext);

            return(contentMapProvider == null || contentMapUrlProvider == null
                                ? (IFileSystem) new EntityFileSystem(dataAdapterDependencies)
                                : new ContentMapFileSystem(contentMapProvider, contentMapUrlProvider, dataAdapterDependencies));
        }
        private bool ValidateEntityPermission(OrganizationServiceContext serviceContext, CrmEntitySearchResult result)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                return(false);
            }

            var permissionResult = new CrmEntityPermissionProvider(PortalName).TryAssert(serviceContext, result.Entity);

            return(permissionResult.RulesExist && permissionResult.CanRead);
        }
コード例 #11
0
        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().MembershipProviderEnabled)
            {
                filterContext.Result = new HttpNotFoundResult();

                return;
            }

            base.OnActionExecuting(filterContext);
        }
コード例 #12
0
        protected virtual bool TryAssertByCrmEntityPermissionProvider(OrganizationServiceContext context, Entity entity)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                return(false);
            }

            var crmEntityPermissionProvider = new CrmEntityPermissionProvider(PortalName);

            return(crmEntityPermissionProvider.TryAssert(context, CrmEntityPermissionRight.Read, entity));
        }
コード例 #13
0
        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            if (!OpenAuthConfigurationManager.GetSection().Enabled&& !AdxstudioCrmConfigurationManager.GetCrmSection().IdentityModelEnabled)
            {
                filterContext.Result = new HttpNotFoundResult();

                return;
            }

            base.OnActionExecuting(filterContext);
        }
コード例 #14
0
ファイル: UrlHelpers.cs プロジェクト: weedkiller/dms
        public static string FederatedSignInUrl(this UrlHelper url, string returnUrl = null)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().IdentityModelEnabled)
            {
                return(LocalSignInUrl(url, returnUrl));
            }

            var fam       = new AdxstudioFederationAuthenticationModule(url.RequestContext.HttpContext);
            var signInUrl = fam.GetSignInRequestUrl(GetReturnUrl(url, returnUrl));

            return(signInUrl);
        }
        private void LoadEventProviders(string eventName)
        {
            var providers = AdxstudioCrmConfigurationManager.CreateEventProviders(eventName);

            foreach (var provider in providers)
            {
                Created  += provider.Created;
                Deleted  += provider.Deleted;
                Executed += provider.Executed;
                Updated  += provider.Updated;
            }
        }
コード例 #16
0
ファイル: Extensions.cs プロジェクト: ITLec/Dynamics-365-XEP
        public static void ConfigureSearchProvider(this IAppBuilder app, CrmWebsite website)
        {
            var searchElement = AdxstudioCrmConfigurationManager.GetCrmSection().Search;

            searchElement.Enabled = website.Settings.Get <bool>("Search/Enabled");

            if (searchElement.Enabled)
            {
                if (searchElement.Providers.Count == 0)
                {
                    ConfigureProviderSettings(searchElement, website);
                }
            }
        }
コード例 #17
0
        private static IEnumerable <Tuple <string, string, int> > ContentStyles(IPortalViewContext portalViewContext, SiteMapNode node, IDictionary <string, object> cache)
        {
            if (node == null)
            {
                return(Enumerable.Empty <Tuple <string, string, int> >());
            }

            var cacheKey = "{0}:ContentStyles:{1}".FormatWith(typeof(StyleExtensions).FullName, node.Url);

            object cached;

            if (cache.TryGetValue(cacheKey, out cached) && cached is IEnumerable <Tuple <string, string, int> > )
            {
                return(cached as IEnumerable <Tuple <string, string, int> >);
            }

            // Get all adx_webpages in the site map path, starting from and including the current entity. These are
            // potential containers for content-managed stylesheets.
            var path    = new List <EntityReference>();
            var current = node;

            while (current != null)
            {
                var entityNode = current as CrmSiteMapNode;

                if (entityNode != null && entityNode.HasCrmEntityName("adx_webpage"))
                {
                    path.Add(entityNode.Entity.ToEntityReference());
                }

                current = current.ParentNode;
            }

            if (!path.Any())
            {
                return(Enumerable.Empty <Tuple <string, string, int> >());
            }

            var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(portalViewContext.PortalName);

            var styles = contentMapProvider == null
                                ? ContentStyles(portalViewContext, path)
                                : ContentStyles(portalViewContext, path, contentMapProvider);

            cache[cacheKey] = styles;

            return(styles);
        }
コード例 #18
0
        private bool SolutionDependenciesAvailable(string[] requiredSolutions)
        {
            if (requiredSolutions == null || !requiredSolutions.Any())
            {
                return(true);
            }

            var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(this.PortalViewContext.PortalName);

            if (contentMapProvider == null)
            {
                return(true);
            }

            var availableSolutions = contentMapProvider.Using(map => map.Solution.Solutions);

            return(requiredSolutions.Intersect(availableSolutions, StringComparer.OrdinalIgnoreCase).Count() == requiredSolutions.Length);
        }
コード例 #19
0
        private CacheItemPolicy GetPolicy(ObjectCache cache, DateTime utcExpiry, string regionName)
        {
            // Add an output cache specific dependency item and key
            cache.AddOrGetExisting(_outputCacheDependency, _outputCacheDependency, ObjectCache.InfiniteAbsoluteExpiration, CacheRegionName);

            // Get the keys from HttpContext
            var name = AdxstudioCrmConfigurationManager.GetCrmSection().OutputObjectCacheName;
            var keys = HttpSingleton <OutputCacheKeyCollection> .GetInstance(name, () => new OutputCacheKeyCollection());

            // Create Monitor and Policy objects
            var monitorKeys = keys.Select(d => d.ToLower()).ToArray();
            var monitor     = GetChangeMonitor(cache, monitorKeys, regionName);
            var policy      = monitor.GetCacheItemPolicy(cache.Name);

            policy.AbsoluteExpiration = ToDateTimeOffset(utcExpiry);
            policy.RemovedCallback   += CacheEventSource.Log.OnRemovedCallback;
            return(policy);
        }
コード例 #20
0
        protected virtual bool TryAssertByCrmEntityPermissionProvider(OrganizationServiceContext context, Entity entity, EntityReference regarding)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                return(false);
            }

            var crmEntityPermissionProvider = new CrmEntityPermissionProvider(PortalName);

            if (string.Equals(entity.LogicalName, "annotation", StringComparison.InvariantCulture) &&
                regarding != null &&
                string.Equals(regarding.LogicalName, "adx_portalcomment", StringComparison.InvariantCulture))
            {
                // If can read portal comment, bypass assertion check on notes and assume read permission.
                return(TryAssertPortalCommentPermission(context, crmEntityPermissionProvider, CrmEntityPermissionRight.Read, regarding));
            }

            return(crmEntityPermissionProvider.TryAssert(context, CrmEntityPermissionRight.Read, entity, regarding: regarding));
        }
コード例 #21
0
        public virtual string GetRedirectWebPageUrl(IPortalContext context, string portalName = null)
        {
            if (context == null || RedirectWebpageId == null || RedirectWebpageId == Guid.Empty)
            {
                return(null);
            }

            var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(portalName);

            var page = contentMapProvider.Using(contentMap => Select(RedirectWebpageId.GetValueOrDefault(), contentMap));

            if (page == null)
            {
                return(null);
            }

            var urlProvider = PortalCrmConfigurationManager.CreateDependencyProvider(portalName).GetDependency <IContentMapEntityUrlProvider>();

            return(contentMapProvider.Using(contentMap => urlProvider.GetUrl(contentMap, page)));
        }
コード例 #22
0
        private ApplicationPath GetApplicationPathForSiteMarker(RequestContext request)
        {
            return(GetApplicationPathForSiteMarker(request.HttpContext.Items, () =>
            {
                var crmWebsite = request.HttpContext.GetWebsite();

                if (crmWebsite == null)
                {
                    return null;
                }

                var website = crmWebsite.Entity;

                if (website == null)
                {
                    return null;
                }

                var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(PortalName);

                if (contentMapProvider == null)
                {
                    var serviceContext = PortalCrmConfigurationManager.CreateServiceContext(PortalName);

                    website = serviceContext.MergeClone(website);

                    return GetApplicationPathForSiteMarker(serviceContext, website, request.HttpContext.Items);
                }

                return contentMapProvider.Using(contentMap =>
                {
                    WebsiteNode websiteNode;

                    return contentMap.TryGetValue(website, out websiteNode)
                                                ? GetApplicationPathForSiteMarker(contentMap, websiteNode, request.HttpContext.Items)
                                                : null;
                });
            }));
        }
コード例 #23
0
        public override void Initialize(string name, NameValueCollection config)
        {
            base.Initialize(name, config);

            var portalName = config["portalName"];

            var contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider(portalName);

            _underlyingProvider = contentMapProvider != null
                                ? new ContentMapUncachedProvider(contentMapProvider)
                                : new UncachedProvider(portalName);

            var cacheInfoFactory = new CrmEntitySecurityCacheInfoFactory(GetType().FullName);

            bool cachingEnabled;

            if (!bool.TryParse(config["cachingEnabled"], out cachingEnabled))
            {
                cachingEnabled = true;
            }

            if (cachingEnabled)
            {
                _underlyingProvider = new ApplicationCachingCrmEntitySecurityProvider(_underlyingProvider, cacheInfoFactory);
            }

            bool requestCachingEnabled;

            if (!bool.TryParse(config["requestCachingEnabled"], out requestCachingEnabled))
            {
                requestCachingEnabled = true;
            }

            if (requestCachingEnabled && HttpContext.Current != null)
            {
                _underlyingProvider = new RequestCachingCrmEntitySecurityProvider(_underlyingProvider, cacheInfoFactory);
            }
        }
コード例 #24
0
ファイル: UrlHelpers.cs プロジェクト: weedkiller/dms
        private static string SignInUrlMembership(this UrlHelper url, string returnUrl = null)
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().MembershipProviderEnabled &&
                !AdxstudioCrmConfigurationManager.GetCrmSection().IdentityModelEnabled &&
                !OpenAuthConfigurationManager.GetSection().Enabled)
            {
                return(null);
            }

            var authenticationType = AdxstudioCrmConfigurationManager.GetCrmSection().LoginButtonAuthenticationType;

            if (_identityModelAuthenticationTypes.Contains(authenticationType, StringComparer.OrdinalIgnoreCase))
            {
                return(FederatedSignInUrl(url, returnUrl));
            }

            if (!string.IsNullOrWhiteSpace(authenticationType))
            {
                return(OpenAuthSignInUrl(url, authenticationType, returnUrl));
            }

            return(LocalSignInUrl(url, returnUrl));
        }
            private Func <OrganizationServiceContext, Entity, bool> GetSecurityAssertion(string portalName)
            {
                var cmsSecurityProvider = PortalCrmConfigurationManager.CreateCrmEntitySecurityProvider(portalName);

                if (!AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
                {
                    return((serviceContext, entity) => cmsSecurityProvider.TryAssert(serviceContext, entity, CrmEntityRight.Read));
                }

                var entityPermissionProvider = new CrmEntityPermissionProvider(portalName);

                return((serviceContext, entity) =>
                {
                    if (cmsSecurityProvider.TryAssert(serviceContext, entity, CrmEntityRight.Read))
                    {
                        return true;
                    }

                    var permissionResult = entityPermissionProvider.TryAssert(serviceContext, entity);

                    return permissionResult.RulesExist && permissionResult.CanRead;
                });
            }
コード例 #26
0
        private EntityPermissionsDrop GetPermissions()
        {
            if (!AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                return(null);
            }

            if (FullEntity == null)
            {
                return(null);
            }

            using (var serviceContext = PortalViewContext.CreateServiceContext())
            {
                var clone = serviceContext.MergeClone(FullEntity);

                var permissionResult = new CrmEntityPermissionProvider(PortalViewContext.PortalName)
                                       .TryAssert(serviceContext, clone);

                return(permissionResult == null
                                        ? null
                                        : new EntityPermissionsDrop(permissionResult));
            }
        }
コード例 #27
0
        /// <summary>
        /// Constructor
        /// </summary>
        public ViewLayout(ViewConfiguration configuration, EntityView view = null, string portalName = null, int languageCode = 0,
                          bool addSelectColumn = false, bool addActionsColumn = false, string selectColumnHeaderText          = "")
        {
            Configuration = configuration;

            var serviceContext = PortalCrmConfigurationManager.CreateServiceContext(portalName);

            if (view == null)
            {
                view = Configuration.GetEntityView(serviceContext, languageCode);
            }

            View = view;

            ViewName = view.Name;

            Id = view.Id;

            SortExpression = view.SortExpression;

            var overrideColumns = new List <ViewColumn>();

            if (addSelectColumn)
            {
                overrideColumns.Add(new ViewColumn("col-select", selectColumnHeaderText ?? string.Empty, null, 20, 0, true, ViewColumnType.Select));
            }

            if (Configuration.ColumnOverrides.Any())
            {
                foreach (var columnA in View.Columns)
                {
                    var match = false;
                    foreach (var columnB in Configuration.ColumnOverrides)
                    {
                        if (columnA.LogicalName == columnB.AttributeLogicalName)
                        {
                            match = true;
                            overrideColumns.Add(new ViewColumn(columnB.AttributeLogicalName,
                                                               string.IsNullOrWhiteSpace(columnB.DisplayName) ? columnA.Name : columnB.DisplayName, null,
                                                               columnB.Width == 0 ? columnA.Width : columnB.Width, 0, columnA.SortDisabled));
                        }
                    }
                    if (!match)
                    {
                        overrideColumns.Add(new ViewColumn(columnA.LogicalName, columnA.Name, columnA.Metadata, columnA.Width, 0, columnA.SortDisabled));
                    }
                }
            }
            else
            {
                overrideColumns.AddRange(View.Columns.Select(c => new ViewColumn(c.LogicalName, c.Name, c.Metadata, c.Width, 0, c.SortDisabled)));
            }

            if (addActionsColumn)
            {
                overrideColumns.Add(new ViewColumn("col-action", configuration.ActionColumnHeaderText ??
                                                   "<span class='sr-only'>Actions</span>", null, configuration.ActionLinksColumnWidth, 0, true, ViewColumnType.Actions));
            }

            ColumnsTotalWidth = overrideColumns.Sum(c => c.Width);
            // Adjust the widths to be percentage based
            foreach (var column in overrideColumns)
            {
                var columnWidth = overrideColumns.FirstOrDefault(o => o.LogicalName == column.LogicalName);
                if (columnWidth == null)
                {
                    continue;
                }
                var width = Convert.ToDouble(columnWidth.Width) / ColumnsTotalWidth * 100;
                column.WidthAsPercent = width;
            }

            Columns = overrideColumns;

            if (configuration.EnableEntityPermissions && AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                var insertActionEnabled   = configuration.InsertActionLink.Enabled;
                var createViewActionLinks = configuration.ViewActionLinks.Where(viewAction => viewAction.Enabled &&
                                                                                viewAction.Type == LinkActionType.Insert);

                if (insertActionEnabled || createViewActionLinks.Any())
                {
                    var crmEntityPermissionProvider = new CrmEntityPermissionProvider(configuration.PortalName);
                    var canCreate = crmEntityPermissionProvider.TryAssert(serviceContext, CrmEntityPermissionRight.Create,
                                                                          configuration.EntityName);

                    if (insertActionEnabled)
                    {
                        configuration.InsertActionLink.Enabled = canCreate;
                    }

                    foreach (var action in createViewActionLinks)
                    {
                        action.Enabled = canCreate;
                    }
                }
            }

            // Produce a secure configuration converted to a Base64 string
            var configurationJson = JsonConvert.SerializeObject(configuration, new JsonSerializerSettings {
                Converters = new List <JsonConverter> {
                    new UrlBuilderConverter()
                }
            });
            var configurationByteArray = Encoding.UTF8.GetBytes(configurationJson);
            var protectedByteArray     = MachineKey.Protect(configurationByteArray, "Secure View Configuration");

            Base64SecureConfiguration = Convert.ToBase64String(protectedByteArray);
        }
        /// <summary>
        /// Process the message from the HTTP POST request and rebuild the search index.
        /// </summary>
        /// <param name="message"></param>
        public static void ProcessMessage(OrganizationServiceCachePluginMessage message, SearchIndexInvalidationData searchIndexInvalidationData = null, OrganizationServiceContext serviceContext = null)
        {
            if (!SearchManager.Enabled)
            {
                ADXTrace.Instance.TraceInfo(TraceCategory.Application, "Search isn't enabled for the current application.");

                return;
            }

            if (message == null)
            {
                ADXTrace.Instance.TraceError(TraceCategory.Application, "Search Index build failure. Plugin Message is null.");

                return;
            }

            SearchProvider provider;
            var            forceBuild = message.Target != null && message.Target.LogicalName == "adx_website";

            if (!TryGetSearchProvider(out provider))
            {
                ADXTrace.Instance.TraceError(TraceCategory.Application, "Search Index build failure. Search Provider could not be found.");

                return;
            }

            if (forceBuild || BuildMessages.Contains(message.MessageName, MessageComparer))
            {
                PerformBuild(provider);

                ADXTrace.Instance.TraceInfo(TraceCategory.Application, "Search Index was successfully built.");

                return;
            }

            IContentMapProvider contentMapProvider = AdxstudioCrmConfigurationManager.CreateContentMapProvider();

            if (UpdateMessages.Contains(message.MessageName, MessageComparer))
            {
                if (message.Target == null || string.IsNullOrEmpty(message.Target.LogicalName))
                {
                    throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an EntityName (entity logical name) parameter.", message.MessageName));
                }

                if (message.Target == null || message.Target.Id == Guid.Empty)
                {
                    throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an ID (entity ID) parameter.", message.MessageName));
                }

                if (FeatureCheckHelper.IsFeatureEnabled(FeatureNames.CmsEnabledSearching))
                {
                    if (message.Target.LogicalName == "savedquery")
                    {
                        var cachedSavedQuery = SearchMetadataCache.Instance.SearchSavedQueries.FirstOrDefault(x => x.SavedQueryId == message.Target.Id);
                        if (cachedSavedQuery != null)
                        {
                            // SavedQueryUniqueId is timestamp to verify which change was published and need to invalidate Search Index
                            var actualSavedQueryUniqueId = SearchMetadataCache.Instance.GetSavedQueryUniqueId(message.Target.Id);
                            if (cachedSavedQuery.SavedQueryIdUnique != actualSavedQueryUniqueId)
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateEntitySet(cachedSavedQuery.EntityName));
                                SearchMetadataCache.Instance.CompleteMetadataUpdateForSearchSavedQuery(cachedSavedQuery, actualSavedQueryUniqueId);
                            }
                        }
                    }

                    if (message.Target.LogicalName == "adx_webpage" && searchIndexInvalidationData != null)
                    {
                        // bypass cache and go straight to CRM in case cache hasn't been updated yet
                        var response = serviceContext.Execute(new RetrieveRequest {
                            Target    = new EntityReference(message.Target.LogicalName, message.Target.Id),
                            ColumnSet = new ColumnSet(new string[] {
                                "adx_parentpageid",
                                "adx_websiteid",
                                "adx_publishingstateid",
                                "adx_partialurl"
                            })
                        }) as RetrieveResponse;

                        if (response != null && response.Entity != null)
                        {
                            var updatedWebPage = response.Entity;

                            // If the parent page or website change, we need to invalidate that whole section of the web page hierarchy since the web roles
                            // may change, including both root and content pages if MLP is enabled.
                            if (!EntityReferenceEquals(searchIndexInvalidationData.ParentPage, updatedWebPage.GetAttributeValue <EntityReference>("adx_parentpageid")) ||
                                !EntityReferenceEquals(searchIndexInvalidationData.Website, updatedWebPage.GetAttributeValue <EntityReference>("adx_websiteid")))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_webpage", message.Target.Id));
                            }
                            // If the publishing state or partial URL change, this will effect all the content pages and localized entities underneath them
                            // if MLP is enabled. If MLP is disabled, LCID will equal null, and then just all pages/entities underneath this will reindex.
                            else if (!EntityReferenceEquals(searchIndexInvalidationData.PublishingState, updatedWebPage.GetAttributeValue <EntityReference>("adx_publishingstateid")) ||
                                     searchIndexInvalidationData.PartialUrl != updatedWebPage.GetAttributeValue <string>("adx_partialurl"))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_webpage", message.Target.Id, searchIndexInvalidationData.Lcid));
                            }
                        }
                    }

                    if (message.Target.LogicalName == "adx_webpageaccesscontrolrule_webrole")
                    {
                        contentMapProvider.Using(contentMap =>
                        {
                            WebPageAccessControlRuleToWebRoleNode webAccessControlToWebRoleNode;

                            if (contentMap.TryGetValue(new EntityReference(message.Target.LogicalName, message.Target.Id), out webAccessControlToWebRoleNode))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_webpage", webAccessControlToWebRoleNode.WebPageAccessControlRule.WebPage.Id));
                            }
                        });
                    }

                    if (message.Target.LogicalName == "adx_webpageaccesscontrolrule")
                    {
                        contentMapProvider.Using(contentMap =>
                        {
                            WebPageAccessControlRuleNode webAccessControlNode;

                            if (contentMap.TryGetValue(new EntityReference(message.Target.LogicalName, message.Target.Id), out webAccessControlNode))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_webpage", webAccessControlNode.WebPage.Id));
                            }
                        });
                    }

                    if (message.Target.LogicalName == "adx_communityforumaccesspermission")
                    {
                        contentMapProvider.Using(contentMap =>
                        {
                            ForumAccessPermissionNode forumAccessNode;

                            if (contentMap.TryGetValue(new EntityReference(message.Target.LogicalName, message.Target.Id), out forumAccessNode))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_communityforum", forumAccessNode.Forum.Id));
                            }
                        });
                    }

                    if (message.Target.LogicalName == "connection")
                    {
                        var fetch = new Fetch
                        {
                            Entity = new FetchEntity("connection")
                            {
                                Filters = new[] { new Filter {
                                                      Conditions = new List <Condition> {
                                                          new Condition("connectionid", ConditionOperator.Equal, message.Target.Id)
                                                      }
                                                  } }
                            }
                        };

                        var connectionEntity = ((RetrieveSingleResponse)serviceContext.Execute(fetch.ToRetrieveSingleRequest())).Entity;

                        var record1Id = connectionEntity.GetAttributeValue <EntityReference>("record1id");
                        var record2Id = connectionEntity.GetAttributeValue <EntityReference>("record2id");

                        // new product association to knowledge article could mean new product filtering rules
                        if (record1Id != null && record1Id.LogicalName == "knowledgearticle" &&
                            record2Id != null && record2Id.LogicalName == "product")
                        {
                            PerformUpdate(provider, updater => updater.UpdateEntity("knowledgearticle", record1Id.Id));
                        }
                    }
                    if (message.Target.LogicalName == "adx_contentaccesslevel")
                    {
                        var fetch = GetEntityFetch("adx_knowledgearticlecontentaccesslevel", "knowledgearticleid",
                                                   "adx_contentaccesslevelid", message.Target.Id.ToString());

                        var entities = FetchEntities(serviceContext, fetch);
                        var guids    = entities.Select(e => e.GetAttributeValue <Guid>("knowledgearticleid")).ToList();

                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("knowledgearticle", "knowledgearticleid", guids));
                    }
                    if (message.Target.LogicalName == "product")
                    {
                        var fetch = GetEntityFetch("connection", "record2id", "record1id", message.Target.Id.ToString());

                        var entities = FetchEntities(serviceContext, fetch);
                        var guids    = entities.Select(e => e.GetAttributeValue <EntityReference>("record2id")).Select(g => g.Id).Distinct().ToList();

                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("knowledgearticle", "knowledgearticleid", guids));
                    }
                    if (message.Target.LogicalName == "annotation")
                    {
                        var annotationFetch = new Fetch
                        {
                            Entity = new FetchEntity("annotation", new[] { "objectid" })
                            {
                                Filters = new[]
                                {
                                    new Filter
                                    {
                                        Conditions = new List <Condition>
                                        {
                                            new Condition("annotationid", ConditionOperator.Equal, message.Target.Id),
                                        }
                                    }
                                }
                            }
                        };


                        var response =
                            (RetrieveSingleResponse)serviceContext.Execute(annotationFetch.ToRetrieveSingleRequest());

                        if (response.Entity == null)
                        {
                            ADXTrace.Instance.TraceError(TraceCategory.Application, $"Retrieve of annotation entity failed for annotationId : {message.Target.Id}");
                            throw new TransientNullReferenceException($"Retrieve of annotation entity failed for annotationId : {message.Target.Id}");
                        }

                        var knowledgeArticle = response.Entity?.GetAttributeValue <EntityReference>("objectid");
                        if (knowledgeArticle == null)
                        {
                            ADXTrace.Instance.TraceError(TraceCategory.Application, $"Could not find objectId in the retrieved annotation with annotationId : {message.Target.Id}");
                            throw new TransientNullReferenceException($"Could not find objectId in the retrieved annotation with annotationId : {message.Target.Id}");
                        }

                        if (knowledgeArticle.Id != Guid.Empty && knowledgeArticle.LogicalName == "knowledgearticle")
                        {
                            //Updating Knowledge Article related to this Annotation
                            PerformUpdate(provider, updater => updater.UpdateEntity("knowledgearticle", knowledgeArticle.Id));
                        }
                    }
                    //Re-indexing annotations and related knowledge articles if NotesFilter gets changes
                    if (message.Target.LogicalName == "adx_sitesetting" && message.Target.Name == "KnowledgeManagement/NotesFilter")
                    {
                        var notes             = GetAllNotes(serviceContext);
                        var knowledgeArticles = notes.Select(n => n.GetAttributeValue <EntityReference>("objectid"))
                                                .Distinct().Select(ka => ka.Id).Distinct()
                                                .ToList();

                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("annotation", "annotationid", notes.Select(n => n.Id).Distinct().ToList()));
                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("knowledgearticle", "knowledgearticleid", knowledgeArticles));

                        return;
                    }
                    if (message.Target.LogicalName == "adx_sitesetting" && message.Target.Name == "KnowledgeManagement/DisplayNotes")
                    {
                        PerformUpdateAsync(provider, updater => updater.DeleteEntitySet("annotation"));

                        var notes             = GetAllNotes(serviceContext);
                        var knowledgeArticles = notes.Select(n => n.GetAttributeValue <EntityReference>("objectid"))
                                                .Distinct().Select(ka => ka.Id).Distinct()
                                                .ToList();

                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("annotation", "annotationid", notes.Select(n => n.Id).Distinct().ToList()));
                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("knowledgearticle", "knowledgearticleid", knowledgeArticles));
                        return;
                    }
                }

                PerformUpdate(provider, updater => updater.UpdateEntity(message.Target.LogicalName, message.Target.Id));

                ADXTrace.Instance.TraceInfo(TraceCategory.Application, string.Format("Search Index was successfully updated. ({0}, {1}:{2})", message.MessageName, EntityNamePrivacy.GetEntityName(message.Target.LogicalName), message.Target.Id));

                return;
            }

            if (FeatureCheckHelper.IsFeatureEnabled(FeatureNames.CmsEnabledSearching))
            {
                if (AssociateDisassociateMessages.Contains(message.MessageName, MessageComparer))
                {
                    if (message.Target == null || string.IsNullOrEmpty(message.Target.LogicalName))
                    {
                        throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an EntityName (entity logical name) parameter.", message.MessageName));
                    }

                    if (message.Target == null || message.Target.Id == Guid.Empty)
                    {
                        throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an ID (entity ID) parameter.", message.MessageName));
                    }

                    if (message.RelatedEntities == null)
                    {
                        throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an EntityName (entity logical name) parameter.", message.MessageName));
                    }

                    if ((message.Target.LogicalName == "adx_webpage" && HasRelatedEntityType(message, "adx_webpageaccesscontrolrule")) ||
                        (message.Target.LogicalName == "adx_communityforum" && HasRelatedEntityType(message, "adx_communityforumaccesspermission")) ||
                        (message.Target.LogicalName == "adx_ideaforum" && HasRelatedEntityType(message, "adx_webrole")))
                    {
                        PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree(message.Target.LogicalName, message.Target.Id));
                    }

                    if (message.Target.LogicalName == "adx_webpageaccesscontrolrule" &&
                        (HasRelatedEntityType(message, "adx_webrole") || HasRelatedEntityType(message, "adx_publishingstate")))
                    {
                        contentMapProvider.Using(contentMap =>
                        {
                            WebPageAccessControlRuleNode webAccessControlNode;

                            if (contentMap.TryGetValue(new EntityReference(message.Target.LogicalName, message.Target.Id), out webAccessControlNode))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_webpage", webAccessControlNode.WebPage.Id));
                            }
                        });
                    }

                    if (message.Target.LogicalName == "adx_communityforumaccesspermission" && HasRelatedEntityType(message, "adx_webrole"))
                    {
                        contentMapProvider.Using(contentMap =>
                        {
                            ForumAccessPermissionNode forumAccessNode;

                            if (contentMap.TryGetValue(new EntityReference(message.Target.LogicalName, message.Target.Id), out forumAccessNode))
                            {
                                PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree("adx_communityforum", forumAccessNode.Forum.Id));
                            }
                        });
                    }

                    if (message.Target.LogicalName == "adx_contentaccesslevel" && HasRelatedEntityType(message, "knowledgearticle"))
                    {
                        foreach (var entityReference in message.RelatedEntities)
                        {
                            if (entityReference.LogicalName == "knowledgearticle")
                            {
                                PerformUpdate(provider, updater => updater.UpdateEntity(entityReference.LogicalName, entityReference.Id));
                            }
                        }
                    }

                    //Perform update for disassociate messages from WebNotification Plugin
                    if (message.Target.LogicalName == "knowledgearticle" && (HasRelatedEntityType(message, "adx_contentaccesslevel")))
                    {
                        PerformUpdate(provider, updater => updater.UpdateEntity(message.Target.LogicalName, message.Target.Id));
                    }

                    ADXTrace.Instance.TraceInfo(TraceCategory.Application, string.Format("Search Index was successfully updated. ({0}, {1}:{2})", message.MessageName, EntityNamePrivacy.GetEntityName(message.Target.LogicalName), message.Target.Id));

                    return;
                }
            }

            if (DeleteMessages.Contains(message.MessageName, MessageComparer))
            {
                if (message.Target == null || string.IsNullOrEmpty(message.Target.LogicalName))
                {
                    throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an EntityName (entity logical name) parameter.", message.MessageName));
                }

                if (message.Target == null || message.Target.Id == Guid.Empty)
                {
                    throw new HttpException((int)HttpStatusCode.BadRequest, string.Format("Message {0} requires an ID (entity ID) parameter.", message.MessageName));
                }

                if (FeatureCheckHelper.IsFeatureEnabled(FeatureNames.CmsEnabledSearching))
                {
                    if (message.Target.LogicalName == "adx_webpageaccesscontrolrule" && searchIndexInvalidationData.WebPage != null)
                    {
                        PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree(searchIndexInvalidationData.WebPage.LogicalName, searchIndexInvalidationData.WebPage.Id));
                    }

                    if (message.Target.LogicalName == "adx_webpageaccesscontrolrule_webrole" && searchIndexInvalidationData.WebPage != null)
                    {
                        PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree(searchIndexInvalidationData.WebPage.LogicalName, searchIndexInvalidationData.WebPage.Id));
                    }

                    if (message.Target.LogicalName == "adx_communityforumaccesspermission" && searchIndexInvalidationData.Forum != null)
                    {
                        PerformUpdateAsync(provider, updater => updater.UpdateCmsEntityTree(searchIndexInvalidationData.Forum.LogicalName, searchIndexInvalidationData.Forum.Id));
                    }

                    if (message.Target.LogicalName == "connection")
                    {
                        // To update Knowledge Article that was related to this connection(Product) we need to retrieve KAid from index
                        var relatedEntityList = GetRelatedEntities("connectionid", message.Target.Id, 1);

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

                        // Taking first here since there can only be one Knowledge Article related to connection
                        var entity = relatedEntityList.First();
                        if (entity.LogicalName != null && entity.LogicalName.Equals("knowledgearticle"))
                        {
                            PerformUpdate(provider, updater => updater.UpdateEntity("knowledgearticle", entity.Id));
                        }
                        return;
                    }
                    if (message.Target.LogicalName == "product" || message.Target.LogicalName == "adx_contentaccesslevel")
                    {
                        IEnumerable <EntityReference> relatedKnowledgeArticles = new List <EntityReference>();
                        var indexedFieldName = "adx_contentaccesslevel";

                        if (message.Target.LogicalName == "product")
                        {
                            indexedFieldName = FixedFacetsConfiguration.ProductFieldFacetName;
                        }

                        relatedKnowledgeArticles = GetRelatedEntities(indexedFieldName, message.Target.Id, 10000);
                        if (!relatedKnowledgeArticles.Any())
                        {
                            return;
                        }

                        var knowledgeArticlesIds =
                            relatedKnowledgeArticles.Where(r => r.LogicalName.Equals("knowledgearticle")).Select(i => i.Id).ToList();

                        PerformUpdateAsync(provider, updater => updater.UpdateEntitySet("knowledgearticle", "knowledgearticleid", knowledgeArticlesIds));
                    }
                    if (message.Target.LogicalName == "annotation")
                    {
                        var relatedKnowledgeArticles = GetRelatedEntities("annotationid", message.Target.Id, 10);
                        var knowledgeArticleId       = relatedKnowledgeArticles.Where(a => a.LogicalName == "knowledgearticle").Select(ka => ka.Id).FirstOrDefault();

                        //Updating Knowledge Article related to this Annotation
                        PerformUpdate(provider, updater => updater.UpdateEntity("knowledgearticle", knowledgeArticleId));
                    }
                }

                PerformUpdate(provider, updater => updater.DeleteEntity(message.Target.LogicalName, message.Target.Id));

                ADXTrace.Instance.TraceInfo(TraceCategory.Application, string.Format("Search Index was successfully updated. ({0}, {1}:{2})", message.MessageName, EntityNamePrivacy.GetEntityName(message.Target.LogicalName), message.Target.Id));

                return;
            }

            var supportedMessages = DeleteMessages.Union(BuildMessages.Union(UpdateMessages, MessageComparer), MessageComparer);

            ADXTrace.Instance.TraceError(TraceCategory.Application, string.Format(@"Search Index Build Failed. Message ""{0}"" is not supported. Valid messages are {1}.", message.MessageName, string.Join(", ", supportedMessages.ToArray())));
        }
コード例 #29
0
        public override T GetDependency <T>(string name)
        {
            if (AdxstudioCrmConfigurationManager.GetCrmSection().ContentMap.Enabled)
            {
                var dependency = GetContentMapDependency <T>();

                if (dependency != null)
                {
                    return(dependency);
                }
            }

            if (typeof(T) == typeof(IEntityWebsiteProvider))
            {
                return(new AdxEntityWebsiteProvider() as T);
            }
            if (typeof(T) == typeof(IEntityUrlProvider))
            {
                return(new AdxEntityUrlProvider(new AdxEntityWebsiteProvider(), PortalName) as T);
            }
            if (typeof(T) == typeof(ICmsDataServiceQueryInterceptorProvider))
            {
                return(new AdxCmsDataServiceQueryInterceptorProvider(PortalName) as T);
            }
            if (typeof(T) == typeof(IRegisterClientSideDependenciesProvider))
            {
                return(new AdxRegisterClientSideDependenciesProvider() as T);
            }
            if (typeof(T) == typeof(ICmsEntityEditingMetadataProvider))
            {
                return(new CmsEntityEditingMetadataProvider(PortalName) as T);
            }
            if (typeof(T) == typeof(ICrmEntityEditingMetadataProvider))
            {
                return(new CrmEntityEditingMetadataProviderAdapter(new CmsEntityEditingMetadataProvider(PortalName), PortalName) as T);
            }
            if (typeof(T) == typeof(ICmsDataServiceProvider))
            {
                return(new AdxCmsDataServiceProvider(PortalName) as T);
            }
            if (typeof(T) == typeof(ICmsEntityServiceProvider))
            {
                return(new CmsEntityServiceProvider(PortalName) as T);
            }
            if (typeof(T) == typeof(IRedirectProvider))
            {
                return(new CompositeRedirectProvider(new RedirectProvider(PortalName), new CanonicalUrlRedirectProvider(), new UrlHistoryRedirectProvider(PortalName)) as T);
            }
            if (typeof(T) == typeof(IPublishingStateTransitionSecurityProvider))
            {
                return(new PublishingStateTransitionSecurityProvider() as T);
            }
            if (typeof(T) == typeof(ICrmEntityFileAttachmentProvider))
            {
                return(new NotesFileAttachmentProvider(PortalName) as T);
            }
            if (typeof(T) == typeof(IPortalRouteHandlerProvider))
            {
                return(new PortalRouteHandlerProvider(PortalName) as T);
            }

            return(base.GetDependency <T>(name));
        }
コード例 #30
0
 private static IContentMapProvider GetContentMapProvider(string portalName)
 {
     return(AdxstudioCrmConfigurationManager.CreateContentMapProvider(portalName));
 }