org.jtalks.tests.jcommune.webdriver.action.Topics.java Source code

Java tutorial

Introduction

Here is the source code for org.jtalks.tests.jcommune.webdriver.action.Topics.java

Source

/**
 * Copyright (C) 2011  JTalks.org Team
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

package org.jtalks.tests.jcommune.webdriver.action;

import org.jtalks.tests.jcommune.assertion.Existence;
import org.jtalks.tests.jcommune.utils.Utils;
import org.jtalks.tests.jcommune.webdriver.JCommuneSeleniumConfig;
import org.jtalks.tests.jcommune.webdriver.entity.branch.Branch;
import org.jtalks.tests.jcommune.webdriver.entity.topic.CodeReview;
import org.jtalks.tests.jcommune.webdriver.entity.topic.CodeReviewComment;
import org.jtalks.tests.jcommune.webdriver.entity.topic.Draft;
import org.jtalks.tests.jcommune.webdriver.entity.topic.Post;
import org.jtalks.tests.jcommune.webdriver.entity.topic.Topic;
import org.jtalks.tests.jcommune.webdriver.entity.user.User;
import org.jtalks.tests.jcommune.webdriver.exceptions.CouldNotOpenPageException;
import org.jtalks.tests.jcommune.webdriver.exceptions.PermissionsDeniedException;
import org.jtalks.tests.jcommune.webdriver.exceptions.TimeoutException;
import org.jtalks.tests.jcommune.webdriver.exceptions.ValidationException;
import org.jtalks.tests.jcommune.webdriver.page.PostPage;
import org.jtalks.tests.jcommune.webdriver.page.TopicPage;
import org.openqa.selenium.By;
import org.openqa.selenium.NoSuchElementException;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;
import org.testng.Assert;
import ru.yandex.qatools.allure.annotations.Step;

import java.util.List;

import static org.apache.commons.collections.CollectionUtils.isEmpty;
import static org.apache.commons.lang3.RandomStringUtils.randomAlphanumeric;
import static org.assertj.core.api.StrictAssertions.assertThat;
import static org.jtalks.tests.jcommune.utils.ReportNgLogger.info;
import static org.jtalks.tests.jcommune.webdriver.JCommuneSeleniumConfig.driver;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.branchPage;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.mainPage;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.moveTopicEditor;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.postPage;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.sectionPage;
import static org.jtalks.tests.jcommune.webdriver.page.Pages.topicPage;

/**
 * Contain topic actions like creating, deleting etc.
 *
 * @author Guram Savinov
 * @author pancheshenko andrey
 */
public class Topics {

    /**
     * Creates new topic. If {@link Topic#getBranch()} is null, then topic is created in a random branch,
     * otherwise the topic is created in a {@link Topic#getBranch()}.
     *
     * @throws PermissionsDeniedException if use cannot post in the first visible branch, she has no permissions
     * @throws CouldNotOpenPageException  if user was not able to find and open a branch with the specified name
     */
    @Step
    public static Topic createTopic(Topic topic)
            throws PermissionsDeniedException, CouldNotOpenPageException, ValidationException {
        if (!JCommuneSeleniumConfig.driver.getCurrentUrl().equals(JCommuneSeleniumConfig.getAppUrl())) {
            mainPage.clickForumsTitle();
        }
        if (topic.getBranch() == null) {
            List<WebElement> branches = sectionPage.getBranches();
            if (isEmpty(branches)) {
                throw new CouldNotOpenPageException("Could not open any branch, there were 0 on the page. "
                        + "Page URL: [" + JCommuneSeleniumConfig.driver.getCurrentUrl() + "]. " + "Page Title: ["
                        + JCommuneSeleniumConfig.driver.getTitle() + "]. " + "Page source: "
                        + JCommuneSeleniumConfig.driver.getPageSource());
            }
            Branch branch = new Branch(branches.get(0).getText());
            topic.withBranch(branch);
        }
        info("Creating " + topic + " in " + topic.getBranch());
        Branches.openBranch(topic.getBranch());
        branchPage.clickCreateTopic();
        topicPage.fillTopicMainFields(topic);
        topicPage.fillPollSpecificFields(topic.getPoll());
        topicPage.clickAnswerToTopicButton();
        topic.setModificationDate(org.joda.time.DateTime.now().plusMinutes(1));
        assertTopicFormValid();
        return topic;
    }

    @Step
    public static Post postAnswer(Topic topic) throws PermissionsDeniedException, CouldNotOpenPageException {
        openRequiredTopic(topic);

        Post newPost = new Post(randomAlphanumeric(200));
        topic.addPost(newPost);
        postPage.getMessageField().sendKeys(newPost.getPostContent());
        postPage.clickAnswerToTopicButton();

        info("Answer to topic [" + topic.getTitle() + "] was left");
        return newPost;
    }

    @Step
    public static Draft typeAnswer(Topic topic) throws PermissionsDeniedException, CouldNotOpenPageException {
        openRequiredTopic(topic);

        Post newDraft = new Draft(randomAlphanumeric(200));
        topic.addPost(newDraft);
        postPage.getMessageField().sendKeys(newDraft.getPostContent());

        info("Draft in topic [" + topic.getTitle() + "] saving ...");
        return (Draft) newDraft;
    }

    @Step
    public static Draft typeAnswerCustomLength(Topic topic, int lengthText)
            throws PermissionsDeniedException, CouldNotOpenPageException {
        openRequiredTopic(topic);

        Post newDraft = new Draft(randomAlphanumeric(lengthText));
        topic.addPost(newDraft);
        postPage.getMessageField().sendKeys(newDraft.getPostContent());

        info("Draft in topic [" + topic.getTitle() + "] saving ...");
        return (Draft) newDraft;
    }

    @Step
    public static Draft pasteAnswer(Topic topic) throws PermissionsDeniedException, CouldNotOpenPageException {
        openRequiredTopic(topic);

        Post newDraft = new Draft(randomAlphanumeric(200));
        topic.addPost(newDraft);

        Utils.setTextToClipboard(newDraft.getPostContent());
        postPage.getMessageField().sendKeys(Utils.PASTE_CHORD);

        info("Draft in topic [" + topic.getTitle() + "] saving ...");
        return (Draft) newDraft;
    }

    @Step
    public static void findAndCloseTopic(Topic topic) {
        openRequiredTopic(topic);
        info("Close topic ...");
        postPage.clickButtonCloseTopic();

        checkCurrentTopicClosed();
    }

    @Step
    public static void postAnswer(Topic topic, Post post)
            throws PermissionsDeniedException, CouldNotOpenPageException, ValidationException {
        openRequiredTopic(topic);

        postPage.fillPostBody(post.getPostContent());
        postPage.clickAnswerToTopicButton();
        assertTopicPostFormValid();

        topic.addPost(post);
        info("Answer to topic [" + topic.getTitle() + "] was left");
    }

    @Step
    public static void editPost(Topic topic, Post postToEdit) {
        openRequiredTopic(topic);

        postPage.clickEditInPostContainingString(postToEdit.getPostContent());
        try {
            (new WebDriverWait(driver, 40)).until(ExpectedConditions.refreshed(
                    ExpectedConditions.presenceOfElementLocated(By.xpath(TopicPage.backButtonOnEditFormSel))));
        } catch (TimeoutException e) {
            info("Edit post method failed by timeout after button [edit] was clicked.");
            throw e;
        }
        String newPostContent = randomAlphanumeric(100);
        topicPage.editPostMessageBody(newPostContent);
        topicPage.clickAnswerToTopicButton();
        for (int i = 0; i < topic.getPosts().size(); i++) {
            if (topic.getPosts().get(i).getPostContent().equals(postToEdit.getPostContent())) {
                topic.getPosts().get(i).setPostContent(newPostContent);
                break;
            }
        }
        (new WebDriverWait(driver, 20)).until(ExpectedConditions.visibilityOf(postPage.getFirstPost()));
    }

    @Step
    public static void deleteTopic(Topic topic) throws PermissionsDeniedException {
        openRequiredTopic(topic);
        info("Clicking delete button for topic's first post");
        try {
            postPage.getDeleteTopicButton().click();
        } catch (NoSuchElementException e) {
            info("Delete button was not found");
            throw new PermissionsDeniedException("Delete button was not found. Lack of permissions?");
        }
        postPage.closeDeleteConfirmDialogOk();
    }

    @Step
    public static void deletePost(Topic topic, Post selectedPost) {
        throw new UnsupportedOperationException();
    }

    @Step
    public static void moveTopic(Topic topic) {
        openRequiredTopic(topic);
        postPage.openMoveTopicEditorDialog();
        String newBranchName = moveTopicEditor.chooseBranchIndex(0);
        moveTopicEditor.clickConfirmMoveButton();
        info("Waiting for the page being refreshed and move performed successfully");
        try {
            (new WebDriverWait(driver, 40))
                    .until(ExpectedConditions.refreshed(ExpectedConditions.presenceOfElementLocated(By
                            .xpath(PostPage.branchNameSel + "[contains(text(),'" + newBranchName.trim() + "')]"))));
        } catch (TimeoutException e) {
            info("Move method failed by timeout after button [move] was clicked.");
            throw e;
        }
        topic.withBranch(newBranchName);
    }

    @Step
    public static void moveTopic(Topic topic, String newBranchName) {
        openRequiredTopic(topic);
        postPage.openMoveTopicEditorDialog();
        moveTopicEditor.chooseBranch(newBranchName);
        moveTopicEditor.clickConfirmMoveButton();
        info("Waiting for the page being refreshed and move performed successfully");
        try {
            (new WebDriverWait(driver, 40))
                    .until(ExpectedConditions.refreshed(ExpectedConditions.presenceOfElementLocated(By
                            .xpath(PostPage.branchNameSel + "[contains(text(),'" + newBranchName.trim() + "')]"))));
        } catch (TimeoutException e) {
            info("Move method failed by timeout after button [move] was clicked.");
            throw e;
        }
        topic.withBranch(newBranchName);
    }

    @Step
    public static void subscribe(Topic topic) throws NoSuchElementException {
        openRequiredTopic(topic);
        try {
            if (postPage.isUserAlreadySubscribed()) {
                info("User already subscribed on the topic");
            } else {
                info("Clicking subscribe button");
                postPage.getSubscribeButton().click();
            }
        } catch (NoSuchElementException e) {
            info("Subscribe button was not found");
            throw new NoSuchElementException("Subscribe button was not found", e);
        }
    }

    @Step
    public static void unsubscribe(Topic topic) throws NoSuchElementException {
        openRequiredTopic(topic);
        try {
            if (postPage.isUserAlreadySubscribed()) {
                info("User already subscribed on the topic. Clicking unsubscribe button");
                postPage.getSubscribeButton().click();
            } else {
                info("User isn't subscribed to branch");
            }
        } catch (NoSuchElementException e) {
            info("Subscribe button was not found");
            throw new NoSuchElementException("Subscribe button was not found", e);
        }
    }

    public static void openRequiredTopic(Topic topic) {
        if (!postPage.isUserInsideCorrectTopic(topic.getTitle())) {
            info("User isn't browsing required topic");
            Branches.openBranch(topic.getBranch());
            openTopicInCurrentBranch(50, topic.getTitle());
        }
    }

    /**
     * Looks through several pages of the branch in order to find the topic with the specified title.
     *
     * @param numberOfPagesToCheck since the topic might not be on the first page (either someone simultaneously creates
     *                             a lot of topics, or there are a lot of sticked topics), we have to iteration through
     *                             this number of pages to search for the topic
     * @param topicToFind          a topic title to look for
     * @return true if the specified topic was found
     * @throws CouldNotOpenPageException if specified topic was not found
     */
    @Step
    public static boolean openTopicInCurrentBranch(int numberOfPagesToCheck, String topicToFind)
            throws CouldNotOpenPageException {
        boolean found;
        while (!(found = branchPage.findAndOpenTopic(topicToFind))) {
            info("Topic [" + topicToFind + "] wasn't found on "
                    + branchPage.getActiveTopicsButton().get(0).getText() + " page");
            if (!branchPage.openNextPage(numberOfPagesToCheck))
                break;
        }
        if (!found) {
            info("No topic with title [" + topicToFind + "] found");
            throw new CouldNotOpenPageException(topicToFind);
        }
        (new WebDriverWait(driver, 20)).until(ExpectedConditions.visibilityOf(postPage.getTopicTitle()));
        return found;
    }

    public static void w3cGoToBranchPage() throws ValidationException {
        Users.signUpAndSignIn();
        Branch branch = new Branch(sectionPage.getBranches().get(0).getText());
        Branches.openBranch(branch);
    }

    public static void w3cGoToTopicCreatePage() throws ValidationException {
        w3cGoToBranchPage();
        branchPage.clickCreateTopic();
    }

    public static void w3cGoToReviewCreatePage() throws ValidationException {
        w3cGoToBranchPage();
        branchPage.clickCreateCodeReview();
    }

    public static boolean isCreated(Topic topic) {
        String expectedTitle = topic.getTitle();
        String actualTitle = postPage.getTopicTitle().getText();

        return actualTitle.equals(expectedTitle);
    }

    public static boolean isDraftCreated() {
        info("Check presence of draft counter ...");
        return postPage.checkCounter();
    }

    public static boolean isInCorrectBranch(Topic topic) {
        return postPage.getBranchName().getText().trim().equals(topic.getBranch().getTitle());
    }

    public static void assertHasNewMessages(Topic newTopic, User userThatWantsToSeeNewMessages) {
        throw new UnsupportedOperationException();
    }

    public static void assertHasNoNewMessages(Topic newTopic, User userThatWantsToSeeNewMessages) {
        throw new UnsupportedOperationException();
    }

    public static void assertIsSubscribed(Topic topic) {
        Assert.assertTrue(postPage.isUserAlreadySubscribed(),
                "Assertion failed! User is not subscribed to the topic.");
    }

    private static void assertTopicFormValid() throws ValidationException {
        String failedFields = "";
        info("Check subject");
        if (Existence.existsImmediately(driver, topicPage.getSubjectErrorMessage())) {
            WebElement subjectError = topicPage.getSubjectErrorMessage();
            failedFields += subjectError.getText() + "\n";
        }
        info("Check body");
        if (Existence.existsImmediately(driver, topicPage.getBodyErrorMessage())) {
            WebElement bodyError = topicPage.getBodyErrorMessage();
            failedFields += bodyError.getText();
        }
        info("Check poll title");
        if (Existence.existsImmediately(driver, topicPage.getPollTitleErrorMessage())) {
            WebElement pollTitleError = topicPage.getPollTitleErrorMessage();
            failedFields += pollTitleError.getText();
        }
        info("Check poll items");
        if (Existence.existsImmediately(driver, topicPage.getPollItemsErrorMessage())) {
            WebElement pollItemsError = topicPage.getPollItemsErrorMessage();
            failedFields += pollItemsError.getText();
        }
        info("Check finished");
        if (!failedFields.equals("")) {
            info("Found validation errors: " + failedFields);
            throw new ValidationException(failedFields);
        }
        info("Check successful. No errors.");
    }

    private static void assertTopicPostFormValid() throws ValidationException {
        String failedFields = "";
        info("Check body");
        if (Existence.existsImmediately(driver, topicPage.getBodyErrorMessage())) {
            WebElement bodyError = topicPage.getBodyErrorMessage();
            failedFields += bodyError.getText();
        }
        info("Check finished");
        if (!failedFields.equals("")) {
            info("Found validation errors: " + failedFields);
            throw new ValidationException(failedFields);
        }
        info("Check successful. No errors.");
    }

    // Code review methods

    public static CodeReview createCodeReview(CodeReview codeReview)
            throws PermissionsDeniedException, CouldNotOpenPageException, ValidationException {
        if (codeReview.getBranch() == null) {
            List<WebElement> branches = sectionPage.getBranches();
            if (isEmpty(branches)) {
                throw new CouldNotOpenPageException("Could not open any branch, there were 0 on the page. "
                        + "Page URL: [" + JCommuneSeleniumConfig.driver.getCurrentUrl() + "]. " + "Page Title: ["
                        + JCommuneSeleniumConfig.driver.getTitle() + "]. " + "Page source: "
                        + JCommuneSeleniumConfig.driver.getPageSource());
            }
            Branch branch = new Branch(sectionPage.getBranches().get(0).getText());
            codeReview.withBranch(branch);
        }
        Branches.openBranch(codeReview.getBranch());
        branchPage.clickCreateCodeReview();
        topicPage.fillCodeReviewFields(codeReview);
        topicPage.clickAnswerToTopicButton();
        assertCodeReviewFormValid();
        return codeReview;
    }

    public static CodeReviewComment leaveCodeReviewComment(CodeReview codeReview,
            CodeReviewComment codeReviewComment) throws PermissionsDeniedException, ValidationException {
        openRequiredTopic(codeReview);
        postPage.clickLineInCodeReviewForComment(codeReviewComment.getCommentedLineNumber());
        postPage.fillCodeReviewCommentBody(codeReviewComment);
        postPage.clickAddCommentToCodeReviewButton();
        assertCodeReviewFormValid();
        codeReview.addComment(codeReviewComment);
        return codeReviewComment;
    }

    public static void editCodeReviewComment(CodeReview codeReview, CodeReviewComment codeReviewComment) {
        openRequiredTopic(codeReview);

        postPage.clickEditInCodeReviewCommentContainingString(codeReviewComment.getPostContent());
        try {
            (new WebDriverWait(driver, 20)).until(ExpectedConditions.refreshed(
                    ExpectedConditions.presenceOfElementLocated(By.xpath(PostPage.codeReviewCommentTextFieldSel))));
        } catch (TimeoutException e) {
            info("Edit post method failed by timeout after button [edit] was clicked.");
            throw e;
        }
        String newCommentContent = randomAlphanumeric(100);
        postPage.editCodeReviewCommentBody(newCommentContent);
        postPage.clickOkButtonInEditComment();
        for (int i = 0; i < codeReview.getComments().size(); i++) {
            if (codeReview.getComments().get(i).getPostContent().equals(codeReviewComment.getPostContent())) {
                codeReview.getComments().get(i).setPostContent(newCommentContent);
                break;
            }
        }
        (new WebDriverWait(driver, 20)).until(ExpectedConditions.visibilityOf(postPage.getFirstPost()));
    }

    public static void assertCodeReviewFormValid() throws ValidationException {
        String failedFields = "";
        info("Check subject");
        if (Existence.existsImmediately(driver, topicPage.getSubjectErrorMessage())) {
            WebElement subjectError = topicPage.getSubjectErrorMessage();
            failedFields += subjectError.getText() + "\n";
        }
        info("Check body");
        if (Existence.existsImmediately(driver, topicPage.getBodyErrorMessage())) {
            WebElement bodyError = topicPage.getBodyErrorMessage();
            failedFields += bodyError.getText();
        }
        info("Check CR comment body");
        if (Existence.existsUsingLowerTimeout(driver, postPage.getCRCommentBodyErrorMessage())) {
            WebElement codeReviewCommentBodyError = postPage.getCRCommentBodyErrorMessage();
            failedFields += codeReviewCommentBodyError.getText() + "\n";
        }
        info("Check finished");
        if (!failedFields.equals("")) {
            info("Found validation errors: " + failedFields);
            throw new ValidationException(failedFields);
        }
        info("Check successful. No errors.");
    }

    public static void editPost(CodeReview codeReview, Post postToEdit) {
        throw new UnsupportedOperationException("Edit post can't be done in code review type topics");
    }

    public static void deleteCodeReviewComment(CodeReview codeReview, CodeReviewComment codeReviewComment) {
        openRequiredTopic(codeReview);

        postPage.clickDeleteInCodeReviewCommentContainingString(codeReviewComment.getPostContent());
        postPage.closeDeleteCRCommentConfirmDialogOk();
    }

    private static void checkCurrentTopicClosed() {
        assertThat(postPage.findButtonReopenTopic()).isNotNull();
    }
}