jira-xray

How to import RobotFramework Test Results into XRAY using Python "requests" and API Keys?


I would like to write a requests program instead of curl command to import the test execution results.

The following curl command works for me perfectly, the only problem is that I need to run it manually after robot execution is completed and also my login credentials need to be used:

curl -H "Content-Type: multipart/form-data" -u adminuser:adminpassword -F "file=@output.xml" "https://<xrayurl>/rest/raven/1.0/import/execution/robot?projectKey=TEST&testEnvironments=SIT1&testPlanKey="TEST-25"

I've tried doing the following and finally succeeded after quite a few failed attempts:

import requests
params = (('projectKey', 'TEST'),)
files = {'file': ('output.xml', open(r'C:\workspace\Results\output.xml', 'rb')),}

response = requests.post('https://<xrayurl>/rest/raven/1.0/import/execution/robot', params=params, files=files, auth=('adminuser', 'adminpassword'))

Appreciate your help/guidance in advance. I'll keep trying options and post an answer if I find one.


Solution

  • First of all, and to clarify, Xray Cloud and Xray Server/datacenter are different products, with distinct APIs (Xray Server/DC REST API, Xray Cloud REST API). This happens for several reasons, including the fact that Jira Cloud and Jira server are different products with different capabilities. Having said that, let me share some examples both for Xray server/DC and for Xray Cloud.

    Xray server/datacenter

    The following code snippet shows how to submit results using HTTP basic auth but also an alternate approach, by using Personal Access Tokens which was something recently added to Jira datacenter and that Xray also supports.

    import requests
     
    jira_base_url = "http://192.168.56.102"
    jira_username = "admin"
    jira_password = "admin"
    personal_access_token = "OTE0ODc2NDE2NTgxOnrhigwOreFoyNIA9lXTZaOcgbNY"
    
    
    # endpoint doc for importing Robot Framework XML reports: https://docs.getxray.app/display/XRAY/Import+Execution+Results+-+REST#ImportExecutionResultsREST-RobotFrameworkXMLresults
    params = (('projectKey', 'CALC'),('fixVersion','v1.0'))
    files = {'file': ('output.xml', open(r'output.xml', 'rb')),}
    
    # importing results using HTTP basic authentication
    # response = requests.post(f'{jira_base_url}/rest/raven/2.0/import/execution/robot', params=params, files=files, auth=(jira_username, jira_password))
    
    # importing results using Personal Access Tokens 
    headers = {'Authorization': 'Bearer ' + personal_access_token}
    response = requests.post(f'{jira_base_url}/rest/raven/1.0/import/execution/robot', params=params, files=files, headers=headers)
    
    print(response.status_code)
    print(response.content)
    

    Xray Cloud

    import requests
    import json
    
    xray_cloud_base_url = "https://xray.cloud.xpand-it.com/api/v2"
    client_id = "215FFD69FE4644728C72182E00000000"
    client_secret = "1c00f8f22f56a8684d7c18cd6147ce2787d95e4da9f3bfb0af8f02ec00000000"
    
    # endpoint doc for authenticating and obtaining token from Xray Cloud: https://docs.getxray.app/display/XRAYCLOUD/Authentication+-+REST+v2
    headers = {'Content-type': 'application/json', 'Accept': 'text/plain'}
    auth_data = { "client_id": client_id, "client_secret": client_secret }
    response = requests.post(f'{xray_cloud_base_url}/authenticate', data=json.dumps(auth_data), headers=headers)
    auth_token = response.json()
    print(auth_token)
    
    # endpoint doc for importing Robot Framework XML reports: https://docs.getxray.app/display/XRAYCLOUD/Import+Execution+Results+-+REST+v2#ImportExecutionResultsRESTv2-RobotFrameworkXMLresults
    params = (('projectKey', 'BOOK'),('fixVersion','1.0'))
    report_content = open(r'output.xml', 'rb')
    headers = {'Authorization': 'Bearer ' + auth_token, 'Content-Type': 'application/xml'}
    response = requests.post(f'{xray_cloud_base_url}/import/execution/robot', params=params, data=report_content, headers=headers)
    
    print(response.status_code)    
    print(response.content)