Написание безопасных, не нагнутоJAVA

Программисты JAVA общаются здесь
Anonymous
Написание безопасных, не нагнуто

Сообщение Anonymous »

Я продолжаю слышать эту рекомендацию, чтобы всегда получить доступ к компонентам свинг на EDT, в том числе в тестах. В простой Java это обычно означает вызов invokelater () /invokeandwait () .
Действительно, некоторые тесты делают , которые, кажется, проблемы с расой. Тем не менее, мне все еще не совсем удобно с тем, как это выглядит. FEST GuiActionRunner делает его еще немного более уродливым, так как Guitask , Guiquery являются абстрактными классами и не могут быть выражены как лямбдас.

Код: Выделить всё

// example test
@Test
@SuppressWarnings({"OptionalGetWithoutIsPresent", "unchecked"})
void givenMatchPredicate_ifNoSearchTextSet_andNextButtonClicked_nothingHappens() {
/*
A
|__B
|  |__C
|__D
*/
DefaultMutableTreeNode root = new DefaultMutableTreeNode(TreeObject.from("A"));
DefaultMutableTreeNode nodeB = new DefaultMutableTreeNode(TreeObject.from("B"));
root.add(nodeB);
TreeObject objectC = TreeObject.from("C");
DefaultMutableTreeNode nodeC = new DefaultMutableTreeNode(objectC);
nodeB.add(nodeC);
DefaultMutableTreeNode nodeD = new DefaultMutableTreeNode(TreeObject.from("D"));
root.add(nodeD);

SwingUtilities.invokeLater(() -> {
/* essentially, a modal dialog with a JTree, searchField and
arrow buttons to navigate between search matches */
TreeSelectDialog dialog = TreeSelectDialog.of(null, () -> root);
BiPredicate predicateMock = mock();
dialog.setMatchPredicate(predicateMock);
JTextComponent searchField = finder.find(dialog, JTextComponent.class).get();
JButton nextButton = finder.find(dialog, JButton.class, "nextButton").get();
tree = finder.find(dialog, JTree.class).get();
SwingUtilities.invokeLater(dialog::doModal);
robot.waitForIdle();
assumeTrue(searchField instanceof ValueField);
assumeFalse(((ValueField) searchField).getPlaceholderText() == null);
Object initialSelectedObject = getSelectedObject();

nextButton.doClick();

then(predicateMock).shouldHaveNoInteractions();
assertEquals(initialSelectedObject, getSelectedObject());
assertEquals(Colors.placeholder(), searchField.getForeground());
dialog.dispose();
});
}
Я попытался рефакторировать его, используя InvocationInterceptor . Тем не менее, мои вызовы waitforidle () не удастся, так как вы не можете вызовать метод из потока диспетчера событий ". invokelater () также выполняет код на EDT, включая waitForidle () , но исключение проглатывается, и не выполняются утверждения. на самом деле отображается (

Код: Выделить всё

doModal()
, по сути, является украшенным setvisible (true) ).
@ExtendWith(EdtExtension.class)
class TreeSelectDialogTest {
// outer SwingUtilities.invokeLater(...) removed
< /code>
import org.junit.jupiter.api.extension.ExtensionContext;
import org.junit.jupiter.api.extension.InvocationInterceptor;
import org.junit.jupiter.api.extension.ReflectiveInvocationContext;
import org.junit.platform.commons.util.ExceptionUtils;

import javax.swing.SwingUtilities;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class EdtExtension implements InvocationInterceptor {

@Override
public void interceptTestMethod(Invocation invocation, ReflectiveInvocationContext invocationContext, ExtensionContext extensionContext) {
invokeInEdt(invocation);
}

private void invokeInEdt(Invocation invocation) {
try {
SwingUtilities.invokeAndWait(() -> {
try {
invocation.proceed();
} catch (Throwable e) {
ExceptionUtils.throwAsUncheckedException(e);
}
});
} catch (InterruptedException | InvocationTargetException e) {
ExceptionUtils.throwAsUncheckedException(e);
}
}
}
< /code>
Caused by: java.lang.IllegalThreadStateException: Cannot call method from the event dispatcher thread
at org.fest.swing.core.BasicRobot.waitForIdle(BasicRobot.java:669)
at org.fest.swing.core.BasicRobot.waitForIdle(BasicRobot.java:654)
< /code>
What it the most concise and readable way to refactor my test? If FEST can help, you can use it.
Java 8.

Подробнее здесь: https://stackoverflow.com/questions/797 ... wing-tests

Вернуться в «JAVA»