Стверджуйте збіги регулярних виразів у JUnit


84

Ruby's Test::Unitмає приємний assert_matchesметод, який можна використовувати в модульних тестах, щоб стверджувати, що регулярний вираз відповідає рядку.

Чи є щось подібне в JUnit? В даний час я роблю це:

assertEquals(true, actual.matches(expectedRegex));

Відповіді:


99

Якщо ви використовуєте assertThat()з матчем Hamcrest тестування регулярних виразів , то, якщо твердження не вдається, ви отримаєте гарне повідомлення, яке вказує очікуваний шаблон і фактичний текст. Твердження також читатиметься вільніше, напр

assertThat("FooBarBaz", matchesPattern("^Foo"));

з Hamcrest 2 ви можете знайти matchesPatternметод за адресою MatchesPattern.matchesPattern.


21
В Hamcrest 2.0 Matchers.matchesPattern(String)тепер вбудовано: github.com/hamcrest/JavaHamcrest/blob/master/hamcrest-library/…
hinneLinks

5
Постійне посилання на те, на що посилається @hinneLinks: github.com/hamcrest/JavaHamcrest/blob/…
піото,

54

Я не маю іншого вибору, який я знаю. Просто перевірте утвердження javadoc, щоб бути впевненим. Тільки крихітна зміна:

assertTrue(actual.matches(expectedRegex));

EDIT: Я використовую матчі Hamcrest з моменту відповіді Фолзера, перевірте це теж!


1
Ах так, assertTrue()це точно приємніше. Я звинувачую автозаповнення Eclipse за те, що я не знав про це. ;)
Джош Гловер

4
assertTrueне можу дати вам стільки деталей, скільки assertEqualsабо assertThatколи тест не вдається
Майк Валенті

1
@ Michael Майже впевнений, що може. assertTrue("Expected string matching '" +expectedRegex+ "'. Got: "+actual, actual.matches(expectedRegex));. Це не так приємно, як Hamcrest.
MikeFHay

@MikeValenty Якщо ви просто порівнюєте значення з is(true), то assertThatне надаєте вам більше деталей, ніж assertTrueце робить. Щоб отримати належні повідомлення про помилки, вам потрібен інший збіг (або ви створюєте повідомлення вручну, як пропонував @MikeFHay).
ThrawnCA

20

Ви можете використовувати Hamcrest, але ви повинні написати свій власний матч:

public class RegexMatcher extends TypeSafeMatcher<String> {

    private final String regex;

    public RegexMatcher(final String regex) {
        this.regex = regex;
    }

    @Override
    public void describeTo(final Description description) {
        description.appendText("matches regex=`" + regex + "`");
    }

    @Override
    public boolean matchesSafely(final String string) {
        return string.matches(regex);
    }


    public static RegexMatcher matchesRegex(final String regex) {
        return new RegexMatcher(regex);
    }
}

використання

import org.junit.Assert;


Assert.assertThat("test", RegexMatcher.matchesRegex(".*est");

18

Ви можете використовувати Hamcrest та jcabi-matchchers :

import static com.jcabi.matchers.RegexMatchers.matchesPattern;
import static org.junit.Assert.assertThat;
assertThat("test", matchesPattern("[a-z]+"));

Детальніше тут: Збірники Hamcrest із регулярним виразом .

Вам знадобляться ці дві залежності в classpath:

<dependency>
  <groupId>org.hamcrest</groupId>
  <artifactId>hamcrest-core</artifactId>
  <version>1.3</version>
  <scope>test</scope>
</dependency>
<dependency>
  <groupId>com.jcabi</groupId>
  <artifactId>jcabi-matchers</artifactId>
  <version>1.3</version>
  <scope>test</scope>
</dependency>

Я виявив, що залежність від основного мозку не потрібна
JohnP2,

4

Оскільки я також шукав цю функціональність, я розпочав проект на GitHub під назвою regex-tester . Це бібліотека, яка полегшує тестування регулярних виразів на Java (наразі працює лише з JUnit).

Зараз бібліотека дуже обмежена, але в ній є збіжник Hamcrest, який працює так

assertThat("test", doesMatchRegex("tes.+"));
assertThat("test", doesNotMatchRegex("tex.+"));

Детальніше про те, як користуватися регулярним виразом-тестером, можна тут .


4

Збіг, подібний до реалізації Ральфа, додано до офіційної бібліотеки збігів Java Hamcrest. На жаль, він ще не доступний у пакеті випусків. Клас на GitHub, хоча якщо ви хочете подивитися.


3

У Hamcrest є відповідний збіг: org.hamcrest.Matchers.matchesPattern (строковий регулярний вираз) .

Оскільки розвиток Hamcrest зупинився, ви не можете використовувати останню доступну версію 1.3:

testCompile("org.hamcrest:hamcrest-library:1.3")

Натомість вам потрібно використовувати нову серію розробників (але все ще датовану січнем 2015 року ):

testCompile("org.hamcrest:java-hamcrest:2.0.0.0")

або ще краще:

configurations {
    testCompile.exclude group: "org.hamcrest", module: "hamcrest-core"
    testCompile.exclude group: "org.hamcrest", module: "hamcrest-library"
}
dependencies {
    testCompile("org.hamcrest:hamcrest-junit:2.0.0.0")
}

У тесті:

Assert.assertThat("123456", Matchers.matchesPattern("^[0-9]+$"));

Я отримую помилку: дублікат класу org.hamcrest.BaseDescription знайдено в модулях jetified-hamcrest-core-1.3.jar (org.hamcrest: hamcrest-core: 1.3) та jetified-java-hamcrest-2.0.0.0.jar (org.hamcrest : java-hamcrest: 2.0.0.0)
a_subscriber

2

інша альтернатива використання assertj. такий підхід приємний, оскільки дозволяє передавати об'єкт шаблону безпосередньо.

import static org.assertj.core.api.Assertions.assertThat;
assertThat("my\nmultiline\nstring").matches(Pattern.compile("(?s)my.*string", Pattern.MULTILINE));

1


це не JUnit, але ось ще один спосіб із fest-assert:

assertThat(myTestedValue).as("your value is so so bad").matches(expectedRegex);
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.