1. 程式人生 > 實用技巧 >Linux find命令

Linux find命令

參考地址:https://mp.baomidou.com/guide/quick-start.html

快速入手:

SpringBoot專案依賴:

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.3.2.RELEASE</version>
    <relativePath/>
</parent>

引入spring-boot-starter

spring-boot-starter-testmybatis-plus-boot-starterlombok依賴:

     <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</
groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-boot-starter</artifactId> <
version>3.3.2</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> <exclusions> <exclusion> <groupId>org.junit.vintage</groupId> <artifactId>junit-vintage-engine</artifactId> </exclusion> </exclusions> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build>

application.yml配置檔案中新增相關配置:

spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/mybatis_plus?useSSL=true&useUnicode=true&characterEncoding=utf-8&serverTimezone=GMT%2B8&allowPublicKeyRetrieval=true
spring.datasource.username=root
spring.datasource.password=root

mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl

在 Spring Boot 啟動類中新增@MapperScan註解,掃描 Mapper 資料夾:

@MapperScan("com.biao.mapper")
@SpringBootApplication
public class MybatisPlusApplication {

    public static void main(String[] args) {
        SpringApplication.run(MybatisPlusApplication.class, args);
    }
}

編寫實體類User.java(此處使用了Lombok簡化程式碼)

@Data
public class User {
    private Long id;
    private String name;
    private Integer age;
    private String email;
}

編寫Mapper類

// mapper 介面繼承一個介面,BaseMapper
public interface UserMapper extends BaseMapper<User> {

}

在測試類測試:

    @Autowired
    private UserMapper userMapper;

    @Test
    public void testSelect() {
        System.out.println(("----- selectAll method test ------"));
        List<User> userList = userMapper.selectList(null);
        Assert.assertEquals(5, userList.size());
        userList.forEach(System.out::println);
    }

測試完畢,那麼,這些sql 是誰寫的呢?

配置日誌

所有的sql現在是不可見的,如果要知道它是怎麼執行的,就要看日誌。

只需要一行,在配置檔案新增:mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl

CRUD 擴充套件

所有sql 都是自動 動態配置的

插入測試

public void insert(){
        User user = new User();
        user.setName("wangbiao");
        user.setAge(3);
        user.setEmail("[email protected]");
        // 沒有set id,它會自動生成id
        // 資料庫插入的預設id,是全域性唯一的
        int insert = userMapper.insert(user);
    }

id 生成策略

uuid  自增id  雪花演算法  redis  zookeeper

參考地址:https://www.cnblogs.com/haoxinyue/p/5208136.html

Twitter的snowflake演算法

snowflake是Twitter開源的分散式ID生成演算法,結果是一個long型的ID。其核心思想是:使用41bit作為毫秒數,10bit作為機器的ID(5個bit是資料中心,5個bit的機器ID),12bit作為毫秒內的流水號(意味著每個節點在每毫秒可以產生 4096 個 ID),最後還有一個符號位,永遠是0。具體實現的程式碼可以參看https://github.com/twitter/snowflake

修改方法

public void update(){
        User user = new User();
        user.setId(123L);   // 根據id 修改資料
        user.setName("aBiu~");
        int i = userMapper.updateById(user);

 }

填充策略

設定資料庫對應的實體類:

@Data
public class User {
    @TableId(type = IdType.ASSIGN_ID)   // 預設就是這個
    private Long id;
    
    private String name;
    private Integer age;
    private String email;
    
    @TableField(fill = FieldFill.INSERT)    // 設定新增時間
    private Date createTime;
    @TableField(fill = FieldFill.INSERT_UPDATE)     // 設定修改時候,新增時間也要新增
    private Date updateTime;
}

既然設定了新增,要配置,寫個handler 的配置類並重寫兩個方法:

@Slf4j
@Component
public class MyMetaObjectHandler implements MetaObjectHandler {
    // 插入時的填充策略
    @Override
    public void insertFill(MetaObject metaObject) {
        // 根據實體類的 createTime updateTime 欄位,新增或 修改資料時執行這個方法,新增一個時間
        this.setFieldValByName("createTime",new Date(),metaObject);
        this.setFieldValByName("updateTime",new Date(),metaObject);
    }
    // 修改時的填充策略
    @Override
    public void updateFill(MetaObject metaObject) {
        // 修改時只修改 修改時間的欄位資料
        this.setFieldValByName("updateTime",new Date(),metaObject);
    }
}

樂觀鎖機制

實現方式:

取出記錄時,獲取當前 version

更新時,帶上這個 version

執行更新時,set version,where 判斷version 版本

如果version 版本不對,就更新失敗。

樂觀鎖外掛

1、給資料庫增加version 欄位,設定預設值1,就是初始時給 1

2、給對應的實體類新增屬性欄位,增加註解:@Version

    @Version
    private Integer version;

3、註冊元件

在config 包裡配置,寫一個MyBatisPlusConfig

// 事務註解
@EnableTransactionManagement
@Configuration
public class MyBatisPlusConfig {

    // 註冊樂觀鎖外掛
    @Bean
    public OptimisticLockerInterceptor optimisticLockerInterceptor() {
        return new OptimisticLockerInterceptor();
    }

}

分頁查詢

1、配置攔截器:

官網程式碼:

//Spring boot方式
@Configuration
@MapperScan("com.baomidou.cloud.service.*.mapper*")
public class MybatisPlusConfig {

    @Bean
    public PaginationInterceptor paginationInterceptor() {
        PaginationInterceptor paginationInterceptor = new PaginationInterceptor();
        // 設定請求的頁面大於最大頁後操作, true調回到首頁,false 繼續請求  預設false
        // paginationInterceptor.setOverflow(false);
        // 設定最大單頁限制數量,預設 500 條,-1 不受限制
        // paginationInterceptor.setLimit(500);
        // 開啟 count 的 join 優化,只針對部分 left join
        paginationInterceptor.setCountSqlParser(new JsqlParserCountOptimize(true));
        return paginationInterceptor;
    }
}

我們只需要在配置檔案寫個方法,寫一行程式碼即可;找到那個配置類

// 事務註解
@EnableTransactionManagement
@Configuration
public class MyBatisPlusConfig {

    // 註冊樂觀鎖外掛
    @Bean
    public OptimisticLockerInterceptor optimisticLockerInterceptor() {
        return new OptimisticLockerInterceptor();
    }
    // 分頁外掛
    @Bean
    public PaginationInterceptor paginationInterceptor(){
        return new PaginationInterceptor();
    }

}

2、測試

  // 測試分頁查詢
    public void testPage(){
        // 第一頁,每一頁顯示5條資料
        Page<User> page = new Page<>(1, 5);
        userMapper.selectPage(page,null);

        page.getRecords().forEach(System.out::println);
    }

這個page 有很多方法,比如上一頁下一頁總數。。。

刪除操作

mapper 可以直接點 出來刪除方法,通過id,map,批量,三種刪除方式,直接執行即可

通過id刪除:userMapper.deleteById(1L);

通過id批量刪除:userMapper.deleteBatchIds(Arrays.asList(1,2,3));

通過map刪除:

     HashMap<String, Object> map = new HashMap<>();
        // name 是屬性,資料庫欄位
        map.put("name","wangbiao");
        userMapper.deleteByMap(map);

邏輯刪除

在資料庫中沒有被刪除,只是通過一個變數來讓它失效。

1、在資料庫表中新增一個deleted 欄位,實體類中新增一個相應的屬性,不要忘記加註解 @TableLogic

    @TableLogic     // 邏輯刪除
    private Integer deleted;

2、配置:

# 全域性邏輯刪除的實體欄位名(since 3.3.0,配置後可以忽略不配置步驟2)
mybatis-plus.global-config.db-config.logic-delete-field= flag 
# 邏輯已刪除值(預設為 1)
mybatis-plus.global-config.db-config.logic-delete-value= 1
# 邏輯未刪除值(預設為 0)
mybatis-plus.global-config.db-config.logic-not-delete-value= 0

3、再次執行刪除:userMapper.deleteById(1L);

就是邏輯刪除,不會真正刪除,記錄依舊在資料庫,但是值已經發生變化。

但是再次查詢這條資料,會查不到的,自動會過濾掉邏輯刪除的。

條件構造器(重點)

一些複雜的sql 就可以使用它來代替。

參考地址:https://mp.baomidou.com/guide/wrapper.html#abstractwrapper

示例:返回多條資料

  public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.isNotNull("name")       // name 不為空的
                .isNotNull("email")     // email 不為空的
                .ge("age",21);      // age 大於21 的,但是好像等於21 的也會查出來
        userMapper.selectList(wrapper).forEach(System.out::println);
    }

還有很多條件可以加,like(模糊)、orderBy(排序)等等,很多,

參考官方地址:https://mp.baomidou.com/guide/wrapper.html#eq

示例2:查詢一條資料的:如果明知道是查出來的是多條資料,就不要用這個

  public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.eq("name","wangbiao");      // 查詢名字等於wangbiao 的
        User user = userMapper.selectOne(wrapper);
        System.out.println(user);
    }

示例3:between  查詢xx 到 xx 之間的總數

    public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.between("age",20,30);   // 查詢年齡20到30之間的
        Integer i = userMapper.selectCount(wrapper);
        System.out.println(i);
    }

示例4:模糊查詢

    @Test
    public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.notLike("name","a");    // 查詢名字不包含a 的
        List<Map<String, Object>> maps = userMapper.selectMaps(wrapper);
        maps.forEach(System.out::println);
    }
    @Test
    public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.likeRight("name","a")  // 查詢包含a 的
                .likeLeft("name","a");  // 左跟 右 就是代表模糊查詢時候的% 百分號在左邊還是在右邊,兩個都寫代表左右兩個% 都有
        List<Map<String, Object>> maps = userMapper.selectMaps(wrapper);
        maps.forEach(System.out::println);
    }

示例5:in 查詢

  public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        wrapper.inSql("id","select id from user where age < 21");   // 這裡可以寫sql,也可以在上一行先查出來,再放到這裡當條件
        List<Object> objects = userMapper.selectObjs(wrapper);
        objects.forEach(System.out::println);   // 返回的是id
    }

示例6:orderBy

   @Test
    public void test(){
        QueryWrapper<User> wrapper = new QueryWrapper<>();
        // 通過id 進行排序
        wrapper.orderByDesc("id");      // 降序,有對應的升序 及其他排序方法
        List<User> users = userMapper.selectList(wrapper);
        users.forEach(System.out::println);
    }

程式碼生成器

確認新增這些依賴:-- 這裡少了swagger API 的依賴,到時生成的實體類會匯入swagger註解失敗報錯

     <dependency>
            <groupId>org.apache.velocity</groupId>
            <artifactId>velocity-engine-core</artifactId>
            <version>2.2</version>
        </dependency>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-generator</artifactId>
            <version>3.3.2</version>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.3.2</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
    </dependencies>

生成程式碼模板類

import com.baomidou.mybatisplus.annotation.DbType;
import com.baomidou.mybatisplus.annotation.FieldFill;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.generator.AutoGenerator;
import com.baomidou.mybatisplus.generator.config.DataSourceConfig;
import com.baomidou.mybatisplus.generator.config.GlobalConfig;
import com.baomidou.mybatisplus.generator.config.PackageConfig;
import com.baomidou.mybatisplus.generator.config.StrategyConfig;
import com.baomidou.mybatisplus.generator.config.po.TableFill;
import com.baomidou.mybatisplus.generator.config.rules.DateType;
import com.baomidou.mybatisplus.generator.config.rules.NamingStrategy;

import java.util.ArrayList;

// 程式碼自動生成器
public class ShengChengCode {
    public static void main(String[] args) {
        // 構建一個程式碼生成器
        AutoGenerator mpg = new AutoGenerator();
        // 配置策略

        // 1、全域性配置
        GlobalConfig gconfig = new GlobalConfig();
        String propertyPath = System.getProperty("user.dir");
        gconfig.setOutputDir(propertyPath+"/src/main/java");
        gconfig.setAuthor("wangbiao");
        gconfig.setOpen(false);
        gconfig.setFileOverride(false);     // 是否覆蓋
        gconfig.setServiceName("%Service");     // 去Service 的i 字首
        gconfig.setIdType(IdType.ID_WORKER);
        gconfig.setDateType(DateType.ONLY_DATE);
        gconfig.setSwagger2(true);
        mpg.setGlobalConfig(gconfig);   // set 到自動生成器裡

        // 2、設定資料來源
        DataSourceConfig dsc = new DataSourceConfig();
        dsc.setUrl("jdbc:mysql://localhost:3306/mybatis_plus?useSSL=true&useUnicode=true&characterEncoding=utf-8&serverTimezone=GMT%2B8&allowPublicKeyRetrieval=true");
        dsc.setDriverName("com.mysql.jdbc.Driver");
        dsc.setUsername("root");
        dsc.setPassword("root");
        dsc.setDbType(DbType.MYSQL);
        mpg.setDataSource(dsc);     // set 到自動生成器裡

        // 3、包的設定
        PackageConfig pc = new PackageConfig();
        pc.setModuleName("blog");
        pc.setParent("com.biao");
        pc.setEntity("po");
        pc.setMapper("mapper");
        pc.setService("service");
        pc.setController("ctrl");
        mpg.setPackageInfo(pc);     // set 到自動生成器裡

        // 4、策略配置 --- 這個是最重要的
        StrategyConfig strategy = new StrategyConfig();
        strategy.setInclude("user");                        // 設定要對映的表,可以寫多個表,逗號,隔開
        strategy.setNaming(NamingStrategy.underline_to_camel);          // 包的命名規則
        strategy.setColumnNaming(NamingStrategy.underline_to_camel);    // 列的名字規則
        strategy.setEntityLombokModel(true);                // 支援lombok 註解
//        strategy.setLogicDeleteFieldName("deleted");        // 邏輯刪除欄位
        // 自動填充     建立和修改的欄位自動填充
//        TableFill create = new TableFill("create", FieldFill.INSERT);
//        TableFill modified = new TableFill("modified", FieldFill.INSERT_UPDATE);
//        ArrayList<TableFill> list = new ArrayList<>();
//        list.add(gmtCreate);
//        list.add(gmtModified);
//        strategy.setTableFillList(list);
        // 樂觀鎖配置
//        strategy.setVersionFieldName("version");
//        strategy.setRestControllerStyle(true);
//        strategy.setControllerMappingHyphenStyle(true);

        mpg.setStrategy(strategy);
        // 執行
        mpg.execute();
    }

}

確定資料庫和配置,啟動這個main 方法即可