Vaadin - Copy invisible value to clipboard and test it using Selenium

July 15, 2019

The invisible web component personified

Introduction

Using add-ons or writing it yourself, copying to the clipboard using Vaadin is not that much of a struggle. It becomes one if you want to generate a value that is not present on screen and copy it to the clipboard.

This is a security mechanism preventing websites from copying data to your clipboard which you’re not aware of.

The same kind of logic applies to reading from your clipboard.

Though, if you have, in the context of your application, something in this way, you’ll need to develop and test it.

Let me show you a way to do this.

Build the UI

Let’s build a simple UI, containing an input, a button and a “hidden” text area. I put “hidden” because it will still be visible in the sources, but not to the naked eye.

Code

final VerticalLayout layout = new VerticalLayout();
final JSClipboard clipboard = new JSClipboard();
final TextArea textArea = new TextArea();
final TextField textField = new TextField();
final Button button = new Button();

// Text Field
textField.setId("textFieldId");
textField.addValueChangeListener(event -> textArea.setValue("This is the content to copy paste containing textField's text : " + textField.getValue()));

// Text Area
textArea.setId("textAreaId");

// Button
button.setId("buttonId");
button.setCaption("Copy to Clipboard");

// JSClipboard
clipboard.apply(button, textArea);
clipboard.addSuccessListener((JSClipboard.SuccessListener) () -> Notification.*show*("Copy to clipboard successful"));
clipboard.addErrorListener((JSClipboard.ErrorListener) () -> Notification.*show*("Copy to clipboard unsuccessful", Notification.Type.*ERROR_MESSAGE*));

// CSS
Page.Styles styles = Page.*getCurrent*().getStyles();
styles.add(" #textAreaId { left: -1000px; position: absolute; }");

layout.addComponents(textField, textArea, button);
layout.setMargin(true);
layout.setSpacing(true);

setContent(layout);

Multiple things to keep in mind here :

  • We’re adding a listener to the visible text field that will update the value of the hidden text area (value to be copied to the clipboard)
  • We’re using the JSClipboard add-on from Vaadin which allows to copy a value from an existing page component
  • We’re adding CSS to the hidden text area to make sure it’s hidden to the naked eye

    textAreaId {

    position: absolute;
    left: -1000px;

    }

Giving us the following result

Testing the built screenTesting the built screen

If I click on the button I get the following result :

This is the content to copy paste containing textField's text : Testing Something

Testing it using Selenium

Now, to test it, there’s nothing easier.

Let’s use a mix of Cucumber and Selenium for this.

Gherkin Scenario

Scenario: Copying to clipboard
  Given I'm on the landing page
  When I write "Text to copy" in the text field
  And I click on the button "Copy to clipboard"
  Then "This is the content to copy paste containing textField's text : Text to copy" is copied to the clipboard

As the other ones are trivial, we’ll focus on the the last step.

So we basically introduced the fact that copying text from an invisible component wasn’t allowed due to security reasons.

The same goes for reading from the clipboard itself. We’ll have to find a workaround in our test.

The steps are explained in the implementation below. We’ll basically reuse the textarea to receive the content of our clipboard and then read it from it.

@Then("^(.*) is copied to the clipboard$")
public void copiedToClipboardStep(String content) {
    WebElement we = driver.findElementById(By.id("textAreaId"));

    // 1. Make sure it was filled
    String beforeValue = we.getAttribute("value");
    assertTrue(!beforeValue.isEmpty());

    // 2. Empty the text area
    we.clear();
    assertTrue(we.getAttribute("value").isEmpty());

    // 3. Paste the clipboard content into the empty text area
    we.sendKeys(Keys.chord(Keys.LEFT_CONTROL, "v"));
    assertEquals(content, we.getAttribute("value"));
}

Conclusion

It was quite easy to copy-paste from an invisible text area, to choose what kind of test to send to the clipboard and test it using e2e testing automation tool, and all that with minimal impact on the user experience.