#include-once #include #include "JSON2.au3" #include #include ; #INDEX# =================================================================================== ; Title ...............: CloudShare API Functions ; File Name............: CS_API.au3 ; File Version.........: 1.0 ; Min. AutoIt Version..: v3.3.2.0 ; Description .........: AutoIt wrapper for Cloudshare API functions ; Author... ...........: Robin Johnston ; =========================================================================================== ; #CONSTANTS# =============================================================================== Global $API_ID = "538GACRZ9FABA07E" ;Robin's one!!! Global $API_KEY = "bkAyYSB3dL8GREF87zfqhjkUcW5xNSVyj0HDpQBqheX5vcHpbLE8WXqYjGmGMORt" Global $V3_URL = "https://use.cloudshare.com/api/v3" Global $V4_URL = "https://api.accelerate.cloudshare.com/v4" Global $OAUTH2_TOKEN_URL = "https://api.accelerate.cloudshare.com/v4/oauth/token" ;============================================================================================ ; #CURRENT# ================================================================================= ;_CS_V3_Get ;_CS_V4_Get ; =========================================================================================== ; #FUNCTION# ;=============================================================================== ; Name...........: _CS_V3_Get ; Description ...: Does a GET call to CS V3 API ; Syntax.........: _CS_V3_Get($vPath) ; Parameters ....: $vPath - the path to add to the base URL ; Return values .: Success - Returns 1 and envName ; Failure - Returns 0 and sets @error: ; Modified.......: ; Remarks .......: Need to flesh this out but basics in place - just returns name but should be a param ; Related .......: ; Link ..........: ; Example .......: _CS_V3_Get("/class/" & $classId) ;============================================================================================ Func _CS_V3_Get($vPath) ; 1. (Normally generated, but now hardcoded for debug) Local $iTimestamp = _GetUnixTime() ;ConsoleWrite("Timestamp (AutoIt UTC): " & $iTimestamp & @CRLF) ; 2. (Normally generated, but now hardcoded for debug) Local $sTokenLength = 10 Local $sToken = _GenerateRandomAlphanumericString($sTokenLength) ;ConsoleWrite("AutoIt DEBUG - Token: " & $sToken & @CRLF) ; 3. Build full URL and Calculate HMAC (SHA1 hash of API_KEY + URL + TIMESTAMP + TOKEN) Local $sURL = $V3_URL & $vPath ;ConsoleWrite("AutoIt DEBUG - URL: " & $sURL & @CRLF) Local $sHmacInput = $API_KEY & $sURL & $iTimestamp & $sToken ;ConsoleWrite("AutoIt DEBUG - HMAC Input (Length: " & StringLen($sHmacInput) & "): '" & $sHmacInput & "'" & @CRLF) Local $sHMAC = _Crypt_HashData($sHmacInput, $CALG_SHA1) ;Remove "0x" prefix and convert to lowercase If StringLeft($sHMAC, 2) = "0x" Then $sHMAC = StringTrimLeft($sHMAC, 2) EndIf $sHMAC = StringLower($sHMAC) ;ConsoleWrite("AutoIt DEBUG - HMAC: " & $sHMAC & @CRLF) ; 4. Construct AUTH_PARAM Local $sAuthParam = "userapiid:" & $API_ID & ";timestamp:" & $iTimestamp & ";token:" & $sToken & ";hmac:" & $sHMAC ;ConsoleWrite("Auth Param: " & $sAuthParam & @CRLF) ; 5. Construct the Authorization header value Local $sAuthorizationHeader = "cs_sha1 " & $sAuthParam ;ConsoleWrite("Authorization Header: " & $sAuthorizationHeader & @CRLF) ; --- HTTP Request using WinHttp --- Local $hOpen = _WinHttpOpen("AutoIt CloudShare Client") If @error Then ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_Open failed: " & @error) Local $hConnect = _WinHttpConnect($hOpen, "use.cloudshare.com") If @error Then _WinHttpCloseHandle($hOpen) ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_Connect failed: " & @error) EndIf ; Extract path from URL for _WinHttp_OpenRequest Local $sUrlPath = StringTrimLeft($sURL, StringInStr($sURL, "use.cloudshare.com") + StringLen("use.cloudshare.com") - 1) If StringLeft($sUrlPath, 1) <> "/" Then $sUrlPath = "/" & $sUrlPath ; Ensure it starts with a slash Local $hRequest = _WinHttpOpenRequest($hConnect, "GET", $sUrlPath, Default, Default, Default, $WINHTTP_FLAG_SECURE) ; Use $WINHTTP_FLAG_SECURE for HTTPS If @error Then _WinHttpCloseHandle($hConnect) _WinHttpCloseHandle($hOpen) ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_OpenRequest failed: " & @error) EndIf ; Set request headers using _WinHttp_AddRequestHeaders() ; Headers are concatenated with @CRLF (carriage return, line feed) Local $sHeadersToSet = "Accept: application/json" & @CRLF & _ "Content-Type: application/json" & @CRLF & _ "Authorization: " & $sAuthorizationHeader _WinHttpAddRequestHeaders($hRequest, $sHeadersToSet) ; Use _WinHttp_AddRequestHeaders() If @error Then _WinHttpCloseHandle($hRequest) _WinHttpCloseHandle($hConnect) _WinHttpCloseHandle($hOpen) ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_AddRequestHeaders failed: " & @error) EndIf ; Send the request Local $bSend = _WinHttpSendRequest($hRequest) If Not $bSend Then _WinHttpCloseHandle($hRequest) _WinHttpCloseHandle($hConnect) _WinHttpCloseHandle($hOpen) ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_SendRequest failed: " & @error) EndIf ; Receive the response Local $bReceive = _WinHttpReceiveResponse($hRequest) If Not $bReceive Then _WinHttpCloseHandle($hRequest) _WinHttpCloseHandle($hConnect) _WinHttpCloseHandle($hOpen) ExitMsgBox($MB_ICONERROR, "Error", "WinHttp_ReceiveResponse failed: " & @error) EndIf ; Get and display response headers using _WinHttp_QueryHeaders() ; The flag $WINHTTP_QUERY_RAW_HEADERS_CRLF ensures a format similar to curl's output Local $sHeaders = _WinHttpQueryHeaders($hRequest, $WINHTTP_QUERY_RAW_HEADERS_CRLF) If @error Then ConsoleWrite("Error getting response headers: " & @error & @CRLF) $sHeaders = "Could not retrieve headers." EndIf ;ConsoleWrite("--- Response Headers ---" & @CRLF & $sHeaders & @CRLF) ; Get and display response body Local $sResponse = _WinHttpReadData($hRequest) ;ConsoleWrite("--- Response Body ---" & @CRLF & $sResponse & @CRLF) ; Clean up handles _WinHttpCloseHandle($hRequest) _WinHttpCloseHandle($hConnect) _WinHttpCloseHandle($hOpen) ; --- Pretty Print JSON --- ;$assetsobj=Json_Decode($sResponse) Local $oJson = _Json_Parse($sResponse) If @error Then MsgBox($MB_ICONERROR, "Error", "Failed to parse CS_V3_Get response.") ConsoleWrite("Full Response: " & $sResponse & @CRLF) Exit EndIf Local $sResult = _Json_Get($oJson, "name") ;ConsoleWrite("Cloudshare Training name is " & $sResult) Return $sResult EndFunc ;==>_CS_V3_Get ; #FUNCTION# ;=============================================================================== ; Name...........: _CS_V4_Get ; Description ...: Does a GET call to CS V4 Accelerate API ; Syntax.........: _CS_V4_Get($vPath) ; Parameters ....: $vPath - the path to add to the base URL ; Return values .: Success - Returns 1 and envName ; Failure - Returns 0 and sets @error: ; Modified.......: ; Remarks .......: Need to flesh this out but basics in place - just returns name but should be a param ; Related .......: ; Link ..........: ; Example .......: _CS_V4_Get("/trainings?name=contains" & $classId) ;============================================================================================ Func _CS_V4_Get($vPath) ; 1. Requesting OAuth2 Access Token - Assume we don't already have one ; Build POST data Local $POST_DATA = "grant_type=client_credentials&client_id=" & $API_ID & "&client_secret=" & $API_KEY ; Send token request Local $oHttp = ObjCreate("WinHttp.WinHttpRequest.5.1") $oHttp.Open("POST", $OAUTH2_TOKEN_URL, False) $oHttp.SetRequestHeader("Content-Type", "application/x-www-form-urlencoded") $oHttp.Send($POST_DATA) ; Parse token response Local $sResponse = $oHttp.ResponseText Local $oJson = _Json_Parse($sResponse) If @error Then MsgBox($MB_ICONERROR, "Error", "Failed to parse token response.") ConsoleWrite("Full Response: " & $sResponse & @CRLF) Exit EndIf Local $ACCESS_TOKEN = _Json_Get($oJson, "access_token") Local $TOKEN_TYPE = _Json_Get($oJson, "token_type") Local $EXPIRES_IN = _Json_Get($oJson, "expires_in") If $ACCESS_TOKEN = "" Or $ACCESS_TOKEN = "null" Then MsgBox($MB_ICONERROR, "Error", "Failed to obtain OAuth2 Access Token.") ConsoleWrite("Full Response: " & $sResponse & @CRLF) Exit EndIf ;ConsoleWrite("Access Token obtained successfully!" & @CRLF) ;ConsoleWrite("Token Type: " & $TOKEN_TYPE & @CRLF) ;ConsoleWrite("Expires In: " & $EXPIRES_IN & " seconds" & @CRLF) ; 2. Making API call with Access Token ; Make the authenticated API call $oHttp.Open("GET", $V4_URL & $vPath, False) $oHttp.SetRequestHeader("Accept", "application/json") $oHttp.SetRequestHeader("Content-Type", "application/json") $oHttp.SetRequestHeader("Authorization", $TOKEN_TYPE & " " & $ACCESS_TOKEN) $oHttp.Send() ;ConsoleWrite("Response Status: " & $oHttp.Status & @CRLF) ;ConsoleWrite("Response:" & @CRLF & $oHttp.ResponseText & @CRLF) ;ConsoleWrite(_Json_Unminify($oHttp.ResponseText)) Local $oJson = _Json_Parse($oHttp.ResponseText) Local $sResult=_Json_Get($oJson,'items[0].description') ;ConsoleWrite("Cloudshare description field is " & $sResult) Return $sResult EndFunc ;==>_CS_V4_Get ; --- Helper Functions --- ; Function to generate a random alphanumeric string Func _GenerateRandomAlphanumericString($iLength) Local $sChars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789" Local $sResult = "" For $i = 1 To $iLength $sResult &= StringMid($sChars, Random(1, StringLen($sChars), 1), 1) Next Return $sResult EndFunc ; Function to display a message box and exit (replaces alert/confirm) Func ExitMsgBox($iFlags, $sTitle, $sText) MsgBox($iFlags, $sTitle, $sText) Exit EndFunc