Skip to content

Commit

Permalink
remove summation and prefixing
Browse files Browse the repository at this point in the history
  • Loading branch information
duncpro committed Aug 12, 2022
1 parent dd4756e commit 37bc5f9
Show file tree
Hide file tree
Showing 5 changed files with 16 additions and 114 deletions.
36 changes: 14 additions & 22 deletions .idea/workspace.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

24 changes: 1 addition & 23 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ Notably `TreeRouter` is not thread safe for mutations. Consider wrapping it in a
to add routes concurrently. In practice route registration typically only happens at startup and the process is quick
enough that multi-threading is unnecessary.

## Router Inspection and Summation
## Router Inspection
In some cases, like when generating API documentation, an application might need to
inspect the state of a router at runtime. This can be accomplished using the `Router.getAllEndpoints()` method.

Expand All @@ -61,27 +61,5 @@ final Router<T> routers = /* ... */;
final Set<PositionedEndpoint<T>> positionedEndpoints = router.getAllEndpoints(Route.ROOT);
```

### Summing Multiple Routers
For large applications consisting of many modules it can be useful to assign
each module its own `Router`. The following example demonstrates summing two routers.

Assume that we are using some library which generates API documentation for a
given `Router` and returns a new `Router` which holds that documentation...
````java
final Router<T> appRouter = /* ... */;
final Router<T> docRouter = generateApiDocs(appRouter);
final TreeRouter<T> masterRouter = TreeRouter.sum(Set.of(appRouter, docRouter));
````
Now there is a single Router which contains the routes for our application and our application's documentation.
### Prefixing Routers
`TreeRouter.prefix` produces a copy of the original router except all routes begin with an arbitrary prefix `Route`.
Our original documentation example can be extended by storing all API docs under a specific route.
```java
final Router<T> docRouter = TreeRouter.prefix(generateApiDocs(appRouter),
new Route("/docs"));
```
## More Docs
There is a Javadoc for this library [here](https://duncpro.github.io/JRoute).
2 changes: 1 addition & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ plugins {
}

group = "com.duncpro"
version = "1.0-SNAPSHOT-4"
version = "1.0-SNAPSHOT-5"

repositories {
mavenCentral()
Expand Down
31 changes: 0 additions & 31 deletions src/main/java/com/duncpro/jroute/router/TreeRouter.java
Original file line number Diff line number Diff line change
Expand Up @@ -67,35 +67,4 @@ protected static <E> RouteTreeNode<E> findOrCreateNode(RouteTreeNode<E> routeTre
final var child = routeTree.getOrCreateChildRoute(route.getElements().get(0));
return findOrCreateNode(child, route.withoutLeadingElement());
}

/**
* Creates a new {@link TreeRouter} containing the sum of all routes in the given sub routers
* at the time of invocation.
* @throws RouteConflictException if the given routers cannot be summed because they
* contain routes which conflict with one another.
*/
public static <E> TreeRouter<E> sum(Collection<Router<E>> subRouters) {
final var masterRouter = new TreeRouter<E>();

subRouters.stream()
.flatMap(subRouter -> subRouter.getAllEndpoints(Route.ROOT).stream())
.forEach(positionedEndpoint -> masterRouter.addRoute(positionedEndpoint.method,
positionedEndpoint.route, positionedEndpoint.endpoint));

return masterRouter;
}

/**
* Returns a new {@link TreeRouter} which is identical to the given {@link Router} except
* all routes have been prefixed with the given {@link Route}. The returned router will not
* reflect any changes made to the original router.
*/
public static <E> TreeRouter<E> prefix(Router<E> router, Route prefix) {
final var prefixedRouter = new TreeRouter<E>();
for (final var positionedEndpoint : router.getAllEndpoints(Route.ROOT)) {
final var prefixedRoute = Route.concat(prefix, positionedEndpoint.route);
prefixedRouter.addRoute(positionedEndpoint.method, prefixedRoute, positionedEndpoint.endpoint);
}
return prefixedRouter;
}
}
37 changes: 0 additions & 37 deletions src/test/java/com/duncpro/jroute/router/TreeRouterTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -136,41 +136,4 @@ void getAllEndpoints() {
assertEquals(2, resolvedEndpoints.size());
}
}

@Test
void sum() {
final Router<Integer> router1 = new TreeRouter<>();
final var endpoint1 = new PositionedEndpoint<>(new Route("/hello/world"), HttpMethod.GET, 1);
router1.addRoute(endpoint1);

final Router<Integer> router2 = new TreeRouter<>();
final var endpoint2 = new PositionedEndpoint<>(new Route("/hello"), HttpMethod.GET, 1);
router2.addRoute(endpoint2);

final var composedRouter = TreeRouter.sum(Set.of(router1, router2));

{
final var resolvedEndpoints = composedRouter.getAllEndpoints(new Route("/hello"));
assertEquals(2, resolvedEndpoints.size());
assertTrue(resolvedEndpoints.stream()
.anyMatch(endpoint -> endpoint.equals(endpoint1)));
assertTrue(resolvedEndpoints.stream()
.anyMatch(endpoint -> endpoint.equals(endpoint2)));
}
}

@Test
void prefix() {
final Router<Object> originalRouter = new TreeRouter<>();
final var endpoint = new Object();

originalRouter.addRoute(HttpMethod.GET, "world", endpoint);

final var prefixedRouter = TreeRouter.prefix(originalRouter, new Route("hello"));
final var resolvedEndpoints = prefixedRouter.getAllEndpoints(Route.ROOT);

assertEquals(1, resolvedEndpoints.size());
final var loneRoute = resolvedEndpoints.stream().findFirst().orElseThrow();
assertEquals(new PositionedEndpoint<>(new Route("hello/world"), HttpMethod.GET, endpoint), loneRoute);
}
}

0 comments on commit 37bc5f9

Please sign in to comment.