编辑器创建文章

This commit is contained in:
zkr_liushenlu 2021-04-13 17:49:55 +08:00
parent 59c998e8dd
commit 83e41a300c
8 changed files with 10798 additions and 81 deletions

View File

@ -203,7 +203,7 @@ public class ArticleManageController extends BaseController {
Thread.currentThread().setName(UUID.randomUUID().toString()); Thread.currentThread().setName(UUID.randomUUID().toString());
Message msg = new Message(); Message msg = new Message();
logger.info("通过文章链接获取文章内容控制层方法开始"); logger.info("通过文章链接获取文章内容控制层方法开始");
String createUser = request.getParameter("createUser"); String createUser = "13152783264";
if (StringUtils.isBlank(createUser)) { if (StringUtils.isBlank(createUser)) {
logger.info("用户已离线"); logger.info("用户已离线");
throw new BusinessException("通过文章链接获取文章内容,用户已离线"); throw new BusinessException("通过文章链接获取文章内容,用户已离线");

View File

@ -1,71 +1,29 @@
package com.ruoyi.content.controller; package com.ruoyi.content.controller;
import com.ruoyi.content.message.Message; import com.ruoyi.content.message.Message;
import com.ruoyi.content.service.CmsRoleAuthorityService; import com.ruoyi.content.service.CommonService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody; import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.Enumeration;
import java.util.List;
/** /**
* 说明公共controller * @program: ruoyi->CommonController
* * @description:
* @author wang.q * @author: LiuShenlu
* @date 2017年8月25日 * @create: 2021-04-09 17:26
*/ **/
@Controller @RestController
@RequestMapping("/common")
public class ContentCommonController { public class ContentCommonController {
private static Logger logger = LoggerFactory.getLogger(ContentCommonController.class);
@Autowired @Autowired
private CmsRoleAuthorityService authorityService; private CommonService commonService;
/** @PostMapping("oss")
* 查询访问人的所有菜单权限 public Message upload(@RequestParam("file") MultipartFile file) {
* Message msg = commonService.upload(file);
* @return
*/
@RequestMapping(value = "/menus")
@ResponseBody
public Message menus(HttpServletRequest req, HttpServletResponse res) {
System.out.println("----------menus------------menus-------------menus------menus----------");
Enumeration<String> headerNames = req.getHeaderNames();
while (headerNames.hasMoreElements()) {
//获取每个请求头名称
String headerName = headerNames.nextElement();
//跟距请求头获取请求值
String value = req.getHeader(headerName);
System.out.println(headerName);
System.out.println(value);
}
System.out.println("--------menus----------menus---------menus----------menus------menus--------");
Message msg = new Message();
try {
List<?> list = authorityService.queryUserRole();
if (list != null && list.size() > 0) {
msg.setObject(list);
msg.setResult(true);
} else {
msg.setResult(false);
msg.setInfo("未获取菜单,或您已离线。请重新登录!");
}
} catch (Exception e) {
// TODO: handle exception
msg.setResult(false);
msg.setInfo(e.getMessage());
logger.info("获取菜单失败【{}】", e.getMessage());
e.printStackTrace();
}
return msg; return msg;
} }
} }

View File

@ -0,0 +1,14 @@
package com.ruoyi.content.service;
import com.ruoyi.content.message.Message;
import org.springframework.web.multipart.MultipartFile;
/**
*
* @author liushenlu
*/
public interface CommonService {
Message upload(MultipartFile file);
}

View File

@ -1138,9 +1138,11 @@ public class ArticleServiceImpl implements ArticleService {
LOGGER.info( LOGGER.info(
"根据文章链接获取文章内容,参数createUser[{}],author[{}],ids[{}],isAuthorization[{}],isReserve[{}],automaticName[{}],introduction[{}],isJoinActive[{}]", "根据文章链接获取文章内容,参数createUser[{}],author[{}],ids[{}],isAuthorization[{}],isReserve[{}],automaticName[{}],introduction[{}],isJoinActive[{}]",
createUser, author, ids, isAuthorization, isReserve, automaticName, introduction, isJoinActive); createUser, author, ids, isAuthorization, isReserve, automaticName, introduction, isJoinActive);
CmsSysUser userInfoDTO = (CmsSysUser) SecurityUtils.getSubject().getPrincipal(); //CmsSysUser userInfoDTO = (CmsSysUser) SecurityUtils.getSubject().getPrincipal();
String companyId = userInfoDTO.getCompanyId();// 渠道id //String companyId = userInfoDTO.getCompanyId();// 渠道id
String email = userInfoDTO.getEmail(); //String email = userInfoDTO.getEmail();
String companyId = "1";// 渠道id
String email = "13152783264";
// 根据登录人查询登录信息shiro里有缓存数据不是最新 // 根据登录人查询登录信息shiro里有缓存数据不是最新
CmsSysUser cmsSysUser = cmsSysUserExMapper.queryLoginInfoByEmail(email); CmsSysUser cmsSysUser = cmsSysUserExMapper.queryLoginInfoByEmail(email);
// 此时后台管理员 // 此时后台管理员
@ -1154,7 +1156,7 @@ public class ArticleServiceImpl implements ArticleService {
createTime}); createTime});
ArticleInfo article = new ArticleInfo(); ArticleInfo article = new ArticleInfo();
article.setArticleAuthor(userInfoDTO.getName() + ""); article.setArticleAuthor(cmsSysUser.getName() + "");
article.setArticleName(articleName); article.setArticleName(articleName);
article.setOriginalUrl("0"); article.setOriginalUrl("0");
article.setShareImgUrl(shareImgUrl); article.setShareImgUrl(shareImgUrl);
@ -1203,7 +1205,7 @@ public class ArticleServiceImpl implements ArticleService {
// 存文章和标签的关系 // 存文章和标签的关系
articleLabelServiceImpl.addlabel(String.valueOf(articleId), labelIds); articleLabelServiceImpl.addlabel(String.valueOf(articleId), labelIds);
this.checkJobNumber(articleId, articleName, shareImgUrl, ids, publishId, companyId, jobNumber, userId, this.checkJobNumber(articleId, articleName, shareImgUrl, ids, publishId, companyId, jobNumber, userId,
userInfoDTO.getName() + "", modifiedEditUrl, modifiedViewUrl, versionNumber); cmsSysUser.getName() + "", modifiedEditUrl, modifiedViewUrl, versionNumber);
msg.setInfo("成功导入文章!"); msg.setInfo("成功导入文章!");
msg.setResult(true); msg.setResult(true);
msg.setObject(resultMap); msg.setObject(resultMap);

View File

@ -0,0 +1,57 @@
package com.ruoyi.content.service.impl;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.content.constants.PropertiesConstants;
import com.ruoyi.content.message.Message;
import com.ruoyi.content.service.CommonService;
import com.ruoyi.content.utils.ImgCompress;
import com.ruoyi.content.utils.OSSUtil;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;
import javax.imageio.ImageIO;
import javax.imageio.stream.ImageOutputStream;
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
/**
* @program: ruoyi->CommonServiceImpl
* @description:
* @author: LiuShenlu
* @create: 2021-04-09 17:29
**/
@Service
public class CommonServiceImpl implements CommonService {
@Override
public Message upload(MultipartFile file) {
Message msg = new Message(true, "上传图片成功");
try {
// 文件名
String fileName = file.getOriginalFilename();
// 文件后缀
String ext = fileName.substring(fileName.lastIndexOf("."));
String fileTime = DateUtils.getMillisecond();
// OSS保存路径
fileName = PropertiesConstants.GALLERY_IMG_PATH + fileTime + ext;
String flag = OSSUtil.uploadFileByInputStream(PropertiesConstants.OSSENDPOINT, PropertiesConstants.OSSID, PropertiesConstants.OSSKEY,
PropertiesConstants.BUCKETNAME, file.getInputStream(), PropertiesConstants.OSSPATH + fileName);
if (StringUtils.isBlank(flag) || StringUtils.equals(flag, "false")) {
msg.setInfo("上传图片上传异常");
msg.setResult(false);
} else {
msg.setObject(PropertiesConstants.OSS_URL + PropertiesConstants.OSSPATH + fileName);
}
} catch (IOException e) {
msg.setInfo("上传图片上传异常");
msg.setResult(false);
e.printStackTrace();
}
return msg;
}
}

File diff suppressed because one or more lines are too long

View File

@ -287,10 +287,8 @@
cache: false, cache: false,
success: function (data) { success: function (data) {
if (data.result) { if (data.result) {
const code = { $.modal.alertSuccess("删除成功!");
'code': 0 $.table.search();
};
$.operate.successCallback(code);
} else { } else {
$.modal.alertError(data.info); $.modal.alertError(data.info);
} }

View File

@ -5,11 +5,164 @@
<th:block th:include="include :: layout-latest-css"/> <th:block th:include="include :: layout-latest-css"/>
<th:block th:include="include :: ztree-css"/> <th:block th:include="include :: ztree-css"/>
<th:block th:include="include :: datetimepicker-css"/> <th:block th:include="include :: datetimepicker-css"/>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0,user-scalable=no"/>
<meta name="format-detection" content="telephone=no,email=no">
</head> </head>
<style> <style>
#tree_1_check { #tree_1_check {
display: none; display: none;
} }
.layui-layer-btn0 {
display: none;
}
p {
margin: 0;
padding: 0;
}
#div1 {
margin: 10px auto;
border: 1px solid #ccc;
}
#div1 .title {
width: 100%;
margin: 0 auto;
position: relative;
z-index: 0;
padding: 5px 24px;
border-top: 1px solid #ccc;
box-sizing: border-box;
}
.text {
min-height: 27.43px;
}
.head, .author {
display: block;
width: 100%;
font-size: 20px;
color: #000;
min-height: 30px;
margin-bottom: 5px;
outline: none;
resize: none;
border: none;
}
.head {
font-size: 24px;
}
.head[contenteditable]:empty:before, .author[contenteditable]:empty:before {
content: attr(placeholder);
color: #D4D4D4;
}
.head[contenteditable]:focus, .author[contenteditable]:focus {
content: none;
}
.editorcontent {
font-size: 18px;
line-height: 20px;
height: 370px;
overflow: auto;
padding-top: 10px;
border-top: 1px solid #ccc;
}
.editorcontent div {
min-height: 27.43px;
}
/* 上传图片*/
.abstract {
font-size: .26rem;
margin: 10px 0;
color: #333;
float: left;
}
.cover_abstract {
width: 100%;
display: flex;
}
.imgload {
position: relative;
width: 25%;
text-align: center;
overflow: hidden;
height: 90px;
line-height: 90px;
background-color: #fbfdff;
border: 1px dashed #c0ccda;
border-radius: 6px;
margin: 0 10px;
box-sizing: border-box;
}
.fileImg {
position: absolute;
top: 0;
left: 0;
display: inline-block;
width: 100%;
height: 100%;
background: none;
margin: 0px;
padding: 0px;
opacity: 0;
filter: alpha(opacity=0);
cursor: pointer;
z-index: 2;
}
.avatar {
position: absolute;
top: 0;
left: 0;
display: inline-block;
width: 100%;
height: 100%;
z-index: 1;
}
.addIcon {
position: relative;
top: 0;
left: 0;
display: inline-block;
width: 100%;
height: 100%;
}
.addIcon::before {
content: '';
position: absolute;
left: 50%;
top: 50%;
width: 30px;
margin-left: -15px;
margin-top: -2px;
border-top: 2px solid #cccccc;
}
.addIcon::after {
content: '';
position: absolute;
left: 50%;
top: 50%;
height: 30px;
margin-left: -2px;
margin-top: -15px;
border-left: 2px solid #ccc;
}
</style> </style>
<body class="gray-bg"> <body class="gray-bg">
<div class="container-div"> <div class="container-div">
@ -53,6 +206,9 @@
<i class="fa fa-remove"></i> 批量移除 <i class="fa fa-remove"></i> 批量移除
</a> </a>
<a class="btn btn-success" style="margin-left: 15px;" data-toggle="modal" data-target="#myModal4"> <a class="btn btn-success" style="margin-left: 15px;" data-toggle="modal" data-target="#myModal4">
<i class="fa fa-newspaper-o"></i> 导入文章
</a>
<a class="btn btn-success" style="margin-left: 15px;" onclick="createArticle()">
<i class="fa fa-newspaper-o"></i> 创建文章 <i class="fa fa-newspaper-o"></i> 创建文章
</a> </a>
</div> </div>
@ -187,7 +343,7 @@
<button type="button" class="close" data-dismiss="modal"><span aria-hidden="true">&times;</span><span <button type="button" class="close" data-dismiss="modal"><span aria-hidden="true">&times;</span><span
class="sr-only">Close</span> class="sr-only">Close</span>
</button> </button>
<h5 class="modal-title" style="text-align: left; font-size: 23px;">创建文章</h5> <h5 class="modal-title" style="text-align: left; font-size: 23px;">导入文章</h5>
</div> </div>
<div class="modal-body" style="background: #ffffff;"> <div class="modal-body" style="background: #ffffff;">
<form class="form-horizontal m" id="form-picAdverts-add3"> <form class="form-horizontal m" id="form-picAdverts-add3">
@ -246,21 +402,78 @@
</div> </div>
</div> </div>
</div> </div>
<div class="modal inmodal" id="myModal5" tabindex="-1" role="dialog" aria-hidden="true">
<div class="modal-dialog" style="width: 800px;">
<div class="modal-content animated fadeIn">
<div class="modal-header" style="border-bottom: 0px solid #e5e5e5; padding: 15px 15px;">
<button type="button" class="close" data-dismiss="modal"><span aria-hidden="true">&times;</span><span
class="sr-only">Close</span>
</button>
<h5 class="modal-title" style="text-align: left; font-size: 23px;">创建文章</h5>
</div>
<div class="modal-body" style="background: #ffffff;">
<form class="form-horizontal" id="form-picAdverts-add5">
<div class="col-md-12" style="margin-top: -15px;">
<div class="form-group">
<div id="div1">
<div class="toolbar"></div>
<div class="title">
<div contenteditable="true" class="head" placeholder="请在这里输入标题"></div>
<div contenteditable="true" class="author" placeholder="请输入作者"></div>
<div class="editorcontent" contenteditable="true">
<div></div>
</div>
</div>
</div>
<p class="abstract" style="margin-left: 15px;">封面摘要:</p>
<p class="abstract" style="margin-left: 135px;">分享描述:</p>
<div>
<div class="cover_abstract">
<div class="imgload">
<input type="file" class="fileImg"
accept="image/png,image/gifimage/jpg, image/jpeg"
onchange="uploadOss(this)">
<img src="" class="avatar" style="display:none"/>
<i class="addIcon"></i>
</div>
<textarea autocomplete="off" placeholder="请输入内容" class="el-textarea__inner"
style="min-height: 33px;height: 90px; width: 70%"></textarea>
</div>
</div>
</div>
</div>
</form>
</div>
<div class="modal-footer" style="border-top: 0px solid #e5e5e5;">
<button type="button" class="btn btn-white" data-dismiss="modal" th:id="modalColse">关闭</button>
<button type="button" class="btn btn-primary" th:onclick="createArticleL()">创建文章</button>
</div>
</div>
</div>
</div>
<th:block th:include="include :: footer"/> <th:block th:include="include :: footer"/>
<th:block th:include="include :: layout-latest-js"/> <th:block th:include="include :: layout-latest-js"/>
<th:block th:include="include :: ztree-js"/> <th:block th:include="include :: ztree-js"/>
<th:block th:include="include :: datetimepicker-js"/> <th:block th:include="include :: datetimepicker-js"/>
<link th:href="@{/css/bootstrapValidator.min.css}" rel="stylesheet"/>
<link th:href="@{/css/fileinput.min.css}" rel="stylesheet"/>
<script th:src="@{/js/bootstrapValidator.min.js}"></script>
<script th:src="@{/js/fileinput.min.js}"></script>
<script th:src="@{/js/fileinput_locale_zh.js}"></script>
<script th:src="@{/js/wangEditor.js}"></script>
<script th:inline="javascript"> <script th:inline="javascript">
var path = ctx; let path = ctx;
var prefix = ctx + "article"; let prefix = ctx + "article";
var baseDataList = []; let baseDataList = [];
var baseDataListSecond = []; let baseDataListSecond = [];
var cloumnTree = []; let cloumnTree = [];
var article; let article;
var publish; let publish;
var number; let number;
let filePath;
$(function () { $(function () {
setFirstQuery(); setFirstQuery();
@ -450,8 +663,21 @@
}); });
}); });
}); });
// 富文本的创建
const E = window.wangEditor;
const editor = new E('#div1');
editor.config.onchange = function (newHtml) {
console.log('change 之后最新的 html', newHtml)
console.log($('.editorcontent').html())
}
editor.create();
function queryCnameBySpecialChannel(id, type, num) { function queryCnameBySpecialChannel(id, type, num) {
if (baseDataListSecond == null) { if (baseDataListSecond == null) {
articleTypeInit(type, num); articleTypeInit(type, num);
@ -484,6 +710,142 @@
return returnValue; return returnValue;
} }
function uploadOss(obj) {
$('#myModal5').modal('hide');
$.modal.loading("上传中。。。");
let formData = new FormData();
formData.append('file', obj.files[0]);
$.ajax({
type: "post",
url: '/oss',
data: formData,
processData: false,//不需要对数据进行处理
contentType: false,
cache: false,
dataType: "json",
success: function (data) {
$(".avatar").attr("src", data.object);
filePath = data.object;
$(".avatar").css('display', 'block');
$(".addIcon").css('display', 'none');
$.modal.closeLoading();
$('#myModal5').modal('show');
},
error: function () {
$.modal.closeLoading();
$('#myModal5').modal('show');
}
});
}
function createArticle() {
$('.head').html('');
$('.author').html('');
$('.el-textarea__inner').text('');
$('.editorcontent').html('<div></div>');
filePath = '';
$(".avatar").attr('src', '')
$(".avatar").css('display', 'none');
$(".addIcon").css('display', 'block');
$('#myModal5').modal('show');
}
function createArticleL() {
let title = $('.head').text();
let author = $('.author').text();
let body = $('.editorcontent').html();
if (title == '') {
$.modal.alertWarning("请输入标题");
return;
}
if (author == '') {
$.modal.alertWarning("请输入作者");
return;
}
if (body == '') {
$.modal.alertWarning("请输入文章内容");
return;
}
if (filePath == '') {
$.modal.alertWarning("请上传分享图片");
return;
}
body = '<div id="js_article" class="rich_media"><div class="rich_media_inner">' +
'<div id="page-content" class="rich_media_area_primary">' +
'<div id="img-content" class="rich_media_wrp"><div id="activity-name">' + title + '</div>'
+ '<div id="meta_content">' + author + '</div>' + body + '</div></div></div></div>';
body = body + '<style>table{border-top: 1px solid #ccc;border-left: 1px solid #ccc;}' +
'table td, table th{border-bottom: 1px solid #ccc; border-right: 1px solid #ccc; padding: 3px 5px;}' +
'table th {border-bottom: 2px solid #ccc; text-align: center;}' +
'blockquote{display: block;border-left: 8px solid #d0e5f2;padding: 5px 10px;margin: 10px 0;' +
'line-height: 1.4;font-size: 100%;background-color: #f1f1f1;}' +
'code {display: inline-block;*display: inline;*zoom: 1;background-color: #f1f1f1;' +
'border-radius: 3px;padding: 3px 5px;margin: 0 3px;}' +
'pre code {display: block;}' +
'ul, ol {margin: 10px 0 10px 20px;}</style>'
$('#myModal5').modal('hide');
$.modal.loading("创建文章中请等待。。。");
$.ajax({
url: path + "article/create",
data: {
'author': "",
'createUser': "",
'ids': "",
'isAuthorization': "0",
'isReserve': "0",
'automaticName': "",
'introduction': "",
'labelIds': "",
'isJoinActive': "0",
'articleName': title,
'shareImgUrl': filePath,
'shareDes': $('.el-textarea__inner').text(),
'articleContent': body
},
type: "post",
success: function (data) {
$.modal.closeLoading();
if (data.result) {
$.modal.alertSuccess("创建成功!");
$.table.search();
// localStorage.setItem("nryx_articleContent", data.object.articleContent); // 文章内容
// localStorage.setItem("nryx_originalUrl", data.object.originalUrl); // 文章链接
// // //文章名称
// localStorage.setItem("nryx_articleName", data.object.articleName); // 文章名称
// localStorage.setItem("nryx_shareImgUrl", data.object.shareImgUrl); // 文章分享图片
// // //文章分享标题
// localStorage.setItem("nryx_shareTitle", data.object.shareTitle); // 文章分享标题
// localStorage.setItem("nryx_shareDes", data.object.shareDes); // 文章分享描述
// localStorage.setItem("nryx_listPicUrl", data.object.listPicUrl); // 文章列表展示图片
// localStorage.setItem("nryx_adId", data.object.adId); // 广告id
// localStorage.setItem("nryx_isAuthorization", data.object.isAuthorization); // 是否授权
// localStorage.setItem("nryx_isJoinActive", data.object.isJoinActive); // 是否添加优选活动
// localStorage['nryx_editahref'] = data.object.articleEditUrl;
// $.table.refresh();
// let btn = ['<i class="fa fa-close"></i> 关闭'];
// let options = {
// title: '创建文章',
// url: localStorage['nryx_editahref'],
// btn: btn,
// callBack: closeFrame
// };
// $.modal.openOptions(options);
} else {
$.modal.alertError(data.info)
}
},
error: function () {
$.modal.closeLoading();
}
});
}
/** **查询公共数据** */ /** **查询公共数据** */
function articleTypeInit(type, num) { function articleTypeInit(type, num) {
$.ajax({ $.ajax({
@ -1017,8 +1379,15 @@
cache: false, cache: false,
success: function (data) { success: function (data) {
if (data.result) { if (data.result) {
$.modal.open('文章预览', data.object.editUrl + '?l=1')
let btn = ['<i class="fa fa-close"></i> 关闭'];
let options = {
title: '文章预览',
url: data.object.editUrl + '?l=1',
btn: btn,
callBack: closeFrame
};
$.modal.openOptions(options);
} else { } else {
$.modal.alertError("预览失败,请稍后重试!"); $.modal.alertError("预览失败,请稍后重试!");
} }
@ -1029,6 +1398,10 @@
}); });
} }
function closeFrame(index, layero) {
$.modal.close(index);
}
//广告列表初始化 //广告列表初始化
function advertisementTypeInit() { function advertisementTypeInit() {
$.ajax({ $.ajax({
@ -1164,7 +1537,6 @@
success: function (data) { success: function (data) {
$.modal.closeLoading(); $.modal.closeLoading();
if (data.result) { if (data.result) {
debugger
localStorage.setItem("nryx_articleContent", data.object.articleContent); // 文章内容 localStorage.setItem("nryx_articleContent", data.object.articleContent); // 文章内容
localStorage.setItem("nryx_originalUrl", data.object.originalUrl); // 文章链接 localStorage.setItem("nryx_originalUrl", data.object.originalUrl); // 文章链接
// //文章名称 // //文章名称
@ -1179,7 +1551,14 @@
localStorage.setItem("nryx_isJoinActive", data.object.isJoinActive); // 是否添加优选活动 localStorage.setItem("nryx_isJoinActive", data.object.isJoinActive); // 是否添加优选活动
localStorage['nryx_editahref'] = data.object.articleEditUrl; localStorage['nryx_editahref'] = data.object.articleEditUrl;
$.table.refresh(); $.table.refresh();
$.modal.open('创建文章', localStorage['nryx_editahref']) let btn = ['<i class="fa fa-close"></i> 关闭'];
let options = {
title: '创建文章',
url: localStorage['nryx_editahref'],
btn: btn,
callBack: closeFrame
};
$.modal.openOptions(options);
} else { } else {
$.modal.alertError(data.info) $.modal.alertError(data.info)
} }