简体   繁体   中英

Resolving subdocument types with Spring Data and MongoDB

I'm encountering an error with a Spring Data repository as it attempts to resolve a property expression:

public interface ContractRepository
    extends MongoRepository<Contract,String> {
    public List<Contract> findByCodeBindings(String binding);
}

Here's the relevant parts of Contract :

@Document(collection="CONTRACTS")
public class PersistentContract extends BaseContract {
    @PersistenceConstructor
    public PersistentContract(String name, Version version, Code code) {
        super(name, version, code);
    }
}

Code is an interface implemented by CodeImpl . It contains a property bindings , which has a getter and setter in Code . So the query's property expression is designed to find those contracts with a nested Code document containing a given binding. So far, so good.

However, the problem is an IllegalArgumentException is getting thrown:

java.lang.IllegalArgumentException: No property bindings found on my.company.Code!
 org.springframework.data.mapping.context.AbstractMappingContext.getPersistentPropertyPath(AbstractMappingContext.java:225)

Debugging that section of code shows that Spring Data is picking apart the expression and determines there's a property of type Code . However, because Code is an interface, it has no properties listed.

Is there a means to hint to Spring Data that either Code has this property or that CodeImpl is the actual type of the code property? I'm surprised that the library doesn't attempt to parse the getters or setters of the interface.

This is using spring-data-commons 1.5.1.RELEASE and spring-data-mongodb 1.2.1.RELEASE.

Appreciate the help.

My solution was to avoid interfaces at all in the persistent object. So BaseContract became the following:

public abstract class BaseContract<T extends Code> {
    public abstract T getCode();
}

And PersistentContract was implemented in terms of concrete classes:

public class PersistentContract extends BaseContract<CodeImpl> {
}

This seems to strike the right balance between coding against interfaces in the base class and satisfying Spring Data's need for concrete classes.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM