# spring-data-commons: the shared layer under every Spring Data store

> Spring Data Commons is the part of Spring Data you depend on without asking for it: the Repository interfaces, the metadata model, the query method name parser and the auditing model that every store specific module builds on. It is Apache-2.0 licensed and generally not something you add to a pom on purpose, which makes its interface changes the thing to watch when you upgrade.

**spring-projects/spring-data-commons** — Spring Data Commons. Interfaces and code shared between the various datastore specific implementations.

- Repository: https://github.com/spring-projects/spring-data-commons
- Website: https://spring.io/projects/spring-data
- Stars: 841 · Forks: 737
- Language: Java
- License: Apache-2.0
- Published: 2026-10-20 · Updated: 2026-10-20 · Language: en
- Canonical page: https://hysenlabs.com/projects/spring-projects-spring-data-commons

## The module you inherit rather than choose

Spring Data Commons is part of the umbrella Spring Data project and provides shared infrastructure across the Spring Data projects. It contains technology neutral repository interfaces as well as a metadata model for persisting Java classes. The project description in the repository says the same thing in one line: interfaces and code shared between the various datastore specific implementations.

That framing is the key to understanding how to evaluate it. Almost nobody chooses spring-data-commons. It arrives as a dependency of Spring Data JPA, Spring Data MongoDB, Spring Data Redis or one of the other store modules, and the version of it in your classpath is decided by that store module, not by you. The Spring Data homepage is the project's home, and the umbrella contains the individual store projects alongside it.

Which is exactly why the module matters even though you did not pick it. When a Spring Data upgrade changes behaviour, the change is often in the shared layer. The repository interfaces, the metadata model and the query method name parsing all live here, and a change to any of them surfaces in every store, not just one.

The goals listed in the README describe what the shared layer is responsible for. Repository and custom object mapping abstractions. Support for cross-store persistence. Dynamic query generation from query method names. Implementation domain base classes providing basic properties. Transparent auditing of the created and last changed values. A way to integrate custom repository code. And easy Spring integration with a custom namespace.

Read as a list, that is the contract every store module implements. A store module that could not support auditing or custom repository fragments would not fit the model, so the shared layer is effectively the specification that the ecosystem is written against.

## Query derivation is where the shared layer earns its keep

The goal of dynamic query generation from query method names is the feature that most developers actually encounter first, and the one most likely to change under them during an upgrade.

The mechanism is that you declare an interface method with a descriptive name and no implementation, and the framework constructs the query. The README does not walk through the derivation rules, and that absence is significant: the rules are documented in the reference documentation rather than in this project README, which is a reasonable choice for a module whose entire job is to be the shared contract.

For an engineer deciding what to check during an upgrade, this is where to look first. The derivation is a parser, and parsers change. A method name that used to resolve to a certain query might resolve differently, or a new reserved word might be introduced that changes how a name is parsed. Because the same shared parser is used by every store, a change here is a change everywhere.

The same reasoning applies to the other abstraction goals. The repository interfaces define the method surface, the metadata model defines how a Java class is described to the store, and the custom object mapping abstraction is the extension point for a property that does not map cleanly. If a store specific module has a feature that does not fit the shared abstractions, it is a sign that the shared layer needs to change, and that change lands in everyone's classpath.

The other two goals are more visible in a project. Implementation domain base classes provide basic properties such as an identifier and auditing fields, and transparent auditing fills in created and last changed values when those annotations are present and auditing is enabled. Custom repository code integration is the fragment mechanism, where you add your own implementation to a repository interface.

The last goal, easy Spring integration with a custom namespace, is what lets a store module be a first class citizen in a Spring application rather than something you wire by hand.

## Adding the dependency, and the snapshot variant

The Maven dependency is the only thing most projects need to know about the module:

```xml
<dependency>
  <groupId>org.springframework.data</groupId>
  <artifactId>spring-data-commons</artifactId>
  <version>${version}</version>
</dependency>
```

The version is a property in the example, which is how Spring's own documentation usually writes it, so the value comes from a parent BOM or a property in your build. In practice, when you use a store module, the version is managed for you and you should not be declaring this artifact at all.

If you do want the latest snapshots of the upcoming major version, the documentation points at the Maven snapshot repository and shows the variant with a SNAPSHOT suffix and the repository declaration:

```xml
<repository>
  <id>spring-snapshot</id>
  <name>Spring Snapshot Repository</name>
  <url>https://repo.spring.io/snapshot</url>
</repository>
```

That is a development convenience rather than a deployment pattern. Snapshots change without notice, and a shared infrastructure module that changes under a running application is a bad trade for production.

The release history shows why the version question deserves attention. The listed releases are 4.2.0-M2 from 2026-09-24, 4.2.0-M1 from 2026-08-21 and 4.1.1 from 2026-08-21. Two milestones of a 4.2 line in progress alongside a 4.1.1 maintenance release, which is a normal Spring release train pattern with a new major line incubating while the current one is patched.

The repository is not archived and the last push was on 2026-10-14, so the module is being worked on as part of the umbrella release process.

## Building from source with the Maven wrapper

The README is explicit that you do not need to build from source to use Spring Data, because the binaries are published to repo.spring.io. Building is for trying out the latest changes, and it is straightforward with the Maven wrapper, which is checked in as the mvnw script along with the mvnw.cmd variant for Windows.

You need JDK 17 or above. The build command is:

```bash
 $ ./mvnw clean install
```

If you prefer the regular mvn command, you need Maven 3.5.0 or above. The wrapper exists precisely so you do not have to care about that, which is the usual reason the wrapper is committed in a Maven project.

Building the reference documentation builds the project as well but without running the tests:

```bash
 $ ./mvnw clean install -Pantora
```

The generated documentation ends up at target/site/index.html. The Pantora profile is the AsciiDoc based documentation build used across the Spring projects, and the target/site output path is the older Maven site layout, which is worth knowing if you are looking for the output after a run.

One more detail about contributing, and it is a hard requirement rather than a convention. All commits must include a Signed-off-by trailer at the end of the commit message, indicating that the contributor agrees to the Developer Certificate of Origin. The README links a blog post on the move from a CLA to the DCO to explain the reasoning. The practical effect for an outside contributor is that git commit --signoff is part of the workflow, and a pull request with an unsigned commit will not pass the build.

## Where the shared layer is the wrong abstraction

There are situations where reaching for this module, or for Spring Data at all, is the wrong call.

The clearest case is a domain that is not relational and not document shaped. Spring Data is built around a repository interface with query methods derived from names, and around an object mapping model that assumes a fairly regular mapping from a Java class to a stored document or row. Systems whose data is inherently graph shaped, or where the query language is the domain itself, need a different model, and forcing Spring Data onto them produces a lot of custom implementation code that defeats the point.

The second case is a small application with a handful of queries. The value of the repository abstraction is that it removes boilerplate CRUD and lets you express intent in method names. For ten tables and three screens, that value is smaller than the cost of a new layer between your code and the database, and a plain data access approach with explicit SQL is less machinery.

The third case, and the one that catches people out, is when you need to write repository fragments or implement a store. The custom repository integration goal is real, but implementing custom fragment code means writing against the shared interfaces, and those interfaces change between versions. The support for custom repository code is a convenience for application code, not an invitation to build a new persistence layer on top of it.

A concrete risk worth naming is the version alignment problem. Because the store modules and this shared module are released on a train, a mismatch between a store module and the commons version it expects produces failures that look like configuration problems rather than version problems, typically at context startup rather than at the call site.

The alternative approaches differ in what they assume. Using a store module without the abstraction means writing your own repository interface and your own implementation, which is more code but no dependency on the derivation rules. Using plain JDBC or a client library directly gives you full control over the queries and no derivation at all. A different framework with its own repository model is a different ecosystem entirely, and the comparison is really about whether you want the shared Spring Data contract in your application at all.

## Licence, governance and where to get help

Spring Data Commons is open source software released under the Apache 2.0 license, with the LICENSE.txt at the repository root. Apache 2.0 carries an explicit patent grant and is the standard choice across the Spring ecosystem, and for a shared infrastructure library that many store modules build on, it is the licence that lets a commercial datastore module be written without the licensing question resurfacing.

The project is governed by the Spring Code of Conduct, and the README states that by participating you are expected to uphold it, with unacceptable behaviour to be reported to the code of conduct address.

The support channels are documented in detail, which is a sign of a project with a large user base. The reference documentation and the Javadocs are the first place to look. For people new to Spring, the README points to the Spring basics on spring.io and to the guides, since Spring Data builds on Spring Framework and a lot of confusion is really confusion about the framework underneath. For upgrades, the GitHub releases and the release notes wiki are the place to check for new and noteworthy features, which is a direct pointer to the shared layer changing behaviour.

Questions go to Stack Overflow with the spring-data tag, and the project monitors it. Bugs go to the GitHub issue tracker, and the reporting guidance is specific and worth following: search the existing issues first, include the Spring Data version and the JVM version, use Markdown escapes around pasted code and stack traces, and if possible attach a test case or a project that reproduces the issue.

The repository layout reflects the standard Spring Data Commons structure, with the pom.xml, the mvnw wrapper scripts, the src directory, and a set of governance and process files: CONTRIBUTING.adoc, SECURITY.adoc and CI.adoc. There is also a file named Spring Data Commons.sonargraph, which is the static analysis rules configuration for the module.

## Conclusion

Adopt Spring Data Commons only as the transitive dependency that comes with a store module such as Spring Data JPA or MongoDB, and pin its version to the one your store module expects, since the interfaces and query derivation rules live here and a mismatch shows up as a context that fails to start. Do not build a custom store on it unless you intend to maintain it. Verify first which Spring Data Commons version your store module pulls in, how your query method names are being derived, and whether the auditing annotations are enabled in your configuration.

## FAQ

### What is Spring Data Commons and when would I add it as a dependency?

It is the module of shared infrastructure across the Spring Data projects, containing technology neutral repository interfaces and a metadata model for persisting Java classes. In practice it comes in as a transitive dependency of a store module such as Spring Data JPA or Spring Data MongoDB rather than being declared on its own.

### Which features does Spring Data Commons provide?

The README lists repository and custom object mapping abstractions, support for cross-store persistence, dynamic query generation from query method names, implementation domain base classes with basic properties, transparent auditing of created and last changed, integration of custom repository code, and easy Spring integration with a custom namespace.

### How do I build Spring Data Commons from source?

You need JDK 17 or above, and the project ships a Maven wrapper, so the command is `./mvnw clean install`. Using the regular mvn command instead requires Maven 3.5.0 or above, and adding the Pantora profile builds the reference documentation into target/site/index.html without running the tests.

### What license is Spring Data Commons released under?

Apache 2.0, with the text in the LICENSE.txt file at the repository root. The README states that Spring Data Commons is open source software released under the Apache 2.0 license.

### What do I need to do to contribute a pull request to Spring Data Commons?

All commits must include a Signed-off-by trailer indicating agreement to the Developer Certificate of Origin, so git commit --signoff is required. The README also points to CONTRIBUTING.adoc for the full details.

## Sources

- [License: Apache-2.0](https://github.com/spring-projects/spring-data-commons/blob/main/LICENSE)
- [Project website](https://spring.io/projects/spring-data)
- [README](https://github.com/spring-projects/spring-data-commons/blob/main/README.md)
- [Releases](https://github.com/spring-projects/spring-data-commons/releases)
- [spring-projects/spring-data-commons on GitHub](https://github.com/spring-projects/spring-data-commons)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/spring-projects-spring-data-commons
