Пример #1
0
        //gavdcodeend 12

        //gavdcodebegin 13
        static void SpCsCsomAddSiteToHubSiteCollection(ClientContext spAdminCtx)
        {
            Tenant myTenant = new Tenant(spAdminCtx);

            myTenant.ConnectSiteToHubSite(
                ConfigurationManager.AppSettings["spBaseUrl"] +
                "/sites/NewSiteForHub",
                ConfigurationManager.AppSettings["spBaseUrl"] +
                "/sites/NewHubSiteCollCsCsom");
            spAdminCtx.ExecuteQuery();
        }
Пример #2
0
        public override TokenParser ProvisionObjects(Web web, ProvisioningTemplate template, TokenParser parser, ProvisioningTemplateApplyingInformation applyingInformation)
        {
            using (var scope = new PnPMonitoredScope(this.Name))
            {
                if (template.WebSettings != null)
                {
                    // Check if this is not a noscript site as we're not allowed to update some properties
                    bool isNoScriptSite = web.IsNoScriptSite();

                    web.EnsureProperties(
#if !ONPREMISES
                        w => w.CommentsOnSitePagesDisabled,
#endif
                        w => w.WebTemplate,
                        w => w.HasUniqueRoleAssignments);

                    var webSettings = template.WebSettings;

                    // Since the IsSubSite function can trigger an executequery ensure it's called before any updates to the web object are done.
                    if (!web.IsSubSite() || (web.IsSubSite() && web.HasUniqueRoleAssignments))
                    {
                        String requestAccessEmailValue = parser.ParseString(webSettings.RequestAccessEmail);
                        if (!String.IsNullOrEmpty(requestAccessEmailValue) && requestAccessEmailValue.Length >= 255)
                        {
                            requestAccessEmailValue = requestAccessEmailValue.Substring(0, 255);
                        }
                        if (!String.IsNullOrEmpty(requestAccessEmailValue))
                        {
                            web.RequestAccessEmail = requestAccessEmailValue;

                            web.Update();
                            web.Context.ExecuteQueryRetry();
                        }
                    }

#if !ONPREMISES
                    if (!isNoScriptSite)
                    {
                        web.NoCrawl = webSettings.NoCrawl;
                    }
                    else
                    {
                        scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipNoCrawlUpdate);
                    }

                    if (web.CommentsOnSitePagesDisabled != webSettings.CommentsOnSitePagesDisabled)
                    {
                        web.CommentsOnSitePagesDisabled = webSettings.CommentsOnSitePagesDisabled;
                    }
#endif
                    var masterUrl = parser.ParseString(webSettings.MasterPageUrl);
                    if (!string.IsNullOrEmpty(masterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.MasterUrl = masterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipMasterPageUpdate);
                        }
                    }
                    var customMasterUrl = parser.ParseString(webSettings.CustomMasterPageUrl);
                    if (!string.IsNullOrEmpty(customMasterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.CustomMasterUrl = customMasterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipCustomMasterPageUpdate);
                        }
                    }
                    if (webSettings.Title != null)
                    {
                        web.Title = parser.ParseString(webSettings.Title);
                    }
                    if (webSettings.Description != null)
                    {
                        web.Description = parser.ParseString(webSettings.Description);
                    }
                    if (webSettings.SiteLogo != null)
                    {
                        var logoUrl = parser.ParseString(webSettings.SiteLogo);
                        // Modern site? Then we assume the SiteLogo is actually a filepath
                        if (web.WebTemplate == "GROUP")
                        {
#if !ONPREMISES
                            if (!string.IsNullOrEmpty(logoUrl) && !logoUrl.ToLower().Contains("_api/groupservice/getgroupimage"))
                            {
                                var fileBytes = ConnectorFileHelper.GetFileBytes(template.Connector, logoUrl);
                                if (fileBytes != null && fileBytes.Length > 0)
                                {
#if !NETSTANDARD2_0
                                    var mimeType = MimeMapping.GetMimeMapping(logoUrl);
#else
                                    var mimeType = "";
                                    var imgUrl   = logoUrl;
                                    if (imgUrl.Contains("?"))
                                    {
                                        imgUrl = imgUrl.Split(new[] { '?' })[0];
                                    }
                                    if (imgUrl.EndsWith(".gif", StringComparison.InvariantCultureIgnoreCase))
                                    {
                                        mimeType = "image/gif";
                                    }
                                    if (imgUrl.EndsWith(".png", StringComparison.InvariantCultureIgnoreCase))
                                    {
                                        mimeType = "image/png";
                                    }
                                    if (imgUrl.EndsWith(".jpg", StringComparison.InvariantCultureIgnoreCase))
                                    {
                                        mimeType = "image/jpeg";
                                    }
#endif
                                    Sites.SiteCollection.SetGroupImage((ClientContext)web.Context, fileBytes, mimeType).GetAwaiter().GetResult();
                                }
                            }
#endif
                        }
                        else
                        {
                            web.SiteLogoUrl = logoUrl;
                        }
                    }
                    var welcomePage = parser.ParseString(webSettings.WelcomePage);
                    if (!string.IsNullOrEmpty(welcomePage))
                    {
                        web.RootFolder.WelcomePage = welcomePage;
                        web.RootFolder.Update();
                    }
                    if (webSettings.AlternateCSS != null)
                    {
                        web.AlternateCssUrl = parser.ParseString(webSettings.AlternateCSS);
                    }
                    web.Update();
                    web.Context.ExecuteQueryRetry();

#if !ONPREMISES
                    if (webSettings.HubSiteUrl != null)
                    {
                        var hubsiteUrl = parser.ParseString(webSettings.HubSiteUrl);
                        try
                        {
                            using (var tenantContext = web.Context.Clone(web.GetTenantAdministrationUrl(), applyingInformation.AccessTokens))
                            {
                                var tenant = new Tenant(tenantContext);
                                tenant.ConnectSiteToHubSite(web.Url, hubsiteUrl);
                                tenantContext.ExecuteQueryRetry();
                            }
                        }
                        catch (Exception ex)
                        {
                            WriteMessage($"Hub site association failed: {ex.Message}", ProvisioningMessageType.Warning);
                        }
                    }
#endif
                }
            }

            return(parser);
        }
Пример #3
0
 protected override void ExecuteCmdlet()
 {
     Tenant.ConnectSiteToHubSite(Site.Url, HubSite.Url);
     ClientContext.ExecuteQueryRetry();
 }
Пример #4
0
        public override TokenParser ProvisionObjects(Web web, ProvisioningTemplate template, TokenParser parser, ProvisioningTemplateApplyingInformation applyingInformation)
        {
            using (var scope = new PnPMonitoredScope(this.Name))
            {
                if (template.WebSettings != null)
                {
                    // Check if this is not a noscript site as we're not allowed to update some properties
                    bool isNoScriptSite = web.IsNoScriptSite();

                    web.EnsureProperties(
#if !SP2013 && !SP2016
                        w => w.NoCrawl,
                        w => w.CommentsOnSitePagesDisabled,
                        w => w.ExcludeFromOfflineClient,
                        w => w.MembersCanShare,
                        w => w.DisableFlows,
                        w => w.DisableAppViews,
                        w => w.HorizontalQuickLaunch,
#if !SP2019
                        w => w.SearchScope,
                        w => w.SearchBoxInNavBar,
#endif
#endif
                        w => w.RootFolder,
                        w => w.Title,
                        w => w.Description,
                        w => w.AlternateCssUrl,
                        w => w.WebTemplate,
                        w => w.HasUniqueRoleAssignments);

                    var webSettings = template.WebSettings;

                    // Since the IsSubSite function can trigger an executequery ensure it's called before any updates to the web object are done.
                    if (!web.IsSubSite() || (web.IsSubSite() && web.HasUniqueRoleAssignments))
                    {
                        String requestAccessEmailValue = parser.ParseString(webSettings.RequestAccessEmail);
                        if (!String.IsNullOrEmpty(requestAccessEmailValue) && requestAccessEmailValue.Length >= 255)
                        {
                            requestAccessEmailValue = requestAccessEmailValue.Substring(0, 255);
                        }
                        if (!String.IsNullOrEmpty(requestAccessEmailValue))
                        {
                            web.RequestAccessEmail = requestAccessEmailValue;

                            web.Update();
                            web.Context.ExecuteQueryRetry();
                        }
                    }

#if !SP2013 && !SP2016
                    if (!isNoScriptSite)
                    {
                        web.NoCrawl = webSettings.NoCrawl;
                    }
                    else
                    {
                        scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipNoCrawlUpdate);
                    }

                    if (web.CommentsOnSitePagesDisabled != webSettings.CommentsOnSitePagesDisabled)
                    {
                        web.CommentsOnSitePagesDisabled = webSettings.CommentsOnSitePagesDisabled;
                    }

                    if (web.ExcludeFromOfflineClient != webSettings.ExcludeFromOfflineClient)
                    {
                        web.ExcludeFromOfflineClient = webSettings.ExcludeFromOfflineClient;
                    }

                    if (web.MembersCanShare != webSettings.MembersCanShare)
                    {
                        web.MembersCanShare = webSettings.MembersCanShare;
                    }

                    if (web.DisableFlows != webSettings.DisableFlows)
                    {
                        web.DisableFlows = webSettings.DisableFlows;
                    }

                    if (web.DisableAppViews != webSettings.DisableAppViews)
                    {
                        web.DisableAppViews = webSettings.DisableAppViews;
                    }

                    if (web.HorizontalQuickLaunch != webSettings.HorizontalQuickLaunch)
                    {
                        web.HorizontalQuickLaunch = webSettings.HorizontalQuickLaunch;
                    }

#if !SP2019
                    if (web.SearchScope.ToString() != webSettings.SearchScope.ToString())
                    {
                        web.SearchScope = (SearchScopeType)Enum.Parse(typeof(SearchScopeType), webSettings.SearchScope.ToString(), true);
                    }

                    if (web.SearchBoxInNavBar.ToString() != webSettings.SearchBoxInNavBar.ToString())
                    {
                        web.SearchBoxInNavBar = (SearchBoxInNavBarType)Enum.Parse(typeof(SearchBoxInNavBarType), webSettings.SearchBoxInNavBar.ToString(), true);
                    }

                    string searchCenterUrl = parser.ParseString(webSettings.SearchCenterUrl);
                    if (!string.IsNullOrEmpty(searchCenterUrl) &&
                        web.GetWebSearchCenterUrl(true) != webSettings.SearchCenterUrl)
                    {
                        web.SetWebSearchCenterUrl(webSettings.SearchCenterUrl);
                    }
#endif
#endif
                    var masterUrl = parser.ParseString(webSettings.MasterPageUrl);
                    if (!string.IsNullOrEmpty(masterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.MasterUrl = masterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipMasterPageUpdate);
                        }
                    }
                    var customMasterUrl = parser.ParseString(webSettings.CustomMasterPageUrl);
                    if (!string.IsNullOrEmpty(customMasterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.CustomMasterUrl = customMasterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipCustomMasterPageUpdate);
                        }
                    }
                    if (!String.IsNullOrEmpty(webSettings.Title))
                    {
                        var newTitle = parser.ParseString(webSettings.Title);
                        if (newTitle != web.Title)
                        {
                            web.Title = newTitle;
                        }
                    }
                    if (!String.IsNullOrEmpty(webSettings.Description))
                    {
                        var newDescription = parser.ParseString(webSettings.Description);
                        if (newDescription != web.Description)
                        {
                            web.Description = newDescription;
                        }
                    }
                    if (webSettings.SiteLogo != null)
                    {
                        var logoUrl = parser.ParseString(webSettings.SiteLogo);
                        if (template.BaseSiteTemplate == "SITEPAGEPUBLISHING#0" && web.WebTemplate == "GROUP")
                        {
                            // logo provisioning throws when applying across base template IDs; provisioning fails in this case
                            // this is the error that is already (rightly so) shown beforehand in the console: WARNING: The source site from which the template was generated had a base template ID value of SITEPAGEPUBLISHING#0, while the current target site has a base template ID value of GROUP#0. This could cause potential issues while applying the template.
                            WriteMessage("Applying site logo across base template IDs is not possible. Skipping site logo provisioning.", ProvisioningMessageType.Warning);
                        }
                        else
                        {
                            // Modern site? Then we assume the SiteLogo is actually a filepath
                            if (web.WebTemplate == "GROUP")
                            {
#if !ONPREMISES
                                if (!string.IsNullOrEmpty(logoUrl) && !logoUrl.ToLower().Contains("_api/groupservice/getgroupimage"))
                                {
                                    var fileBytes = ConnectorFileHelper.GetFileBytes(template.Connector, logoUrl);
                                    if (fileBytes != null && fileBytes.Length > 0)
                                    {
#if !NETSTANDARD2_0
                                        var mimeType = MimeMapping.GetMimeMapping(logoUrl);
#else
                                        var mimeType = "";
                                        var imgUrl   = logoUrl;
                                        if (imgUrl.Contains("?"))
                                        {
                                            imgUrl = imgUrl.Split(new[] { '?' })[0];
                                        }
                                        if (imgUrl.EndsWith(".gif", StringComparison.InvariantCultureIgnoreCase))
                                        {
                                            mimeType = "image/gif";
                                        }
                                        if (imgUrl.EndsWith(".png", StringComparison.InvariantCultureIgnoreCase))
                                        {
                                            mimeType = "image/png";
                                        }
                                        if (imgUrl.EndsWith(".jpg", StringComparison.InvariantCultureIgnoreCase))
                                        {
                                            mimeType = "image/jpeg";
                                        }
#endif
                                        Sites.SiteCollection.SetGroupImageAsync((ClientContext)web.Context, fileBytes, mimeType).GetAwaiter().GetResult();
                                    }
                                }
#endif
                            }
                            else
                            {
                                web.SiteLogoUrl = logoUrl;
                            }
                        }
                    }
                    var welcomePage = parser.ParseString(webSettings.WelcomePage);
                    if (!string.IsNullOrEmpty(welcomePage))
                    {
                        if (welcomePage != web.RootFolder.WelcomePage)
                        {
                            web.RootFolder.WelcomePage = welcomePage;
                            web.RootFolder.Update();
                        }
                    }
                    if (!string.IsNullOrEmpty(webSettings.AlternateCSS))
                    {
                        var newAlternateCssUrl = parser.ParseString(webSettings.AlternateCSS);
                        if (newAlternateCssUrl != web.AlternateCssUrl)
                        {
                            web.AlternateCssUrl = newAlternateCssUrl;
                        }
                    }

                    // Temporary disabled as this change is a breaking change for folks that have not set this property in their provisioning templates
                    //web.QuickLaunchEnabled = webSettings.QuickLaunchEnabled;

                    web.Update();
                    web.Context.ExecuteQueryRetry();

#if !ONPREMISES
                    if (webSettings.HubSiteUrl != null)
                    {
                        if (TenantExtensions.IsCurrentUserTenantAdmin(web.Context as ClientContext))
                        {
                            var hubsiteUrl = parser.ParseString(webSettings.HubSiteUrl);
                            try
                            {
                                using (var tenantContext = web.Context.Clone(web.GetTenantAdministrationUrl(), applyingInformation.AccessTokens))
                                {
                                    var tenant = new Tenant(tenantContext);
                                    tenant.ConnectSiteToHubSite(web.Url, hubsiteUrl);
                                    tenantContext.ExecuteQueryRetry();
                                }
                            }
                            catch (Exception ex)
                            {
                                WriteMessage($"Hub site association failed: {ex.Message}", ProvisioningMessageType.Warning);
                            }
                        }
                        else
                        {
                            WriteMessage("You need to be a SharePoint admin when associating to a Hub site.", ProvisioningMessageType.Warning);
                        }
                    }
#endif
                }
            }

            return(parser);
        }
Пример #5
0
        private void SetSiteProperties(Func <TenantOperationMessage, bool> timeoutFunction)
        {
            var props          = GetSiteProperties(Identity.Url);
            var updateRequired = false;

            if (ParameterSpecified(nameof(Title)))
            {
                props.Title    = Title;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(DenyAddAndCustomizePages)))
            {
                props.DenyAddAndCustomizePages = DenyAddAndCustomizePages ? DenyAddAndCustomizePagesStatus.Enabled : DenyAddAndCustomizePagesStatus.Disabled;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(LocaleId)))
            {
                props.Lcid     = LocaleId;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(AllowSelfServiceUpgrade)))
            {
                props.AllowSelfServiceUpgrade = AllowSelfServiceUpgrade;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(SharingAllowedDomainList)))
            {
                props.SharingAllowedDomainList = SharingAllowedDomainList;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(SharingBlockedDomainList)))
            {
                props.SharingBlockedDomainList = SharingBlockedDomainList;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(SharingDomainRestrictionMode)))
            {
                props.SharingDomainRestrictionMode = SharingDomainRestrictionMode;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(StorageQuota)))
            {
                props.StorageMaximumLevel = StorageQuota;
                updateRequired            = true;
            }
            if (ParameterSpecified(nameof(StorageQuotaWarningLevel)))
            {
                props.StorageWarningLevel = StorageQuotaWarningLevel;
                updateRequired            = true;
            }
            if (ParameterSpecified(nameof(StorageQuotaReset)))
            {
                props.StorageMaximumLevel = 0;
                updateRequired            = true;
            }
            if (ParameterSpecified(nameof(ResourceQuota)))
            {
                props.UserCodeMaximumLevel = ResourceQuota;
                updateRequired             = true;
            }
            if (ParameterSpecified(nameof(ResourceQuotaWarningLevel)))
            {
                props.UserCodeWarningLevel = ResourceQuotaWarningLevel;
                updateRequired             = true;
            }
            if (ParameterSpecified(nameof(SharingCapability)))
            {
                props.SharingCapability = SharingCapability;
                updateRequired          = true;
            }
            if (ParameterSpecified(nameof(DefaultLinkPermission)))
            {
                props.DefaultLinkPermission = DefaultLinkPermission;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(ShowPeoplePickerSuggestionsForGuestUsers)))
            {
                Tenant.EnsureProperty(t => t.ShowPeoplePickerSuggestionsForGuestUsers);
                if (!Tenant.ShowPeoplePickerSuggestionsForGuestUsers)
                {
                    WriteWarning("ShowPeoplePickerSuggestionsForGuests users has been disabled for this tenant. See Set-PnPTenant");
                }
                props.ShowPeoplePickerSuggestionsForGuestUsers = ShowPeoplePickerSuggestionsForGuestUsers;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(DefaultSharingLinkType)))
            {
                props.DefaultSharingLinkType = DefaultSharingLinkType;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(DefaultLinkToExistingAccess)))
            {
                props.DefaultLinkToExistingAccess = DefaultLinkToExistingAccess.Value;
                updateRequired = true;
            }
            if (ParameterSpecified(nameof(DefaultLinkToExistingAccessReset)))
            {
                props.DefaultLinkToExistingAccessReset = true;
                updateRequired = true;
            }
#pragma warning disable CS0618
            if (ParameterSpecified(nameof(BlockDownloadOfNonViewableFiles)) || ParameterSpecified(nameof(AllowDownloadingNonWebViewableFiles)))
            {
                var value = ParameterSpecified(nameof(BlockDownloadLinksFileTypes)) ? !BlockDownloadOfNonViewableFiles : AllowDownloadingNonWebViewableFiles;
                if (ConditionalAccessPolicy == SPOConditionalAccessPolicyType.AllowLimitedAccess)
                {
                    props.AllowDownloadingNonWebViewableFiles = value;
                    updateRequired = true;
                    if (!value)
                    {
                        WriteWarning("Users will not be able to download files that cannot be viewed on the web. To allow download of files that cannot be viewed on the web run the cmdlet again and set AllowDownloadingNonWebViewableFiles to true.");
                    }
                }
                else
                {
                    if (ShouldContinue("To set AllowDownloadingNonWebViewableFiles parameter you need to set the -ConditionalAccessPolicy parameter to AllowLimitedAccess. We can set the Conditional Access Policy of this site to AllowLimitedAccess. Would you like to continue?", string.Empty))
                    {
                        ConditionalAccessPolicy                   = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                        props.ConditionalAccessPolicy             = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                        props.AllowDownloadingNonWebViewableFiles = value;
                        if (!value)
                        {
                            WriteWarning("Users will not be able to download files that cannot be viewed on the web. To allow download of files that cannot be viewed on the web run the cmdlet again and set AllowDownloadingNonWebViewableFiles to true.");
                        }
                    }
                }
            }
#pragma warning restore CS0618

            if (ParameterSpecified(nameof(CommentsOnSitePagesDisabled)))
            {
                props.CommentsOnSitePagesDisabled = CommentsOnSitePagesDisabled;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(DisableAppViews)))
            {
                props.DisableAppViews = DisableAppViews;
                updateRequired        = true;
            }

            if (ParameterSpecified(nameof(DisableCompanyWideSharingLinks)))
            {
                props.DisableCompanyWideSharingLinks = DisableCompanyWideSharingLinks;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(DisableFlows)))
            {
                props.DisableFlows = DisableFlows;
                updateRequired     = true;
            }

            if (ParameterSpecified(nameof(EnablePWA)))
            {
                props.PWAEnabled = EnablePWA ? PWAEnabledStatus.Enabled : PWAEnabledStatus.Disabled;
                updateRequired   = true;
            }

            if (ParameterSpecified(nameof(OverrideTenantAnonymousLinkExpirationPolicy)))
            {
                props.OverrideTenantAnonymousLinkExpirationPolicy = OverrideTenantAnonymousLinkExpirationPolicy.ToBool();
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(AnonymousLinkExpirationInDays)) && AnonymousLinkExpirationInDays.HasValue)
            {
                props.AnonymousLinkExpirationInDays = AnonymousLinkExpirationInDays.Value;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(DisableSharingForNonOwners)))
            {
                var office365Tenant = new Office365Tenant(ClientContext);
                ClientContext.Load(office365Tenant);
                ClientContext.ExecuteQueryRetry();
                office365Tenant.DisableSharingForNonOwnersOfSite(Identity.Url);
            }

            if (ParameterSpecified(nameof(ConditionalAccessPolicy)) && ConditionalAccessPolicy == SPOConditionalAccessPolicyType.ProtectionLevel)
            {
                if (IsRootSite(Identity.Url))
                {
                    throw new PSInvalidOperationException("You cannot set the conditional access policy 'ProtectionLevel' on the root site.");
                }
                if (string.IsNullOrEmpty(ProtectionLevelName))
                {
                    props.AuthContextStrength = null;
                }
                else
                {
                    props.AuthContextStrength = ProtectionLevelName;
                }
                updateRequired = true;
            }
            else
            {
                if (ParameterSpecified(nameof(ProtectionLevelName)))
                {
                    throw new PSArgumentException("ConditionalAccessPolicy has to be set too when using this parameter.");
                }
                if (ParameterSpecified(nameof(ConditionalAccessPolicy)))
                {
                    props.AuthContextStrength = null;
                    updateRequired            = true;
                }
            }

            if (ClientContext.ServerVersion >= new Version(16, 0, 8715, 1200)) // ServerSupportsIpLabelId2
            {
                if (ParameterSpecified(nameof(SensitivityLabel)))
                {
                    props.SensitivityLabel2 = SensitivityLabel;
                    updateRequired          = true;
                }
                if (ParameterSpecified(nameof(RemoveLabel)))
                {
                    props.SensitivityLabel2 = null;
                    updateRequired          = true;
                }
            }
            else
            {
                WriteWarning("Server does not support setting sensitity label");
            }

            if (ParameterSpecified(nameof(LimitedAccessFileType)))
            {
                if (ConditionalAccessPolicy == SPOConditionalAccessPolicyType.AllowLimitedAccess)
                {
                    props.LimitedAccessFileType = LimitedAccessFileType;
                    updateRequired = true;
                }
                else if (ShouldContinue("To set LimitedAccessFileType you need to set the -ConditionalAccessPolicy parameter to AllowLimitedAccess. We can set the Conditional Access Policy of this site to AllowLimitedAccess. Would you like to continue?", string.Empty))
                {
                    ConditionalAccessPolicy       = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                    props.ConditionalAccessPolicy = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                    props.LimitedAccessFileType   = LimitedAccessFileType;
                    updateRequired = true;
                }
            }

            if (ParameterSpecified(nameof(AllowEditing)))
            {
                if (ConditionalAccessPolicy == SPOConditionalAccessPolicyType.AllowLimitedAccess)
                {
                    props.AllowEditing = AllowEditing;
                }
                else if (ShouldContinue("To set AllowEditing you need to set the -ConditionalAccessPolicy parameter to AllowLimitedAccess. We can set the Conditional Access Policy of this site to AllowLimitedAccess. Would you like to continue?", string.Empty))
                {
                    ConditionalAccessPolicy       = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                    props.ConditionalAccessPolicy = SPOConditionalAccessPolicyType.AllowLimitedAccess;
                    props.AllowEditing            = AllowEditing;
                }
            }

            if (ParameterSpecified(nameof(RestrictedToGeo)))
            {
                props.RestrictedToRegion = RestrictedToGeo;
                updateRequired           = true;
            }

            if (ParameterSpecified(nameof(ExternalUserExpirationInDays)))
            {
                props.ExternalUserExpirationInDays = ExternalUserExpirationInDays;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(OverrideTenantExternalUserExpirationPolicy)))
            {
                props.OverrideTenantExternalUserExpirationPolicy = OverrideTenantExternalUserExpirationPolicy;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(AddInformationSegment)) && AddInformationSegment.Length > 0)
            {
                props.IBSegmentsToAdd = AddInformationSegment;
                updateRequired        = true;
            }

            if (ParameterSpecified(nameof(RemoveInformationSegment)) && RemoveInformationSegment.Length > 0)
            {
                props.IBSegmentsToRemove = RemoveInformationSegment;
                updateRequired           = true;
            }

            if (ParameterSpecified(nameof(BlockDownloadLinksFileType)))
            {
                props.BlockDownloadLinksFileType = BlockDownloadLinksFileType;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(OverrideBlockUserInfoVisibility)))
            {
                props.OverrideBlockUserInfoVisibility = OverrideBlockUserInfoVisibility;
                updateRequired = true;
            }

            if (ParameterSpecified(nameof(HubSiteId)))
            {
                var hubsiteProperties = Tenant.GetHubSitePropertiesById(HubSiteId);
                ClientContext.Load(hubsiteProperties);
                ClientContext.ExecuteQueryRetry();
                if (hubsiteProperties == null || string.IsNullOrEmpty(hubsiteProperties.SiteUrl))
                {
                    throw new PSArgumentException("Hubsite not found with the ID specified");
                }
                if (hubsiteProperties.ID != Guid.Empty)
                {
                    Tenant.ConnectSiteToHubSiteById(Identity.Url, hubsiteProperties.ID);
                }
                else
                {
                    Tenant.ConnectSiteToHubSite(Identity.Url, hubsiteProperties.SiteUrl);
                }
                ClientContext.ExecuteQueryRetry();
            }

            if (updateRequired)
            {
                var op = props.Update();
                ClientContext.Load(op, i => i.IsComplete, i => i.PollingInterval);
                ClientContext.ExecuteQueryRetry();

                if (Wait)
                {
                    WaitForIsComplete(ClientContext, op, timeoutFunction, TenantOperationMessage.SettingSiteProperties);
                }
            }

            if (Owners != null && Owners.Count > 0)
            {
                var admins = new List <UserEntity>();
                foreach (var owner in Owners)
                {
                    var userEntity = new UserEntity {
                        LoginName = owner
                    };
                    admins.Add(userEntity);
                }
                Tenant.AddAdministrators(admins, new Uri(Identity.Url));
            }
        }
        public override TokenParser ProvisionObjects(Web web, ProvisioningTemplate template, TokenParser parser, ProvisioningTemplateApplyingInformation applyingInformation)
        {
            using (var scope = new PnPMonitoredScope(this.Name))
            {
                if (template.WebSettings != null)
                {
                    // Check if this is not a noscript site as we're not allowed to update some properties
                    bool isNoScriptSite = web.IsNoScriptSite();

                    web.EnsureProperties(
#if !ONPREMISES
                        w => w.CommentsOnSitePagesDisabled,
#endif
                        w => w.HasUniqueRoleAssignments);

                    var webSettings = template.WebSettings;
#if !ONPREMISES
                    if (!isNoScriptSite)
                    {
                        web.NoCrawl = webSettings.NoCrawl;
                    }
                    else
                    {
                        scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipNoCrawlUpdate);
                    }

                    if (!web.IsSubSite() || (web.IsSubSite() && web.HasUniqueRoleAssignments))
                    {
                        String requestAccessEmailValue = parser.ParseString(webSettings.RequestAccessEmail);
                        if (!String.IsNullOrEmpty(requestAccessEmailValue) && requestAccessEmailValue.Length >= 255)
                        {
                            requestAccessEmailValue = requestAccessEmailValue.Substring(0, 255);
                        }
                        if (!String.IsNullOrEmpty(requestAccessEmailValue))
                        {
                            web.RequestAccessEmail = requestAccessEmailValue;

                            web.Update();
                            web.Context.ExecuteQueryRetry();
                        }
                    }

                    if (web.CommentsOnSitePagesDisabled != webSettings.CommentsOnSitePagesDisabled)
                    {
                        web.CommentsOnSitePagesDisabled = webSettings.CommentsOnSitePagesDisabled;
                    }
#endif
                    var masterUrl = parser.ParseString(webSettings.MasterPageUrl);
                    if (!string.IsNullOrEmpty(masterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.MasterUrl = masterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipMasterPageUpdate);
                        }
                    }
                    var customMasterUrl = parser.ParseString(webSettings.CustomMasterPageUrl);
                    if (!string.IsNullOrEmpty(customMasterUrl))
                    {
                        if (!isNoScriptSite)
                        {
                            web.CustomMasterUrl = customMasterUrl;
                        }
                        else
                        {
                            scope.LogWarning(CoreResources.Provisioning_ObjectHandlers_WebSettings_SkipCustomMasterPageUpdate);
                        }
                    }
                    if (webSettings.Title != null)
                    {
                        web.Title = parser.ParseString(webSettings.Title);
                    }
                    if (webSettings.Description != null)
                    {
                        web.Description = parser.ParseString(webSettings.Description);
                    }
                    if (webSettings.SiteLogo != null)
                    {
                        web.SiteLogoUrl = parser.ParseString(webSettings.SiteLogo);
                    }
                    var welcomePage = parser.ParseString(webSettings.WelcomePage);
                    if (!string.IsNullOrEmpty(welcomePage))
                    {
                        web.RootFolder.WelcomePage = welcomePage;
                        web.RootFolder.Update();
                    }
                    if (webSettings.AlternateCSS != null)
                    {
                        web.AlternateCssUrl = parser.ParseString(webSettings.AlternateCSS);
                    }
                    web.Update();
                    web.Context.ExecuteQueryRetry();

#if !ONPREMISES
                    if (webSettings.HubSiteUrl != null)
                    {
                        var hubsiteUrl = parser.ParseString(webSettings.HubSiteUrl);
                        try
                        {
                            using (var tenantContext = web.Context.Clone(web.GetTenantAdministrationUrl()))
                            {
                                var tenant = new Tenant(tenantContext);
                                tenant.ConnectSiteToHubSite(web.Url, hubsiteUrl);
                                tenantContext.ExecuteQueryRetry();
                            }
                        }
                        catch (Exception ex)
                        {
                            WriteMessage($"Hub site association failed: {ex.Message}", ProvisioningMessageType.Warning);
                        }
                    }
#endif
                }
            }

            return(parser);
        }