UriPathTemplate { public boolean matches(String uri) { return matcher(uri).matches(); } UriPathTemplate(String uriPattern); boolean matches(String uri); Map<String, Object> match(String uri);  }
@Test public void should_be_save_for_multi_threading() throws Exception { final Consumer<Integer> r = a -> { try { template.matches("aaabbaabaabaaabaaaabaabaaaaabbaaabbab"); } catch (StringIndexOutOfBoundsException e) { e.printStackTrace(); throw e; } }; final Runnable s = () -> Stream.iterate(0, i -> i + 1).limit(100000).forEach(r); final List<Thread> threads = Stream.iterate(0, i -> i + 1).limit(10).map(i -> new Thread(s)).collect(Collectors.toList()); threads.forEach(t -> t.setUncaughtExceptionHandler((t1, e) -> t1.getThreadGroup().interrupt())); threads.forEach(Thread::start); threads.forEach(t -> { try { t.join(); } catch (InterruptedException ire) { Assert.fail(); } catch (Exception e) { throw e; } }); }