Skip to content

Commit

Permalink
release ArchUnit 1.2.0
Browse files Browse the repository at this point in the history
Signed-off-by: codecholeric <[email protected]>
  • Loading branch information
actions-user committed Nov 6, 2023
1 parent 60e7f2c commit be9f746
Show file tree
Hide file tree
Showing 7 changed files with 268 additions and 36 deletions.
6 changes: 3 additions & 3 deletions Gemfile.lock
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
GEM
remote: https://rubygems.org/
specs:
activesupport (7.0.4.3)
activesupport (7.0.7.2)
concurrent-ruby (~> 1.0, >= 1.0.2)
i18n (>= 1.6, < 2)
minitest (>= 5.1)
Expand Down Expand Up @@ -39,7 +39,7 @@ GEM
activesupport (>= 2)
nokogiri (>= 1.4)
http_parser.rb (0.8.0)
i18n (1.12.0)
i18n (1.14.1)
concurrent-ruby (~> 1.0)
jekyll (4.3.2)
addressable (~> 2.4)
Expand Down Expand Up @@ -82,7 +82,7 @@ GEM
rb-inotify (~> 0.9, >= 0.9.10)
mercenary (0.4.0)
mini_portile2 (2.8.1)
minitest (5.18.0)
minitest (5.19.0)
multipart-post (2.1.1)
nokogiri (1.14.3)
mini_portile2 (~> 2.8.0)
Expand Down
2 changes: 1 addition & 1 deletion _data/navigation.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,6 @@ main:
- title: "User Guide"
url: /userguide/html/000_Index.html
- title: "API"
url: https://javadoc.io/doc/com.tngtech.archunit/archunit/1.1.0
url: https://javadoc.io/doc/com.tngtech.archunit/archunit/1.2.0
- title: "About"
url: /about
4 changes: 2 additions & 2 deletions _pages/getting-started.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,15 +15,15 @@ ArchUnit can be obtained from Maven Central.
<dependency>
<groupId>com.tngtech.archunit</groupId>
<artifactId>archunit</artifactId>
<version>1.1.0</version>
<version>1.2.0</version>
<scope>test</scope>
</dependency>
```

#### Gradle
```groovy
dependencies {
testImplementation 'com.tngtech.archunit:archunit:1.1.0'
testImplementation 'com.tngtech.archunit:archunit:1.2.0'
}
```

Expand Down
8 changes: 8 additions & 0 deletions _posts/2023-11-06-release-v1.2.0.markdown
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
---
layout: splash
title: "New release of ArchUnit (v1.2.0)"
date: 2023-11-06 12:00:00
categories: news release
---

A new release of ArchUnit (v1.2.0) is out. For details see [the release on GitHub](https://github.com/TNG/ArchUnit/releases/tag/v1.2.0 "ArchUnit v1.2.0 on GitHub").
2 changes: 1 addition & 1 deletion userguide/007_The_Lang_API.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -278,7 +278,7 @@ ClassesTransformer<JavaPackage> packages = new AbstractClassesTransformer<JavaPa
@Override
public Iterable<JavaPackage> doTransform(JavaClasses classes) {
Set<JavaPackage> result = new HashSet<>();
classes.getDefaultPackage().accept(alwaysTrue(), new PackageVisitor() {
classes.getDefaultPackage().traversePackageTree(alwaysTrue(), new PackageVisitor() {
@Override
public void visit(JavaPackage javaPackage) {
result.add(javaPackage);
Expand Down
105 changes: 103 additions & 2 deletions userguide/008_The_Library_API.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -115,10 +115,9 @@ note right on link #crimson: one adapter must not know\nabout any other adapter
----



=== Slices

Currently there are two "slice" rules offered by the Library API. These are basically rules
Currently, there are two "slice" rules offered by the Library API. These are basically rules
that slice the code by packages, and contain assertions on those slices. The entrance point is:

[source,java,options="nowrap"]
Expand Down Expand Up @@ -197,6 +196,108 @@ cycles.maxNumberToDetect=50
cycles.maxNumberOfDependenciesPerEdge=5
----

==== The Cycle Detection Core API

The underlying infrastructure for cycle detection that the `slices()` rule makes use of can also be accessed
without any rule syntax around it. This allows to use the pure cycle detection algorithm in custom
checks or libraries. The core class of the cycle detection is

[source,java,options="nowrap"]
----
com.tngtech.archunit.library.cycle_detection.CycleDetector
----

It can be used on a set of a generic type `NODE` in combination with a generic `Set<EDGE>`
(where `EDGE implements Edge<NODE>`) representing the edges of the graph:

[source,java,options="nowrap"]
----
Set<MyNode> nodes = // ...
Set<Edge<MyNode>> edges = // ...
Cycles<Edge<MyNode>> foundCycles = CycleDetector.detectCycles(nodes, edges);
----

Edges are parameterized by a generic type `EDGE` to allow custom edge types that can
then transport additional meta-information if needed.


=== Modularization Rules

[NOTE]
Note: ArchUnit doesn't strive to be a "competition" for module systems like the
Java Platform Module System. Such systems have advantages like checks at compile time
versus test time as ArchUnit does. So, if another module system works well in your
environment, there is no need to switch over. But ArchUnit can bring JPMS-like features
to older code bases, e.g. Java 8 projects, or environments where the JPMS is for some
reason no option. It also can accompany a module system by adding additional rules e.g.
on the API of a module.

To express the concept of modularization ArchUnit offers `ArchModule`s. The entrypoint into
the API is `ModuleRuleDefinition`, e.g.

[source,java,options="nowrap"]
----
ModuleRuleDefinition.modules().definedByPackages("..example.(*)..").should().beFreeOfCycles();
----

As the example shows, it shares some concepts with the <<Slices>> API. For example `definedByPackages(..)`
follows the same semantics as `slices().matching(..)`.
Also, the configuration options for cycle detection mentioned in the last section are shared by these APIs.
But, it also offers several powerful concepts beyond that API to express many different modularization scenarios.

One example would be to express modules via annotation. We can introduce a custom annotation
like `@AppModule` and follow a convention to annotate the top-level `package-info` file
of each package we consider the root of a module. E.g.

[source,java,options="nowrap"]
.com/myapp/example/module_one/package-info.java
----
@AppModule(
name = "Module One",
allowedDependencies = {"Module Two", "Module Three"},
exposedPackages = {"..module_one.api.."}
)
package com.myapp.example.module_one;
----

We can then define a rule using this annotation:

[source,java,options="nowrap"]
----
modules()
.definedByAnnotation(AppModule.class)
.should().respectTheirAllowedDependenciesDeclaredIn("allowedDependencies",
consideringOnlyDependenciesInAnyPackage("..example.."))
.andShould().onlyDependOnEachOtherThroughPackagesDeclaredIn("exposedPackages")
----

As the example shows, the syntax carries on meta-information (like the annotation of the annotated
`package-info`) into the created `ArchModule` objects where it can
be used to define the rule. In this example, the allowed dependencies are taken from the `@AppModule`
annotation on the respective `package-info` and compared to the actual module dependencies. Any
dependency not listed is reported as violation.
Likewise, the exposed packages are taken from the `@AppModule` annotation and any dependency
where the target class's package doesn't match any declared package identifier is reported
as violation.

Note that the `modules()` API can be adjusted in many ways to model custom requirements.
For further details, please take a look at the examples provided
https://github.com/TNG/ArchUnit-Examples/blob/main/example-junit5/src/test/java/com/tngtech/archunit/exampletest/junit5/ModulesTest.java[here].

==== Modularization Core API

The infrastructure to create modules and inspect their dependencies can also be used outside
the rule syntax, e.g. for custom checks or utility code:

[source,java,options="nowrap"]
----
ArchModules<?> modules = ArchModules.defineByPackages("..example.(*)..").modularize(javaClasses);
ArchModule<?> coreModule = modules.getByIdentifier("core");
Set<? extends ModuleDependency<?>> coreDependencies = coreModule.getModuleDependenciesFromSelf();
coreDependencies.forEach(...);
----


=== General Coding Rules

The Library API also offers a small set of coding rules that might be useful in various projects.
Expand Down
Loading

0 comments on commit be9f746

Please sign in to comment.