อาการ
หลังจากที่คุณติดตั้งการอัปเดตความปลอดภัยสําหรับ Microsoft SharePoint Server ในเดือนตุลาคมต่อไปนี้ สถานการณ์สมมติของเวิร์กโฟลว์ SharePoint 2010 บางอย่างMicrosoftอาจถูกบล็อก นอกจากนี้ แท็กเหตุการณ์ "6ksbk" จะถูกบันทึกในบันทึก SharePoint Unified Logging System (ULS)
สาเหตุ
เมื่อต้องการเพิ่มความปลอดภัยให้กับเวิร์กโฟลว์ SharePoint ขณะนี้ SharePoint สนับสนุนการเข้ารหัสอักขระ UTF-8 สําหรับไฟล์ workflow .xoml เท่านั้น
หมายเหตุ: เครื่องมือเวิร์กโฟลว์ SharePoint เช่น SharePoint Designer Microsoft Visual Studio และ Nintex สร้างเวิร์กโฟลว์ ไฟล์ .xoml โดยใช้การเข้ารหัสอักขระ UTF-8 ตามค่าเริ่มต้น ลูกค้าจะไม่ได้รับผลกระทบจากการปรับปรุงความปลอดภัยนี้ เว้นแต่ว่าพวกเขาจะแก้ไขไฟล์ .xoml ของเวิร์กโฟลว์ด้วยตนเองและแปลงเป็นการเข้ารหัสอักขระอื่น ปัญหานี้มีการบันทึกไว้ในบทความ KB นี้เกี่ยวกับความเป็นไปได้น้อยมากที่ลูกค้าอาจเลือกที่จะทําเช่นนี้
วิธีแก้ไขปัญหา
ถ้าคุณได้แก้ไขไฟล์ .xoml ของเวิร์กโฟลว์ด้วยตนเองและแปลงเป็นการเข้ารหัสอักขระอื่นที่ไม่ใช่ UTF-8 คุณจะต้องแก้ไขไฟล์อีกครั้งเพื่อแปลงกลับเป็น UTF-8 ตรวจสอบให้แน่ใจว่าการประกาศ XML ของไฟล์กําหนดการเข้ารหัสเป็น UTF-8 บันทึกไฟล์ในรูปแบบการเข้ารหัสอักขระ UTF-8 ด้วยตัวแก้ไขข้อความของคุณ แล้วปรับใช้ใหม่
สคริปต์ PowerShell ต่อไปนี้สามารถใช้ใน SharePoint Management Shell เพื่อสแกนไฟล์ .xoml ของเวิร์กโฟลว์ในไซต์คอลเลกชัน SharePoint เพื่อตรวจสอบว่าไฟล์เหล่านั้นได้รับผลกระทบจากการเปลี่ยนแปลงนี้หรือไม่ ผลลัพธ์ IsGoodWorkflow จะถูก True สําหรับไฟล์ workflow .xoml ที่ใช้การเข้ารหัสอักขระ UTF-8 และเข้ากันได้กับการเปลี่ยนแปลงนี้ ผลลัพธ์ IsGoodWorkflow จะถูก False สําหรับไฟล์ workflow .xoml ที่ไม่ได้ใช้การเข้ารหัสอักขระ UTF-8 และจําเป็นต้องปรับเปลี่ยน
<#
.SYNOPSIS
Script to check character encoding of workflow .xoml files found in a site collection.
.DESCRIPTION
This script checks the character encoding of workflow .xoml files found in a site collection based
on the security improvement documented here: https://support.microsoft.com/topic/sharepoint-2010-workflows-might-be-blocked-by-enhanced-security-policy-kb5020238-eb91e24d-eea4-4490-a281-86503adc8b27
This could be altered to take an SPWebApplication object, iterate through all SPSite objects in the Sites SPSiteCollection,
and then iterate through all SPWeb subsites in the AllWebs SPWebCollection.
.EXAMPLE
Get-WorkflowStatusForSite -SiteCollectionUrl https://sharepoint
.EXAMPLE
Get-WorkflowStatusForSite -SiteCollectionUrl https://sharepoint -IgnoreSubSites
.INPUTS
None
.OUTPUTS
PSCustomObject with Site, Web, WorkflowFileName and IsGoodWorkflow Result
Site Web WorkflowFileName IsGoodWorkflow
---- --- ---------------- --------------
SPSite Url=http://sharepoint http://sharepoint/WorkflowTest 2010 Log Workflow.xoml True
SPSite Url=http://sharepoint http://sharepoint/WorkflowTest Another Test Log.xoml True
.NOTES
Version .1
#>
param(
[Parameter(Position=2,HelpMessage="The site collection URL to validate.")]
[string]$SiteCollectionUrl,
[Parameter(Position=3,HelpMessage="Ignore subsites below the top-level site in the site collection.")]
[switch]$IgnoreSubSites
)
function IsGoodWorkflow
{
param
(
[Parameter(Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)]
[System.Xml.XmlReader]$xmlReader
)
try {
$xDoc = [System.Xml.Linq.XDocument]::Load($xmlReader)
if ($null -ne $xDoc -and $null -ne $xDoc.Declaration -and $null -ne $xDoc.Declaration.Encoding)
{
if ($xdoc.Declaration.Encoding.ToLower() -ne "utf-8")
{
return $false
}
}
}
catch
{
return $false
}
return $true
}
function CheckWorkflowFile
{
param
(
[Parameter(Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)]
[Microsoft.SharePoint.SPFile]$SPFile
)
$xmlReader = [System.Xml.XmlReader]::Create($SPFile.OpenBinaryStream())
if ($null -ne $xmlReader)
{
$isGood = $xmlReader | IsGoodWorkflow
$xmlReader.Close()
$xmlReader.Dispose()
return [PSCustomObject]@{
Site = $SPFile.Item.Web.Site
Web = $SPFile.Item.Web.Url
WorkflowFileName = $SPFile.Name
IsGoodWorkflow = $isGood
}
}
}
function CheckWorkflowsForWeb
{
param
(
[Parameter(Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)]
[Microsoft.SharePoint.SPWeb]$SPWeb
)
write-host "Checking $SPweb"
$WorkflowsList = $SPWeb.Lists["Workflows"]
$results = @()
if ($WorkflowsList)
{
Write-Host "Found: " $WorkflowsList.Title
foreach ($listItem in $WorkflowsList.Items)
{
if ($listItem.File -and $listItem.File.Name.ToLower().EndsWith(".xoml"))
{
Write-Host "Found Workflow: " $listItem.File.Name
$results += (CheckWorkflowFile $listItem.File)
}
}
}
return $results
}
function CheckWorkflowsForSite
{
param
(
[Parameter(Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)]
[Microsoft.SharePoint.SPSite]$SPSite,
[switch]$IgnoreSubSites
)
$results = @()
if ($IgnoreSubSites)
{
$SPWeb = $SPSite.RootWeb
$results += CheckWorkflowsForWeb $SPWeb
$SPWeb.Dispose()
}
else
{
foreach ($SPWeb in $SPSite.AllWebs)
{
$results += CheckWorkflowsForWeb $SPWeb
$SPWeb.Dispose()
}
}
return $results
}
if ([string]::IsNullOrEmpty($SiteCollectionUrl))
{
$SiteCollectionUrl = Read-Host "Please provide a site collection URL (Default: http://sharepoint)"
if ([String]::IsNullOrEmpty($SiteCollectionUrl))
{
$SiteCollectionUrl = "http://sharepoint"
}
}
$SPSite = Get-SPSite $SiteCollectionUrl -ErrorAction SilentlyContinue
if ($null -eq $SPSite)
{
Write-Host "Site collection $SiteCollectionUrl not found." -ForegroundColor Red
return;
}
$results = CheckWorkflowsForSite $SPSite
# Dispose of the Site
$SPSite.Dispose()
# Results can be exported to a CSV or manipulated
$results
การเปลี่ยนแปลงประวัติ
ตารางต่อไปนี้สรุปการเปลี่ยนแปลงที่สําคัญที่สุดบางรายการในหัวข้อนี้
วันที่ |
คำอธิบาย |
---|---|
วันที่ 22 พฤศจิกายน 2565 |
เพิ่มบันทึกย่อในส่วน "สาเหตุ" และอัปเดตส่วน "วิธีแก้ไขปัญหาชั่วคราว" ด้วยสคริปต์ PowerShell เพื่อสแกนไฟล์ .xoml ของเวิร์กโฟลว์ |