目录
后端相关代码
前端相关代码
效果
Controller层
@PostMapping
public AjaxResult selectProduct(@RequestParam(defaultValue = "1")int pageNum, @RequestParam(defaultValue = "5")int pageSize, @RequestBody(required = false)ProductDTO productDTO){
return AjaxResult.success(productService.selectProduct(pageNum,pageSize,productDTO));
}
Service层
@Override
public IPage selectProduct(int pageNum, int pageSize, @Param("productDTO")ProductDTO productDTO) {
Page page = new Page<>(pageNum, pageSize);
// 非空判断
if (productDTO == null) {
productDTO = new ProductDTO();
}
page.setCurrent(pageNum);
return productMapper.selectProduct(page,productDTO);
}
Mapper层
@Mapper
public interface ProductMapper extends BaseMapper {
IPage selectProduct(IPage page, @Param("productDTO")ProductDTO productDTO);
}
Mapper.xml
Product
@AllArgsConstructor
@NoArgsConstructor
public class Product implements Serializable {
private Integer pid;
private String pname;
private Double price;
@TableField(value = "category_id")
private String categoryId;
private static final long serialVersionUID = 1L;
public Integer getPid() {
return pid;
}
public void setPid(Integer pid) {
this.pid = pid;
}
public String getPname() {
return pname;
}
public void setPname(String pname) {
this.pname = pname == null ? null : pname.trim();
}
public Double getPrice() {
return price;
}
public void setPrice(Double price) {
this.price = price;
}
public String getCategoryId() {
return categoryId;
}
public void setCategoryId(String categoryId) {
this.categoryId = categoryId == null ? null : categoryId.trim();
}
}
以上要求有相关数据库,sql语句如下:
-- auto-generated definition
create table product
(
pid int auto_increment
primary key,
pname varchar(20) not null,
price double null,
category_id varchar(20) null
);
基于Element-ui和axios
注意这边要在main.js添加响应拦截:
import Vue from "vue";
import App from "./App.vue";
import router from "./router";
import store from "./store";
import 'element-ui/lib/theme-chalk/index.css';
import ElementUI from "element-ui";
import axios from "axios";
Vue.config.productionTip = false;
Vue.prototype.$axios = axios;
Vue.use(ElementUI);
//------------------请求拦截-------------------//
axios.interceptors.request.use(config => {
//例:若存在token则带token
const token = store.state.token;
if (token) {
config.headers.Authorization = token
}
return config;
}, err => {
console.log("请求拦截=>", err);
return err;
})
//------------------响应拦截-------------------//
//-------------对响应数据做点什么-------------//
axios.interceptors.response.use(res => {
console.log("响应拦截=>", res.data);
//例:后端数据处理错误,并返回错误原因;前端获取错误原因并展示
if (res.data.success == false) {
Message({
message: res.data.data.message + ',请重试!',
type: 'warning'
});
}
console.log("响应拦截=>", res);
return res ? res.data : res;
}, err => {
console.log(err);
//打印完整的错误信息
console.log("响应拦截错误完整信息=>",err.response)
//也可以在这里对不同的错误码做不同的展示处理
throw err;
})
new Vue({
router,
store,
render: (h) => h(App),
}).$mount("#app");
上面我没有作条件查询,因此没有传ProductDTO进去,相当于无条件查询,会列出所有的数据列表:
关键的请求代码是:
axios.post(`http://localhost:8080/product?pageNum=${params.pageNum}&pageSize=${params.pageSize}`)
params是请求体参数,如下定义:
const params = {
pageNum: this.pageNum,
pageSize: this.pageSize
};
当然加上条件查询的话,你还得加上一个VTO:
const productDTO = {
// 根据需要设置其他的查询条件
};
这边要注意一个地方:设置请求头: 在发送请求时,确保设置适当的请求头,特别是Content-Type
头,以指示后端请求体的格式。对于JSON格式的请求体,通常使用Content-Type: application/json
。
当然 如果每次请求都声明header未免太过麻烦,我们可以在main.js中设置,即作请求拦截器,整个代码示例如下:
import Vue from "vue";
import App from "./App.vue";
import router from "./router";
import store from "./store";
import 'element-ui/lib/theme-chalk/index.css';
import ElementUI from "element-ui";
import axios from "axios";
Vue.config.productionTip = false;
Vue.prototype.$axios = axios;
Vue.use(ElementUI);
//------------------请求拦截-------------------//
axios.interceptors.request.use(config => {
//例:若存在token则带token
const token = store.state.token;
config.headers['Content-Type'] = 'application/json';//这边声明了请求头类型
if (token) {
config.headers.Authorization = token
}
return config;
}, err => {
console.log("请求拦截=>", err);
return err;
})
//------------------响应拦截-------------------//
//-------------对响应数据做点什么-------------//
axios.interceptors.response.use(res => {
console.log("响应拦截=>", res.data);
//例:后端数据处理错误,并返回错误原因;前端获取错误原因并展示
if (res.data.success == false) {
Message({
message: res.data.data.message + ',请重试!',
type: 'warning'
});
}
console.log("响应拦截=>", res);
return res ? res.data : res;
}, err => {
console.log(err);
//打印完整的错误信息
console.log("响应拦截错误完整信息=>",err.response)
//也可以在这里对不同的错误码做不同的展示处理
throw err;
})
new Vue({
router,
store,
render: (h) => h(App),
}).$mount("#app");
前端设置了选择pagesize大小的功能:
至此,一个最简单的前后端对接的例子完成,后续根据自己的需求拓展,例如文件上传、登录校验功能或增加条件查询的功能等