数据库

spring boot + spring data mongo

2018-07-17  本文已影响74人  金刚_30bf

环境

spring boot : 2.0.3
spring data : 2.0.8

配置

  1. 使用@EnableMongoRepositories 注解
    需要在一个@Configuration 类上, 且需要确定该类所在的包包含repository定义所在的包。

@Configuration
@EnableMongoRepositories
public class WeaselWebMVCConfig  implements WebMvcConfigurer{

    @Bean
    public LogInterceptor getLogInterceptor() {
        return new LogInterceptor();
    }
    
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(getLogInterceptor());
        WebMvcConfigurer.super.addInterceptors(registry);
    }
}

注意: 当使用该注解时如何获取 MongoTemplate引用,
注意到该注解包含一个 模板引用:

    /**
     * Configures the name of the {@link MongoTemplate} bean to be used with the repositories detected.
     * 
     * @return
     */
    String mongoTemplateRef() default "mongoTemplate";

因此,可以在代码中直接装配使用之, 如下测试代码:

    @Autowired
    private MongoTemplate mongoTemplate;
    
    @Test
    public void test4MongoTemplategen() {
        System.out.println("获取 MongoTemplate 引用。");
        
        System.out.println(this.mongoTemplate.toString());
    }
  1. Application 类
@SpringBootApplication
public class WeaselApplication {

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        
        SpringApplication.run(WeaselApplication.class, args);
    }
}

创建domain

package com.dus.weasel.domain;

import java.util.Arrays;
import java.util.Date;
import java.util.concurrent.atomic.AtomicLong;

public class UserInfo {

    //客户id、 客户名称、客户昵称、邮件地址、密码、注册时间、头像、上次登录时间、登录次数
    
    private Long userId;
    private String userName;
    private String nickName;
    private String email;
    private String pwd;
    private Date regTime;
    private byte[] headImage;
    private Date lastLoginTime;
    private AtomicLong loginCount;
    
    
    
    
    @Override
    public String toString() {
        return "UserInfo [userId=" + userId + ", userName=" + userName + ", nickName=" + nickName + ", email=" + email
                + ", pwd=" + pwd + ", regTime=" + regTime + ", headImage=" + Arrays.toString(headImage)
                + ", lastLoginTime=" + lastLoginTime + ", loginCount=" + loginCount + "]";
    }
    
    public Long getUserId() {
        return userId;
    }
    public void setUserId(Long userId) {
        this.userId = userId;
    }
    public String getUserName() {
        return userName;
    }
    public void setUserName(String userName) {
        this.userName = userName;
    }
    public String getNickName() {
        return nickName;
    }
    public void setNickName(String nickName) {
        this.nickName = nickName;
    }
    public String getEmail() {
        return email;
    }
    public void setEmail(String email) {
        this.email = email;
    }
    public String getPwd() {
        return pwd;
    }
    public void setPwd(String pwd) {
        this.pwd = pwd;
    }
    public Date getRegTime() {
        return regTime;
    }
    public void setRegTime(Date regTime) {
        this.regTime = regTime;
    }
    public byte[] getHeadImage() {
        return headImage;
    }
    public void setHeadImage(byte[] headImage) {
        this.headImage = headImage;
    }
    public Date getLastLoginTime() {
        return lastLoginTime;
    }
    public void setLastLoginTime(Date lastLoginTime) {
        this.lastLoginTime = lastLoginTime;
    }
    public AtomicLong getLoginCount() {
        return loginCount;
    }
    public void setLoginCount(AtomicLong loginCount) {
        this.loginCount = loginCount;
    }
    
    
    
}

创建 repository

package com.dus.weasel.repository;

import org.springframework.data.mongodb.repository.MongoRepository;

import com.dus.weasel.domain.UserInfo;

public interface UserInfoRepository extends MongoRepository<UserInfo, Long>{

}

测试

package com.dus.repository.test;

import java.util.Date;
import java.util.List;
import java.util.Optional;
import java.util.concurrent.atomic.AtomicLong;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.domain.Example;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.dus.weasel.WeaselApplication;
import com.dus.weasel.domain.UserInfo;
import com.dus.weasel.repository.UserInfoRepository;

@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes=WeaselApplication.class)// 指定spring-boot的启动类
public class UserInfoRepositoyTests {

    @Autowired
    private UserInfoRepository repo;
    
    @Test
    public void testsave() {
        UserInfo user = new UserInfo();
        user.setUserName("username");
        user.setUserId(1l);
        user.setEmail("www@163.com.cn");
        user.setLastLoginTime(new Date());
        user.setNickName("nick");
        user.setRegTime(new Date());
        user.setPwd("1234");
        user.setLoginCount(new AtomicLong(0));
        user.setHeadImage("This is an image for head show! ".getBytes());
        
        System.out.println(user.toString());
        
        UserInfo resuser =  repo.insert(user);
        
        System.out.println("after insert:");
        System.out.println(resuser.toString());
        
    }
    
    @Test
    public void testfind() {
        long count = repo.count();
        System.out.println("Current db userinfo counts=" + count);
        UserInfo q = new UserInfo();
        q.setNickName("Nick");
        Example<UserInfo> exa = Example.of(q);
        
        Optional<UserInfo> user = repo.findOne(exa);
        
        if (user.isPresent()) {
            System.out.println("get Result:" + user.get().toString());
        } else {
            System.out.println("Not Result");
        }
        
        Optional<UserInfo> ru = repo.findById(1l);
        
        if (ru.isPresent()) {
            System.out.println("findById get Result:" + ru.get().toString());
        } else {
            System.out.println("findById Not Result");
        }
        
        // 分页 
        Page<UserInfo> pu = repo.findAll(PageRequest.of(0, 1));
        System.out.println("分页查询!");
        System.out.println(pu.getTotalElements());
        System.out.println(pu.getTotalPages());
        System.out.println(pu.getSize());
        System.out.println(pu.getNumber());
        System.out.println(pu.getNumberOfElements());
        
        List<UserInfo> luser = pu.getContent();
        System.out.println("list size :" + luser.size());
        System.out.println(luser.get(0).toString());
    }
}
  1. 注入 UserInfoRepository repo;
  2. 插入 使用 UserInfo resuser = repo.insert(user);
    插入后库里的数据:
{ "_id" : ObjectId("5b4da0882e0694540c89394e"), "userId" : NumberLong(1), "userName" : "username", "nickName" : "nick", "email" : "www@163.com.cn", "pwd" : "1234", "regTime" : ISODate("2018-07-17T07:53:44.661Z"), "headImage" : BinData(0,"VGhpcyBpcyBhbiBpbWFnZSBmb3IgaGVhZCBzaG93ISA="), "lastLoginTime" : ISODate("2018-07-17T07:53:44.661Z"), "loginCount" : NumberLong(0), "_class" : "com.dus.weasel.domain.UserInfo" }

注意: 这里没有映射id , 而是使用了传入的id 。
若用使用mongdb的id, 则需要:
在domain的类上添加Id注解 :

    @Id
    private Long userId;

插入数据库的数据中没有了userId , 而是_id . 但这个Id不会自动生成,输入传入。

  1. 查询
    使用Example的查询 。

  2. 根据id的查询

  3. 分页查询

自定义repository 方法 (通过方法名)

在 UserInfoRepository 添加如下方法:

public interface UserInfoRepository extends MongoRepository<UserInfo, Long>{

    List<UserInfo> findByNickNameAndEmail(String nickname, String email);
    List<UserInfo> findByNickNameOrEmail(String nickname, String email);
        Optional<List<UserInfo>> findByLoginCount(Long count);
}

测试 :

    @Test
    public void test4CustomQueryMethodName() {
        List<UserInfo> lu  = repo.findByNickNameAndEmail("nick", "www@163.com.cn");
        if (lu == null || lu.isEmpty()) {
            System.out.println("查询结果为空!");
        } else {
            System.out.println(lu.size());
            for ( UserInfo u : lu) {
                System.out.println(u.toString());
            }
        }
    }

测试

    @Test
    public void test4CustomQueryMethodName2() {
        List<UserInfo> lu  = repo.findByNickNameOrEmail("nick", "www@163.com.2222cn");
        if (lu == null || lu.isEmpty()) {
            System.out.println("查询结果为空!");
        } else {
            System.out.println(lu.size());
            for ( UserInfo u : lu) {
                System.out.println(u.toString());
            }
        }
    }

测试

    @Test
    public void test4CustomQueryMethodNameOptinal() {
        Optional<List<UserInfo>> lu  = repo.findByLoginCount(3l);
        if (!lu.isPresent()) {
            System.out.println("查询结果为空!");
        } else {
            List<UserInfo> ll = lu.get();
            System.out.println("jieguo:" + ll.size());
            for ( UserInfo u : ll) {
                System.out.println(u.toString());
            }
        }
    }

从测试结果看 , 即时查询为空 , Optional<List<UserInfo>> lu = repo.findByLoginCount(3l); , 也会返回一个空list对象 , 因此使用Optional意义不大。

自定义repository 方法 (自定义查询代码 )

  1. 创建接口

特别注意: 接口和实现类的命名要完全一致,并且实现类以Impl为后缀,否则会异常, 框架会尝试按方法名解析推测查询条件。

public interface UserInfoCustomRepo {

    List<UserInfo> customSelectAll(String name);
    void update(UserInfo user);
}
  1. 实现接口
public class UserInfoCustomRepoImpl implements UserInfoCustomRepo{

    @Autowired
    private MongoTemplate template;
    
    @Override
    public List<UserInfo> customSelectAll(String name) {
        System.out.println("In Custom UserInfo repo :customSelectAll ");
        return template.find(new Query(where("userName").is(name)), UserInfo.class);
    }

    @Override
    public void update(UserInfo user) {
        System.out.println("In Custom UserInfo repo :update ");
        template.save(user);
    }

}

注入MongoTemplate ;
通过模板实现代码;

  1. 使用该自定义接口
public interface UserInfoRepository extends MongoRepository<UserInfo, Long> , UserInfoCustomRepo {
}
  1. 测试
    @Test
    public void test4CustomSelecAll() {
        List<UserInfo> lu = repo.customSelectAll("username");
        System.out.println(lu.size());
        for (UserInfo u : lu) {
            System.out.println(u.toString());
        }
    }
    
    @Test
    public void test4update() {
        UserInfo user = new UserInfo();
        user.setId("5b4db8092e069460b8cd4604");
        user.setEmail("new@123413.comc");
        user.setNickName("new nick");
        user.setLoginCount(new AtomicLong(33l));
        user.setLastLoginTime(new Date());
        
        repo.update(user);
        
    }

spring data mongo 配置日志打印nosql

在application.yml配置文件中添加:

logging:
  level:
    org:
      springframework:
        data:
          mongodb:
            core: DEBUG

索引

domain类的字段上添加 :
@Indexed(unique = true) 唯一索引。

@Indexed 索引。

类上添加:
@CompoundIndexes({
@CompoundIndex(name = "age_idx", def = "{'lastName': 1, 'age': -1}")
})
组合索引。

上一篇下一篇

猜你喜欢

热点阅读