我试图把我的头围绕着JPA,并且学到了很多东西.JPA是一个Java规范,提供程序实现此规范.我明白那一部分.
我不明白的是Spring Data如何进入图片.Spring Data也是像Hibernate或OpenJPA这样的提供商吗?如果没有,那是什么?Spring Data如何"让事情变得更轻松"?
我第一次尝试设置和使用Spring Data.当然,您可能希望使用最新版本(Spring Data JPA 1.4.3.RELEASE和Hibernate 4.3.0.Final).根据在线示例配置后,应用程序引发了异常.
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jpa</artifactId>
<version>1.4.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>Hibernate 4.3.0.Final</version>
<exclusions>
<exclusion>
<artifactId>commons-collections</artifactId>
<groupId>commons-collections</groupId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-search</artifactId>
<version>4.4.2.Final</version>
<exclusions>
<exclusion>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
</exclusion>
</exclusions>
</dependency>
Run Code Online (Sandbox Code Playgroud)
这是错误/异常:
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'entityManagerFactory' defined in class path resource [test-service-persistance-application-context.xml]: Invocation of init method failed; nested exception is java.lang.NoSuchMethodError: javax.persistence.Table.indexes()[Ljavax/persistence/Index;
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1553)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:539)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:475)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:304)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:228)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:300)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:195)
at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:973)
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:750)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:482) …Run Code Online (Sandbox Code Playgroud) 有没有办法覆盖Spring Data Rest执行的findAll查询?
我需要一种基于某些特定标准过滤结果的方法,似乎使用a @NamedQuery应该是我正在寻找的线,所以我设置了一个测试.
@Entity
@Table(name = "users")
@NamedQueries({
@NamedQuery(name = "User.findAll", query="SELECT u FROM User u WHERE u.username = 'test'"),
@NamedQuery(name = "User.findNameEqualsTest", query="SELECT u FROM User u WHERE u.username = 'test'")
})
public class User implements Serializable, Identifiable<Long> { }
Run Code Online (Sandbox Code Playgroud)
有了这个,我希望SDR能够利用我的findAll()查询(返回1个结果),而是执行相同的旧findAll逻辑(返回所有结果).
在我的存储库中,我添加了:
@Repository
@RestResource(path = "users", rel = "users")
public interface UserJpaRepository extends JpaRepository<User, Long> {
public Page<User> findNameEqualsTest(Pageable pageable);
}
Run Code Online (Sandbox Code Playgroud)
在这种情况下,它会拿起提供的@NamedQuery.所以...
我该如何重写默认findAll()逻辑?我需要实际构建一组复杂的标准并将其应用于结果集.
我有一些我无法删除的对象,并且必须更新名为"已删除"的公共字段而不是它.我在那里读到我可以使用编写通用查询#{#entityName}.出于这个原因,我试图覆盖这样的CrudRepository#delete(…)方法:
public interface DeleteableRepository<T, ID extends Serializable> extends CrudRepository<T,ID>{
@Override
@Query("UPDATE #{#entityName} x set x.deleted = 1 where x.id = ?1")
public void delete(ID id);
}
Run Code Online (Sandbox Code Playgroud)
但我有一个单元测试,显示我错了!
@Test
public void testDelete() {
SomeDeleteableObject sdo = new SomeDeletableObject();
sdo = getDeleteableRepository().create(sdo);
Assert.assertNotNull(sdo);
Assert.assertNotNull(sdo.getId());
Assert.assertFalse(sdo.isDeleted());
getDeleteableRepository().delete(sdo);
sdo = getDeleteableRepository().findOne(sdo.getId());
//Fails here
}
Run Code Online (Sandbox Code Playgroud)
是不是可以覆盖那样的CrudRepository方法?
spring-data提供了一种通过定义方法名称来生成SQL搜索的方法.
以下工作正常:
@Entity
public class Book {
Date from, to;
}
//CrudRepository<Book>
findByFromDateBetween(Date departure, Date arrival);
Run Code Online (Sandbox Code Playgroud)
但为什么以下不起作用呢?
findByFromDateBetweenAndToDateBetween(Date departure, Date arrival);
Run Code Online (Sandbox Code Playgroud)
要连接两个日期搜索,我必须重复日期:
findByFromDateBetweenAndToDateBetween(Date departure, Date arrival, Date departure, Date arrival);
Run Code Online (Sandbox Code Playgroud)
问题:是否可以重复使用参数?
我有一个名为EmployeeDepartment的实体,如下所示
@IdClass(EmployeeDepartmentPK.class) //EmployeeDepartmentPK is a serializeable object
@Entity
EmployeeDepartment{
@Id
private String employeeID;
@Id
private String departmentCode;
---- Getters, Setters and other props/columns
}
Run Code Online (Sandbox Code Playgroud)
我有一个Spring Data Repository,如下所示
@RepositoryRestResource(....)
public interface IEmployeeDepartmentRepository extends PagingAndSortingRepository<EmployeeDepartment, EmployeeDepartmentPK> {
}
Run Code Online (Sandbox Code Playgroud)
此外,我有一个注册转换器从String转换为EmployeeDepartmentPK.
现在,对于一个由ID employeeID ="abc123"和departmentCode ="JBG"限定的实体,我希望在调用SDR接口时使用的ID是abc123_JBG.例如,http:// localhost/EmployeeDepartment/abc123_JBG应该获取结果,事实确实如此.
但是,当我尝试使用PUT保存实体时,Spring Data Commons的BasicPersistentEntity类中可用的ID属性的departmentCode值为abc123_JBG.这是错的.我不确定这是否是预期的行为.
请帮忙.
谢谢!
我正在浏览Spring Data MongoDB - 参考文档,我发现这些示例有点过于简单化了.
特别是我试图了解如何处理并发环境中的陈旧数据.例如,假设我有以下实体:
public class Person {
private final String username;
private final String firstname;
private final String lastname;
[...]
}
Run Code Online (Sandbox Code Playgroud)
现在,如果我CrudRepository用来保存/更新/删除我的实体,那么想象一下这样一个场景,其中两个线程检索同一个实体,其中一个删除它,另一个更新其lastname字段.如果delete调用在调用之前完成,save那么我的实体将被删除然后重新创建,此时预期的行为将导致save操作失败.
到目前为止,我已经看到两种解决此问题的方法:
@Version注释.找不到任何文档说Spring Data支持使用版本化文档在MongoDB中进行乐观锁定.如果有人能指出我的链接,我们将不胜感激.MongoOperations.findAndModify如果返回则使用和失败null.这种方法的缺点是我不能再实现我的存储库API以获得"获取实体"和"保存更新的实体"类型的语义.例如:
User user = userRepository.findByUsername("uniqueUsername");
user.setLastName("Archer");
userRepository.update(user);
Run Code Online (Sandbox Code Playgroud)我想将其中的一部分推送到存储库我猜:
userRepository.updateLastname("uniqueUsername", "Archer");
Run Code Online (Sandbox Code Playgroud)
但我有点担心,如果我想要做的每种类型的更新都需要一个新方法,我的存储库接口将无法控制地增长.
我意识到我还没有提出过一个问题,所以这就是:使用Spring Data for MongoDB设计应用程序的最佳实践是什么?
这是我的文件:
@Document(collection = "posts")
public class Post {
@Id
String id;
String title;
String description;
}
Run Code Online (Sandbox Code Playgroud)
我正在尝试使用like运算符查询带有标题或说明的帖子.我的存储库
public class PostsRepository extends MongoRepository<Post, String> {
@Query(value = "{ $or: [ { 'title' : ?0 }, { 'description' : ?0 } ] }")
Page<Post> queryByTitleOrDescription(String query, Pageable pageable);
}
Run Code Online (Sandbox Code Playgroud)
如何使用LIKE在两个字段之间或之间执行此查询?
我正在尝试将Spring Data用于MongoDB.我正在使用MongoDB的全文搜索功能,并希望为文本索引字段(@TextIndexed)尝试Spring Data注释.此功能在Spring Data MongoDB的1.6.0.BUILD-SNAPSHOT中可用.
我试图在Spring中设置简单的应用程序上下文并运行简单的JUnit测试.但是我的应用程序上下文加载失败,因为我将1.5.1.RELEASE更改为1.6.0.BUILD-SNAPSHOT.
我得到的错误如下:
Caused by: org.springframework.beans.BeanInstantiationException: Could
not instantiate bean class
[org.springframework.data.mongodb.core.MongoTemplate]: Constructor
threw exception; nested exception is java.lang.NoClassDefFoundError:
org/springframework/objenesis/ObjenesisStd at
org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:163) at
org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:121) at
org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:280)
... 51 more Caused by: java.lang.NoClassDefFoundError:
org/springframework/objenesis/ObjenesisStd at
org.springframework.data.mongodb.core.convert.DefaultDbRefResolver.<init>(DefaultDbRefResolver.java:72) at
org.springframework.data.mongodb.core.MongoTemplate.getDefaultMongoConverter(MongoTemplate.java:1961) at
org.springframework.data.mongodb.core.MongoTemplate.<init>(MongoTemplate.java:210) at
org.springframework.data.mongodb.core.MongoTemplate.<init>(MongoTemplate.java:174) at
sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at
sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39) at
sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27) at
java.lang.reflect.Constructor.newInstance(Constructor.java:513) at
org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:148)
... 53 more Caused by: java.lang.ClassNotFoundException:
org.springframework.objenesis.ObjenesisStd at
java.net.URLClassLoader$1.run(URLClassLoader.java:202) at
java.security.AccessController.doPrivileged(Native Method) at
java.net.URLClassLoader.findClass(URLClassLoader.java:190) at
java.lang.ClassLoader.loadClass(ClassLoader.java:306) at
sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301) at
java.lang.ClassLoader.loadClass(ClassLoader.java:247)
Run Code Online (Sandbox Code Playgroud)
现在,我试图org.springframework.objenesis.ObjenesisStd …
我一直在使用Spring Data和MongoDB,并且有一个关于限制某些查询的数据量的问题.我已经看到在其中添加自定义查询MongoRepository,但是我没有看到任何限制数据量和返回基本上是较大类的子集的类的示例.
例如,我有一个User具有多个字段的类,但我还想创建一个具有UserShort该类字段子集的User类.例如UserShort,只包含id和firstName/ lastName/ email字段,而不是一切.
我已经看到我可以指定/限制返回的字段,但是我可以让那些返回到不同的类吗?此刻UserShort将返回null,除非我指定的User类,而不是,但字段将被限制到我指定的人.不确定这是否可行?我意识到User下面的课程不是很大,但这是我追求的概念.
用户界面:
public interface Users {}
Run Code Online (Sandbox Code Playgroud)
子集类:
public class UserShort implements Users {
@Id
private String id;
private String firstName;
private String lastName;
@Indexed(unique = true)
private String email;
//getters / setters
}
Run Code Online (Sandbox Code Playgroud)
全班:
@Document
public class User implements Users {
@Id
private String id;
private String firstName;
private String lastName; …Run Code Online (Sandbox Code Playgroud) spring ×9
spring-data ×7
java ×6
jpa ×4
mongodb ×3
crud ×1
hibernate ×1
jpql ×1
objenesis ×1
postgresql ×1