ReadyAPI - add webbased actions for token retrieval
Hi,
Could someone help me to add webbased actions to retrieve the token please?
Explanation:
I've retrieved my JWT token by using the AuthManager, but up to the moment where the user needs to login on the webpage. Thus, the clicks on the webpage needs to be programmed with a script.
I've tried to use the [Auth Repository > Automation] scripts tab (according the documentation from SmartBear) but that doesn't work. An error occurs when I want the value of the dropdownlist: "The function is missing a name" or something like that.
Then I thoughed: maybe I should use Events, but I don't know which event could ensure the last authentication steps before the testcase is run.
Logically, when the token is retrieved in the AuthManager and this is assigned to the REST step, the last actions to do is to execute some clicks on the webpage to complete the login. Also, I have to use a certificate (in this case, for test environment, a dummy certificate, that is located on my harddrive).
I'm a little lost in how to do so. Anyone an idea please?
I do have a groovyscript teststep, and I can retrieve the token to put on project level, but I'm looking for a way to do it on the most highest level possible for maintenance purposes. So, I don't want to copy that script for each testcase/teststep.
My script:
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.chrome.ChromeDriver;
import java.util.concurrent.TimeUnit;
import org.openqa.selenium.support.ui.Select
//setup the driver
System.setProperty("webdriver.chrome.driver", "C:/Users/me/AppData/Local/Programs/SmartBear/ReadyAPI-3.9.2/bin/ext/chromedriver.exe")
//1| define the driver
def driver = new ChromeDriver()
//driver.manage().timeouts().implicitlyWait(60, TimeUnit.SECONDS)
//2| and now use this to visit the login page
def link = context.expand( 'https://the-site-to-login.something/ ' )
driver.get(link)
//3| get the JWT-token from AuthManager
def oAuthProfile = testRunner.testCase.testSuite.getProject().getAuthRepository().getEntry("TST-USER")
def getTstToken = oAuthProfile.getAccessToken()
log.info getTstToken
//put the accesstoken on ProjectLevel
def setToken = testRunner.testCase.testSuite.project.setPropertyValue("projToken", getTstToken)
// 4 | click | linkText=Gelieve een taal te selecteren
driver.findElement(By.linkText("Gelieve een taal te selecteren")).click()
driver.findElement(By.id("aButton")).click()
// 5 | click | id=profile
def element = driver.findElement(By.id("profile"))
// 6 | select | id=profile | label=TheNameImSearchingFor
Select s = new Select( element )
s.selectByVisibleText("TheNameImSearchingFor" )
def first = s.getFirstSelectedOption()
String selectedoption = first.getText()
log.info selectedoption
driver.quit()
Thanks in advance for any insights!
Kind regards,
AAB
Hello AAB
I tried to unpack your question... If reading to the end, it seems like you have a work around by using a groovy script to accomplish what you ask for guidance about at the top of your post. I can offer tips or techniques to you that you can further question or discard.
-- Auth Manager... I didn't even know that existed. 🙂 When I have needed an OAuth token in the past, i just had a testcase or teststep that I would invoke OAuth token generator itself instead of adding a middle man of Auth Manager. If you look at all the URL's that you need to provide in the Auth Manager user interface, why not invoke them yourself in a testcase or teststep for better control. After all, this is ReadyAPI and it invokes API's very well. 🙂 Auth Manager is just invoking them for you. In short, my technique is to call needed URL's yourself to get JWT or Auth code and abandon Auth Manager. This may or may not suite your needs but has worked for me in the past.
-- "I'm looking for a way to do it on the most highest level possible for maintenance purposes."... All the way from the project level on down, the running of an action has a "Setup Script" (in the tabs along the bottom of the editor) available to you to interject code to run at that level. Put your work around groovy script that you shared in at the highest levels "Setup Script" so that you only maintain it once. The technique I use is to put a teststep in at testcase in a suite that I have disabled. I call that testcase/teststep from every location I need it with a couple of lines of groovy script code. I do have to perpetuate that in all the testcases that I need the code in, but it is just a call out to single task that I only maintain once in the disabled testsuite. Below is a sample, but googling for ways to invoke a common testcase/teststep are plentiful and often meet needs of keeping code in one place for maintainability.
def invokeTestSuiteName = 'Common Code'; def invokeTestCaseName = 'Global Processing By Test Case Name'; def properties = new com.eviware.soapui.support.types.StringToObjectMap(); def async = false; testRunner.testCase.testSuite.project.getTestSuiteByName(invokeTestSuiteName).setPropertyValue(invokeTestSuiteName.replaceAll('\\s', '') + "testCaseName", testRunner.testCase.name); def result = testRunner.testCase.testSuite.project.getTestSuiteByName(invokeTestSuiteName).getTestCaseByName(invokeTestCaseName).run (properties, async); def httpResponse = testRunner.testCase.testSuite.project.getTestSuiteByName(invokeTestSuiteName).getPropertyValue( invokeTestSuiteName.replaceAll('\\s', '') + "APIHttpResponse"); def requestId = testRunner.testCase.testSuite.project.getTestSuiteByName(invokeTestSuiteName).getPropertyValue( invokeTestSuiteName.replaceAll('\\s', '') + "APIRequestId"); assert (result.status.toString() == 'FINISHED'), "Invoked testcase should have a 'FINISHED' result but it was a '" + result.status.toString() + "' result instead. " + httpResponse + ' ' + requestId;