最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

SpringBoot SSMP 整合案例分享

 更新時間:2022年08月19日 10:33:46   作者:Lemonade22???????  
這篇文章主要介紹了SpringBoot SSMP 整合案例分享,文章圍繞主題展開詳細(xì)的內(nèi)容介紹,具有一定的參考價值,需要的小伙伴可以參考一下

前言:

  • - 先開發(fā)基礎(chǔ)CRUD功能,做一層測一層
  • - 調(diào)通頁面,確認(rèn)異步提交成功后,制作所有功能
  • - 添加分頁功能與查詢功能

1 搭建SpringBoot應(yīng)用

  • 勾選 SpringMVC 與 MySQL 坐標(biāo)
  • 修改配置文件為yml格式
  • 設(shè)置端口為80方便訪問(可選)

2 實體類開發(fā)

Lombok,一個Java類庫,提供了一組注解,簡化POJO實體類開發(fā)

  • lombok版本由SpringBoot提供,無需指定版本。
  • 常用注解:@Data
  • 為當(dāng)前實體類在編譯期設(shè)置對應(yīng)的 get/set 方法,toString方法,hashCode方法,equals方法等
@Data
public class Book {
        private Integer id;
        private String type;
        private String name;
        private String description; 
}

3 數(shù)據(jù)層(dao層)開發(fā)

技術(shù)實現(xiàn)方案:

  • MyBatisPlus
  • Druid
  • (1)導(dǎo)入 MyBatisPlus 與 Druid 對應(yīng)的 starter
  • (2)配置數(shù)據(jù)源與 MyBatisPlus 對應(yīng)的基礎(chǔ)配置(id 生成策略使用數(shù)據(jù)庫自增策略)
spring:
  datasource:
    druid:
      driver-class-name: com.mysql.cj.jdbc.Driver
      url: jdbc:mysql://localhost:3306/ssm_db?servierTimezone=UTC
      username: root
      password: root

mybatis-plus:
  global-config:
    db-config:
      table-prefix: tbl_
      id-type: auto

(3)繼承 BaseMapper 并指定泛型

@Mapper
public interface BookDao extends BaseMapper<Book> {  
}

(4)制作測試類測試結(jié)果

@SpringBootTest
public class BookDaoTestCase {
    @Autowired
    private BookDao bookDao;

    @Test
    void testSave(){
        Book book = new Book();
        book.setName("測試數(shù)據(jù)");
        book.setType("測試類型");
        bookDao.insert(book);
    }
    @Test
    void testGetById() {
        System.out.println(bookDao.selectById(1));
    }
}

(5)為方便調(diào)試可以開啟 MyBatisPlus 的日志(使用配置方式開啟日志,設(shè)置日志輸出方式為標(biāo)準(zhǔn)輸出)

mybatis-plus:
  global-config:
    db-config:
      table-prefix: tbl_
      id-type: auto
  configuration:
    log-impl: org.apache.ibatis.logging.stdout.StdOutImpl

4 數(shù)據(jù)層開發(fā)分頁功能

  • 分頁操作需要設(shè)定分頁對象 IPage,IPage 對象中封裝了分頁操作中的所有數(shù)據(jù)(數(shù)據(jù)、當(dāng)前頁碼值、每頁數(shù)據(jù)總量、最大頁碼值、數(shù)據(jù)總量)。
  • 分頁操作是在 MyBatisPlus 的常規(guī)操作基礎(chǔ)上增強(qiáng)得到,內(nèi)部是動態(tài)的拼寫 SQL 語句,使用 MyBatisPlus 攔截器實現(xiàn)。
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

// MyBatisPlus攔截器
@Configuration
public class MPConfig {
    @Bean
    public MybatisPlusInterceptor mybatisPlusInterceptor() {
        //1.定義Mp攔截
        MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
        //2.添加具體的攔截器
        interceptor.addInnerInterceptor(new PaginationInnerInterceptor());
        return interceptor;
    }
}

5 數(shù)據(jù)層開發(fā)?條件查詢功能 QueryWrapper

  • 使用 QueryWrapper 對象封裝查詢條件,推薦使用 LambdaQueryWrapper 對象,將所有查詢操作封裝成方法調(diào)用。
// 條件查詢功能
@Test
void testGetByCondition(){
    IPage page = new Page(1,10);
    LambdaQueryWrapper<Book> lqw = new LambdaQueryWrapper<Book>();
    lqw.like(Book::getName,"Spring");
    bookDao.selectPage(page,lqw);
}

@Test
void testGetByCondition2(){
    QueryWrapper<Book> qw = new QueryWrapper<Book>();
    qw.like("name","Spring");
    bookDao.selectList(qw);
}

  • 支持動態(tài)拼寫查詢條件 Strings.isNotEmpty(name)
@Test
void testGetByCondition(){
    String name = "Spring";
    IPage page = new Page(1,10);
    LambdaQueryWrapper<Book> lqw = new LambdaQueryWrapper<Book>();
    lqw.like(Strings.isNotEmpty(name),Book::getName,"Spring");
    bookDao.selectPage(page,lqw);
}

6 業(yè)務(wù)層(Service層)開發(fā)

# Service層接口定義與數(shù)據(jù)層接口定義具有較大區(qū)別,不要混用

// 業(yè)務(wù)層關(guān)注的是業(yè)務(wù)操作
login(String username,String password);

// 數(shù)據(jù)層關(guān)注的是數(shù)據(jù)庫操作
selectByUserNameAndPassword(String username,String password);
// 接口定義
public interface BookService {

    boolean save(Book book);
    boolean delete(Integer id);
    boolean update(Book book);
    Book getById(Integer id);
    List<Book> getAll();

    IPage<Book> getByPage(int currentPage,int pageSize);
}
// 實現(xiàn)類定義
@Service
public class BookServiceImpl implements BookService {

    @Autowired
    private BookDao bookDao;

    public Boolean save(Book book) {
        return bookDao.insert(book) > 0; 
    }

    public Boolean delete(Integer id) {
        return bookDao.deleteById(id) > 0; 
    }
    public Boolean update(Book book) {
        return bookDao.updateById(book) > 0; 
    } 
    public Book getById(Integer id) {
        return bookDao.selectById(id);
    }
    public List<Book> getAll() {
        return bookDao.selectList(null);
    }
    public IPage<Book> getByPage(int currentPage, int pageSize) {
        IPage page = new Page<Book>(currentPage,pageSize);
        return bookDao.selectPage(page,null);
    }
}

7 業(yè)務(wù)層開發(fā)——快速開發(fā)?使用ISerivce和ServiceImpl

  • > - 快速開發(fā)方案
  • >     -   使用MyBatisPlus提供的業(yè)務(wù)層通用接口(ISerivce<T>)與業(yè)務(wù)層通用實現(xiàn)類(`ServiceImpl<M,T>`)
  • >     -   在通用類基礎(chǔ)上做功能重載或功能追加
  • >     -   注意重載時不要覆蓋原始操作,避免原始提供的功能丟失

接口:

public interface BookService extends IService<Book> {

    // 追加的操作與原始操作通過名稱區(qū)分,功能類似
    boolean saveBook(Book book);
    boolean modify(Book book);
    boolean delete(Integer id);
    IPage<Book> getPage(int currentPage, int pageSize);
    IPage<Book> getPage(int currentPage, int pageSize, Book book);
}

實現(xiàn)類:

@Service
public class BookServiceImpl extends ServiceImpl<BookDao, Book> implements BookService {
    @Autowired
    private BookDao bookDao;
    @Override
    public boolean saveBook(Book book) {
        return bookDao.insert(book) > 0;
    }
    @Override
    public boolean modify(Book book) {
        return bookDao.updateById(book) > 0;
    }
    @Override
    public boolean delete(Integer id) {
        return bookDao.deleteById(id) > 0;
    }

    @Override
    public IPage<Book> getPage(int currentPage, int pageSize) {
        IPage page = new Page(currentPage, pageSize);
        bookDao.selectPage(page, null);
        return page;
    }
    @Override
    public IPage<Book> getPage(int currentPage, int pageSize, Book book) {
        LambdaQueryWrapper<Book> lqw = new LambdaQueryWrapper<Book>();
        lqw.like(Strings.isNotEmpty(book.getType()), Book::getType, book.getType());
        lqw.like(Strings.isNotEmpty(book.getName()), Book::getName, book.getName());
        lqw.like(Strings.isNotEmpty(book.getDescription()), Book::getDescription, book.getDescription());
        IPage page = new Page(currentPage, pageSize);
        bookDao.selectPage(page, lqw);
        return page;
    }
}

8 基于 Restful 進(jìn)行表現(xiàn)層開發(fā)

  • 基于Restful制作表現(xiàn)層接口
    • 新增:POST
    • 刪除:DELETE
    • 修改:PUT
    • 查詢:GET
  • 接收參數(shù)
    • 實體數(shù)據(jù):@RequestBody
    • 路徑變量:@PathVariable
// 功能測試
@GetMapping("/{currentPage}/{pageSize}")
public R getPage(@PathVariable int currentPage, @PathVariable int pageSize, Book book) {

    IPage<Book> page = bookService.getPage(currentPage, pageSize, book);
    // 如果當(dāng)前頁碼大于了總頁碼,那么將最大頁碼值作為當(dāng)前頁碼,重新執(zhí)行查詢操作
    // 源碼中  long pages = this.getTotal() / this.getSize();
    if (currentPage > page.getPages()) {
        page = bookService.getPage((int) page.getPages(), pageSize, book);
    }
    return new R(true, page);
}    

9 表現(xiàn)層消息一致性處理 R(統(tǒng)一返回值)

設(shè)計表現(xiàn)層返回結(jié)果的模型類,用于后端與前端進(jìn)行數(shù)據(jù)格式統(tǒng)一,也稱為前后端數(shù)據(jù)協(xié)議:

  • 1. 設(shè)計統(tǒng)一的返回值結(jié)果類型便于前端開發(fā)讀取數(shù)據(jù)
  • 2. 返回值結(jié)果類型可以根據(jù)需求自行設(shè)定,沒有固定格式
  • 3. 返回值結(jié)果模型類用于后端與前端進(jìn)行數(shù)據(jù)格式統(tǒng)一,也稱為前后端數(shù)據(jù)協(xié)議
  • - flag:false
  • - Data: null
  • - 消息(msg): 要顯示信息    

10 前后端協(xié)議聯(lián)調(diào)

  • 前后端分離結(jié)構(gòu)設(shè)計中頁面歸屬前端服務(wù)器
  • 單體工程中頁面放置在 resources / static 目錄下(建議執(zhí)行clean)
  • 前端發(fā)送異步請求,調(diào)用后端接口
    • created鉤子函數(shù)用于初始化頁面時發(fā)起調(diào)用
    • 頁面使用 axios 發(fā)送異步請求獲取數(shù)據(jù)后確認(rèn)前后端是否聯(lián)通
//列表
getAll() {
    axios.get("/books").then((res)=>{
    		console.log(res.data);
    });
},

查詢

將查詢數(shù)據(jù)返回到頁面,利用前端數(shù)據(jù)雙向綁定進(jìn)行數(shù)據(jù)展示:

//列表
getAll() {
    axios.get("/books").then((res)=>{
    		this.dataList = res.data.data;
    });
},

添加

  • 1. 請求方式使用POST調(diào)用后臺對應(yīng)操作
  • 2. 添加操作結(jié)束后動態(tài)刷新頁面加載數(shù)據(jù)
  • 3. 根據(jù)操作結(jié)果不同,顯示對應(yīng)的提示信息
  • 4. 彈出添加Div時清除表單數(shù)據(jù)
//彈出添加窗口
handleCreate() {
    this.dialogFormVisible = true;
},
  
//清除數(shù)據(jù),重置表單
resetForm() {
		this.formData = {};
},
  
//彈出添加窗口
handleCreate() {
		this.dialogFormVisible = true;
		this.resetForm();
},  
  
//添加
handleAdd () {
		//發(fā)送異步請求
		axios.post("/books",this.formData).then((res)=>{
				//如果操作成功,關(guān)閉彈層,顯示數(shù)據(jù)
				if(res.data.flag){
						this.dialogFormVisible = false;
						this.$message.success("添加成功");
				}else {
					this.$message.error("添加失敗");
				}
		}).finally(()=>{
				this.getAll();
		});
},  
  
//取消添加
cancel(){
		this.dialogFormVisible = false;
		this.$message.info("操作取消");
},  

刪除

  • 1. 請求方式使用Delete調(diào)用后臺對應(yīng)操作
  • 2. 刪除操作需要傳遞當(dāng)前行數(shù)據(jù)對應(yīng)的id值到后臺
  • 3. 刪除操作結(jié)束后動態(tài)刷新頁面加載數(shù)據(jù)
  • 4. 根據(jù)操作結(jié)果不同,顯示對應(yīng)的提示信息
  • 5. 刪除操作前彈出提示框避免誤操作
// 刪除
handleDelete(row) {
    axios.delete("/books/"+row.id).then((res)=>{
        if(res.data.flag){
            this.$message.success("刪除成功");
        }else{
            this.$message.error("刪除失敗");
        }
    }).finally(()=>{
        this.getAll();
    });
}

// 刪除
handleDelete(row) {
    //1.彈出提示框
    this.$confirm("此操作永久刪除當(dāng)前數(shù)據(jù),是否繼續(xù)?","提示",{
        type:'info'
    }).then(()=>{
        //2.做刪除業(yè)務(wù)
        axios.delete("/books/"+row.id).then((res)=>{
        ……
        }).finally(()=>{
            this.getAll();
        });
    }).catch(()=>{
        //3.取消刪除
        this.$message.info("取消刪除操作");
    });
}
//彈出編輯窗口
handleUpdate(row) {
    axios.get("/books/"+row.id).then((res)=>{
        if(res.data.flag){
            //展示彈層,加載數(shù)據(jù)
            this.formData = res.data.data;
            this.dialogFormVisible4Edit = true; 
        }else{
            this.$message.error("數(shù)據(jù)同步失敗,自動刷新"); }
        });
},

//刪除
handleDelete(row) {
    axios.delete("/books/"+row.id).then((res)=>{
        if(res.data.flag){
            this.$message.success("刪除成功");
        }else{
            this.$message.error("數(shù)據(jù)同步失敗,自動刷新"); 
        }
    }).finally(()=>{
        this.getAll();
    });
}

1.加載要修改數(shù)據(jù)通過傳遞當(dāng)前行數(shù)據(jù)對應(yīng)的id值到后臺查詢數(shù)據(jù) 2.利用前端數(shù)據(jù)雙向綁定將查詢到的數(shù)據(jù)進(jìn)行回顯

修改

  • 1. 請求方式使用PUT調(diào)用后臺對應(yīng)操作
  • 2. 修改操作結(jié)束后動態(tài)刷新頁面加載數(shù)據(jù)(同新增)
  • 3. 根據(jù)操作結(jié)果不同,顯示對應(yīng)的提示信息(同新增)
//修改
handleEdit() {
    axios.put("/books",this.formData).then((res)=>{
        //如果操作成功,關(guān)閉彈層并刷新頁面
        if(res.data.flag){
            this.dialogFormVisible4Edit = false;
            this.$message.success("修改成功");
        }else {
            this.$message.error("修改失敗,請重試");
        }
    }).finally(()=>{
        this.getAll();
    });
},
  
// 取消添加和修改
cancel(){
    this.dialogFormVisible = false;
    this.dialogFormVisible4Edit = false;
    this.$message.info("操作取消");
},

11 業(yè)務(wù)消息一致性處理

對異常進(jìn)行統(tǒng)一處理,出現(xiàn)異常后,返回指定信息:

  • 使用注解 @RestControllerAdvice 定義 SpringMVC 異常處理器用來處理異常的
  • 異常處理器必須被掃描加載,否則無法生效
  • 表現(xiàn)層返回結(jié)果的模型類中添加消息屬性用來傳遞消息到頁面
// 作為springmvc的異常處理器
@RestControllerAdvice
public class ProjectExceptionAdvice {

    // 攔截所有的異常信息
    @ExceptionHandler(Exception.class)
    public R doException(Exception e){
        // 記錄日志
        // 通知運維
        // 通知開發(fā)
        e.printStackTrace();
        return new R("服務(wù)器故障,請稍后重試哈!");
    }
}

12 分頁功能

頁面使用 el 分頁組件添加分頁功能:

  • 定義分頁組件需要使用的數(shù)據(jù)并將數(shù)據(jù)綁定到分頁組件
  • 替換查詢?nèi)抗δ転榉猪摴δ?/li>
  • 加載分頁數(shù)據(jù)
  • 分頁頁碼值切換

使用el分頁組件:

  • 定義分頁組件綁定的數(shù)據(jù)模型
  • 異步調(diào)用獲取分頁數(shù)據(jù)
  • 分頁數(shù)據(jù)頁面回顯

到此這篇關(guān)于SpringBoot SSMP 整合案例分享的文章就介紹到這了,更多相關(guān)SpringBoot SSMP 內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Java壓縮集合的三種方法

    Java壓縮集合的三種方法

    這篇文章主要介紹了Java壓縮集合的三種方法,幫助大家更好的理解和使用Java,感興趣的朋友可以了解下
    2021-01-01
  • 詳解SpringMVC的攔截器鏈實現(xiàn)及攔截器鏈配置

    詳解SpringMVC的攔截器鏈實現(xiàn)及攔截器鏈配置

    攔截器(Interceptor)是一種動態(tài)攔截方法調(diào)用的機(jī)制,在SpringMVC中動態(tài)攔截控制器方法的執(zhí)行。本文將詳細(xì)講講SpringMVC中攔截器參數(shù)及攔截器鏈配置,感興趣的可以嘗試一下
    2022-08-08
  • 一文教你如何使用Java靈活讀取Excel內(nèi)容

    一文教你如何使用Java靈活讀取Excel內(nèi)容

    這篇文章主要給大家介紹了關(guān)于如何使用Java靈活讀取Excel內(nèi)容的相關(guān)資料,讀取Excel數(shù)據(jù)是Java開發(fā)中常見的任務(wù),文中通過代碼示例介紹的非常詳細(xì),需要的朋友可以參考下
    2023-09-09
  • java中List去除重復(fù)數(shù)據(jù)的5種方式總結(jié)

    java中List去除重復(fù)數(shù)據(jù)的5種方式總結(jié)

    這篇文章主要給大家總結(jié)介紹了關(guān)于java中List去除重復(fù)數(shù)據(jù)的5種方式,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-01-01
  • 詳解kafka中的消息分區(qū)分配算法

    詳解kafka中的消息分區(qū)分配算法

    kafka有分區(qū)機(jī)制,一個主題topic在創(chuàng)建的時候,會設(shè)置分區(qū)。如果只有一個分區(qū),那所有的消費者都訂閱的是這一個分區(qū)消息;如果有多個分區(qū)的話,那消費者之間又是如何分配的呢?本文就來為大家詳細(xì)講解一下
    2022-04-04
  • springboot中使用redis的方法代碼詳解

    springboot中使用redis的方法代碼詳解

    &#8203;redis 作為一個高性能的內(nèi)存數(shù)據(jù)庫,如果不會用就太落伍了,之前在 node.js 中用過 redis,本篇記錄如何將 redis 集成到 spring boot 中。感興趣的朋友跟隨小編一起看看吧
    2019-05-05
  • SpringBoot使用@RestController處理GET和POST請求的代碼詳解

    SpringBoot使用@RestController處理GET和POST請求的代碼詳解

    在Spring?MVC中,@RestController注解的控制器類可以處理多種HTTP請求方法,包括GET和POST,所以本文就給大家詳細(xì)介紹了SpringBoot使用@RestController處理GET和POST請求的示例代碼,需要的朋友可以參考下
    2024-07-07
  • 如何使用Java爬蟲批量爬取圖片

    如何使用Java爬蟲批量爬取圖片

    這篇文章主要介紹了如何使用Java爬蟲批量爬取圖片,對于爬蟲的入門來說,圖片相對來說是比較容易獲取的,因為大部分圖片都不是敏感數(shù)據(jù),所以不會遇到什么反爬措施,對于入門爬蟲來說是比較合適的,需要的朋友可以參考下
    2023-04-04
  • Java基礎(chǔ)之堆內(nèi)存溢出的解決

    Java基礎(chǔ)之堆內(nèi)存溢出的解決

    這篇文章主要介紹了Java基礎(chǔ)之堆內(nèi)存溢出的解決,文中有非常詳細(xì)的圖文示例及代碼示例,對正在學(xué)習(xí)java的小伙伴們有很好地幫助,需要的朋友可以參考下
    2021-05-05
  • Java不帶break將導(dǎo)致case穿透問題

    Java不帶break將導(dǎo)致case穿透問題

    這篇文章主要介紹了Java不帶break將導(dǎo)致case穿透問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-02-02

最新評論

虹口区| 宁德市| 邵阳县| 海林市| 河曲县| 阜南县| 麻栗坡县| 若尔盖县| 东莞市| 宾阳县| 社会| 崇阳县| 辽源市| 麦盖提县| 青川县| 庆阳市| 澄城县| 沁水县| 盈江县| 延津县| 昭觉县| 祁门县| 尖扎县| 屯留县| 克山县| 柯坪县| 丁青县| 土默特左旗| 鸡东县| 大化| 永春县| 岳池县| 铁力市| 彭泽县| 慈利县| 柘荣县| 贺州市| 蕲春县| 兴文县| 葵青区| 罗城|