// initialize a PublishedContentCache instance with // an XmlStore containing the master xml // an IAppCache that should be at request-level // a RoutesCache - need to cleanup that one // a preview token string (or null if not previewing) public PublishedContentCache( XmlStore xmlStore, // an XmlStore containing the master xml IDomainCache domainCache, // an IDomainCache implementation IAppCache appCache, // an IAppCache that should be at request-level IGlobalSettings globalSettings, ISiteDomainHelper siteDomainHelper, IUmbracoContextAccessor umbracoContextAccessor, PublishedContentTypeCache contentTypeCache, // a PublishedContentType cache RoutesCache routesCache, // a RoutesCache string previewToken) // a preview token string (or null if not previewing) : base(previewToken.IsNullOrWhiteSpace() == false) { _appCache = appCache; _globalSettings = globalSettings; _umbracoContextAccessor = umbracoContextAccessor; _routesCache = routesCache; // may be null for unit-testing _contentTypeCache = contentTypeCache; _domainCache = domainCache; _domainHelper = new DomainHelper(_domainCache, siteDomainHelper); _xmlStore = xmlStore; _xml = _xmlStore.Xml; // capture - because the cache has to remain consistent if (previewToken.IsNullOrWhiteSpace() == false) { _previewContent = new PreviewContent(_xmlStore, previewToken); } }
public static bool GetAssignedWithCulture(this IDomainCache domainCache, string culture, int documentId, bool includeWildcards = false) { var assigned = domainCache.GetAssigned(documentId, includeWildcards); // It's super important that we always compare cultures with ignore case, since we can't be sure of the casing! return(culture is null?assigned.Any() : assigned.Any(x => x.Culture.Equals(culture, StringComparison.InvariantCultureIgnoreCase))); }
// TODO: figure this out // after the current snapshot has been resync-ed // it's too late for UmbracoContext which has captured previewDefault and stuff into these ctor vars // but, no, UmbracoContext returns snapshot.Content which comes from elements SO a resync should create a new cache public ContentCache(bool previewDefault, ContentStore.Snapshot snapshot, IAppCache snapshotCache, IAppCache elementsCache, IDomainCache domainCache, IGlobalSettings globalSettings, IVariationContextAccessor variationContextAccessor) : base(previewDefault) { _snapshot = snapshot; _snapshotCache = snapshotCache; _elementsCache = elementsCache; _domainCache = domainCache; _globalSettings = globalSettings; _variationContextAccessor = variationContextAccessor; }
public static bool GetAssignedWithCulture(this IDomainCache domainCache, string?culture, int documentId, bool includeWildcards = false) { IEnumerable <Domain> assigned = domainCache.GetAssigned(documentId, includeWildcards); // It's super important that we always compare cultures with ignore case, since we can't be sure of the casing! // Comparing with string.IsNullOrEmpty since both empty string and null signifies invariant. return(string.IsNullOrEmpty(culture) ? assigned.Any() : assigned.Any(x => x.Culture?.Equals(culture, StringComparison.InvariantCultureIgnoreCase) ?? false)); }
// TODO: figure this out // after the current snapshot has been resync-ed // it's too late for UmbracoContext which has captured previewDefault and stuff into these ctor vars // but, no, UmbracoContext returns snapshot.Content which comes from elements SO a resync should create a new cache public ContentCache( bool previewDefault, ContentStore.Snapshot snapshot, IAppCache snapshotCache, IAppCache?elementsCache, IDomainCache domainCache, IOptions <GlobalSettings> globalSettings, IVariationContextAccessor variationContextAccessor) : base(previewDefault) { _snapshot = snapshot; _snapshotCache = snapshotCache; _elementsCache = elementsCache; _domainCache = domainCache ?? throw new ArgumentNullException(nameof(domainCache)); _globalSettings = globalSettings.Value; _variationContextAccessor = variationContextAccessor; }
/// <summary> /// Finds the domain for the specified node, if any, that best matches a specified uri. /// </summary> /// <param name="domainCache">A domain cache.</param> /// <param name="siteDomainHelper">The site domain helper.</param> /// <param name="nodeId">The node identifier.</param> /// <param name="current">The uri, or null.</param> /// <param name="culture">The culture, or null.</param> /// <returns>The domain and its uri, if any, that best matches the specified uri and culture, else null.</returns> /// <remarks> /// <para>If at least a domain is set on the node then the method returns the domain that /// best matches the specified uri and culture, else it returns null.</para> /// <para>If culture is null, uses the default culture for the installation instead. Otherwise, /// will try with the specified culture, else return null.</para> /// </remarks> internal static DomainAndUri DomainForNode(IDomainCache domainCache, ISiteDomainHelper siteDomainHelper, int nodeId, Uri current, string culture = null) { // be safe if (nodeId <= 0) { return(null); } // get the domains on that node var domains = domainCache.GetAssigned(nodeId).ToArray(); // none? if (domains.Length == 0) { return(null); } // else filter // it could be that none apply (due to culture) return(SelectDomain(domains, current, culture, domainCache.DefaultCulture, siteDomainHelper.MapDomain)); }
/// <summary> /// Find the domains for the specified node, if any, that match a specified uri. /// </summary> /// <param name="domainCache">A domain cache.</param> /// <param name="siteDomainHelper">The site domain helper.</param> /// <param name="nodeId">The node identifier.</param> /// <param name="current">The uri, or null.</param> /// <param name="excludeDefault">A value indicating whether to exclude the current/default domain. True by default.</param> /// <returns>The domains and their uris, that match the specified uri, else null.</returns> /// <remarks>If at least a domain is set on the node then the method returns the domains that /// best match the specified uri, else it returns null.</remarks> internal static IEnumerable <DomainAndUri> DomainsForNode(IDomainCache domainCache, ISiteDomainHelper siteDomainHelper, int nodeId, Uri current, bool excludeDefault = true) { // be safe if (nodeId <= 0) { return(null); } // get the domains on that node var domains = domainCache.GetAssigned(nodeId).ToArray(); // none? if (domains.Length == 0) { return(null); } // get the domains and their uris var domainAndUris = SelectDomains(domains, current).ToArray(); // filter return(siteDomainHelper.MapDomains(domainAndUris, current, excludeDefault, null, domainCache.DefaultCulture).ToArray()); }
public DomainHelper(IDomainCache domainCache, ISiteDomainHelper siteDomainHelper) { _domainCache = domainCache; _siteDomainHelper = siteDomainHelper; }
/// <summary> /// Finds the site root (if any) matching the http request, and updates the PublishedRequest accordingly. /// </summary> /// <returns>A value indicating whether a domain was found.</returns> internal bool FindDomain(IPublishedRequestBuilder request) { const string tracePrefix = "FindDomain: "; // note - we are not handling schemes nor ports here. _logger.LogDebug("{TracePrefix}Uri={RequestUri}", tracePrefix, request.Uri); var umbracoContext = _umbracoContextAccessor.GetRequiredUmbracoContext(); IDomainCache domainsCache = umbracoContext.PublishedSnapshot.Domains; var domains = domainsCache.GetAll(includeWildcards: false).ToList(); // determines whether a domain corresponds to a published document, since some // domains may exist but on a document that has been unpublished - as a whole - or // that is not published for the domain's culture - in which case the domain does // not apply bool IsPublishedContentDomain(Domain domain) { // just get it from content cache - optimize there, not here IPublishedContent domainDocument = umbracoContext.PublishedSnapshot.Content.GetById(domain.ContentId); // not published - at all if (domainDocument == null) { return(false); } // invariant - always published if (!domainDocument.ContentType.VariesByCulture()) { return(true); } // variant, ensure that the culture corresponding to the domain's language is published return(domainDocument.Cultures.ContainsKey(domain.Culture)); } domains = domains.Where(IsPublishedContentDomain).ToList(); var defaultCulture = domainsCache.DefaultCulture; // try to find a domain matching the current request DomainAndUri domainAndUri = DomainUtilities.SelectDomain(domains, request.Uri, defaultCulture: defaultCulture); // handle domain - always has a contentId and a culture if (domainAndUri != null) { // matching an existing domain _logger.LogDebug("{TracePrefix}Matches domain={Domain}, rootId={RootContentId}, culture={Culture}", tracePrefix, domainAndUri.Name, domainAndUri.ContentId, domainAndUri.Culture); request.SetDomain(domainAndUri); // canonical? not implemented at the moment // if (...) // { // _pcr.RedirectUrl = "..."; // return true; // } } else { // not matching any existing domain _logger.LogDebug("{TracePrefix}Matches no domain", tracePrefix); request.SetCulture(defaultCulture ?? CultureInfo.CurrentUICulture.Name); } _logger.LogDebug("{TracePrefix}Culture={CultureName}", tracePrefix, request.Culture); return(request.Domain != null); }
public static bool GetAssignedWithCulture(this IDomainCache domainCache, string culture, int documentId, bool includeWildcards = false) { var assigned = domainCache.GetAssigned(documentId, includeWildcards); return(culture is null?assigned.Any() : assigned.Any(x => x.Culture == culture)); }