PowerShell调用Sharepoint 2013 REST API更新列表项

时间:2016-03-16 18:55:01

标签: rest powershell sharepoint

尝试了几个不同的示例后,我无法使用Sharepoint REST API更新列表项。我从请求中收到了400错误。

creplace是由于Sharepoint由于某种原因发送了ID和Id,并且在我的Get-SPListItems方法中破坏了ConvertFrom-Json。

function Update-SPListItems
{
    param
    (
        $listUpdate
    )
    $requestDigest = Get-RequestDigest

    foreach($item in $listUpdate.Results)
    {
        $restUrl = $item.__metadata.uri
        $item.tsFeedbackStatus = "Open"
        $item.Modified = Get-Date -Format s

        $updatedItem = $item | ConvertTo-Json
        #convert back the duplicate field
        $updatedItem = $updatedItem -creplace '"ignoreId":','"Id":'

        $itemJsonBytes = [System.Text.Encoding]::ASCII.GetBytes($updatedItem)
        try 
         {
            #examples have shown POST/MERGE, POST/PATCH, MERGE/MERGE,
            #PATCH/PATCH, none of them in those combinations have worked
            $request = [System.Net.WebRequest]::Create($restUrl)
            $request.Credentials = $Credential.GetNetworkCredential()
            $request.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f")
            $request.Headers.Add("If-Match", "*")
            $request.Headers.Add("X-RequestDigest", $requestDigest)
            $request.Headers.Add("X-HTTP-Method", "MERGE")
            $request.Accept = "application/json;odata=verbose" 
            $request.Method = "POST"
            $request.ContentType = "application/json;odata=verbose" 
            $request.ContentLength = $itemJsonBytes.Length
            $stream = $request.GetRequestStream()
            $stream.Write($itemJsonBytes, 0, $itemJsonBytes.Length)
            $stream.Close()

            $response = $request.GetResponse()
        }
        catch [System.Exception]
        {
            Write-Error $_.Exception.ToString()        
        }

    }
}

这是确切的错误:

  

Update-SPListItems:System.Net.WebException:远程服务器返回错误:(400)Bad Request。

     

在System.Net.HttpWebRequest.GetResponse()

     

在CallSite.Target(Closure,CallSite,Object)

     

在C:\ Users \ user \ Desktop \ SPListTest.ps1:120 char:11

     
      
  • $ result = Update-SPListItems $ list

  •   
  • ~~~~~~~~~~~~~~~~~~~~~~~~

  •   
  • CategoryInfo:NotSpecified:(:) [Write-Error],WriteErrorException

  •   
  • FullyQualifiedErrorId:Microsoft.PowerShell.Commands.WriteErrorException,Update-SPListItems

  •   

1 个答案:

答案 0 :(得分:0)

为此尝试以下可重复使用的功能。它每次都对我有用。确保正确传递参数。这内置了身份验证,甚至适用于旧版本的PowerShell。

function Request-Rest{    
    [CmdletBinding()]
    PARAM (
        [Parameter(Mandatory=$False)]
        [String]$Metadata,

        [Parameter(Mandatory=$true)]
        [String] $URL,

        [Parameter(Mandatory=$False)]
        [Switch]$listUpdate,

        [Parameter(Mandatory=$False)]
        [String]$RequestDigest,

        [Parameter(Mandatory=$false)]
        [Microsoft.SharePoint.Client.SharePointOnlineCredentials] $credentials,

        [Parameter(Mandatory=$false)]
        [String] $UserAgent = "PowerShell API Client",

        [Parameter(Mandatory=$false)]
        [Switch] $JSON,

        [Parameter(Mandatory=$false)]
        [Switch] $Raw
    )
    #Create a URI instance since the HttpWebRequest.Create Method will escape the URL by default.   
    #$URL = Fix-Url $Url
    $URI = New-Object System.Uri($URL,$true)   

    #Create a request object using the URI   
    $request = [System.Net.HttpWebRequest]::Create($URI)   

    #Build up a User Agent   
    $request.UserAgent = $(   
        "{0} (PowerShell {1}; .NET CLR {2}; {3})" -f $UserAgent, $(if($Host.Version){$Host.Version}else{"1.0"}),  
        [Environment]::Version,  
        [Environment]::OSVersion.ToString().Replace("Microsoft Windows ", "Win")  
        )

    if ($credentials -eq $null)
    {
        $request.UseDefaultCredentials = $true
    }
    else
    {
        $request.Credentials = $credentials
    }

    $request.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f")

    #Request Method
    $request.Method = "POST"

    #Headers
    if($listUpdate)
    {
        $request.Headers.Add("X-RequestDigest", $RequestDigest)
        $request.Headers.Add("If-Match", "*")
        $request.Headers.Add("X-HTTP-Method", "MERGE")

        $request.ContentType = "application/json;odata=verbose"
        $request.Accept = "application/json;odata=verbose"
    }

    #Request Body
    if($Metadata) {  
        $Body = [byte[]][char[]]$Metadata   
        $request.ContentLength = $Body.Length 

        $stream = $request.GetRequestStream()
        $stream.Write($Body, 0, $Body.Length)
    }
    else {
        $request.ContentLength = 0
    }


    try
    {
        [System.Net.HttpWebResponse] $response = [System.Net.HttpWebResponse] $request.GetResponse()
    }
    catch
    {
            Throw "Exception occurred in $($MyInvocation.MyCommand): `n$($_.Exception.Message)"
    }

    $reader = [IO.StreamReader] $response.GetResponseStream()  

    if (($PSBoundParameters.ContainsKey('JSON')) -or ($PSBoundParameters.ContainsKey('Raw')))
    {
        $output = $reader.ReadToEnd()  
    }
    else
    {
        $output = $reader.ReadToEnd()  
    }

    $reader.Close()  

    if($output.StartsWith("<?xml"))
    {
        [xml]$outputXML = [xml]$output
    }
    else
    {
        [xml]$outputXML = [xml] ("<xml>" + $output + "</xml>")
    }

    Write-Output $outputXML 

    $response.Close()
}