Create Team City Build configurations using restapi and powershell - rest

I am trying to create build configurations via the restapi and powershell and keep getting the following error:
Exception calling "GetResponse" with "0" argument(s): "The remote server returned an error: (405) Method Not Allowed."
It seems that I can use GET fine, the issue appears to be with the PUT command
Code Snippet
$url = http://%teamcityServer%:8111/app/rest/buildTypes/id:%projectname%"
$req = [System.Net.WebRequest]::Create($url)
$req.ContentType = "text/plain"
$req.UseDefaultCredentials = $true
$req.Credentials = Get-Credential("username")
$req.Method ="PUT"
$req.ContentLength = 0
$req.Accept = "*/*"
$resp = $req.GetResponse()
$results = [xml]$resp.ReadToEnd()
Output from the Team City log
2015-09-10 09:14:30,582] WARN [io-8111-exec-70] - est.jersey.ExceptionMapperUtil - Error has occurred during request processing (405). Error: javax.ws.rs.WebApplicationException. Not supported request. Please check URL, HTTP method and transfered data are correct. metadata: [Allow:[HEAD,DELETE,GET,OPTIONS],] Request: PUT '/app/rest/buildTypes/id:%project%'
Team City Version is 9.1.1 so I believe this is possible.
I'm fairly new to the restapi so any input is appreciated.

Its possible but you need to post xml data to create builds/projects. For example if you need to create a project you can POST XML something like
<newProjectDescription name='New Project Name' id='newProjectId' copyAllAssociatedSettings='true'><parentProject locator='id:project1'/><sourceProject locator='id:project2'/></newProjectDescription>
to http://teamcity:8111/httpAuth/app/rest/projects.
Check more info on Teamcity REST documentation.
You didn't mention your powershell version, but if you are using 3.0 or later you can call Invoke-WebRequest cmdlet and your code should look something like:
Invoke-WebRequest -Uri $uri -Credential $cred -Method Post -Body $body -ContentType "Application/xml"
For PowerShell 2.0 You can write your own Web-Request method like:
function Web-Request{
param(
[Parameter(Mandatory=$true)]
[string]
$Uri,
[Parameter(Mandatory=$false)]
[string]
$Username = $null,
[Parameter(Mandatory=$false)]
[string]
$Password = $null,
[Parameter(Mandatory=$true)]
[string]
$ContentType,
[Parameter(Mandatory=$true)]
[string]
$Method,
[Parameter(Mandatory=$false)]
[string]
$PostString
)
$webRequest = [System.Net.WebRequest]::Create($Uri)
$webRequest.ContentType = $ContentType
$webRequest.Method = $Method
$webRequest.Accept = "*/*"
if ($Username)
{
$webRequest.Credentials = new-object system.net.networkcredential($Username, $Password)
}
try
{
switch -regex ($Method)
{
"PUT|POST" # PUT and POST behaves similar ways except that POST is only used for creation while PUT for creation/modification
{
if ($PostString -ne "")
{
$PostStringBytes = [System.Text.Encoding]::UTF8.GetBytes($PostString)
$webrequest.ContentLength = $PostStringBytes.Length
$requestStream = $webRequest.GetRequestStream()
$requestStream.Write($PostStringBytes, 0,$PostStringBytes.length)
}
else
{
$requestStream = $webRequest.GetRequestStream()
}
}
"DELETE"
{
$requestStream = $webRequest.GetRequestStream()
}
default
{
# GET requests usually don't have bodies, default will behave like a GET
}
}
if ($requestStream -ne $null)
{
$requestStream.Close()
}
[System.Net.WebResponse] $resp = $webRequest.GetResponse();
$rs = $resp.GetResponseStream();
[System.IO.StreamReader] $sr = New-Object System.IO.StreamReader -argumentList $rs;
[string] $results = $sr.ReadToEnd();
}
catch
{
$results = "Error : $_.Exception.Message"
}
finally
{
if ($sr -ne $null) { $sr.Close(); }
if ($resp -ne $null) { $resp.Close(); }
$resp = $null;
$webRequest = $null;
$sr = $null;
$requestStream = $null;
}
return $results
}

Related

Send message to azure service bus with properties

I am using the following powershell code to send a message to an Azure Service Bus Topic with a property set:
function Send-AzServiceBusMessage {
param(
[Parameter(Mandatory = $true)]
[string] $ResourceGroupName,
[Parameter(Mandatory = $true)]
[string] $NamespaceName,
[Parameter(Mandatory = $true)]
[string] $TopicName,
[Parameter(Mandatory = $false)]
[string] $PolicyName = 'RootManageSharedAccessKey',
[Parameter(Mandatory = $false)]
[string] $Property1
)
$message = [PSCustomObject] #{ "Body" = "Test message"; "Property1" = $Property1 }
$namespace = (Get-AzServiceBusNamespace -ResourceGroupName $ResourceGroupName -Name $namespacename).Name
$key = (Get-AzServiceBusKey -ResourceGroupName $ResourceGroupName -Namespace $namespacename -Name $PolicyName).PrimaryKey
$message.psobject.properties.Remove("Body")
$token = New-AzServiceBusSasToken -Namespace $namespace -Policy $PolicyName -Key $Key
#set up the parameters for the Invoke-WebRequest
$headers = #{ "Authorization" = "$token"; "Content-Type" = "application/atom+xml;type=entry;charset=utf-8" }
$uri = "https://$namespace.servicebus.windows.net/$TopicName/messages"
$headers.Add("BrokerProperties", $(ConvertTo-Json -InputObject $Message -Compress))
$result = Invoke-WebRequest -Uri $uri -Headers $headers -Method Post -Body $body
if ($result.StatusCode -ne 201) {
$result
}
I have a rule set up on a topic subscription such that:
Property1 in ('somevalue')
However, if I set up a catch all subscription with no rules, I can see the message is being received by that and not by the subscription with the rule. So my question is how do I send messages with properties set using powershell. Similar to this in C#:
var message = new BrokeredMessage { MessageId = Guid.NewGuid().ToString()};
message.Properties["Property1"] = "somevalue";
Based on the documentation it looks like you have to nest your custom properties in a Properties member:
$headers.Add("BrokerProperties", $(ConvertTo-Json -InputObject #{ Properties = $message } -Compress))
The solution was as above with the following modifications:
$message = [PSCustomObject] #{ "Body" = "Test message" }
$headers = #{ "Authorization" = "$token"; "Content-Type" = "application/atom+xml;type=entry;charset=utf-8"; "Property1" = $Property1 }
$headers.Add("BrokerProperties", $(ConvertTo-Json -InputObject $Message -Compress))

Missing AzureRmProfileProvider module

I'm currently in Azure trying to execute a run book using a PowerShell script and my script spits out an error staying that it cannot find this class:
Microsoft.Azure.Commands.Common.Authentication.Abstractions.AzureRmProfileProvider
Can you help find out how I can add this class to my script?
Provided below is my script:
[CmdletBinding()]
[OutputType([string])]
Param
(
# VM Name
[Parameter(Mandatory = $true,
ValueFromPipelineByPropertyName = $true,
Position = 0)]
$VMName
)
$VerbosePreference = 'Continue' #remove when publishing runbook
#region Runbook variables
Write-Verbose -Message 'Retrieving hardcoded Runbook Variables'
$Resourcegroupname = 'scriptextensiondemo-rg'
$ExtensionName = 'WindowsUpdate'
$APIVersion = '2017-03-30'
$ScriptExtensionUrl = 'https://[enteryourvaluehere].blob.core.windows.net/script/Install-WindowsUpdate.ps1'
#endregion
#region Connection to Azure
Write-Verbose -Message 'Connecting to Azure'
$connectionName = 'AzureRunAsConnection'
try
{
# Get the connection "AzureRunAsConnection "
$servicePrincipalConnection = Get-AutomationConnection -Name $connectionName
'Logging in to Azure...'
Add-AzureRmAccount `
-ServicePrincipal `
-TenantId $servicePrincipalConnection.TenantId `
-ApplicationId $servicePrincipalConnection.ApplicationId `
-CertificateThumbprint $servicePrincipalConnection.CertificateThumbprint
}
catch
{
if (!$servicePrincipalConnection)
{
$ErrorMessage = "Connection $connectionName not found."
throw $ErrorMessage
}
else
{
Write-Error -Message $_.Exception.Message
throw $_.Exception
}
}
#endregion
#region Get AccessToken
Write-Verbose 'Get Access Token'
$currentAzureContext = Get-AzureRmContext
$azureRmProfile = [Microsoft.Azure.Commands.Common.Authentication.Abstractions.AzureRmProfileProvider]::Instance.Profile
$profileClient = New-Object -TypeName Microsoft.Azure.Commands.ResourceManager.Common.RMProfileClient -ArgumentList ($azureRmProfile)
$token = $profileClient.AcquireAccessToken($currentAzureContext.Subscription.TenantId)
#endregion
#region Get extension info
Write-Verbose -Message 'Get extension info'
$Uri = 'https://management.azure.com/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Compute/virtualMachines/{2}/extensions/{3}?api-version={4}' -f $($currentAzureContext.Subscription), $Resourcegroupname, $VMName, $ExtensionName, $APIVersion
$params = #{
ContentType = 'application/x-www-form-urlencoded'
Headers = #{
'authorization' = "Bearer $($token.AccessToken)"
}
Method = 'Get'
URI = $Uri
}
$ExtensionInfo = Invoke-RestMethod #params -ErrorAction SilentlyContinue
if (!($ExtensionInfo))
{
Write-Verbose 'No Custom Script Extension Configured. Please do an initial script configuration first'
#region configure custom script extension
$Uri = 'https://management.azure.com/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Compute/virtualMachines/{2}/extensions/{3}?api-version={4}' -f $($currentAzureContext.Subscription), $Resourcegroupname, $VMName, $ExtensionName, '2017-03-30'
$body = #"
{
"location": "westeurope",
"properties": {
"publisher": "Microsoft.Compute",
"type": "CustomScriptExtension",
"typeHandlerVersion": "1.4",
"autoUpgradeMinorVersion": true,
"forceUpdateTag": "InitialConfig",
"settings": {
"fileUris" : ["$ScriptExtensionUrl"],
"commandToExecute": "powershell -ExecutionPolicy Unrestricted -file Install-WindowsUpdate.ps1"
}
}
}
"#
$params = #{
ContentType = 'application/json'
Headers = #{
'authorization' = "Bearer $($token.AccessToken)"
}
Method = 'PUT'
URI = $Uri
Body = $body
}
$InitialConfig = Invoke-RestMethod #params
$InitialConfig
exit
#endregion
}
#endregion
#region Get Extension message info
Write-Verbose 'Get Extension message info'
$Uri = 'https://management.azure.com/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Compute/virtualMachines/{2}/extensions/{3}?$expand=instanceView&api-version={4}' -f $($currentAzureContext.Subscription), $Resourcegroupname, $VMName, $ExtensionName, $APIVersion
$params = #{
ContentType = 'application/x-www-form-urlencoded'
Headers = #{
'authorization' = "Bearer $($token.AccessToken)"
}
Method = 'Get'
URI = $Uri
}
$StatusInfo = Invoke-RestMethod #params
#$StatusInfo
[regex]::Replace($($StatusInfo.properties.instanceView.SubStatuses[0].Message), '\\n', "`n")
#endregion
#region Update Script Extension
try
{
Write-Verbose 'Update Script Extension'
$Uri = 'https://management.azure.com/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Compute/virtualMachines/{2}/extensions/{3}?api-version={4}' -f $($currentAzureContext.Subscription), $Resourcegroupname, $VMName, $ExtensionName, '2017-03-30'
$body = #"
{
"location": "westeurope",
"properties": {
"publisher": "Microsoft.Compute",
"type": "CustomScriptExtension",
"typeHandlerVersion": "1.4",
"autoUpgradeMinorVersion": true,
"forceUpdateTag": "$(New-Guid)",
"settings": {
"fileUris" : ["$ScriptExtensionUrl"],
"commandToExecute": "powershell -ExecutionPolicy Unrestricted -file Install-WindowsUpdate.ps1"
}
}
}
"#
$params = #{
ContentType = 'application/json'
Headers = #{
'authorization' = "Bearer $($token.AccessToken)"
}
Method = 'PUT'
URI = $Uri
Body = $body
}
$Updating = Invoke-RestMethod #params
$Updating
}
catch
{
Write-Error -Message $_.Exception.Message
throw $_.Exception
}
#endregion
Nothing related with outdated Azure modules in my case.
Problem comes from the fact that ps was not able to find the type during parsing but it's available during execution. So simply "cheating" the parser through storing the commandlet within a literal executed with invoke-command it works:
$profile = Invoke-Expression "[Microsoft.Azure.Commands.Common.Authentication.Abstractions.AzureRmProfileProvider]::Instance.Profile"
Regards.
The problem is likely to be that you're running outdated Azure Modules or at least they don't match with the one you have installed in your computer. Try updaing the Azure modules in your Automation Account. Also make sure the modules that you're using are included as well.

Loading SharePoint Online pages with Invoke-Webrequest from Powershell

I want to be able to load SharePoint Online pages with Invoke-Webrequest from Powershell.
Can someone please show me how to successfully navigate past the login screen?
Here is how I get list items from SPO. You need to have "Microsoft.SharePoint.Client.SharePointOnlineCredentials" dll.
Then use the below function that I have modified for SPO.
Advantage: This will even work with older PowerShell versions. If you want to target only higher level of PowerShell then also this code will work. Optionally you can use Invoke-Webrequest instead of System.Net.HttpWebRequest and System.Net.HttpWebResponse.
function Get-ListItems {
[CmdletBinding()]
PARAM (
[Parameter(Mandatory=$true)]
[String] $URL
)
#$URL = Fix-Url $URL
$xml = Request-Rest -URL $URL
return $xml
}
function Request-Rest{
[CmdletBinding()]
PARAM (
[Parameter(Mandatory=$true)]
[String] $URL,
[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.
$URI = New-Object System.Uri($URL,$true)
#Create a request object using the URI
$request = [System.Net.HttpWebRequest]::Create($URI)
#Build up a nice 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
}
if ($PSBoundParameters.ContainsKey('JSON'))
{
$request.Accept = "application/json"
}
$request.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f")
#$request.Accept = "application/json;odata=verbose"
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
{
[xml]$output = $reader.ReadToEnd()
}
$reader.Close()
Write-Output $output
$response.Close()
}
Though I do not know the direct way to pass the credentials along with Invoke-WebRequest itself, one workaround I found is, capture the cookie values by manual authenticating the SharePoint page and use those for subsequent requests. You can use fiddler or some other similar tool to grab the cookies. The two cookie names were 'FedAuth' and 'rtFa'
$session = New-Object Microsoft.PowerShell.Commands.WebRequestSession
$cookieCollection = New-Object System.Net.CookieCollection
$cookie1 = New-Object System.Net.Cookie
$cookie1.Domain = "<your domain>.sharepoint.com"
$cookie1.Name = "FedAuth"
$cookie1.Value = "<cookie value here>"
$cookieCollection.Add($cookie1)
$cookie2 = New-Object System.Net.Cookie
$cookie2.Domain = "<your domain>.sharepoint.com"
$cookie2.Name = "rtFa"
$cookie2.Value = "<cookie value here>"
$cookieCollection.Add($cookie2)
$session.Cookies.Add($cookieCollection)
$uri = "https:<your site collection here>/_layouts/15/SharePointDesignerSettings.aspx"
$response = Invoke-WebRequest -Uri $uri -WebSession $session -Method Default
$form = $response.Forms[0]
You can use $form to examine the Html elements. If you want to submit the changes made to form use the below line
$response = Invoke-WebRequest -Uri $uri -WebSession $session -Method POST -Body $form
Note: There is an issue with Invoke-WebRequest with respect to field submission.. basically it uses 'id' of input element instead of 'name' in form fields collection.. the below url has the code to convert field Id to Name
https://d-fens.ch/2013/05/11/invoke-webrequest-uses-id-attribute-of-input-element-as-field-name-in-form-fields-collection/
If you are looking for the final content of a page, Invoke-WebRequest will not do what you need. Much of the content of a SharePoint page is loaded asynchronously using JavaScript. Invoke-WebRequest will only return the initial HTML content from the page.
What kind of content are you looking for from the page? Most everything about SharePoint can be accessed using RESTful queries (Invoke-RESTMethod and the SharePoint REST API) or from the PowerShell SharePoint PNP and SharePoint Online cmdlet libraries.

How to POST .json file in Powershell without Invoke-WebRequest?

What I am currently doing:
Invoke-WebRequest -Uri https://coolWebsite.com/ext/ext -ContentType application/json -Method POST -Body $someJSONFile
I am looking for a way to POST this same .json file in Powershell without using Invoke-WebRequest, if it is possible. This new method would preferably allow me to get the server output content and parse through it in powershell.
Maybe by calling an outside cURL method? I really am not sure and all my internet research has proved fruitless.
How can I achieve this above result without Invoke-WebRequest?
You can try this :
# RestRequest.ps1
Add-Type -AssemblyName System.ServiceModel.Web, System.Runtime.Serialization, System.Web.Extensions
$utf8 = [System.Text.Encoding]::UTF8
function Request-Rest
{
[CmdletBinding()]
PARAM (
[Parameter(Mandatory=$true)]
[String] $URL,
[Parameter(Mandatory=$false)]
[System.Net.NetworkCredential] $credentials,
[Parameter(Mandatory=$true)]
[String] $JSON)
# Remove NewLine from json
$JSON = $JSON -replace "$([Environment]::NewLine) *",""
# Create a URL instance since the HttpWebRequest.Create Method will escape the URL by default.
# $URL = Fix-Url $Url
$URI = New-Object System.Uri($URL,$true)
try
{
# Create a request object using the URI
$request = [System.Net.HttpWebRequest]::Create($URI)
# Build up a nice User Agent
$UserAgent = "My 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"))
$request.Credentials = $credentials
$request.KeepAlive = $true
$request.Pipelined = $true
$request.AllowAutoRedirect = $false
$request.Method = "POST"
$request.ContentType = "application/json"
$request.Accept = "application/json"
$utf8Bytes = [System.Text.Encoding]::UTF8.GetBytes($JSON)
$request.ContentLength = $utf8Bytes.Length
$postStream = $request.GetRequestStream()
$postStream.Write($utf8Bytes, 0, $utf8Bytes.Length)
#Write-String -stream $postStream -string $JSON
$postStream.Dispose()
try
{
#[System.Net.HttpWebResponse] $response = [System.Net.HttpWebResponse] $request.GetResponse()
$response = $request.GetResponse()
}
catch
{
$response = $Error[0].Exception.InnerException.Response;
Throw "Exception occurred in $($MyInvocation.MyCommand): `n$($_.Exception.Message)"
}
$reader = [IO.StreamReader] $response.GetResponseStream()
$output = $reader.ReadToEnd()
$reader.Close()
$response.Close()
Write-Output $output
}
catch
{
$output = #"
{
"error":1,
"error_desc":"Error : Problème d'accès au serveur $($_.Exception.Message)"
}
"#
Write-Output $output
}
}
Edited 19-10-2015
Here is an example usage :
#$urlBase = "http://192.168.1.1:8080/"
#######################################################################
# Login #
#######################################################################
$wsLogin = "production/login"
Function login
{
[CmdletBinding()]
PARAM
(
[ValidateNotNullOrEmpty()]
[String] $login,
[String] $passwd
)
Write-Verbose $wsLogin
#$jsonIn = [PSCustomObject]#{"login"=$login;"passwd"=$passwd} | ConvertTo-Json
$jsonIn = #"
{
"login":"$login",
"passwd":"$passwd"
}
"#
Write-Verbose $jsonIn
$jsonOut = Request-Rest -URL "$urlBase$wsLogin" -JSON $jsonIn -credentials $null
Write-Verbose $jsonOut
#return $jsonOut | ConvertFrom-Json
return $jsonOut
}
It is easy to convert that code to cURL
curl -v --insecure -X POST -H "Content-Type: application/json" --data-binary someJSONFile.js https://coolWebsite.com/ext/ext/

JIRA REST API gives HTTP error 400 with PowerShell v3

I'm attempting to write some PowerShell functions to interface with our Atlassian JIRA system (JIRA 5.2, download version). Unfortunately, I've found through trial and error that the Invoke-RestMethod doesn't seem to work (doesn't support authentication headers), so I've written up a simple function called Invoke-JiraMethod. I can confirm that this method works for GET requests; I've been able to use it to get Jira objects to my heart's desire. As soon as I tried to create an issue, though, I started getting a HTTP 400 / Bad request error.
I've followed the steps here to get my issue metadata, and I'm filling out all the required fields in my input object. Could anyone help me figure out how to solve the 400 error? I can provide more information if needed - I just didn't want to overflow the description of the question. :)
Function Invoke-JiraMethod
{
<#
.Synopsis
Low-level function that directly invokes a REST method on JIRA
.Description
Low-level function that directly invokes a REST method on JIRA. This is designed for
internal use.
#>
[CmdletBinding()]
param
(
[ValidateSet("Get","Post")] [String] $Method,
[String] $URI,
[String] $Username,
[String] $Password
)
process
{
$token = [System.Convert]::ToBase64String([System.Text.Encoding]::UTF8.GetBytes("${Username}:${Password}"))
$webRequest = [System.Net.WebRequest]::Create($URI)
$webRequest.Method = $Method.ToUpper()
$webRequest.AuthenticationLevel = "None"
$webRequest.Headers.Add('Authorization', "Basic $token")
#$webRequest.Headers.Add('Authorization', $token)
$webRequest.PreAuthenticate = $true
$webRequest.ContentType = "application/json"
Write-Verbose "Invoking JIRA method $Method with URI $URI"
$response = $webRequest.GetResponse()
$requestStream = $response.GetResponseStream()
$readStream = New-Object -TypeName System.IO.StreamReader -ArgumentList $requestStream
$json = $readStream.ReadToEnd()
$readStream.Close()
$response.Close()
$result = $json | ConvertFrom-Json
Write-Output $result
}
}
Function New-JiraIssue
{
param
(
[Parameter(Mandatory = $true,
Position = 0)]
[string] $ProjectKey,
[Parameter(Mandatory = $true,
Position = 1)]
[string] $IssueType,
[Parameter(Mandatory = $false)]
[string] $Priority = 3,
[Parameter(Mandatory = $true,
Position = 2)]
[string] $Summary,
[Parameter(Mandatory = $true,
Position = 3)]
[string] $Description,
[Parameter(Mandatory = $true,
Position = 4)]
[string] $Location,
[Parameter(Mandatory = $true,
Position = 5)]
[string] $Phone,
[Parameter(Mandatory = $false)]
[string] $Reporter,
[Parameter(Mandatory = $false)]
[PSCredential] $Credential
)
process
{
$ProjectObject = New-Object -TypeName PSObject -Property #{"key"=$ProjectKey}
$IssueTypeObject = New-Object -TypeName PSObject -Property #{"id"=$IssueType}
if ( -not ($Reporter))
{
Write-Verbose "Reporter not specified; defaulting to $JiraDefaultUser"
$Reporter = $JiraDefaultUser
}
$ReporterObject = New-Object -TypeName PSObject -Property #{"name"=$Reporter}
$fields = New-Object -TypeName PSObject -Property ([ordered]#{
"project"=$ProjectObject;
"summary"=$Summary;
"description"=$Description;
"issuetype"=$IssueTypeObject;
"priority"=$Priority;
"reporter"=$ReporterObject;
"labels"="";
$CustomFields["Location"]=$Location;
$CustomFields["Phone"]=$Phone;
})
$json = New-Object -TypeName PSObject -Property (#{"fields"=$fields}) | ConvertTo-Json
Write-Verbose "Created JSON object:`n$json"
# https://muwebapps.millikin.edu/jira/rest/api/latest/issue/IT-2806
# $result = Invoke-RestMethod -Uri $JiraURLIssue -Method Post -ContentType "application/json" -Body $json -Credential $Credential
if ($Username -or $Password)
{
$result = (Invoke-JiraMethod -Method Post -URI "${JiraURLIssue}" -Username $Username -Password $Password)
} else {
$result = (Invoke-JiraMethod -Method Post -URI "${JiraURLIssue}" -Username $JiraDefaultUser -Password $JiraDefaultPassword)
}
Write-Output $result
}
}
Thanks in advance!
I was receiving the error 400 because the issue type id number I had put into the json data wasn't mapped to anything. fiddler helped me diagnose that.
I used this bit of code to figure out authenticating to jira via invoke-restmethod's -Headers option: http://poshcode.org/3461
then I put the json data into a here string, and ran invoke-restmethod.
code bits below. replace "any valid... type id number" with actual project and issue type ids you get from your jira admin.
$uri = "$BaseURI/rest/api/2/issue"
$jsonString = #'
{
"fields": {
"project":
{
"id": "any valid project id number"
},
"summary": "No REST for the Wicked.",
"description": "Creating of an issue using ids for projects and issue types using the REST API",
"issuetype": {
"id": "any valid issue type id number"
}
}
}
'#
$headers = Get-HttpBasicHeader $Credentials
Invoke-RestMethod -uri $uri -Headers $headers -Method Post -Body $jsonString -ContentType "application/json"