修改了对象存储

This commit is contained in:
Machengtianjiang 2020-12-31 09:13:13 +08:00
parent 241de49166
commit ec74a2d3de
16 changed files with 506 additions and 186 deletions

View File

@ -33,6 +33,8 @@
<version>${wx-java.version}</version> <version>${wx-java.version}</version>
</dependency> </dependency>
</dependencies> </dependencies>
</project> </project>

View File

@ -64,14 +64,14 @@ public class WineryGoodsController extends BaseController {
if (StringUtils.isNotBlank(wineryGoods.getGoodsSpec())){ if (StringUtils.isNotBlank(wineryGoods.getGoodsSpec())){
lqw.eq(WineryGoods::getGoodsSpec ,wineryGoods.getGoodsSpec()); lqw.eq(WineryGoods::getGoodsSpec ,wineryGoods.getGoodsSpec());
} }
if (StringUtils.isNotBlank(wineryGoods.getGoodDesc())){ if (StringUtils.isNotBlank(wineryGoods.getGoodsDesc())){
lqw.eq(WineryGoods::getGoodDesc ,wineryGoods.getGoodDesc()); lqw.eq(WineryGoods::getGoodsDesc ,wineryGoods.getGoodsDesc());
} }
if (StringUtils.isNotBlank(wineryGoods.getGoodFaceImg())){ if (StringUtils.isNotBlank(wineryGoods.getGoodsFaceImg())){
lqw.eq(WineryGoods::getGoodFaceImg ,wineryGoods.getGoodFaceImg()); lqw.eq(WineryGoods::getGoodsFaceImg ,wineryGoods.getGoodsFaceImg());
} }
if (StringUtils.isNotBlank(wineryGoods.getGoodImg())){ if (StringUtils.isNotBlank(wineryGoods.getGoodsImg())){
lqw.eq(WineryGoods::getGoodImg ,wineryGoods.getGoodImg()); lqw.eq(WineryGoods::getGoodsImg ,wineryGoods.getGoodsImg());
} }
List<WineryGoods> list = iWineryGoodsService.list(lqw); List<WineryGoods> list = iWineryGoodsService.list(lqw);
return getDataTable(list); return getDataTable(list);

View File

@ -58,15 +58,15 @@ private static final long serialVersionUID=1L;
/** 商品说明 */ /** 商品说明 */
@Excel(name = "商品说明") @Excel(name = "商品说明")
private String goodDesc; private String goodsDesc;
/** 商品封面 */ /** 商品封面 */
@Excel(name = "商品封面") @Excel(name = "商品封面")
private String goodFaceImg; private String goodsFaceImg;
/** 商品图片 */ /** 商品图片 */
@Excel(name = "商品图片") @Excel(name = "商品图片")
private String goodImg; private String goodsImg;
/** 创建者 */ /** 创建者 */
private String createBy; private String createBy;

View File

@ -35,6 +35,7 @@
<mybatis-plus.version>3.4.1</mybatis-plus.version> <mybatis-plus.version>3.4.1</mybatis-plus.version>
<hutool.version>5.4.0</hutool.version> <hutool.version>5.4.0</hutool.version>
<wx-java.version>4.0.0</wx-java.version> <wx-java.version>4.0.0</wx-java.version>
<cos-java.version>5.6.34</cos-java.version>
</properties> </properties>
<!-- 依赖声明 --> <!-- 依赖声明 -->

View File

@ -2,12 +2,15 @@ package com.ruoyi.web.controller.common;
import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpServletResponse;
import com.ruoyi.common.utils.file.CosUtils;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType; import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController; import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile; import org.springframework.web.multipart.MultipartFile;
import com.ruoyi.common.config.RuoYiConfig; import com.ruoyi.common.config.RuoYiConfig;
@ -20,30 +23,30 @@ import com.ruoyi.framework.config.ServerConfig;
/** /**
* 通用请求处理 * 通用请求处理
* *
* @author ruoyi * @author ruoyi
*/ */
@RestController @RestController
public class CommonController public class CommonController {
{
private static final Logger log = LoggerFactory.getLogger(CommonController.class); private static final Logger log = LoggerFactory.getLogger(CommonController.class);
@Autowired @Autowired
private ServerConfig serverConfig; private ServerConfig serverConfig;
@Autowired
private CosUtils cosUtils;
/** /**
* 通用下载请求 * 通用下载请求
* *
* @param fileName 文件名称 * @param fileName 文件名称
* @param delete 是否删除 * @param delete 是否删除
*/ */
@GetMapping("common/download") @GetMapping("common/download")
public void fileDownload(String fileName, Boolean delete, HttpServletResponse response, HttpServletRequest request) public void fileDownload(String fileName, Boolean delete, HttpServletResponse response, HttpServletRequest request) {
{ try {
try if (!FileUtils.checkAllowDownload(fileName)) {
{
if (!FileUtils.checkAllowDownload(fileName))
{
throw new Exception(StringUtils.format("文件名称({})非法,不允许下载。 ", fileName)); throw new Exception(StringUtils.format("文件名称({})非法,不允许下载。 ", fileName));
} }
String realFileName = System.currentTimeMillis() + fileName.substring(fileName.indexOf("_") + 1); String realFileName = System.currentTimeMillis() + fileName.substring(fileName.indexOf("_") + 1);
@ -52,13 +55,10 @@ public class CommonController
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE);
FileUtils.setAttachmentResponseHeader(response, realFileName); FileUtils.setAttachmentResponseHeader(response, realFileName);
FileUtils.writeBytes(filePath, response.getOutputStream()); FileUtils.writeBytes(filePath, response.getOutputStream());
if (delete) if (delete) {
{
FileUtils.deleteFile(filePath); FileUtils.deleteFile(filePath);
} }
} } catch (Exception e) {
catch (Exception e)
{
log.error("下载文件失败", e); log.error("下载文件失败", e);
} }
} }
@ -67,37 +67,44 @@ public class CommonController
* 通用上传请求 * 通用上传请求
*/ */
@PostMapping("/common/upload") @PostMapping("/common/upload")
public AjaxResult uploadFile(MultipartFile file) throws Exception public AjaxResult uploadFile(MultipartFile file) throws Exception {
{ try {
try
{
// 上传文件路径 // 上传文件路径
String filePath = RuoYiConfig.getUploadPath(); // String filePath = RuoYiConfig.getUploadPath();
// 上传并返回新文件名称 // 上传并返回新文件名称
String fileName = FileUploadUtils.upload(filePath, file); // String fileName = FileUploadUtils.upload(filePath, file);
String url = serverConfig.getUrl() + fileName;
String fileName = cosUtils.upload(file);
String url = serverConfig.getUrl() + "/common/file?fileName=" + fileName;
AjaxResult ajax = AjaxResult.success(); AjaxResult ajax = AjaxResult.success();
ajax.put("fileName", fileName); ajax.put("fileName", fileName);
ajax.put("url", url); ajax.put("url", url);
return ajax; return ajax;
} } catch (Exception e) {
catch (Exception e)
{
return AjaxResult.error(e.getMessage()); return AjaxResult.error(e.getMessage());
} }
} }
/**
* 通用文件获取请求
*/
@GetMapping("/common/file")
public void uploadFile(@RequestParam(required = true) String fileName, HttpServletResponse response) throws Exception {
cosUtils.getFile(fileName, response);
}
/** /**
* 本地资源通用下载 * 本地资源通用下载
*/ */
@GetMapping("/common/download/resource") @GetMapping("/common/download/resource")
public void resourceDownload(String resource, HttpServletRequest request, HttpServletResponse response) public void resourceDownload(String resource, HttpServletRequest request, HttpServletResponse response)
throws Exception throws Exception {
{ try {
try if (!FileUtils.checkAllowDownload(resource)) {
{
if (!FileUtils.checkAllowDownload(resource))
{
throw new Exception(StringUtils.format("资源文件({})非法,不允许下载。 ", resource)); throw new Exception(StringUtils.format("资源文件({})非法,不允许下载。 ", resource));
} }
// 本地资源路径 // 本地资源路径
@ -109,9 +116,7 @@ public class CommonController
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE);
FileUtils.setAttachmentResponseHeader(response, downloadName); FileUtils.setAttachmentResponseHeader(response, downloadName);
FileUtils.writeBytes(downloadPath, response.getOutputStream()); FileUtils.writeBytes(downloadPath, response.getOutputStream());
} } catch (Exception e) {
catch (Exception e)
{
log.error("下载文件失败", e); log.error("下载文件失败", e);
} }
} }

View File

@ -1,6 +1,9 @@
package com.ruoyi.web.controller.system; package com.ruoyi.web.controller.system;
import java.io.IOException; import java.io.IOException;
import com.ruoyi.common.utils.file.CosUtils;
import com.ruoyi.framework.config.ServerConfig;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.PostMapping;
@ -38,6 +41,13 @@ public class SysProfileController extends BaseController
@Autowired @Autowired
private TokenService tokenService; private TokenService tokenService;
@Autowired
private CosUtils cosUtils;
@Autowired
private ServerConfig serverConfig;
/** /**
* 个人信息 * 个人信息
*/ */
@ -111,7 +121,11 @@ public class SysProfileController extends BaseController
if (!file.isEmpty()) if (!file.isEmpty())
{ {
LoginUser loginUser = tokenService.getLoginUser(ServletUtils.getRequest()); LoginUser loginUser = tokenService.getLoginUser(ServletUtils.getRequest());
String avatar = FileUploadUtils.upload(RuoYiConfig.getAvatarPath(), file);
String fileName = cosUtils.upload(file);
String avatar = "/common/file?fileName=" + fileName;
// String avatar = FileUploadUtils.upload(RuoYiConfig.getAvatarPath(), file);
if (userService.updateUserAvatar(loginUser.getUsername(), avatar)) if (userService.updateUserAvatar(loginUser.getUsername(), avatar))
{ {
AjaxResult ajax = AjaxResult.success(); AjaxResult ajax = AjaxResult.success();

View File

@ -78,8 +78,9 @@ token:
# 令牌密钥 # 令牌密钥
secret: abcdefghijklmnopqrstuvwxyz secret: abcdefghijklmnopqrstuvwxyz
# 令牌有效期默认30分钟 # 令牌有效期默认30分钟
expireTime: 30 # expireTime: 30
expireTime: 300
# MyBatis配置 # MyBatis配置
# https://baomidou.com/config/ # https://baomidou.com/config/
mybatis-plus: mybatis-plus:

View File

@ -136,6 +136,14 @@
<artifactId>lombok</artifactId> <artifactId>lombok</artifactId>
</dependency> </dependency>
<!-- 对象存储 -->
<dependency>
<groupId>com.qcloud</groupId>
<artifactId>cos_api</artifactId>
<version>${cos-java.version}</version>
</dependency>
</dependencies> </dependencies>
</project> </project>

View File

@ -0,0 +1,39 @@
package com.ruoyi.common.config;
import com.qcloud.cos.COSClient;
import com.qcloud.cos.ClientConfig;
import com.qcloud.cos.auth.BasicCOSCredentials;
import com.qcloud.cos.auth.COSCredentials;
import com.qcloud.cos.region.Region;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
/**
* @author tottimctj
* @since 2020-12-28
*/
@Configuration
public class CosConfig {
@Bean(name = "cosCredentials")
public COSCredentials cosCredentials() {
// 1 初始化用户身份信息secretId, secretKey
String secretId = "AKIDovztW8x0DpQnunSw2uXUDhw3IH0fQC75";
String secretKey = "rCH8tOfjX5XjegYBXfkZWc2E75nJq9Dx";
COSCredentials cred = new BasicCOSCredentials(secretId, secretKey);
return cred;
}
@Bean(name = "cosClientConfig")
public ClientConfig cosClientConfig() {
// 2 设置 bucket 的区域, COS 地域的简称请参照 https://cloud.tencent.com/document/product/436/6224
// clientConfig 中包含了设置 region, https(默认 http), 超时, 代理等 set 方法, 使用可参见源码或者常见问题 Java SDK 部分
Region region = new Region("ap-beijing");
ClientConfig clientConfig = new ClientConfig(region);
return clientConfig;
}
}

View File

@ -0,0 +1,108 @@
package com.ruoyi.common.utils.file;
import cn.hutool.core.util.ReUtil;
import cn.hutool.core.util.StrUtil;
import com.qcloud.cos.COSClient;
import com.qcloud.cos.ClientConfig;
import com.qcloud.cos.auth.COSCredentials;
import com.qcloud.cos.model.*;
import com.qcloud.cos.transfer.Download;
import com.ruoyi.common.utils.uuid.UUID;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Objects;
import java.util.Optional;
import static cn.hutool.core.util.IdUtil.fastSimpleUUID;
/**
* @author tottimctj
* @since 2020-12-28
*/
@Component
public class CosUtils {
@Autowired
COSCredentials cosCredentials;
@Autowired
ClientConfig clientConfig;
// 指定要上传到的存储桶
final String bucketName = "winery-1257413599";
String SPECIAL_CHARACTERS = "[`~! @#$%^&*()+=|{}':;',//[//]<>/?~@#¥%……&*_——+|{}【】‘;:”“’。,、?]";
public String upload(MultipartFile file) {
// 指定要上传到 COS 上对象键
String key = ReUtil.replaceAll(StrUtil.trim(fastSimpleUUID() + Optional.of(file.getOriginalFilename()).orElse(StrUtil.EMPTY)), SPECIAL_CHARACTERS, StrUtil.EMPTY);
// 生成 cos 客户端
COSClient cosClient = new COSClient(cosCredentials, clientConfig);
ObjectMetadata metadata = new ObjectMetadata();
metadata.setContentType(file.getContentType());
metadata.setContentLength(file.getSize());
file.getContentType();
try {
PutObjectResult putObjectResult = cosClient.putObject(bucketName, key, file.getInputStream(), metadata);
file.getInputStream().close();
} catch (IOException e) {
e.printStackTrace();
} finally {
cosClient.shutdown();
}
return key;
}
public void getFile(String fileName, HttpServletResponse response) {
COSClient cosClient = new COSClient(cosCredentials, clientConfig);
GetObjectRequest getObjectRequest = new GetObjectRequest(bucketName, fileName);
// 限流使用的单位是bit/s, 这里设置下载带宽限制为 10MB/s
getObjectRequest.setTrafficLimit(80 * 1024 * 1024);
COSObject cosObject = cosClient.getObject(getObjectRequest);
response.setContentType(cosObject.getObjectMetadata().getContentType());
response.setContentLengthLong(cosObject.getObjectMetadata().getContentLength());
OutputStream os = null;
try {
os = response.getOutputStream();
while (true) {
int line = cosObject.getObjectContent().read();
if (line == -1) {
break;
} else {
os.write(line);
}
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
// 关闭输入流
cosClient.shutdown();
}
}

View File

@ -19,15 +19,15 @@
<!-- BEGIN 如果想使用 Tomcat 注释掉以下代码 --> <!-- BEGIN 如果想使用 Tomcat 注释掉以下代码 -->
<!-- SpringBoot Web容器 --> <!-- SpringBoot Web容器 -->
<dependency> <dependency>
<groupId>org.springframework.boot</groupId> <groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId> <artifactId>spring-boot-starter-web</artifactId>
<exclusions> <exclusions>
<exclusion> <exclusion>
<artifactId>spring-boot-starter-tomcat</artifactId> <artifactId>spring-boot-starter-tomcat</artifactId>
<groupId>org.springframework.boot</groupId> <groupId>org.springframework.boot</groupId>
</exclusion> </exclusion>
</exclusions> </exclusions>
</dependency> </dependency>
<!-- web 容器使用 undertow 性能更强 --> <!-- web 容器使用 undertow 性能更强 -->
<dependency> <dependency>
@ -37,10 +37,10 @@
<!-- END --> <!-- END -->
<!-- BEGIN 如果想使用 Tomcat 解除以下代码注释 --> <!-- BEGIN 如果想使用 Tomcat 解除以下代码注释 -->
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>org.springframework.boot</groupId>--> <!-- <groupId>org.springframework.boot</groupId>-->
<!-- <artifactId>spring-boot-starter-web</artifactId>--> <!-- <artifactId>spring-boot-starter-web</artifactId>-->
<!-- </dependency>--> <!-- </dependency>-->
<!-- END --> <!-- END -->
<!-- SpringBoot 拦截器 --> <!-- SpringBoot 拦截器 -->
@ -79,6 +79,7 @@
<artifactId>ruoyi-system</artifactId> <artifactId>ruoyi-system</artifactId>
</dependency> </dependency>
</dependencies> </dependencies>
</project> </project>

View File

@ -107,6 +107,7 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter
).permitAll() ).permitAll()
.antMatchers("/profile/**").anonymous() .antMatchers("/profile/**").anonymous()
.antMatchers("/common/download**").anonymous() .antMatchers("/common/download**").anonymous()
.antMatchers("/common/file**").anonymous()
.antMatchers("/common/download/resource**").anonymous() .antMatchers("/common/download/resource**").anonymous()
.antMatchers("/swagger-ui.html").anonymous() .antMatchers("/swagger-ui.html").anonymous()
.antMatchers("/swagger-resources/**").anonymous() .antMatchers("/swagger-resources/**").anonymous()

View File

@ -1,68 +1,74 @@
<template> <template>
<div class="component-upload-image"> <div class="component-upload-image">
<el-upload <el-upload
:action="uploadImgUrl" :action="uploadImgUrl"
list-type="picture-card" accept="image/*"
:on-success="handleUploadSuccess" list-type="picture-card"
:before-upload="handleBeforeUpload" :on-success="handleUploadSuccess"
:on-error="handleUploadError" :before-upload="handleBeforeUpload"
name="file" :on-error="handleUploadError"
:show-file-list="false" :on-remove="handleRemove"
:headers="headers" name="file"
style="display: inline-block; vertical-align: top" :show-file-list="false"
> :headers="headers"
<img v-if="value" :src="value" class="avatar" /> style="display: inline-block; vertical-align: top"
<i v-else class="el-icon-plus avatar-uploader-icon"></i> >
</el-upload> <img v-if="value" :src="value" class="avatar" />
</div> <i v-else class="el-icon-plus avatar-uploader-icon"></i>
</template> </el-upload>
</div>
<script> </template>
import { getToken } from "@/utils/auth";
<script>
export default { import { getToken } from "@/utils/auth";
components: {},
data() { export default {
return { components: {},
uploadImgUrl: process.env.VUE_APP_BASE_API + "/common/upload", // data() {
headers: { return {
Authorization: "Bearer " + getToken(), uploadImgUrl: process.env.VUE_APP_BASE_API + "/common/upload", //
}, headers: {
}; Authorization: "Bearer " + getToken(),
}, },
props: { };
value: { },
type: String, props: {
default: "", value: {
}, type: String,
}, default: "",
methods: { },
handleUploadSuccess(res) { },
this.$emit("input", res.url); methods: {
this.loading.close(); handleUploadSuccess(res) {
}, this.$emit("input", res.url);
handleBeforeUpload() { this.loading.close();
this.loading = this.$loading({ },
lock: true, handleBeforeUpload() {
text: "上传中", this.loading = this.$loading({
background: "rgba(0, 0, 0, 0.7)", lock: true,
}); text: "上传中",
}, background: "rgba(0, 0, 0, 0.7)",
handleUploadError() { });
this.$message({ },
type: "error", handleUploadError() {
message: "上传失败", this.$message({
}); type: "error",
this.loading.close(); message: "上传失败",
}, });
}, this.loading.close();
watch: {}, },
}; handleRemove(file, fileList) {
</script> console.log(file, fileList);
this.$emit("input", '');
<style scoped lang="scss"> },
.avatar { },
width: 100%; watch: {},
height: 100%; };
} </script>
</style>
<style scoped lang="scss">
.avatar {
width: 100%;
height: 100%;
}
</style>

View File

@ -0,0 +1,105 @@
<template>
<div class="component-upload-image">
<!-- <el-upload-->
<!-- :action="uploadImgUrl"-->
<!-- list-type="picture-card"-->
<!-- :on-success="handleUploadSuccess"-->
<!-- :before-upload="handleBeforeUpload"-->
<!-- :on-error="handleUploadError"-->
<!-- name="file"-->
<!-- :show-file-list="false"-->
<!-- :headers="headers"-->
<!-- style="display: inline-block; vertical-align: top"-->
<!-- >-->
<!-- <img v-if="value" :src="value| image" class="avatar"/>-->
<!-- <i v-else class="el-icon-plus avatar-uploader-icon"></i>-->
<!-- </el-upload>-->
<el-upload
class="upload-demo"
accept="image/*"
:action="uploadImgUrl"
:headers="headers"
:on-success="handleUploadSuccess"
:before-upload="handleBeforeUpload"
:on-error="handleUploadError"
:on-preview="handlePreview"
:on-remove="handleRemove"
name="file"
:file-list="fileList"
list-type="picture">
<el-button size="small" type="primary">点击上传</el-button>
<div slot="tip" class="el-upload__tip">只能上传jpg/png文件且不超过500kb</div>
</el-upload>
</div>
</template>
<script>
import {getToken} from "@/utils/auth";
export default {
components: {},
data() {
return {
uploadImgUrl: process.env.VUE_APP_BASE_API + "/common/upload", //
headers: {
Authorization: "Bearer " + getToken(),
},
};
},
props: {
value: {
type: String,
default: "",
},
},
filters: {
image(value) {
return process.env.VUE_APP_BASE_API + "/common/file?fileName=" + value
}
},
computed: {
fileList() {
return this.value.split(',').map(x => {
return process.env.VUE_APP_BASE_API + "/common/file?fileName=" + x
})
}
},
methods: {
handleUploadSuccess(res) {
this.$emit("input", res.fileName);
this.loading.close();
},
handleBeforeUpload() {
this.loading = this.$loading({
lock: true,
text: "上传中",
background: "rgba(0, 0, 0, 0.7)",
});
},
handleUploadError() {
this.$message({
type: "error",
message: "上传失败",
});
this.loading.close();
},
handleRemove(file, fileList) {
console.log(file, fileList);
},
handlePreview(file) {
console.log(file);
}
},
watch: {},
};
</script>
<style scoped lang="scss">
.avatar {
width: 100%;
height: 100%;
}
</style>

View File

@ -98,7 +98,8 @@ export function selectDictLabels(datas, value, separator) {
// 通用下载方法 // 通用下载方法
export function download(fileName) { export function download(fileName) {
window.location.href = baseURL + "/common/download?fileName=" + encodeURI(fileName) + "&delete=" + true; // window.location.href = baseURL + "/common/download?fileName=" + encodeURI(fileName) + "&delete=" + true;
window.location.href = baseURL + "/common/file?fileName=" + encodeURI(fileName)
} }
// 字符串格式化(%s ) // 字符串格式化(%s )

View File

@ -21,21 +21,21 @@
</el-form-item> </el-form-item>
<el-form-item label="商品类型" prop="goodsType"> <el-form-item label="商品类型" prop="goodsType">
<el-select v-model="queryParams.goodsType" placeholder="请选择商品类型" clearable size="small"> <el-select v-model="queryParams.goodsType" placeholder="请选择商品类型" clearable size="small">
<el-option label="请选择字典生成" value="" /> <el-option label="请选择字典生成" value=""/>
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="商品说明" prop="goodDesc"> <el-form-item label="商品说明" prop="goodsDesc">
<el-input <el-input
v-model="queryParams.goodDesc" v-model="queryParams.goodsDesc"
placeholder="请输入商品说明" placeholder="请输入商品说明"
clearable clearable
size="small" size="small"
@keyup.enter.native="handleQuery" @keyup.enter.native="handleQuery"
/> />
</el-form-item> </el-form-item>
<el-form-item label="商品封面" prop="goodFaceImg"> <el-form-item label="商品封面" prop="goodsFaceImg">
<el-input <el-input
v-model="queryParams.goodFaceImg" v-model="queryParams.goodsFaceImg"
placeholder="请输入商品封面" placeholder="请输入商品封面"
clearable clearable
size="small" size="small"
@ -56,7 +56,8 @@
size="mini" size="mini"
@click="handleAdd" @click="handleAdd"
v-hasPermi="['winery:winery_goods:add']" v-hasPermi="['winery:winery_goods:add']"
>新增</el-button> >新增
</el-button>
</el-col> </el-col>
<el-col :span="1.5"> <el-col :span="1.5">
<el-button <el-button
@ -66,7 +67,8 @@
:disabled="single" :disabled="single"
@click="handleUpdate" @click="handleUpdate"
v-hasPermi="['winery:winery_goods:edit']" v-hasPermi="['winery:winery_goods:edit']"
>修改</el-button> >修改
</el-button>
</el-col> </el-col>
<el-col :span="1.5"> <el-col :span="1.5">
<el-button <el-button
@ -76,7 +78,8 @@
:disabled="multiple" :disabled="multiple"
@click="handleDelete" @click="handleDelete"
v-hasPermi="['winery:winery_goods:remove']" v-hasPermi="['winery:winery_goods:remove']"
>删除</el-button> >删除
</el-button>
</el-col> </el-col>
<el-col :span="1.5"> <el-col :span="1.5">
<el-button <el-button
@ -85,22 +88,23 @@
size="mini" size="mini"
@click="handleExport" @click="handleExport"
v-hasPermi="['winery:winery_goods:export']" v-hasPermi="['winery:winery_goods:export']"
>导出</el-button> >导出
</el-button>
</el-col> </el-col>
<right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar> <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
</el-row> </el-row>
<el-table v-loading="loading" :data="winery_goodsList" @selection-change="handleSelectionChange"> <el-table v-loading="loading" :data="winery_goodsList" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="55" align="center" /> <el-table-column type="selection" width="55" align="center"/>
<el-table-column label="商品ID" align="center" prop="id" v-if="false"/> <el-table-column label="商品ID" align="center" prop="id" v-if="false"/>
<el-table-column label="商品名称" align="center" prop="goodsName" /> <el-table-column label="商品名称" align="center" prop="goodsName"/>
<el-table-column label="商品简称" align="center" prop="goodsAlias" /> <el-table-column label="商品简称" align="center" prop="goodsAlias"/>
<el-table-column label="商品类型" align="center" prop="goodsType" /> <el-table-column label="商品类型" align="center" prop="goodsType"/>
<el-table-column label="关联规格" align="center" prop="goodsSpec" /> <el-table-column label="关联规格" align="center" prop="goodsSpec"/>
<el-table-column label="商品说明" align="center" prop="goodDesc" /> <el-table-column label="商品说明" align="center" prop="goodsDesc"/>
<el-table-column label="商品封面" align="center" prop="goodFaceImg" /> <el-table-column label="商品封面" align="center" prop="goodsFaceImg"/>
<el-table-column label="商品图片" align="center" prop="goodImg" /> <el-table-column label="商品图片" align="center" prop="goodsImg"/>
<el-table-column label="备注" align="center" prop="remark" /> <el-table-column label="备注" align="center" prop="remark"/>
<el-table-column label="操作" align="center" class-name="small-padding fixed-width"> <el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template slot-scope="scope"> <template slot-scope="scope">
<el-button <el-button
@ -109,14 +113,16 @@
icon="el-icon-edit" icon="el-icon-edit"
@click="handleUpdate(scope.row)" @click="handleUpdate(scope.row)"
v-hasPermi="['winery:winery_goods:edit']" v-hasPermi="['winery:winery_goods:edit']"
>修改</el-button> >修改
</el-button>
<el-button <el-button
size="mini" size="mini"
type="text" type="text"
icon="el-icon-delete" icon="el-icon-delete"
@click="handleDelete(scope.row)" @click="handleDelete(scope.row)"
v-hasPermi="['winery:winery_goods:remove']" v-hasPermi="['winery:winery_goods:remove']"
>删除</el-button> >删除
</el-button>
</template> </template>
</el-table-column> </el-table-column>
</el-table> </el-table>
@ -134,30 +140,34 @@
<el-form ref="form" :model="form" :rules="rules" label-width="80px"> <el-form ref="form" :model="form" :rules="rules" label-width="80px">
<el-form-item label="商品名称" prop="goodsName"> <el-form-item label="商品名称" prop="goodsName">
<el-input v-model="form.goodsName" placeholder="请输入商品名称" /> <el-input v-model="form.goodsName" placeholder="请输入商品名称"/>
</el-form-item> </el-form-item>
<el-form-item label="商品简称" prop="goodsAlias"> <el-form-item label="商品简称" prop="goodsAlias">
<el-input v-model="form.goodsAlias" placeholder="请输入商品简称" /> <el-input v-model="form.goodsAlias" placeholder="请输入商品简称"/>
</el-form-item> </el-form-item>
<el-form-item label="商品类型" prop="goodsType"> <el-form-item label="商品类型" prop="goodsType">
<el-select v-model="form.goodsType" placeholder="请选择商品类型"> <el-select v-model="form.goodsType" placeholder="请选择商品类型">
<el-option label="请选择字典生成" value="" /> <el-option label="请选择字典生成" value=""/>
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="关联规格" prop="goodsSpec"> <el-form-item label="关联规格" prop="goodsSpec">
<el-input v-model="form.goodsSpec" type="textarea" placeholder="请输入内容" /> <el-input v-model="form.goodsSpec" type="textarea" placeholder="请输入内容"/>
</el-form-item> </el-form-item>
<el-form-item label="商品说明" prop="goodDesc"> <el-form-item label="商品说明" prop="goodsDesc">
<el-input v-model="form.goodDesc" placeholder="请输入商品说明" /> <el-input v-model="form.goodsDesc" placeholder="请输入商品说明"/>
</el-form-item> </el-form-item>
<el-form-item label="商品封面" prop="goodFaceImg"> <el-form-item label="商品封面" prop="goodsFaceImg">
<el-input v-model="form.goodFaceImg" placeholder="请输入商品封面" />
<upload-image :value="form.goodsFaceImg" @input="inputGoodsFaceImg"/>
<!-- <el-input v-model="form.goodsFaceImg" placeholder="请输入商品封面" />-->
</el-form-item> </el-form-item>
<el-form-item label="商品图片" prop="goodImg"> <el-form-item label="商品图片" prop="goodsImg">
<el-input v-model="form.goodImg" placeholder="请输入商品图片" /> <upload-image-multiple :value="form.goodsImg" @input="inputGoodsImg"/>
<!-- <el-input v-model="form.goodsImg" placeholder="请输入商品图片"/>-->
</el-form-item> </el-form-item>
<el-form-item label="备注" prop="remark"> <el-form-item label="备注" prop="remark">
<el-input v-model="form.remark" type="textarea" placeholder="请输入内容" /> <el-input v-model="form.remark" type="textarea" placeholder="请输入内容"/>
</el-form-item> </el-form-item>
</el-form> </el-form>
<div slot="footer" class="dialog-footer"> <div slot="footer" class="dialog-footer">
@ -169,12 +179,24 @@
</template> </template>
<script> <script>
import { listWinery_goods, getWinery_goods, delWinery_goods, addWinery_goods, updateWinery_goods, exportWinery_goods } from "@/api/winery/winery_goods"; import {
listWinery_goods,
getWinery_goods,
delWinery_goods,
addWinery_goods,
updateWinery_goods,
exportWinery_goods
} from "@/api/winery/winery_goods";
import UploadImage from '@/components/UploadImage/index'
import UploadImageMultiple from '@/components/UploadImageMultiple/index'
export default { export default {
name: "Winery_goods", name: "Winery_goods",
components: { components: {
UploadImage,
UploadImageMultiple,
}, },
computed: {},
data() { data() {
return { return {
// //
@ -203,21 +225,27 @@ export default {
goodsAlias: undefined, goodsAlias: undefined,
goodsType: undefined, goodsType: undefined,
goodsSpec: undefined, goodsSpec: undefined,
goodDesc: undefined, goodsDesc: undefined,
goodFaceImg: undefined, goodsFaceImg: undefined,
goodImg: undefined, goodsImg: undefined,
}, },
// //
form: {}, form: {},
// //
rules: { rules: {}
}
}; };
}, },
created() { created() {
this.getList(); this.getList();
}, },
methods: { methods: {
inputGoodsFaceImg(fileName) {
this.form.goodsFaceImg = fileName
},
inputGoodsImg(fileName) {
this.form.goodsImg = fileName
},
/** 查询商品信息列表 */ /** 查询商品信息列表 */
getList() { getList() {
this.loading = true; this.loading = true;
@ -240,9 +268,9 @@ export default {
goodsAlias: undefined, goodsAlias: undefined,
goodsType: undefined, goodsType: undefined,
goodsSpec: undefined, goodsSpec: undefined,
goodDesc: undefined, goodsDesc: undefined,
goodFaceImg: undefined, goodsFaceImg: undefined,
goodImg: undefined, goodsImg: undefined,
createBy: undefined, createBy: undefined,
createTime: undefined, createTime: undefined,
updateBy: undefined, updateBy: undefined,
@ -264,7 +292,7 @@ export default {
// //
handleSelectionChange(selection) { handleSelectionChange(selection) {
this.ids = selection.map(item => item.id) this.ids = selection.map(item => item.id)
this.single = selection.length!==1 this.single = selection.length !== 1
this.multiple = !selection.length this.multiple = !selection.length
}, },
/** 新增按钮操作 */ /** 新增按钮操作 */
@ -307,28 +335,28 @@ export default {
handleDelete(row) { handleDelete(row) {
const ids = row.id || this.ids; const ids = row.id || this.ids;
this.$confirm('是否确认删除商品信息编号为"' + ids + '"的数据项?', "警告", { this.$confirm('是否确认删除商品信息编号为"' + ids + '"的数据项?', "警告", {
confirmButtonText: "确定", confirmButtonText: "确定",
cancelButtonText: "取消", cancelButtonText: "取消",
type: "warning" type: "warning"
}).then(function() { }).then(function () {
return delWinery_goods(ids); return delWinery_goods(ids);
}).then(() => { }).then(() => {
this.getList(); this.getList();
this.msgSuccess("删除成功"); this.msgSuccess("删除成功");
}) })
}, },
/** 导出按钮操作 */ /** 导出按钮操作 */
handleExport() { handleExport() {
const queryParams = this.queryParams; const queryParams = this.queryParams;
this.$confirm('是否确认导出所有商品信息数据项?', "警告", { this.$confirm('是否确认导出所有商品信息数据项?', "警告", {
confirmButtonText: "确定", confirmButtonText: "确定",
cancelButtonText: "取消", cancelButtonText: "取消",
type: "warning" type: "warning"
}).then(function() { }).then(function () {
return exportWinery_goods(queryParams); return exportWinery_goods(queryParams);
}).then(response => { }).then(response => {
this.download(response.msg); this.download(response.msg);
}) })
} }
} }
}; };