diff --git a/.gitignore b/.gitignore index 416921d..066f018 100644 --- a/.gitignore +++ b/.gitignore @@ -166,4 +166,13 @@ cython_debug/ /service/user_account.json /service/models -secrets/ \ No newline at end of file +secrets/ + + +# test-automation-ignore -files +com.hybrid.joshsoftware.lingoai/target/ +com.hybrid.joshsoftware.lingoai/Reports/ +com.hybrid.joshsoftware.lingoai/test-output/ +com.hybrid.joshsoftware.lingoai/.settings/ +com.hybrid.joshsoftware.lingoai/.classpath +com.hybrid.joshsoftware.lingoai/.project diff --git a/com.hybrid.joshsoftware.lingoai/Configuration/lingo.properties b/com.hybrid.joshsoftware.lingoai/Configuration/lingo.properties new file mode 100644 index 0000000..9adfa70 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/Configuration/lingo.properties @@ -0,0 +1,2 @@ +appUrl = https://thelingo.co.in/signin +headless = false diff --git a/com.hybrid.joshsoftware.lingoai/TestData/TestData.xlsx b/com.hybrid.joshsoftware.lingoai/TestData/TestData.xlsx new file mode 100644 index 0000000..494c6da Binary files /dev/null and b/com.hybrid.joshsoftware.lingoai/TestData/TestData.xlsx differ diff --git a/com.hybrid.joshsoftware.lingoai/TranscribeFiles/batman.mp3 b/com.hybrid.joshsoftware.lingoai/TranscribeFiles/batman.mp3 new file mode 100644 index 0000000..7d302c4 Binary files /dev/null and b/com.hybrid.joshsoftware.lingoai/TranscribeFiles/batman.mp3 differ diff --git a/com.hybrid.joshsoftware.lingoai/XMLFiles/e2e.xml b/com.hybrid.joshsoftware.lingoai/XMLFiles/e2e.xml new file mode 100644 index 0000000..bf2d9aa --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/XMLFiles/e2e.xml @@ -0,0 +1,20 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/com.hybrid.joshsoftware.lingoai/pom.xml b/com.hybrid.joshsoftware.lingoai/pom.xml new file mode 100644 index 0000000..aedbb52 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/pom.xml @@ -0,0 +1,41 @@ + + 4.0.0 + com.hybrid.joshsoftware.lingoai + com.hybrid.joshsoftware.lingoai + 0.0.1-SNAPSHOT + + + + org.seleniumhq.selenium + selenium-java + 4.29.0 + + + + + org.testng + testng + 7.10.2 + + + + org.apache.poi + poi + 5.4.0 + + + + org.apache.poi + poi-ooxml + 5.4.0 + + + + com.aventstack + chaintest-testng + 1.0.12 + + + \ No newline at end of file diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/BaseClass/BaseClass.java b/com.hybrid.joshsoftware.lingoai/src/main/java/BaseClass/BaseClass.java new file mode 100644 index 0000000..ee9331d --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/BaseClass/BaseClass.java @@ -0,0 +1,39 @@ +package BaseClass; + +import org.openqa.selenium.WebDriver; +import org.testng.annotations.AfterClass; +import org.testng.annotations.BeforeClass; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +import Helper.BrowserFactory; +import Helper.ConfigUtility; + +public class BaseClass { + + public WebDriver driver; + + // @Parameters({"browser_name"}) + @BeforeClass + public void startBrowser() { + + ChainTestListener.log(" *** Instantiating Browser *** "); + + driver = BrowserFactory.startBrowser("Chrome", ConfigUtility.getProperty("appUrl"), + ConfigUtility.getProperty("headless")); + + } + + @AfterClass + public void tearDown() { + ChainTestListener.log("LOG INFO: CLOSING BROWSER"); + if (driver != null) { + driver.quit(); + ChainTestListener.log("LOG INFO: BROWSER CLOSED"); + } else { + System.out.println("LOG INFO: BROWSER NOT INITIATED "); + } + + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/BrowserFactory.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/BrowserFactory.java new file mode 100644 index 0000000..df07050 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/BrowserFactory.java @@ -0,0 +1,82 @@ +package Helper; + +import java.time.Duration; + +import org.openqa.selenium.WebDriver; +import org.openqa.selenium.chrome.ChromeDriver; +import org.openqa.selenium.chrome.ChromeOptions; +import org.openqa.selenium.edge.EdgeDriver; +import org.openqa.selenium.firefox.FirefoxDriver; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +public class BrowserFactory { + + static WebDriver driver; + + // Initializing driver for screenshot in listener during failure + public static WebDriver getDriver() { + return driver; + } + + public static WebDriver startBrowser(String browser, String appUrl) { + if (browser.equalsIgnoreCase("Chrome")) { + driver = new ChromeDriver(); + } else if (browser.equalsIgnoreCase("Firefox")) { + driver = new FirefoxDriver(); + } + + else if (browser.equalsIgnoreCase("Edge")) { + driver = new EdgeDriver(); + } else { + System.out.println("We only support CHROME, FIREFOX, EDGE Browser"); + System.out.println("Starting Default Browser"); + driver = new ChromeDriver(); + } + driver.manage().window().maximize(); + driver.manage().timeouts().pageLoadTimeout(Duration.ofSeconds(60)); + driver.get(appUrl); + driver.manage().timeouts().implicitlyWait(Duration.ofSeconds(10)); + return driver; + } + + public static WebDriver startBrowser(String browser, String appUrl, String headless) { + + if (browser.equalsIgnoreCase("Chrome")) { + + if (headless.equalsIgnoreCase("true")) { + ChainTestListener.log("LOG INFO: CHROME BROWSER Initialized In HEADLESS"); + ChromeOptions options = new ChromeOptions(); + options.addArguments("headless"); + driver = new ChromeDriver(options); + } + + else { + ChainTestListener.log("LOG INFO: Chrome Browser Initialized "); + driver = new ChromeDriver(); + } + } + + else if (browser.equalsIgnoreCase("Firefox")) { + ChainTestListener.log("LOG INFO: FireFox Browser Initialized "); + driver = new FirefoxDriver(); + } else if (browser.equalsIgnoreCase("Edge")) { + ChainTestListener.log("LOG INFO: Edge Browser Initialized "); + driver = new EdgeDriver(); + } + + else { + ChainTestListener.log("LOG INFO: Sorry We Only support 'CHROME', 'FIREFOX', 'EDGE' "); + ChainTestListener.log("LOG INFO: Initializing Chrome Browser"); + driver = new ChromeDriver(); + } + + driver.manage().window().maximize(); + driver.manage().timeouts().pageLoadTimeout(Duration.ofSeconds(60)); + ChainTestListener.log("LOG INFO: Launching Lingo AI URL"); + driver.get(appUrl); + driver.manage().timeouts().implicitlyWait(Duration.ofSeconds(10)); + return driver; + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/ConfigUtility.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/ConfigUtility.java new file mode 100644 index 0000000..48ffeb8 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/ConfigUtility.java @@ -0,0 +1,27 @@ +package Helper; + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.util.Properties; + +public class ConfigUtility { + + public static String getProperty(String key) { + Properties prop = null; + + try { + + prop = new Properties(); + prop.load( + new FileInputStream(new File(System.getProperty("user.dir") + "/Configuration/lingo.properties"))); + } catch (FileNotFoundException e) { + System.out.println("File Not Found " + e.getMessage()); + } catch (IOException e) { + System.out.println("Issue On loading " + e.getMessage()); + } + return prop.getProperty(key); + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/DateUtility.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/DateUtility.java new file mode 100644 index 0000000..3b3042c --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/DateUtility.java @@ -0,0 +1,17 @@ +package Helper; + +import java.time.LocalDate; +import java.time.format.DateTimeFormatter; + +public class DateUtility { + + public static String getDate() { + LocalDate today = LocalDate.now(); // gets current date + + DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd MMM yyyy"); + String formattedDate = today.format(formatter); + + return formattedDate; // e.g., 22 July 2025 + } + +} \ No newline at end of file diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/Utility.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/Utility.java new file mode 100644 index 0000000..2141b02 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Helper/Utility.java @@ -0,0 +1,123 @@ +package Helper; + +import java.time.Duration; +import java.util.ArrayList; +import java.util.List; + +import org.openqa.selenium.By; +import org.openqa.selenium.JavascriptExecutor; +import org.openqa.selenium.OutputType; +import org.openqa.selenium.TakesScreenshot; +import org.openqa.selenium.WebDriver; +import org.openqa.selenium.WebElement; +import org.openqa.selenium.support.ui.ExpectedConditions; +import org.openqa.selenium.support.ui.WebDriverWait; + +public class Utility { + + public static String getScreenshot(WebDriver driver) { + TakesScreenshot ts = (TakesScreenshot) driver; + return ts.getScreenshotAs(OutputType.BASE64); + } + + public static String getTitle(WebDriver driver) { + return driver.getTitle(); + } + + public static boolean isCurrentUrlMatch(WebDriver driver, String url) { + + WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(5)); + return wait.until(ExpectedConditions.urlContains(url)); + + } + + public static void pause(int millisec) { + try { + Thread.sleep(millisec); + } catch (InterruptedException e) { + System.out.println(e.getMessage()); + } + } + + public static boolean checkElementInvisibility(WebDriver driver, By locator) { + WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(10)); + return wait.until(ExpectedConditions.invisibilityOfElementLocated(locator)); + + } + + public static WebElement checkElement(WebDriver driver, By locator) { + WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(300)); + + WebElement ele = wait.until(ExpectedConditions.elementToBeClickable(locator)); + + Utility.highlightElement(driver, ele); + + return ele; + + } + +// public static WebElement checkElementVisibility(WebDriver driver, By locator) { +// WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(60)); +// +// WebElement ele = wait.until(ExpectedConditions.visibilityOfElementLocated(locator)); +// +// Utility.highlightElement(driver, ele); +// +// return ele; +// +// } + + public static List checkListElementPresence(WebDriver driver, By locator) { + WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(60)); + return wait.until(ExpectedConditions.presenceOfAllElementsLocatedBy(locator)); + } + + public static void highlightElement(WebDriver driver, WebElement element) { + JavascriptExecutor js = (JavascriptExecutor) driver; + js.executeScript("arguments[0].setAttribute('style','background:yellow;border: 2px solid red;');", element); + pause(500); + js.executeScript("arguments[0].setAttribute('style','border: solid 2px white');", element); + } + + public static void typeonElement(WebDriver driver, By locator, String textToType) { + // System.out.println(textToType); + + Utility.checkElement(driver, locator).sendKeys(textToType); + } + + public static void clickOnElement(WebDriver driver, By locator) { + Utility.checkElement(driver, locator).click(); + } + + public static String getElementText(WebDriver driver, By locator) { + System.out.println(driver.findElement(locator).getText()); + return Utility.checkElement(driver, locator).getText(); + } + + public static boolean isElementDisplayed(WebDriver driver, By locator) { + return Utility.checkElement(driver, locator).isDisplayed(); + } + + public static List getActualList(WebDriver driver, By locator) { + return driver.findElements(locator); + } + + public static List getMenuList(WebDriver driver, int size, By locator) { + List actual_list = new ArrayList(); + List list_webElement = Utility.getActualList(driver, locator); + + if (list_webElement.size() == size) { + for (WebElement webElement : list_webElement) { + String str = webElement.getText(); + + actual_list.add(str); + } + + } else { + System.out.println("List Count Mismatch"); + } + + return actual_list; + } + +} \ No newline at end of file diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Listeners/MyTestNGListener.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Listeners/MyTestNGListener.java new file mode 100644 index 0000000..dc43206 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Listeners/MyTestNGListener.java @@ -0,0 +1,47 @@ +package Listeners; + +import org.testng.ITestContext; +import org.testng.ITestListener; +import org.testng.ITestResult; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +import Helper.BrowserFactory; +import Helper.Utility; + +public class MyTestNGListener implements ITestListener { + + public void onTestStart(ITestResult result) { + + ChainTestListener.log("Log:PASS - Test Pass " + result.getMethod().getMethodName()); + + } + + public void onTestSuccess(ITestResult result) { + ChainTestListener.log("Log:PASS - Test PASS " + result.getMethod().getMethodName()); + } + + public void onTestFailure(ITestResult result) { + ChainTestListener.log("Log:FAIL - Test FAIL " + result.getMethod().getMethodName() + " " + + result.getThrowable().getMessage()); + String screenshot = Utility.getScreenshot(BrowserFactory.getDriver()); + ChainTestListener.embed(screenshot, "image/png"); + + } + + public void onTestSkipped(ITestResult result) { + ChainTestListener.log("Log:SKIP - Test SKIPPED " + result.getMethod().getMethodName()); + + } + +// public void onStart(ITestContext context) { +// ChainTestListener.log(""); +// +// } +// +// public void onFinish(ITestContext context) { +// ChainTestListener.log(""); +// +// } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/AudioResultPage.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/AudioResultPage.java new file mode 100644 index 0000000..22da371 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/AudioResultPage.java @@ -0,0 +1,153 @@ +package Pages; + +import java.time.Duration; +import java.util.ArrayList; +import java.util.List; + +import org.openqa.selenium.By; +import org.openqa.selenium.WebDriver; +import org.openqa.selenium.WebElement; +import org.openqa.selenium.support.ui.ExpectedConditions; +import org.openqa.selenium.support.ui.WebDriverWait; +import org.testng.Reporter; + +import Helper.DateUtility; +import Helper.Utility; + +public class AudioResultPage { + + WebDriver driver; + + public AudioResultPage(WebDriver driver) { + + this.driver = driver; + + } + + // Audio Processing Result Locators + By txt_uploaded_audio_file = By + .xpath("//p[text()='Complete analysis of your uploaded audio file with translation and insights']"); + + // Audio File Details Container Locators + By txt_audio_file_detais = By.xpath("//h3[text()='Audio File Details']"); + By list_actual_audio_file_Details_label = By.xpath( + "//h3[text()='Audio File Details']/parent::div/following-sibling::div//p[contains(@class,'text-muted-foreground')]"); + By button_playAudio = By.xpath("//button[text()='Play Audio']"); + By button_pauseAudio = By.xpath("//button[text()='Pause Audio']"); + By file_name = By.xpath("//p[text()='File Name']//following-sibling::p"); + By file_duration = By.xpath("//p[text()='Duration']//following-sibling::div"); + By file_actual_date = By.xpath("//p[text()='Upload Date']//following-sibling::p"); + By file_orignal_language = By.xpath("//p[text()='Original Language']//following-sibling::div"); + By button_timeline = By.xpath("//button[text()='Timeline']"); + + // Validate Transcribe button Options + By listButton_transcribe_Options = By.xpath("//div[@role='tablist']//button"); + + // Englsih Translation COntainer + By containerTxt_Englishtranslation = By.xpath("//h3[text()='English Translation']"); + + // Timeline Conversation Container + By conversation_container = By.xpath("//h3[text()='Conversation Timeline']"); + By conversation_timeline_text_seq = By.xpath( + "//h3[text()='Conversation Timeline']/parent::div/following-sibling::div//div[contains(@class,'items-start')]"); + + public boolean getAudioFileUploadedMsg() { + return Utility.isElementDisplayed(driver, txt_uploaded_audio_file); + } + + public List verifyLabelAudioContainer() { + + List actual_audio_file_Details_label_list = Utility.checkListElementPresence(driver, + list_actual_audio_file_Details_label); + + List actual_myList = new ArrayList(); + + if (actual_audio_file_Details_label_list.size() == 4) { + + for (int i = 0; i < actual_audio_file_Details_label_list.size(); i++) { + String a = actual_audio_file_Details_label_list.get(i).getText(); + + actual_myList.add(a); + } + } else { + Reporter.log("*** File Details List Count Mismatch ***", true); + } + return actual_myList; + } + + public boolean checkPlayAudioButtonStatus() { + return Utility.isElementDisplayed(driver, button_playAudio); + + } + + public boolean checkEnglishTranslationContainerText() { + return Utility.isElementDisplayed(driver, containerTxt_Englishtranslation); + + } + + public String getUploadedFileName() { + return Utility.getElementText(driver, file_name); + + } + + public String getUploadedFileDuration() { + return Utility.getElementText(driver, file_duration); + + } + + public String getTodayDate() { + return DateUtility.getDate(); + } + + public String getUploadedFileDate() { + return Utility.getElementText(driver, file_actual_date); + + } + + public String checkFileOrignalLanguage() { + return Utility.getElementText(driver, file_orignal_language); + + } + + public List checkTranscribeOptions() { + List actual_transcribe_Options_List = Utility.checkListElementPresence(driver, + listButton_transcribe_Options); + + List myList = new ArrayList(); + if (actual_transcribe_Options_List.size() == 3) { + for (int i = 0; i < actual_transcribe_Options_List.size(); i++) { + String a = actual_transcribe_Options_List.get(i).getText(); + + myList.add(a); + } + } else { + Reporter.log("*** Transcribe Options Count Mismatch ***", true); + } + + return myList; + + } + + public void clickPlayAudioButton() { + Utility.clickOnElement(driver, button_playAudio); + if (Utility.getElementText(driver, button_pauseAudio).equals("Pause Audio")) { + Utility.clickOnElement(driver, button_timeline); + } else { + Reporter.log("Pause Button Text Mismatch", true); + } + } + + public boolean checkConversationContainerStatus() { + return Utility.isElementDisplayed(driver, conversation_container); + } + + public void checkConversationTranscribe() { + List abc = Utility.checkListElementPresence(driver, conversation_timeline_text_seq); + for (WebElement xyz : abc) { + WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(60)); + wait.until(ExpectedConditions.attributeContains(xyz, "class", "bg-green-100/50 border-green-50")); + System.out.println("TRUE > Getting Green Border"); + } + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/HomePage.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/HomePage.java new file mode 100644 index 0000000..545d418 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/HomePage.java @@ -0,0 +1,180 @@ +package Pages; + +import java.util.ArrayList; +import java.util.List; + +import org.openqa.selenium.By; +import org.openqa.selenium.WebDriver; +import org.openqa.selenium.WebElement; +import org.testng.Assert; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +import Helper.Utility; + +public class HomePage { + + WebDriver driver; + + // driver Initialization + public HomePage(WebDriver driver) { + this.driver = driver; + } + + // Locators > HomePage + By mic_container = By.xpath("//p[contains(text(),'upload an audio or video file')]"); + By button_uploadfile = By.xpath("//button[text()='Upload File']"); + By button_startRecording = By.xpath("//button[contains(text(),'Start Recording')]"); + By verifyFileUploaded = By.xpath("//p"); + By button_transcribe = By.xpath("//button[text()='Transcribe']"); + By button_restart = By.xpath("//button[text()='Restart']"); + By h1_checkAudioResults = By.xpath("//h1[text()='Audio Processing Results']"); + By transcribing_msg = By.xpath("//p[contains(text(),'Transcribing')]"); + By save_transcribe_msg = By.xpath("//p[contains(text(),'Saving')]"); + + // Locators > ProfileOptions Container + By profileIcon = By.xpath("//a[contains(text(),'View Records')]//parent::button/following-sibling::div"); + By profileOption_account = By.xpath("//div[@role='menu']/div[text()='My Account']"); + By profileOption_separator = By.xpath("//div[@role='separator']"); + By profile_menuOptions = By.xpath("//div[@role='menuitem']"); + By txt_profileOption = By.xpath("//div[text()='Profile']"); + By container_profile = By.xpath("//h2[text()='Profile']//parent::div"); + By heading_profileContainer = By.xpath("//h2[text()='Profile']"); + By profile_email = By.xpath("//h2[text()='Profile']//parent::div//p"); + By txt_email_initials = By.xpath("//h2[text()='Profile']//parent::div//div[contains(@class,'text-white')]"); + By close_profileContainer = By.xpath("//h2[text()='Profile']//parent::div//button"); + By list_profileTranscribeDetails = By.xpath("//div[contains(@class,'grid')]//div"); + + // Locators > LingoBot + By txt_lingoBot = By.xpath("//div[text()='Lingo bot']"); + By container_lingoBot = By.xpath("//h2[text()='Meeting Recorder Bot']/parent::div"); + By headingTxt_lingoBotContainer = By.xpath("//h2[text()='Meeting Recorder Bot']"); + By subHeadingTxt_lingoBotContainer = By.xpath("//h2[text()='Meeting Recorder Bot']/parent::div//p"); + By buttonCancel_LingoBot = By.xpath("//h2[text()='Meeting Recorder Bot']/parent::div//button[text()='Cancel']"); + + // Logout + By button_logout = By.xpath("//div[text()='Logout']"); + + public String uploadMp3File(String file_path) { + driver.findElement(By.xpath("//button[text()='Upload File']//preceding::input[@type='file']")) + .sendKeys(file_path); + return Utility.getElementText(driver, verifyFileUploaded); + + } + + public void clickTranscribe() { + ChainTestListener.log("LOG INFO: CLICKING ON TRANSCRIBE"); + Utility.clickOnElement(driver, button_transcribe); + } + + public String captureTranscribingMsg() { + + return Utility.getElementText(driver, transcribing_msg); + } + + public String captureTranscribeSaveMsg() { + return Utility.getElementText(driver, save_transcribe_msg); + } + + public String captureAudioProcessingResult() { + return Utility.getElementText(driver, h1_checkAudioResults); + } + + public void clickProfileIcon() { + Utility.clickOnElement(driver, profileIcon); + } + + public String getAccountText() { + return Utility.getElementText(driver, profileOption_account); + } + + public boolean isProfileSeparatorDisplayed() { + return Utility.isElementDisplayed(driver, profileOption_separator); + } + + public List getProfileMenuOptions() { + return Utility.getMenuList(driver, 4, profile_menuOptions); + } + + public void clickProfileOptiontxt() { + Utility.clickOnElement(driver, txt_profileOption); + } + + public boolean isProfileContainerDisplayed() { + return Utility.isElementDisplayed(driver, container_profile); + } + + public String getProfileContainerHeadingText() { + return Utility.getElementText(driver, heading_profileContainer); + } + + public String getProfileEmail() { + return Utility.getElementText(driver, profile_email); + } + + public String getemailInitials() { + return Utility.getElementText(driver, txt_email_initials); + } + + public String getInitials() { + String email = this.getProfileEmail(); + String email_upper = email.toUpperCase(); + char exp_c1 = email_upper.charAt(0); + return String.valueOf(exp_c1); + } + + public void clickProfileClose() { + Utility.clickOnElement(driver, close_profileContainer); + } + + public List getTranscribeDetails() throws Exception { + + List user_transcribe_details = Utility.getActualList(driver, list_profileTranscribeDetails); + + List actual_user_transcribe_details = new ArrayList(); + + for (WebElement element : user_transcribe_details) { + String str1 = element.getText(); + String arr[] = str1.split("\n"); + String strA = arr[0]; + String strB = arr[1]; + actual_user_transcribe_details.add(strA); + // Assert.assertNotNull(strB); + if (strB.equals(null)) { + throw new Exception("Null Value Observed at Transcribe Profile Details" + strB); + } + + } + return actual_user_transcribe_details; + } + + public void clickLingoBot() { + Utility.clickOnElement(driver, txt_lingoBot); + + } + + public boolean isLingoBotContainerDisplayed() { + return Utility.isElementDisplayed(driver, container_lingoBot); + } + + public boolean isLingoBotContainerHeadingDisplayed() { + return Utility.isElementDisplayed(driver, headingTxt_lingoBotContainer); + } + + public String getLingoBotSubHeading() { + return Utility.getElementText(driver, subHeadingTxt_lingoBotContainer); + } + + public void clickLingoCancelButton() { + Utility.clickOnElement(driver, buttonCancel_LingoBot); + } + + public boolean IsLingoBotContainerInvisible() { + return Utility.checkElementInvisibility(driver, container_lingoBot); + } + + public void clickLogout() { + Utility.clickOnElement(driver, button_logout); + } + +} \ No newline at end of file diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/LoginPage.java b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/LoginPage.java new file mode 100644 index 0000000..e522fd2 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/Pages/LoginPage.java @@ -0,0 +1,43 @@ +package Pages; + +import org.openqa.selenium.By; +import org.openqa.selenium.WebDriver; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +import Helper.Utility; + +public class LoginPage { + + WebDriver driver; + + public LoginPage(WebDriver driver) { + this.driver = driver; + } + + By email = By.name("userEmail"); + By password = By.xpath("//input[@name='password']"); + By signinButton = By.xpath("//button[@type='submit']"); + By signupLink = By.partialLinkText("Sign Up"); + By homepage_signIn = By.xpath("//button//a[text()='Sign In']"); + + public HomePage loginWithValidCreds(String user_email, String user_pw) { + + ChainTestListener.log("LOG INFO: ENTERING USER EMAIL"); + Utility.typeonElement(driver, email, user_email); + + ChainTestListener.log("LOG INFO: ENTERING USER PASSWORD"); + Utility.typeonElement(driver, password, user_pw); + + ChainTestListener.log("LOG INFO: ENTERING USER SIGNIN"); + Utility.clickOnElement(driver, signinButton); + + return new HomePage(driver); + + } + + public boolean isSignInButtonDisplayed() { + return Utility.isElementDisplayed(driver, homepage_signIn); + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/DataProviders.java b/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/DataProviders.java new file mode 100644 index 0000000..933dfe7 --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/DataProviders.java @@ -0,0 +1,15 @@ +package dataproviders; + +import org.testng.annotations.DataProvider; + +public class DataProviders { + + @DataProvider(name = "LoginCredsData") + public static Object[][] testData() { + + Object obj[][] = ExcelUtility.readExcelData("LoginCreds"); + return obj; + + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/ExcelUtility.java b/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/ExcelUtility.java new file mode 100644 index 0000000..94a78ce --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/main/java/dataproviders/ExcelUtility.java @@ -0,0 +1,62 @@ +package dataproviders; + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.io.IOException; + +import org.apache.poi.ss.usermodel.CellType; +import org.apache.poi.xssf.usermodel.XSSFWorkbook; + +public class ExcelUtility { + static XSSFWorkbook wb; + + public static Object[][] readExcelData(String sheet_name) { + + FileInputStream fis = null; + + File src = new File(System.getProperty("user.dir") + "/TestData/TestData.xlsx"); + + try { + fis = new FileInputStream(src); + wb = new XSSFWorkbook(fis); + + } catch (FileNotFoundException e) { + System.out.println("File Not Found " + e.getMessage()); + } catch (IOException e) { + + System.out.println("File Not able to load " + e.getMessage()); + } + int row_count = wb.getSheet(sheet_name).getPhysicalNumberOfRows(); + int column_count = wb.getSheet(sheet_name).getRow(0).getPhysicalNumberOfCells(); + + Object obj[][] = new Object[row_count][column_count]; + for (int i = 0; i < row_count; i++) { + for (int j = 0; j < column_count; j++) { + obj[i][j] = ExcelUtility.getCellType(sheet_name, i, j); + + } + + } + + return obj; + + } + + public static String getCellType(String sheet_name, int row, int cell) { + String data = ""; + CellType cellType = wb.getSheet(sheet_name).getRow(row).getCell(cell).getCellType(); + + if (cellType == CellType.STRING) { + data = wb.getSheet(sheet_name).getRow(row).getCell(cell).getStringCellValue(); + } else if (cellType == CellType.NUMERIC) { + data = String.valueOf(wb.getSheet(sheet_name).getRow(row).getCell(cell).getNumericCellValue()); + } + + else if (cellType == CellType.BOOLEAN) { + data = String.valueOf(wb.getSheet(sheet_name).getRow(row).getCell(cell).getBooleanCellValue()); + } + return data; + } + +} diff --git a/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/LingoAILogin.java b/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/LingoAILogin.java new file mode 100644 index 0000000..0958f1c --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/LingoAILogin.java @@ -0,0 +1,128 @@ +package testcases; + + +import org.testng.annotations.Test; +import org.testng.AssertJUnit; +import java.util.ArrayList; +import java.util.List; + +import org.testng.Assert; +import org.testng.AssertJUnit; +import org.testng.annotations.Test; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +//import com.aventstack.chaintest.plugins.ChainTestListener; + +import BaseClass.BaseClass; +import Helper.Utility; +import Pages.AudioResultPage; +import Pages.HomePage; +import Pages.LoginPage; +import dataproviders.DataProviders; + +//@Listeners(ChainTestListener.class) +public class LingoAILogin extends BaseClass { + + LoginPage login; + HomePage home; + AudioResultPage result; + + @Test(priority = 1, dataProvider = "LoginCredsData", dataProviderClass = DataProviders.class, description = "Validate E2E after Uploading MP3 File") + public void testMP3FileUpload(String u_name, String pw) { + + // batman.mp3 + // effective_communication.mp4" + + // String upload_file = "/home/ue/Downloads/batman.mp3"; + String upload_file = System.getProperty("user.dir") + "/TranscribeFiles/batman.mp3"; + + // Login With Valid Creds + login = new LoginPage(driver); + System.out.println("LOG INFO: LOGIN TO LIGO AI"); + home = login.loginWithValidCreds(u_name, pw); + + AssertJUnit.assertTrue(Utility.isCurrentUrlMatch(driver, "thelingo.co.in/new")); + + // Upload MP3 File + if (upload_file.contains("mp3")) { + ChainTestListener.log("LOG INFO: CHOSEN FILE TO UPLOAD ===> MP3 "); + + String actual_file_uploaded_title = home.uploadMp3File(upload_file); + Assert.assertTrue(actual_file_uploaded_title.contains("batman.mp3"), "File Mismatch"); + } + + // Upload MP4 + else if (upload_file.contains("mp4")) { + ChainTestListener.log("LOG INFO: CHOSEN FILE TO UPLOAD ===> MP4 "); + String actual_file_uploaded_title = home.uploadMp3File(upload_file); + Assert.assertTrue(actual_file_uploaded_title.contains("effective_communication.mp4"), "File Mismatch"); + } + // Options Not Supported + else { + ChainTestListener.log("LOG INFO: CURRENTLY WE SUPPORT MP3 AND MP4 FILES ONLY"); + } + // String actual_audio_result_title = + home.clickTranscribe(); + + // Validate Post Transcribe Click Message + Assert.assertTrue(home.captureTranscribingMsg().contains("Transcribing"), "Transcribe Text Mismatch"); + Assert.assertTrue(home.captureTranscribeSaveMsg().contains("Saving"), "Saving Text Mismatch"); + + // Validate Audio Processing Results + AssertJUnit.assertTrue(home.captureAudioProcessingResult().contains("Audio Processing Results")); + } + + @Test(priority = 2, description = "Validate E2E after uploading MP4", dependsOnMethods = { "testMP3FileUpload" }) + public void validateMP3Upload() { + + List expected_audio_file_Details_list = new ArrayList(); + expected_audio_file_Details_list.add("File Name"); + expected_audio_file_Details_list.add("Duration"); + expected_audio_file_Details_list.add("Upload Date"); + expected_audio_file_Details_list.add("Original Language"); + + result = new AudioResultPage(driver); + Assert.assertEquals(result.verifyLabelAudioContainer(), expected_audio_file_Details_list, + "Audio File Details Container Label Mismatch"); + + // Validate "Play Audio Button" + Assert.assertTrue(result.checkPlayAudioButtonStatus(), "*** Button Status Not enabled ***"); + + // Validate English Translation Container + Assert.assertTrue(result.checkEnglishTranslationContainerText()); + + // Validating File Name + Assert.assertTrue(result.getUploadedFileName().contains("batman.mp3")); + + // Validating Duration + Assert.assertNotNull(result.getUploadedFileDuration()); + + // Validate Date Format > Current Date + Assert.assertEquals(result.getUploadedFileDate(), result.getTodayDate(), "***** Date Mismatch *****"); + + // Validate Orignal Language > NOT NULL + Assert.assertNotNull(result.checkFileOrignalLanguage()); + + // Validate Transcribe button Options + List exp_transcribe_buttons_option = new ArrayList(); + exp_transcribe_buttons_option.add("Translation"); + exp_transcribe_buttons_option.add("Timeline"); + exp_transcribe_buttons_option.add("Summary"); + + Assert.assertEquals(result.checkTranscribeOptions(), exp_transcribe_buttons_option, + "Transcribe Option Mismatch"); + + } + + @Test(priority = 3, description = "Play Audio And Validate Transcribe") + public void playAudioFile() { + + result = new AudioResultPage(driver); + result.clickPlayAudioButton(); + AssertJUnit.assertTrue(result.checkConversationContainerStatus()); + result.checkConversationTranscribe(); + + } + +} \ No newline at end of file diff --git a/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/ProfileIcon.java b/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/ProfileIcon.java new file mode 100644 index 0000000..479ef6f --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/test/java/testcases/ProfileIcon.java @@ -0,0 +1,140 @@ +package testcases; + +import java.util.ArrayList; +import java.util.List; + +import org.testng.Assert; +import org.testng.AssertJUnit; +import org.testng.annotations.Test; + +import com.aventstack.chaintest.plugins.ChainTestListener; + +import BaseClass.BaseClass; +import Helper.Utility; +import Pages.HomePage; +import Pages.LoginPage; +import dataproviders.DataProviders; + +public class ProfileIcon extends BaseClass { + + HomePage home; + LoginPage login; + + @Test(priority = 1, dataProvider = "LoginCredsData", dataProviderClass = DataProviders.class, description = "Profile Icon Click and Validate Profile Options") + public void testProfileDropdownOptions(String u_name, String pw) { + + login = new LoginPage(driver); + home = login.loginWithValidCreds(u_name, pw); + + Assert.assertTrue(Utility.isCurrentUrlMatch(driver, "thelingo.co.in/new"), "URL Mismatch"); + + List expected_profileOption_list = new ArrayList(); + + expected_profileOption_list.add("Profile"); + expected_profileOption_list.add("Lingo bot"); + expected_profileOption_list.add("Upgrade plan"); + expected_profileOption_list.add("Logout"); + ChainTestListener.log(" Expected Profile option List loaded "); + + // Click Profile Icon and check Visibility + home.clickProfileIcon(); + ChainTestListener.log(" Clicked On Profile icon "); + + // Validating My Account Text + Assert.assertTrue(home.getAccountText().contains("My Account"), "Account Text Mismatch On Profile DD"); + ChainTestListener.log("Account Text Label Is Displayed "); + + // Validating Separator + Assert.assertTrue(home.isProfileSeparatorDisplayed(), " Separation Isn't displayed "); + ChainTestListener.log(" Profile Separator Is Displayed "); + + Assert.assertEquals(home.getProfileMenuOptions(), expected_profileOption_list, + "Mismatch In Actual Profile Options ANd Expected Profile Option"); + ChainTestListener.log("Profile List Option Matching Succesful"); + + } + + @Test(priority = 2, dataProvider = "LoginCredsData", dataProviderClass = DataProviders.class, dependsOnMethods = { + "testProfileDropdownOptions" }) + public void clickProfileOptions(String u_name, String pw) throws Exception { + + List exp_user_transcribe_details = new ArrayList(); + exp_user_transcribe_details.add("Recordings:"); + exp_user_transcribe_details.add("Limit:"); + exp_user_transcribe_details.add("Remaining:"); + exp_user_transcribe_details.add("Subscription:"); + + // Profile Option Click From dd + home.clickProfileOptiontxt(); + ChainTestListener.log("Clicked on Profile Option From DD"); + + // Verify Profile Container Visibility + Assert.assertTrue(home.isProfileContainerDisplayed(), "Profile COntainer Visibility Error"); + ChainTestListener.log("Verifiication for Profile Container visibility"); + + // Verify Profile Heading + Assert.assertTrue(home.getProfileContainerHeadingText().equals("Profile"), "Profile Header Text Mismatch"); + ChainTestListener.log("Verifiication for Profile Heading visibility"); + + // Verify Email Displayed + Assert.assertEquals(home.getProfileEmail(), u_name, "Profile Email Mismatch "); + ChainTestListener.log("Verifiication of Profile Email Successful"); + + // Verify Email Initials + Assert.assertEquals(home.getemailInitials(), home.getInitials(), "Initials Not Matching "); + ChainTestListener.log("Verifiication for Profile Email Initials visibility"); + + // Verify profile transcribe details + Assert.assertEquals(home.getTranscribeDetails(), exp_user_transcribe_details, + "Transcribe Details List Mismatch"); + ChainTestListener.log("Verifiication for Profile Transcribe Option"); + + home.clickProfileClose(); + + } + + @Test(priority = 3, dependsOnMethods = { "testProfileDropdownOptions" }) + public void testLingoBot() { + + home.clickProfileIcon(); + ChainTestListener.log("Clicked Profile Icon"); + + home.clickLingoBot(); + ChainTestListener.log("Clicked Lingo Bot From DD"); + + Assert.assertTrue(home.isLingoBotContainerDisplayed(), "Lingo Container Visibility Error "); + ChainTestListener.log("Lingo Bot Container Visibility Checked"); + + Assert.assertTrue(home.isLingoBotContainerHeadingDisplayed(), "Lingo Bot Container Heading Mismatch"); + ChainTestListener.log("Lingo Bot Container Heading Visibility Checked"); + + AssertJUnit.assertEquals(home.getLingoBotSubHeading(), "Do you want to add a bot for meeting Summarization?"); + ChainTestListener.log("Lingo Bot Container Sub-Heading Visibility Checked"); + + home.clickLingoCancelButton(); + ChainTestListener.log("Lingo Bot Cancel Button Clicked"); + + Assert.assertTrue(home.IsLingoBotContainerInvisible(), "Lingo Bot Container still Visible"); + ChainTestListener.log("Checked Invisibility after Lingo Bot Container Cancel "); + + /* + * + * Currently code missing for "ADD BOT" + * + */ + } + + @Test(priority = 3, dependsOnMethods = { "testProfileDropdownOptions" }) + public void testLogout() { + + home.clickProfileIcon(); + ChainTestListener.log("Clicked Profile Icon"); + + home.clickLogout(); + ChainTestListener.log(" Clicked On Logout "); + + Assert.assertTrue(login.isSignInButtonDisplayed(), "Logout Error, Signin Button Not Displayed"); + ChainTestListener.log(" Logout Assertion Successful"); + + } +} diff --git a/com.hybrid.joshsoftware.lingoai/src/test/resources/config.properties b/com.hybrid.joshsoftware.lingoai/src/test/resources/config.properties new file mode 100644 index 0000000..cdddc2a --- /dev/null +++ b/com.hybrid.joshsoftware.lingoai/src/test/resources/config.properties @@ -0,0 +1,36 @@ +# chaintest configuration +chaintest.project.name=Lingo AI + +# storage +chaintest.storage.service.enabled=false +# [azure-blob, aws-s3] +chaintest.storage.service=azure-blob +# s3 bucket or azure container name +chaintest.storage.service.container-name= + +# generators: +## chainlp +chaintest.generator.chainlp.enabled=false +chaintest.generator.chainlp.class-name=com.aventstack.chaintest.generator.ChainLPGenerator +chaintest.generator.chainlp.host.url=http://localhost/ +chaintest.generator.chainlp.client.request-timeout-s=30 +chaintest.generator.chainlp.client.expect-continue=false +chaintest.generator.chainlp.client.max-retries=3 +chaintest.generator.chainlp.persist-embeds=true + +## simple +chaintest.generator.simple.enabled=true +chaintest.generator.simple.document-title= LingoAI Automation Report +chaintest.generator.simple.class-name=com.aventstack.chaintest.generator.ChainTestSimpleGenerator +chaintest.generator.simple.output-file=Reports/chaintest/Index.html +chaintest.generator.simple.offline=true +chaintest.generator.simple.dark-theme=true +chaintest.generator.simple.datetime-format=yyyy-MM-dd hh:mm:ss a +chaintest.generator.simple.js= +chaintest.generator.simple.css= + +## email +chaintest.generator.email.enabled=true +chaintest.generator.email.class-name=com.aventstack.chaintest.generator.ChainTestEmailGenerator +chaintest.generator.email.output-file=Reports/chaintest/Email.html +chaintest.generator.email.datetime-format=yyyy-MM-dd hh:mm:ss a \ No newline at end of file