👽 细节修复

pull/5/head
RYAN0UP_ 2018-05-05 01:01:34 +08:00
parent 767fa132b6
commit 75caa32785
99 changed files with 1124 additions and 968 deletions

View File

@ -1,61 +0,0 @@
# Halo界面预览
## 安装页
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-install.png)
## 后台登录
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-login.png)
## 后台首页
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-index.png)
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-index-2.png)
## 文章列表
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-posts.png)
## 文章编辑
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-edit.png)
## 标签列表
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-tags.png)
## 预设页面
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-pages.png)
## 附件页面
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-attach.png)
## 评论管理
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-comments.png)
## 菜单管理
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-menus.png)
## 系统设置
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-options.png)
## 主题管理
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-themes.png)
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-admin-themes-options.png)
## Material主题(感谢[Viosey](https://viosey.com))
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-index-material.png)
## Anatole主题(感谢[Caicai](https://www.caicai.me/))
![](https://cdn.ryanc.cc/img/github/halo-blog/halo-index-anatole.png)

View File

@ -42,13 +42,13 @@ Let's start: http://localhost:8090
## Demo 演示
[界面预览](PREVIEW.md)
[界面预览](https://halo-doc.ryanc.cc/preview)
[Ryan0up'S Blog](https://ryanc.cc)
[SNAIL BLOG](https://slogc.cc)
[宋浩志博客](http://songhaozhi.com/)
[宋浩志博客](http://songhaozhi.com)
## Download 下载

View File

@ -66,14 +66,13 @@
</dependency>
<!-- mysql-->
<!--
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
-->
<!-- H2Database -->
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>

View File

@ -16,7 +16,6 @@ import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
* @author : RYAN0UP
* @date : 2018/1/2
* @version : 1.0
* description:
*/
@Slf4j
@Configuration

View File

@ -20,7 +20,6 @@ import java.util.Map;
* @author : RYAN0UP
* @date : 2017/12/22
* @version : 1.0
* description: Springboot
*/
@Slf4j
@Configuration

View File

@ -0,0 +1,33 @@
package cc.ryanc.halo.config;
import cc.ryanc.halo.security.XssFilter;
import com.google.common.collect.Maps;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.Map;
/**
* @author : RYAN0UP
* @version : 1.0
* @date : 2018/5/4
*/
@Configuration
public class XssConfig {
@Bean
public FilterRegistrationBean xssFilterRegistrationBean() {
FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean();
filterRegistrationBean.setFilter(new XssFilter());
filterRegistrationBean.setOrder(1);
filterRegistrationBean.setEnabled(true);
filterRegistrationBean.addUrlPatterns("/*");
Map<String, String> initParameters = Maps.newHashMap();
//后台不做拦截请求
initParameters.put("excludes", "/admin/*");
initParameters.put("isIncludeRichText", "true");
filterRegistrationBean.setInitParameters(initParameters);
return filterRegistrationBean;
}
}

View File

@ -11,9 +11,8 @@ import java.util.Date;
/**
* @author : RYAN0UP
* @date : 2018/1/10
* @version : 1.0
* description :
* @date : 2018/1/10
*/
@Data
@Entity

View File

@ -10,9 +10,8 @@ import java.util.List;
/**
* @author : RYAN0UP
* @date : 2017/11/30
* @version : 1.0
* description :
* @date : 2017/11/30
*/
@Data
@Entity

View File

@ -10,7 +10,6 @@ import java.util.Date;
* @author : RYAN0UP
* @date : 2018/1/22
* @version : 1.0
* description :
*/
@Data
@Entity

View File

@ -7,15 +7,12 @@ import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
import java.io.Serializable;
import java.util.Date;
/**
* @author : RYAN0UP
* @date : 2018/2/26
* @version : 1.0
* description :
*/
@Data
@Entity
@Table(name = "halo_gallery")

View File

@ -12,7 +12,6 @@ import java.io.Serializable;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
*/
@Data
@Entity

View File

@ -11,9 +11,8 @@ import java.util.Date;
/**
* @author : RYAN0UP
* @date : 2018/1/19
* @version : 1.0
* description :
* @date : 2018/1/19
*/
@Data
@Entity
@ -49,7 +48,8 @@ public class Logs implements Serializable {
*/
private Date logCreated;
public Logs() { }
public Logs() {
}
public Logs(String logTitle, String logContent, String logIp, Date logCreated) {
this.logTitle = logTitle;

View File

@ -12,7 +12,6 @@ import java.io.Serializable;
* @author : RYAN0UP
* @date : 2018/1/24
* @version : 1.0
* description :
*/
@Data
@Entity

View File

@ -12,7 +12,6 @@ import java.io.Serializable;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
*/
@Data
@Entity

View File

@ -5,13 +5,14 @@ import lombok.Data;
import javax.persistence.*;
import java.io.Serializable;
import java.util.*;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
* @date : 2017/11/14
*/
@Data
@Entity

View File

@ -12,7 +12,6 @@ import java.util.List;
* @author : RYAN0UP
* @date : 2018/1/12
* @version : 1.0
* description :
*/
@Data
@Entity

View File

@ -2,15 +2,17 @@ package cc.ryanc.halo.model.domain;
import lombok.Data;
import javax.persistence.*;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
import java.io.Serializable;
import java.util.Date;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
* @date : 2017/11/14
*/
@Data
@Entity

View File

@ -1,7 +1,6 @@
package cc.ryanc.halo.model.dto;
import cc.ryanc.halo.model.domain.Attachment;
import cc.ryanc.halo.model.domain.User;
import java.util.ArrayList;
import java.util.HashMap;
@ -12,7 +11,7 @@ import java.util.Map;
* @author : RYAN0UP
* @date : 2017/12/29
* @version : 1.0
* description:
* description:
*/
public class HaloConst {

View File

@ -2,9 +2,8 @@ package cc.ryanc.halo.model.dto;
/**
* @author : RYAN0UP
* @date : 2018/1/19
* @version : 1.0
* description :
* @date : 2018/1/19
*/
public interface LogsRecord {

View File

@ -8,7 +8,6 @@ import java.io.Serializable;
* @author : RYAN0UP
* @date : 2018/1/3
* @version : 1.0
* description :
*/
@Data
public class Theme implements Serializable {

View File

@ -7,9 +7,8 @@ import org.springframework.data.jpa.repository.JpaRepository;
/**
* @author : RYAN0UP
* @date : 2018/1/10
* @version : 1.0
* description :
* @date : 2018/1/10
*/
public interface AttachmentRepository extends JpaRepository<Attachment, Long> {

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2017/11/30
* @version : 1.0
* description:
*/
public interface CategoryRepository extends JpaRepository<Category,Long>{

View File

@ -13,7 +13,6 @@ import java.util.List;
* @author : RYAN0UP
* @date : 2018/1/22
* @version : 1.0
* description :
*/
public interface CommentRepository extends JpaRepository<Comment,Long> {

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2018/2/26
* @version : 1.0
* description :
*/
public interface GalleryRepository extends JpaRepository<Gallery,Long> {
}

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
*/
public interface LinkRepository extends JpaRepository<Link,Long>{
}

View File

@ -10,7 +10,6 @@ import java.util.List;
* @author : RYAN0UP
* @date : 2018/1/19
* @version : 1.0
* description :
*/
public interface LogsRepository extends JpaRepository<Logs,Long> {

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2018/1/24
* @version : 1.0
* description :
*/
public interface MenuRepository extends JpaRepository<Menu,Long> {
}

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
*/
public interface OptionsRepository extends JpaRepository<Options,Long>{

View File

@ -16,7 +16,6 @@ import java.util.List;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
*/
public interface PostRepository extends JpaRepository<Post,Long>{

View File

@ -7,7 +7,6 @@ import org.springframework.data.jpa.repository.JpaRepository;
* @author : RYAN0UP
* @date : 2018/1/12
* @version : 1.0
* description :
*/
public interface TagRepository extends JpaRepository<Tag,Long>{

View File

@ -9,7 +9,6 @@ import java.util.List;
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
*/
public interface UserRepository extends JpaRepository<User,Long>{

View File

@ -0,0 +1,32 @@
package cc.ryanc.halo.security;
import org.apache.commons.lang3.StringUtils;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.safety.Whitelist;
/**
* @author : RYAN0UP
* @version : 1.0
* @date : 2018/5/4
*/
public class JsoupUtil {
/**
*
*/
private static final Whitelist whitelist = Whitelist.basicWithImages();
private static final Document.OutputSettings outputSettings = new Document.OutputSettings().prettyPrint(false);
static {
whitelist.addAttributes(":all", "style");
}
public static String clean(String content) {
if (StringUtils.isNotBlank(content)) {
content = content.trim();
}
return Jsoup.clean(content, "", whitelist, outputSettings);
}
}

View File

@ -0,0 +1,77 @@
package cc.ryanc.halo.security;
import org.apache.commons.lang3.BooleanUtils;
import org.apache.commons.lang3.StringUtils;
import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* @author : RYAN0UP
* @version : 1.0
* @date : 2018/5/4
*/
public class XssFilter implements Filter {
/**
*
*/
private static boolean IS_INCLUDE_RICH_TEXT = false;
private List<String> excludes = new ArrayList<>();
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain filterChain) throws IOException, ServletException {
HttpServletRequest req = (HttpServletRequest) request;
HttpServletResponse resp = (HttpServletResponse) response;
if (handleExcludeURL(req, resp)) {
filterChain.doFilter(request, response);
return;
}
XssHttpServletRequestWrapper xssRequest = new XssHttpServletRequestWrapper((HttpServletRequest) request, IS_INCLUDE_RICH_TEXT);
filterChain.doFilter(xssRequest, response);
}
private boolean handleExcludeURL(HttpServletRequest request, HttpServletResponse response) {
if (excludes == null || excludes.isEmpty()) {
return false;
}
String url = request.getServletPath();
for (String pattern : excludes) {
Pattern p = Pattern.compile("^" + pattern);
Matcher m = p.matcher(url);
if (m.find()) {
return true;
}
}
return false;
}
@Override
public void init(FilterConfig filterConfig) throws ServletException {
String isIncludeRichText = filterConfig.getInitParameter("isIncludeRichText");
if (StringUtils.isNotBlank(isIncludeRichText)) {
IS_INCLUDE_RICH_TEXT = BooleanUtils.toBoolean(isIncludeRichText);
}
String temp = filterConfig.getInitParameter("excludes");
if (temp != null) {
String[] url = temp.split(",");
for (int i = 0; url != null && i < url.length; i++) {
excludes.add(url[i]);
}
}
}
@Override
public void destroy() {
}
}

View File

@ -0,0 +1,81 @@
package cc.ryanc.halo.security;
import org.apache.commons.lang3.StringUtils;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
/**
* @author : RYAN0UP
* @version : 1.0
* @date : 2018/5/4
*/
public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper {
HttpServletRequest orgRequest = null;
private boolean isIncludeRichText = false;
public XssHttpServletRequestWrapper(HttpServletRequest request, boolean isIncludeRichText) {
super(request);
orgRequest = request;
this.isIncludeRichText = isIncludeRichText;
}
/**
* request
*
* @param req req
* @return HttpServletRequest
*/
public static HttpServletRequest getOrgRequest(HttpServletRequest req) {
if (req instanceof XssHttpServletRequestWrapper) {
return ((XssHttpServletRequestWrapper) req).getOrgRequest();
}
return req;
}
@Override
public String getParameter(String name) {
Boolean flag = ("content".equals(name) || name.endsWith("WithHtml"));
if (flag && !isIncludeRichText) {
return super.getParameter(name);
}
name = JsoupUtil.clean(name);
String value = super.getParameter(name);
if (StringUtils.isNotBlank(value)) {
value = JsoupUtil.clean(value);
}
return value;
}
@Override
public String[] getParameterValues(String name) {
String[] arr = super.getParameterValues(name);
if (arr != null) {
for (int i = 0; i < arr.length; i++) {
arr[i] = JsoupUtil.clean(arr[i]);
}
}
return arr;
}
@Override
public String getHeader(String name) {
name = JsoupUtil.clean(name);
String value = super.getHeader(name);
if (StringUtils.isNotBlank(value)) {
value = JsoupUtil.clean(value);
}
return value;
}
/**
* request
*
* @return HttpServletRequest
*/
public HttpServletRequest getOrgRequest() {
return orgRequest;
}
}

View File

@ -9,9 +9,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/10
* @version : 1.0
* description :
* @date : 2018/1/10
*/
public interface AttachmentService {

View File

@ -7,9 +7,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2017/11/30
* @version : 1.0
* description :
* @date : 2017/11/30
*/
public interface CategoryService {

View File

@ -10,9 +10,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/22
* @version : 1.0
* description :
* @date : 2018/1/22
*/
public interface CommentService {

View File

@ -9,9 +9,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/2/26
* @version : 1.0
* description :
* @date : 2018/2/26
*/
public interface GalleryService {
@ -48,12 +47,14 @@ public interface GalleryService {
/**
*
*
* @return list
*/
List<Gallery> findAllGalleries();
/**
*
*
* @param galleryId galleryId
* @return gallery
*/

View File

@ -7,9 +7,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
public interface LinkService {

View File

@ -9,9 +9,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/19
* @version : 1.0
* description :
* @date : 2018/1/19
*/
public interface LogsService {
@ -25,6 +24,7 @@ public interface LogsService {
/**
*
*
* @param logsId logsId
*/
void removeByLogsId(Long logsId);

View File

@ -4,9 +4,8 @@ import java.util.Map;
/**
* @author : RYAN0UP
* @date : 2018/1/23
* @version : 1.0
* description :
* @date : 2018/1/23
*/
public interface MailService {
@ -21,6 +20,7 @@ public interface MailService {
/**
*
*
* @param to
* @param subject
* @param content

View File

@ -7,9 +7,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/24
* @version : 1.0
* description :
* @date : 2018/1/24
*/
public interface MenuService {
@ -38,6 +37,7 @@ public interface MenuService {
/**
*
*
* @param menuId menuId
* @return Menu
*/

View File

@ -6,9 +6,8 @@ import java.util.Map;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
* @date : 2017/11/14
*/
public interface OptionsService {

View File

@ -5,7 +5,6 @@ import cc.ryanc.halo.model.domain.Tag;
import cc.ryanc.halo.model.dto.Archive;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.repository.query.Param;
import java.util.Date;
import java.util.List;
@ -13,9 +12,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description :
* @date : 2017/11/14
*/
public interface PostService {

View File

@ -7,9 +7,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/12
* @version : 1.0
* description :
* @date : 2018/1/12
*/
public interface TagService {

View File

@ -7,9 +7,8 @@ import java.util.List;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
public interface UserService {
@ -31,6 +30,7 @@ public interface UserService {
/**
*
*
* @param userEmail userEmail
* @param userPass userPass
* @return list

View File

@ -4,9 +4,6 @@ import cc.ryanc.halo.model.domain.Attachment;
import cc.ryanc.halo.repository.AttachmentRepository;
import cc.ryanc.halo.service.AttachmentService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
@ -16,9 +13,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/10
* @version : 1.0
* description :
* @date : 2018/1/10
*/
@Service
public class AttachmentServiceImpl implements AttachmentService {

View File

@ -4,8 +4,6 @@ import cc.ryanc.halo.model.domain.Category;
import cc.ryanc.halo.repository.CategoryRepository;
import cc.ryanc.halo.service.CategoryService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
@ -14,9 +12,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @version : 1.0=
* @date : 2017/11/30
* @version : 1.0
* description: Category
*/
@Service
public class CategoryServiceImpl implements CategoryService {

View File

@ -9,15 +9,13 @@ import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import javax.swing.text.html.Option;
import java.util.List;
import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/22
* @version : 1.0
* description :
* @date : 2018/1/22
*/
@Service
public class CommentServiceImpl implements CommentService {

View File

@ -13,9 +13,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/2/26
* @version : 1.0
* description :
* @date : 2018/2/26
*/
@Service
public class GalleryServiceImpl implements GalleryService {

View File

@ -4,8 +4,6 @@ import cc.ryanc.halo.model.domain.Link;
import cc.ryanc.halo.repository.LinkRepository;
import cc.ryanc.halo.service.LinkService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import java.util.List;
@ -13,9 +11,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
@Service
public class LinkServiceImpl implements LinkService {

View File

@ -13,9 +13,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/19
* @version : 1.0
* description :
* @date : 2018/1/19
*/
@Service
public class LogsServiceImpl implements LogsService {

View File

@ -14,9 +14,8 @@ import java.util.Map;
/**
* @author : RYAN0UP
* @date : 2018/1/23
* @version : 1.0
* description :
* @date : 2018/1/23
*/
@Service
public class MailServiceImpl implements MailService {

View File

@ -11,9 +11,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/24
* @version : 1.0
* description :
* @date : 2018/1/24
*/
@Service
public class MenuServiceImpl implements MenuService {

View File

@ -3,7 +3,6 @@ package cc.ryanc.halo.service.impl;
import cc.ryanc.halo.model.domain.Options;
import cc.ryanc.halo.repository.OptionsRepository;
import cc.ryanc.halo.service.OptionsService;
import cc.ryanc.halo.util.HaloUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@ -14,9 +13,8 @@ import java.util.Map;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
@Service
public class OptionsServiceImpl implements OptionsService {

View File

@ -9,9 +9,8 @@ import cc.ryanc.halo.service.PostService;
import cc.ryanc.halo.util.HaloUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.stereotype.Service;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
import java.util.Date;
@ -20,9 +19,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
@Service
public class PostServiceImpl implements PostService {
@ -268,6 +266,7 @@ public class PostServiceImpl implements PostService {
/**
*
*
* @param year year year
* @param month month month
* @param pageable pageable pageable

View File

@ -12,9 +12,8 @@ import java.util.Optional;
/**
* @author : RYAN0UP
* @date : 2018/1/12
* @version : 1.0
* description :
* @date : 2018/1/12
*/
@Service
public class TagServiceImpl implements TagService {

View File

@ -11,9 +11,8 @@ import java.util.List;
/**
* @author : RYAN0UP
* @date : 2017/11/14
* @version : 1.0
* description:
* @date : 2017/11/14
*/
@Service
public class UserServiceImpl implements UserService {

View File

@ -11,7 +11,6 @@ import com.sun.syndication.io.WireFeedOutput;
import io.github.biezhi.ome.OhMyEmail;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.ResourceUtils;
import org.springframework.util.StringUtils;
import javax.imageio.ImageIO;
import javax.imageio.ImageReadParam;
@ -25,7 +24,6 @@ import java.net.URI;
import java.net.URL;
import java.net.URLConnection;
import java.security.MessageDigest;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.Instant;
import java.time.ZoneId;

View File

@ -6,7 +6,10 @@ import cc.ryanc.halo.model.domain.Post;
import cc.ryanc.halo.model.domain.User;
import cc.ryanc.halo.model.dto.HaloConst;
import cc.ryanc.halo.model.dto.LogsRecord;
import cc.ryanc.halo.service.*;
import cc.ryanc.halo.service.CommentService;
import cc.ryanc.halo.service.LogsService;
import cc.ryanc.halo.service.PostService;
import cc.ryanc.halo.service.UserService;
import cc.ryanc.halo.util.HaloUtil;
import cc.ryanc.halo.web.controller.core.BaseController;
import lombok.extern.slf4j.Slf4j;

View File

@ -6,6 +6,7 @@ import cc.ryanc.halo.model.domain.User;
import cc.ryanc.halo.model.dto.HaloConst;
import cc.ryanc.halo.service.CommentService;
import cc.ryanc.halo.service.MailService;
import cc.ryanc.halo.service.PostService;
import cc.ryanc.halo.service.UserService;
import cc.ryanc.halo.util.HaloUtil;
import cc.ryanc.halo.web.controller.core.BaseController;
@ -52,6 +53,9 @@ public class CommentController extends BaseController{
@Autowired
private UserService userService;
@Autowired
private PostService postService;
/**
*
*
@ -81,18 +85,18 @@ public class CommentController extends BaseController{
*
*
* @param commentId
* @param session session
* @param status
* @return /admin/comments
*/
@GetMapping(value = "/throw")
public String moveToTrash(@PathParam("commentId") Long commentId,
HttpSession session){
@PathParam("status") String status){
try {
commentService.updateCommentStatus(commentId,2);
}catch (Exception e){
log.error("未知错误:{0}",e.getMessage());
}
return "redirect:/admin/comments";
return "redirect:/admin/comments?status="+status;
}
/**
@ -117,7 +121,7 @@ public class CommentController extends BaseController{
try {
if (status == 1 && matcher.find()) {
Map<String, Object> map = new HashMap<>();
map.put("pageUrl", comment.getPost().getPostUrl());
map.put("pageUrl", HaloConst.OPTIONS.get("blog_url")+"/archives/"+comment.getPost().getPostUrl()+"#comment-id-"+comment.getCommentId());
map.put("pageName", comment.getPost().getPostTitle());
map.put("commentContent", comment.getCommentContent());
map.put("blogUrl", HaloConst.OPTIONS.get("blog_url"));
@ -169,8 +173,7 @@ public class CommentController extends BaseController{
HttpServletRequest request,
HttpSession session){
try {
Post post = new Post();
post.setPostId(postId);
Post post = postService.findByPostId(postId).get();
//博主信息
User user = (User) session.getAttribute(HaloConst.USER_SESSION_KEY);
@ -191,7 +194,7 @@ public class CommentController extends BaseController{
comment.setCommentAuthorIp(HaloUtil.getIpAddr(request));
comment.setCommentAuthorAvatarMd5(HaloUtil.getMD5(userService.findUser().getUserEmail()));
comment.setCommentDate(new Date());
String lastContent = " //<a href='#'>@"+lastComment.getCommentAuthor()+"</a>:"+lastComment.getCommentContent();
String lastContent = " //<a href='#comment-id-"+lastComment.getCommentId()+"'>@"+lastComment.getCommentAuthor()+"</a>:"+lastComment.getCommentContent();
comment.setCommentContent(commentContent+lastContent);
comment.setCommentAgent(userAgent);
comment.setCommentParent(commentId);
@ -210,6 +213,7 @@ public class CommentController extends BaseController{
map.put("blogTitle",HaloConst.OPTIONS.get("blog_title"));
map.put("commentAuthor",lastComment.getCommentAuthor());
map.put("pageName",lastComment.getPost().getPostTitle());
map.put("pageUrl",HaloConst.OPTIONS.get("blog_url")+"/archives/"+post.getPostUrl()+"#comment-id-"+comment.getCommentId());
map.put("commentContent",lastComment.getCommentContent());
map.put("replyAuthor",user.getUserDisplayName());
map.put("replyContent",commentContent);

View File

@ -212,6 +212,7 @@ public class PageController {
/**
*
*
* @param post post
* @param session session
*/

View File

@ -141,11 +141,12 @@ public class PostController extends BaseController{
@PostMapping(value = "/new/push")
@ResponseBody
public void pushPost(@ModelAttribute Post post, @RequestParam("cateList") List<String> cateList, @RequestParam("tagList") String tagList, HttpSession session){
//发表用户
//判断博主是否登录
User user = (User)session.getAttribute(HaloConst.USER_SESSION_KEY);
if(null==user){
return;
}
//判断是否为更新文章操作
if(null!=post.getPostId()){
post = postService.findByPostId(post.getPostId()).get();
}
@ -299,11 +300,17 @@ public class PostController extends BaseController{
}
String blogUrl = HaloConst.OPTIONS.get("blog_url");
List<Post> posts = postService.findAllPosts(HaloConst.POST_TYPE_POST);
String urls = "";
StringBuilder urls = new StringBuilder();
for(Post post:posts){
urls+=blogUrl+"/archives/"+post.getPostUrl()+"\n";
urls.append(blogUrl);
urls.append("/archives/");
urls.append(post.getPostUrl());
urls.append("\n");
}
String result = HaloUtil.baiduPost(blogUrl, baiduToken, urls.toString());
if (StringUtils.isEmpty(result)) {
return false;
}
HaloUtil.baiduPost(blogUrl,baiduToken,urls);
return true;
}
}

View File

@ -8,6 +8,7 @@ import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import javax.servlet.http.HttpServletRequest;
/**
* @author : RYAN0UP
* @date : 2017/12/26

View File

@ -1,7 +1,9 @@
package cc.ryanc.halo.web.controller.front;
import cc.ryanc.halo.model.domain.Comment;
import cc.ryanc.halo.model.domain.Post;
import cc.ryanc.halo.model.dto.HaloConst;
import cc.ryanc.halo.service.CommentService;
import cc.ryanc.halo.service.PostService;
import cc.ryanc.halo.web.controller.core.BaseController;
import lombok.extern.slf4j.Slf4j;
@ -32,6 +34,9 @@ public class ArchivesController extends BaseController {
@Autowired
private PostService postService;
@Autowired
private CommentService commentService;
/**
*
*
@ -91,7 +96,6 @@ public class ArchivesController extends BaseController {
Post post = postService.findByPostUrl(postUrl, HaloConst.POST_TYPE_POST);
//获得当前文章的发布日期
Date postDate = post.getPostDate();
try {
//查询当前文章日期之前的所有文章
List<Post> beforePosts = postService.findByPostDateBefore(postDate);
@ -104,10 +108,12 @@ public class ArchivesController extends BaseController {
if (null != afterPosts && afterPosts.size() > 0) {
model.addAttribute("afterPost", afterPosts.get(afterPosts.size() - 1));
}
}catch (Exception e){
log.error("未知错误:{0}",e.getMessage());
}
Sort sort = new Sort(Sort.Direction.DESC,"commentDate");
Pageable pageable = new PageRequest(0,999,sort);
Page<Comment> comments = commentService.findCommentsByPostAndCommentStatus(post,pageable,2);
model.addAttribute("post", post);
model.addAttribute("comments",comments);
return this.render("post");
}

View File

@ -90,7 +90,7 @@ public class CommentsController {
Map<String, Object> map = new HashMap<>();
map.put("author", userService.findUser().getUserDisplayName());
map.put("pageName", postService.findByPostId(post.getPostId()).get().getPostTitle());
map.put("blogUrl",HaloConst.OPTIONS.get("blog_url"));
map.put("pageUrl", HaloConst.OPTIONS.get("blog_url")+"/archives/"+post.getPostUrl()+"#comment-id-"+comment.getCommentId());
map.put("visitor", comment.getCommentAuthor());
map.put("commentContent", comment.getCommentContent());
mailService.sendTemplateMail(userService.findUser().getUserEmail(), "有新的评论", map, "common/mail/mail_admin.ftl");

View File

@ -69,7 +69,6 @@ public class IndexController extends BaseController {
Pageable pageable = new PageRequest(page - 1, size, sort);
Page<Post> posts = postService.findPostByStatus(0, HaloConst.POST_TYPE_POST, pageable);
model.addAttribute("posts", posts);
return this.render("index");
}

View File

@ -1,14 +1,20 @@
package cc.ryanc.halo.web.controller.front;
import cc.ryanc.halo.model.domain.Comment;
import cc.ryanc.halo.model.domain.Gallery;
import cc.ryanc.halo.model.domain.Link;
import cc.ryanc.halo.model.domain.Post;
import cc.ryanc.halo.model.dto.HaloConst;
import cc.ryanc.halo.service.CommentService;
import cc.ryanc.halo.service.GalleryService;
import cc.ryanc.halo.service.LinkService;
import cc.ryanc.halo.service.PostService;
import cc.ryanc.halo.web.controller.core.BaseController;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
@ -33,6 +39,9 @@ public class PagesController extends BaseController {
@Autowired
private LinkService linkService;
@Autowired
private CommentService commentService;
/**
*
*
@ -69,6 +78,12 @@ public class PagesController extends BaseController {
@GetMapping(value = "/p/{postUrl}")
public String getPage(@PathVariable(value = "postUrl") String postUrl, Model model) {
Post post = postService.findByPostUrl(postUrl, HaloConst.POST_TYPE_PAGE);
Sort sort = new Sort(Sort.Direction.DESC,"commentDate");
Pageable pageable = new PageRequest(0,999,sort);
Page<Comment> comments = commentService.findCommentsByPostAndCommentStatus(post,pageable,2);
model.addAttribute("comments",comments);
model.addAttribute("post", post);
return this.render("post");
}

View File

@ -64,6 +64,7 @@ public class TagsController extends BaseController {
/**
*
*
* @param model model
* @param tagUrl
* @param page

View File

@ -1,9 +1,7 @@
package cc.ryanc.halo.web.interceptor;
import cc.ryanc.halo.model.dto.HaloConst;
import cc.ryanc.halo.service.OptionsService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
@ -20,9 +18,6 @@ import javax.servlet.http.HttpServletResponse;
@Component
public class InstallInterceptor implements HandlerInterceptor {
@Autowired
private OptionsService optionsService;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object o) throws Exception {
if (StringUtils.equals("true", HaloConst.OPTIONS.get("is_install"))) {
@ -33,8 +28,10 @@ public class InstallInterceptor implements HandlerInterceptor {
}
@Override
public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { }
public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { }
public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {
}
}

View File

@ -29,8 +29,10 @@ public class LoginInterceptor implements HandlerInterceptor{
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { }
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { }
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
}
}

View File

@ -7,22 +7,28 @@ server:
spring:
datasource:
type: com.alibaba.druid.pool.DruidDataSource
# H2database 配置
driver-class-name: org.h2.Driver
url: jdbc:h2:file:~/halo/halo
username: admin
#driver-class-name: org.h2.Driver
#url: jdbc:h2:file:~/halo/halo
#username: admin
#password: 123456
# MySql配置
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://127.0.0.1:3306/halodb?characterEncoding=utf8&useSSL=false
username: root
password: 123456
h2:
console:
settings:
web-allow-others: true
path: /h2-console
enabled: true
#h2:
#console:
#settings:
#web-allow-others: true
#path: /h2-console
#enabled: true
jpa:
hibernate:
ddl-auto: update
show-sql: true
database-platform: org.hibernate.dialect.H2Dialect
show-sql: false
freemarker:
allow-request-override: false
cache: false

View File

@ -34,3 +34,18 @@ function stringEncode(str){
}
return div.innerHTML;
}
/**
*
*/
function saveOptions(option) {
var param = $('#'+option).serialize();
$.ajax({
type: 'post',
url: '/admin/option/save',
data: param,
success: function (result) {
showMsg("保存成功!","success",1000);
}
});
}

View File

@ -58,12 +58,12 @@
<#switch comment.commentStatus>
<#case 0>
<button class="btn btn-primary btn-xs " onclick="replyShow('${comment.commentId}','${comment.post.postId}')" <#if comment.isAdmin==1>disabled</#if>>回复</button>
<button class="btn btn-danger btn-xs " onclick="modelShow('/admin/comments/throw?commentId=${comment.commentId}','确定移动到回收站?')">丢弃</button>
<button class="btn btn-danger btn-xs " onclick="modelShow('/admin/comments/throw?commentId=${comment.commentId}&status=1','确定移动到回收站?')">丢弃</button>
<#break >
<#case 1>
<a data-pjax="true" class="btn btn-primary btn-xs " href="/admin/comments/revert?commentId=${comment.commentId}&status=1">通过</a>
<button class="btn btn-info btn-xs " onclick="replyShow('${comment.commentId}','${comment.post.postId}')">通过并回复</button>
<button class="btn btn-danger btn-xs " onclick="modelShow('/admin/comments/throw?commentId=${comment.commentId}','确定移动到回收站?')">丢弃</button>
<button class="btn btn-danger btn-xs " onclick="modelShow('/admin/comments/throw?commentId=${comment.commentId}&status=1','确定移动到回收站?')">丢弃</button>
<#break >
<#case 2>
<a data-pjax="true" class="btn btn-primary btn-xs " href="/admin/comments/revert?commentId=${comment.commentId}&status=2">还原</a>

View File

@ -333,6 +333,7 @@
</section>
<script src="/static/plugins/toast/js/jquery.toast.min.js"></script>
<script src="/static/plugins/layer/layer.js"></script>
<script src="/static/js/app.js"></script>
<script type="application/javascript">
$(document).ready(function () {
var dateBegin = new Date("${options.blog_start?default('0000-00-00')}");
@ -356,32 +357,6 @@
$('#btnWidgetsOption').click(function () {
$('#widgetOptionsPanel').slideToggle(400);
});
function saveOptions(option) {
var param = $('#'+option).serialize();
$.ajax({
type: 'post',
url: '/admin/option/save',
data: param,
success: function (result) {
$.toast({
text: '保存成功',
heading: '提示',
icon: 'success',
showHideTransition: 'fade',
allowToastClose: true,
hideAfter: 1000,
stack: 1,
position: 'top-center',
textAlign: 'left',
loader: true,
loaderBg: '#ffffff',
afterHidden: function () {
window.location.reload();
}
});
}
});
}
</script>
</div>
<#include "module/_footer.ftl">

View File

@ -76,11 +76,7 @@
</div>
</div>
<div class="form-group">
<label for="blogLogo" class="col-sm-2 control-label">LOGO
<span data-toggle="tooltip" data-placement="top" title="如果不设置图片Logo将使用网站标题作为Logo" style="cursor: pointer">
<i class="fa fa-question-circle" aria-hidden="true"></i>
</span>
</label>
<label for="blogLogo" class="col-sm-2 control-label">LOGO</label>
<div class="col-sm-4">
<div class="input-group">
<input type="text" class="form-control selectData" id="blogLogo" name="blog_logo" value="${options.blog_logo?if_exists}">
@ -121,14 +117,14 @@
</div>
</div>
<div class="form-group">
<label for="desc" class="col-sm-2 control-label">站点描述:</label>
<label for="desc" class="col-sm-2 control-label">博客描述:</label>
<div class="col-sm-4">
<input type="text" class="form-control" id="desc" name="seo_desc" value="${options.seo_desc?if_exists}">
</div>
</div>
<div class="form-group">
<label for="baiduToken" class="col-sm-2 control-label">百度推送token
<span data-toggle="tooltip" data-placement="top" title="自行百度获取" style="cursor: pointer">
<span data-toggle="tooltip" data-placement="top" title="百度站长平台获取" style="cursor: pointer">
<i class="fa fa-question-circle" aria-hidden="true"></i>
</span>
</label>
@ -432,17 +428,17 @@
<div class="col-sm-4">
<select class="form-control" id="adminTheme" name="admin_theme">
<option value="skin-blue" ${((options.admin_theme?default('skin-blue'))=='skin-blue')?string('selected','')}>默认主题</option>
<option value="skin-blue-light" ${((options.admin_theme?default('skin-blue'))=='skin-blue-light')?string('selected','')}>上蓝左白</option>
<option value="skin-black" ${((options.admin_theme?default('skin-blue'))=='skin-black')?string('selected','')}>上白左黑</option>
<option value="skin-black-light" ${((options.admin_theme?default('skin-blue'))=='skin-black-light')?string('selected','')}>上白左白</option>
<option value="skin-green" ${((options.admin_theme?default('skin-blue'))=='skin-green')?string('selected','')}>上绿左黑</option>
<option value="skin-green-light" ${((options.admin_theme?default('skin-blue'))=='skin-green-light')?string('selected','')}>上绿左白</option>
<option value="skin-purple" ${((options.admin_theme?default('skin-blue'))=='skin-purple')?string('selected','')}>上紫左黑</option>
<option value="skin-purple-light" ${((options.admin_theme?default('skin-blue'))=='skin-purple-light')?string('selected','')}>上紫左白</option>
<option value="skin-red" ${((options.admin_theme?default('skin-blue'))=='skin-red')?string('selected','')}>上红左黑</option>
<option value="skin-red-light" ${((options.admin_theme?default('skin-blue'))=='skin-red-light')?string('selected','')}>上红左白</option>
<option value="skin-yellow" ${((options.admin_theme?default('skin-blue'))=='skin-yellow')?string('selected','')}>上黄左黑</option>
<option value="skin-yellow-light" ${((options.admin_theme?default('skin-blue'))=='skin-yellow-light')?string('selected','')}>上黄左白</option>
<option value="skin-blue-light" ${((options.admin_theme?if_exists)=='skin-blue-light')?string('selected','')}>上蓝左白</option>
<option value="skin-black" ${((options.admin_theme?if_exists)=='skin-black')?string('selected','')}>上白左黑</option>
<option value="skin-black-light" ${((options.admin_theme?if_exists)=='skin-black-light')?string('selected','')}>上白左白</option>
<option value="skin-green" ${((options.admin_theme?if_exists)=='skin-green')?string('selected','')}>上绿左黑</option>
<option value="skin-green-light" ${((options.admin_theme?if_exists)=='skin-green-light')?string('selected','')}>上绿左白</option>
<option value="skin-purple" ${((options.admin_theme?if_exists)=='skin-purple')?string('selected','')}>上紫左黑</option>
<option value="skin-purple-light" ${((options.admin_theme?if_exists)=='skin-purple-light')?string('selected','')}>上紫左白</option>
<option value="skin-red" ${((options.admin_theme?if_exists)=='skin-red')?string('selected','')}>上红左黑</option>
<option value="skin-red-light" ${((options.admin_theme?if_exists)=='skin-red-light')?string('selected','')}>上红左白</option>
<option value="skin-yellow" ${((options.admin_theme?if_exists)=='skin-yellow')?string('selected','')}>上黄左黑</option>
<option value="skin-yellow-light" ${((options.admin_theme?if_exists)=='skin-yellow-light')?string('selected','')}>上黄左白</option>
</select>
</div>
</div>
@ -457,32 +453,32 @@
</label>
</div>
</div>
<div class="form-group">
<label for="postEditor" class="col-sm-2 control-label">文章编辑器:
<span data-toggle="tooltip" data-placement="top" title="请勿将它们混用" style="cursor: pointer">
<i class="fa fa-question-circle" aria-hidden="true"></i>
</span>
</label>
<div class="col-sm-4">
<select class="form-control" id="postEditor" name="post_editor">
<option value="editor.md" ${((options.post_editor?default('editor.md'))=='editor.md')?string('selected','')}>Markdown</option>
<option value="ckeditor" ${((options.post_editor?default('editor.md'))=='ckeditor')?string('selected','')}>富文本</option>
</select>
</div>
</div>
<div class="form-group">
<label for="pageEditor" class="col-sm-2 control-label">页面编辑器:
<span data-toggle="tooltip" data-placement="top" title="请勿将它们混用" style="cursor: pointer">
<i class="fa fa-question-circle" aria-hidden="true"></i>
</span>
</label>
<div class="col-sm-4">
<select class="form-control" id="pageEditor" name="page_editor">
<option value="editor.md" ${((options.page_editor?default('editor.md'))=='editor.md')?string('selected','')}>Markdown</option>
<option value="ckeditor" ${((options.page_editor?default('editor.md'))=='ckeditor')?string('selected','')}>富文本</option>
</select>
</div>
</div>
<#--<div class="form-group">-->
<#--<label for="postEditor" class="col-sm-2 control-label">文章编辑器:-->
<#--<span data-toggle="tooltip" data-placement="top" title="请勿将它们混用" style="cursor: pointer">-->
<#--<i class="fa fa-question-circle" aria-hidden="true"></i>-->
<#--</span>-->
<#--</label>-->
<#--<div class="col-sm-4">-->
<#--<select class="form-control" id="postEditor" name="post_editor">-->
<#--<option value="editor.md" ${((options.post_editor?default('editor.md'))=='editor.md')?string('selected','')}>Markdown</option>-->
<#--<option value="ckeditor" ${((options.post_editor?default('editor.md'))=='ckeditor')?string('selected','')}>富文本</option>-->
<#--</select>-->
<#--</div>-->
<#--</div>-->
<#--<div class="form-group">-->
<#--<label for="pageEditor" class="col-sm-2 control-label">页面编辑器:-->
<#--<span data-toggle="tooltip" data-placement="top" title="请勿将它们混用" style="cursor: pointer">-->
<#--<i class="fa fa-question-circle" aria-hidden="true"></i>-->
<#--</span>-->
<#--</label>-->
<#--<div class="col-sm-4">-->
<#--<select class="form-control" id="pageEditor" name="page_editor">-->
<#--<option value="editor.md" ${((options.page_editor?default('editor.md'))=='editor.md')?string('selected','')}>Markdown</option>-->
<#--<option value="ckeditor" ${((options.page_editor?default('editor.md'))=='ckeditor')?string('selected','')}>富文本</option>-->
<#--</select>-->
<#--</div>-->
<#--</div>-->
</div>
<div class="box-footer">
<button type="button" class="btn btn-primary btn-sm " onclick="saveOptions('adminOptions')">保存</button>
@ -562,12 +558,17 @@
</section>
<script src="/static/plugins/toast/js/jquery.toast.min.js"></script>
<script src="/static/plugins/layer/layer.js"></script>
<script src="/static/js/app.js"></script>
<@compress single_line=true>
<script>
$(function () {
$('[data-toggle="tooltip"]').tooltip();
checkCommentOption();
});
/**
* 打开附件
*/
function openAttach(id) {
layer.open({
type: 2,
@ -580,17 +581,10 @@
scrollbar: false
});
}
function saveOptions(option) {
var param = $('#'+option).serialize();
$.ajax({
type: 'post',
url: '/admin/option/save',
data: param,
success: function (result) {
showMsg("保存成功!","success",1000);
}
});
}
/**
* 更新所有文章的摘要
*/
function updateAllSummary() {
$.ajax({
type: 'GET',
@ -607,6 +601,10 @@
}
});
}
/**
* 主动提交文章到百度
*/
function pushAllToBaidu() {
$.ajax({
type: 'GET',
@ -623,6 +621,10 @@
}
});
}
/**
* 评论切换
*/
function checkCommentOption() {
var native = $('input:radio[value=native]:checked').val();
var valine = $('input:radio[value=valine]:checked').val();
@ -655,6 +657,10 @@
$('.changyan-options').hide();
}
}
/**
* 后台布局切换
*/
function viewLayout() {
var layout = $('input:radio[value=layout-boxed]:checked').val();
if(layout!=null){
@ -663,6 +669,10 @@
$('body').removeClass('layout-boxed');
}
}
/**
* 预览侧边栏
*/
function viewSideBar() {
var layout = $('input:radio[value=sidebar-collapse]:checked').val();
if(layout!=null){
@ -680,6 +690,10 @@
$('input[name=sidebar_style]').click(function () {
viewSideBar();
});
/**
* 预览后台样式切换
*/
$(function () {
var beforeTheme;
$('#adminTheme').change(function () {

View File

@ -31,7 +31,9 @@
<div class="pull-left">
<img src="http://www.gravatar.com/avatar/${comment.commentAuthorAvatarMd5?default("hash")}?s=256&d=${options.native_comment_avatar?default("mm")}" class="img-circle" alt="User Image">
</div>
<h5>${comment.commentAuthor}<small> ${comment.commentDate}</small></h5>
<h4>${comment.commentAuthor}
<small> ${comment.commentDate?string("yyyy/MM/dd HH:mm")}</small>
</h4>
<p>${comment.commentContent}</p>
</a>
</li>

View File

@ -97,12 +97,21 @@
.native-list-one-head-name {
font-size: .875rem;
font-weight: 700;
margin-right: .875rem;
cursor: pointer;
text-decoration: none;
color: #555;
}
.native-list-one-head-admin{
padding: .1em 0.2em;
border-radius: 2px;
font-size: 70%;
font-weight: 700;
background-color: #87ceeb;
color: #fff;
display: inline;
}
.ua {
display: inline-block;
padding: .2rem .5rem;
@ -142,59 +151,80 @@
<div class="native-wrap">
<div class="comment-header">
<input type="hidden" name="postId" value="${post.postId}">
<input type="text" class="comment-input comment-input-who" name="commentAuthor" id="commentAuthor" placeholder="昵称">
<input type="text" class="comment-input comment-input-who" name="commentAuthor" id="commentAuthor"
placeholder="昵称">
<input type="text" class="comment-input comment-input-email" name="commentAuthorEmail" placeholder="邮箱">
<input type="text" class="comment-input comment-input-website" name="commentAuthorUrl" placeholder="网址(https/http)">
<input type="text" class="comment-input comment-input-website" name="commentAuthorUrl"
placeholder="网址(https/http)">
</div>
<div class="comment-content">
<textarea class="comment-input comment-input-content" name="commentContent" id="commentContent" placeholder="come on"></textarea>
<textarea class="comment-input comment-input-content" name="commentContent" id="commentContent"
placeholder="come on"></textarea>
</div>
<div class="comment-footer">
<button type="button" class="comment-submit" id="btn-push">提交</button>
</div>
</div>
<div class="native-info" style="padding-top: 5px;font-size: 12px;color: #0F192A;">
<span id="native-info-total">${post.comments?size}</span>条评论
<span id="native-info-total">${comments.getTotalElements()}</span>条评论
</div>
<ul class="native-list">
</ul>
<div class="native-loading" style="text-align: center;padding-top: 5px">
<img src="/static/images/tail-spin.svg" width="36" alt="">
<#list comments.content as comment>
<li class="native-list-one" id="comment-id-${comment.commentId}">
<img class="native-list-one-img" src="//www.gravatar.com/avatar/${comment.commentAuthorAvatarMd5?if_exists}?s=256&d=${options.native_comment_avatar?default('mm')}">
<section>
<div class="native-list-one-head">
<a class="native-list-one-head-name" rel="nofollow" href="${comment.commentAuthorUrl?if_exists}">${comment.commentAuthor?if_exists}</a>
<#if comment.isAdmin==1>
<label class="native-list-one-head-admin">博主</label>
</#if>
<#--<span class="ua"></span>-->
<#--<span class="ua"></span>-->
</div>
<div class="native-list-one-content">
<p>${comment.commentContent?if_exists}</p>
</div>
<div class="native-list-one-footer">
<span class="native-list-one-footer-time">${comment.commentDate?string("yyyy-MM-dd HH:mm")}</span>
<span rid="" at="@${comment.commentAuthor?if_exists}" class="native-list-one-footer-reback">回复</span>
</div>
</section>
</li>
</#list>
</ul>
</div>
<script src="//cdn.bootcss.com/jquery/3.3.1/jquery.min.js"></script>
<script src="//cdn.bootcss.com/blueimp-md5/2.10.0/js/md5.min.js"></script>
<script src="//cdn.bootcss.com/UAParser.js/0.7.17/ua-parser.min.js"></script>
<script>
$(document).ready(function(){
$.ajax({
type: "get",
async: true,
url: "/getComment/${post.postId}",
dataType: "json",
success: function(data){
setTimeout(function(){
$('.native-loading').hide();
},1000);
var parser = new UAParser();
$.each(data,function(i,element){
parser.setUA(element.commentAgent);
var result = parser.getResult();
var browser = result.browser.name+' '+result.browser.version;
var os = result.os.name + ' ' + result.os.version;
var author = element.commentAuthor;
var authorEmail = element.commentAuthorEmail;
var authorUrl = element.commentAuthorUrl;
var timestamp = element.commentDate;
var date = new Date(timestamp).toLocaleDateString();
var content = element.commentContent;
var authorPic = md5(authorEmail);
$('.native-list').append("<li class=\"native-list-one\"><img class=\"native-list-one-img\" src=\"//www.gravatar.com/avatar/"+authorPic+"?s=256&d=${options.native_comment_avatar?default('default')}\"><section><div class=\"native-list-one-head\"><a class=\"native-list-one-head-name\" rel=\"nofollow\" href=\""+authorUrl+"\" target=\"_blank\">"+author+"</a> <span class=\"ua\">"+browser+"</span> <span class=\"ua\">"+os+"</span></div><div class=\"native-list-one-content\"><p>"+content+"</p></div><div class=\"native-list-one-footer\"><span class=\"native-list-one-footer-time\">"+date+"</span> <span rid=\"\" at=\"@"+author+"\" mail=\""+authorEmail+"\" class=\"native-list-one-footer-reback\">回复</span></div></section></li>");
});
}
});
});
<#--$(document).ready(function () {-->
<#--$.ajax({-->
<#--type: "get",-->
<#--async: true,-->
<#--url: "/getComment/${post.postId}",-->
<#--dataType: "json",-->
<#--success: function (data) {-->
<#--setTimeout(function () {-->
<#--$('.native-loading').hide();-->
<#--}, 1000);-->
<#--var parser = new UAParser();-->
<#--$.each(data, function (i, element) {-->
<#--parser.setUA(element.commentAgent);-->
<#--var result = parser.getResult();-->
<#--var browser = result.browser.name + ' ' + result.browser.version;-->
<#--var os = result.os.name + ' ' + result.os.version;-->
<#--var author = element.commentAuthor;-->
<#--var authorEmail = element.commentAuthorEmail;-->
<#--var authorUrl = element.commentAuthorUrl;-->
<#--var timestamp = element.commentDate;-->
<#--var date = new Date(timestamp).toLocaleDateString();-->
<#--var content = element.commentContent;-->
<#--var authorPic = md5(authorEmail);-->
<#--$('.native-list').append("<li class=\"native-list-one\"><img class=\"native-list-one-img\" src=\"//www.gravatar.com/avatar/" + authorPic + "?s=256&d=${options.native_comment_avatar?default('default')}\"><section><div class=\"native-list-one-head\"><a class=\"native-list-one-head-name\" rel=\"nofollow\" href=\"" + authorUrl + "\" target=\"_blank\">" + author + "</a> <span class=\"ua\">" + browser + "</span> <span class=\"ua\">" + os + "</span></div><div class=\"native-list-one-content\"><p>" + content + "</p></div><div class=\"native-list-one-footer\"><span class=\"native-list-one-footer-time\">" + date + "</span> <span rid=\"\" at=\"@" + author + "\" mail=\"" + authorEmail + "\" class=\"native-list-one-footer-reback\">回复</span></div></section></li>");-->
<#--});-->
<#--}-->
<#--});-->
<#--});-->
$('#btn-push').click(function () {
var author = $("#commentAuthor");
if (author.val() == '') {

View File

@ -12,7 +12,7 @@
${visitor}${commentContent}
</p>
<br />
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">你可以点击<a href="${blogUrl}">查看完整内容</a></p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">你可以点击<a href="${pageUrl}">查看完整内容</a></p>
</div>
</div>
</div>

View File

@ -5,8 +5,7 @@
留言审核通过通知
</h1>
<div class="emailtext" style="background:#fff;padding:20px 32px 40px;">
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">您在${blogTitle}《
<a href="${pageUrl}">${pageName}</a>》发表的评论:</p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">您在${blogTitle}《<a href="${pageUrl}">${pageName}</a>》发表的评论:</p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;padding:10px 20px;background:#f8f8f8;margin:0px">${commentContent}</p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">已通过管理员审核并显示。
<br /> 您可在此查看您的评论:

View File

@ -14,7 +14,7 @@
<br />
<p style="color: #6e6e6e;font-size:13px;line-height:24px;padding:10px 20px;background:#f8f8f8;margin:0px">${replyContent}</p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">你可以点击
<a href="${blogUrl}">查看完整内容</a>
<a href="${pageUrl}">查看完整内容</a>
</p>
<p style="color: #6e6e6e;font-size:13px;line-height:24px;">欢迎再度光临
<a href="${blogUrl}">${blogTitle}</a>

View File

@ -11,7 +11,7 @@
<div class="information">
<div class="back_btn">
<li>
<a onclick="window.history.go(-1)" style="display:none;" class="fa fa-chevron-left"></a>
<a onclick="window.history.go(-1)" style="display: none" class="fa fa-chevron-left"></a>
</li>
</div>
<div class="avatar">

View File

@ -28,12 +28,12 @@
<span class="date">${post.postDate?string("yyyy-MM-dd")}</span>
<i class="fa fa-comment-o"></i>
<a href="/archives/${post.postUrl}#comment_widget">Comments</a>
<if post.tags?size gt 0>
<#if post.tags?size gt 0>
<i class="fa fa-tag"></i>
<#list post.tags as tag>
<a href="/tags/${tag.tagUrl}" class="tag">&nbsp;${tag.tagName}</a>
</#list>
</if>
</#if>
</div>
</div>
</div>

View File

@ -1,29 +0,0 @@
<#include "module/macro.ftl">
<@layout title="${post.postTitle?if_exists} | ${options.blog_title?if_exists}" keywords="${options.seo_keywords?if_exists}" description="${options.seo_desc?if_exists}">
<!-- Post Module -->
<div class="material-post_container">
<div class="material-post mdl-grid">
<div class="mdl-card mdl-shadow--4dp mdl-cell mdl-cell--12-col">
<!-- Post Header(Thumbnail & Title) -->
<#include "_partial/post-header.ftl">
<#if options.theme_material_scheme?if_exists == "Paradox">
<!-- Paradox Post Info -->
<#include "_partial/Paradox-post-info.ftl">
</#if>
<!-- Post Content -->
<#include "_partial/post-content.ftl">
<#if options.theme_material_scheme?if_exists == "Isolation">
<#include "_partial/Isolation-post-info.ftl">
</#if>
<#include "_partial/comment.ftl">
</div>
<!-- Post Prev & Next Nav -->
<#include "_partial/post-nav.ftl">
</div>
</div>
</@layout>