从零开始摸索VUE,配合Golang搭建导航网站(二十四.vue-admin-template带筛选的列表展示,初识双向绑定)

704 阅读2分钟

「这是我参与11月更文挑战的第24天,活动详情查看:2021最后一次更文挑战

前言

前一篇文章实现了接入后端的增删改查的接口,都较为简单,今天增加一个新的接口,根据分类列表的选择来控制详情数据的渲染,具体实现展示如下:

动画.gif

前端实现

主要是前端加了一个api请求方法,然后了一个新的页面,后端也有加了一个接口

主要代码

先亮出主要代码,再复述涉及到了哪些细节知识点 修改scr/view/index.vue文件内容如下:

<template>
  <div class="app-container">
    <el-form :inline="true" class="filter-form" :show-message="false">
      <el-form-item label="类型:">
        <el-select v-model="type" placeholder="请选择类型" style="max-width:140px">
          <el-option v-for="item in typelist" :key="item.ID" :value="item.ID" :label="item.Name" />
        </el-select>
      </el-form-item>
      <el-form-item>
         <el-button type="primary" icon="el-icon-plus" @click="openAddFrom()">新增数据</el-button>
      </el-form-item>
    </el-form>

    <el-table
      v-loading="listLoading"
      :data="list"
      element-loading-text="加载中..."
      border
      fit
      highlight-current-row
    >
      <el-table-column align="center" label="ID" width="95">
        <template slot-scope="scope">
          {{ scope.row.ID }}
        </template>
      </el-table-column>
      <el-table-column label="Title">
        <template slot-scope="scope">
          {{ scope.row.Name }}
        </template>
      </el-table-column>
      <el-table-column align="center" fixed="right" label="操作" width="190px">
        <template slot-scope="scope">
          <div class="flex-btns">
            <el-button :loading="scope.row.loading" type="primary" @click="bindEdit(scope.row)">编辑</el-button>
            <el-button type="info" @click="deteleType(scope.row)">删除</el-button>

          </div>
        </template>
      </el-table-column>
    </el-table>

  </div>
</template>

<script>
import { getTypeList, getUrlList } from '@/api/url'
export default {

  data() {
    return {
      filterText: '',
      typelist: [],
      list: [],
      type: '全部'
    }
  },

  watch: {
    type(val) {
    this.listLoading = true
      getUrlList({
        id: val
      }).then(response => {
        this.list = response.data.Value
        this.listLoading = false
      })
    }
  },
  created() {
    this.fetchData()
  },
  methods: {
    fetchData() {
      this.listLoading = true
      getTypeList().then(response => {
        this.typelist = response.data
      })
      getUrlList({
        id: 0
      }).then(response => {
        this.list = response.data.Value
        this.listLoading = false
      })
    }
  }
}
</script>

src/api/url.js添加一个路由:


export function getUrlList(data) {
  return request({
    url: '/admin/getUrlList',
    method: 'POST',
    data
  })
}


大部分代码跟上篇文章差不多,只引入了两个方法,新增了watch监听方法

v-model ,:value,:label

实现了页面的双向绑定,页面中使用了v-model绑定了一个名为type的变量,然后created生命周期钩子函数中初始化了type为全部这个值。
:是v-bind的缩写,:value:lable是在select 的option循环中用于动态数据绑定。可以在Element-UI官网看到el-select的介绍,value和lable都是select的选项属性:

image.png

watch

用于监控一个值的变换,页面中监控了type,然后根据type的参数提供给getUrlList方法用于更新列表的数据,非常简单

后端实现

路由添加:

最开始使用的是GET方法,发现需要前端传json字符串才行,最后来改成了POST方法

admin.POST("/getUrlList", controller.GetUrlList)

控制器

func GetUrlList(c *gin.Context) {
	var json request.GetUrlListRequest
	if err := c.ShouldBindJSON(&json); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
		return
	}
	result := global.NewResult(c)
	list, err := service.GetUrlList(json)
	if err != nil {
		result.Error(5201, err.Error(), "域名列表获取失败")
		return
	}
	result.Success(list)
}

服务方法

func GetUrlList(json request.GetUrlListRequest) (data interface{}, err error) {

	list, nil := model.GetUrlList(json.Id)
	return list, nil
}

验证器


type GetUrlListRequest struct {
	Id int `form:"id" json:"id"`
}

有一个注意的地方就是验证器,id传0逻辑就是获取全部,但是验证器认为0就是没有传所以这里验证器字段就不能设置为必须,所以就去掉了`binding:"required"``。

模型方法

func GetUrlList(id int) (data interface{}, err error) {
	var list []UrlList
	if id != 0 {
		res := db.Debug().Where("type_id = ?", id).Find(&list)
		return res, nil
	} else {
		res := db.Debug().Find(&list)
		return res, nil
	}

}

id是0就查全部,不是零就查type_list的所有数据。

总结

进的这个带筛选的列表接口真正让我感觉到VUE的简单快捷,使用双向绑定就很简单的解决了数据的重新请求,之前JQuery的时候还需要读取HTML标签属性变量,设置HTML标签属性变量,模板渲染标签属性变量,非常繁琐~,下篇完善一下这个分类下详情数据的增删改。