Beispiel #1
0
func adminSetPostState(w http.ResponseWriter, r *http.Request, state int) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	p := &models.Post{ID: id}
	if err := db.Select(p); err != nil {
		logs.Error("adminSetPostState:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}
	// 不可能存在状态值为0的文章,出现此值,表明数据库没有该条记录
	if p.State == models.PostStateAll {
		util.RenderJSON(w, http.StatusNotFound, nil, nil)
		return
	}

	p = &models.Post{ID: id, State: state}
	if _, err := db.Update(p); err != nil {
		logs.Error("adminSetPostState:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if err := stats.UpdatePostsSize(); err != nil {
		logs.Error("admin.adminSetPostState:", err)
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusCreated, "{}", nil)
}
Beispiel #2
0
// @api delete /admin/api/posts/{id} 删除文章
// @apiGroup admin
//
// @apiRequest json
// @apiHeader Authorization xxx
//
// @apiSuccess 204 no content
func adminDeletePost(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	tx, err := db.Begin()
	if err != nil {
		logs.Error("deletePost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	// 删除文章
	sql := "DELETE FROM #posts WHERE {id}=?"
	if _, err := tx.Exec(true, sql, id); err != nil {
		logs.Error("deletePost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	// 删除评论
	sql = "DELETE FROM #comments WHERE {postID}=?"
	if _, err := tx.Exec(true, sql, id); err != nil {
		logs.Error("deletePost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	//删除关联数据
	sql = "DELETE FROM #relationships WHERE {postID}=?"
	if _, err := tx.Exec(true, sql, id); err != nil {
		logs.Error("deletePost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	if err := tx.Commit(); err != nil {
		tx.Rollback()
		logs.Error("deletePost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if err := stats.UpdatePostsSize(); err != nil {
		logs.Error("admin.adminDeletePost:", err)
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}
Beispiel #3
0
// @api put /admin/api/tags/{id} 修改某id的标签内容
// @apiParam id int 需要修改的标签id
// @apiGroup admin
//
// @apiRequest json
// @apiHeader Authorization xxx
// @apiParam name        string 唯一名称
// @apiParam title       string 显示的标题
// @apiParam description string 描述信息,可以是html
// @apiExample json
// {
//     "name": "tag-1",
//     "title":"标签1",
//     "description": "<h1>desc</h1>"
// }
//
// @apiSuccess 204 no content
//
// @apiError 400 bad request
// @apiParam message string 错误信息
// @apiParam detail  array  说细的错误信息,用于描述哪个字段有错
// @apiExample json
// {
//     "message": "格式错误",
//     "detail":[
//         {"title":"不能包含特殊字符"},
//         {"name": "已经存在同名"}
//     ]
// }
func adminPutTag(w http.ResponseWriter, r *http.Request) {
	t := &models.Tag{}
	if !util.ReadJSON(w, r, t) {
		return
	}

	// 检测是否为空
	errs := &util.ErrorResult{Message: "格式错误", Detail: map[string]string{}}
	if len(t.Name) == 0 {
		errs.Add("name", "不能为空")
	}
	if len(t.Title) == 0 {
		errs.Add("title", "不能为空")
	}
	if errs.HasErrors() {
		util.RenderJSON(w, http.StatusBadRequest, errs, nil)
		return
	}

	var ok bool
	t.ID, ok = util.ParamID(w, r, "id")
	if !ok {
		return
	}

	// 检测是否存在同名
	titleExists, nameExists, err := tagIsExists(t)
	if err != nil {
		logs.Error("adminPutTag:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}
	if titleExists {
		errs.Add("title", "与已有标签同名")
	}
	if nameExists {
		errs.Add("name", "与已有标签同名")
	}
	if errs.HasErrors() {
		util.RenderJSON(w, http.StatusBadRequest, errs, nil)
		return
	}

	if _, err := db.Update(t); err != nil {
		logs.Error("adminPutTag:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}
Beispiel #4
0
// @api get /admin/api/posts/{id} 获取某一篇文章的详细内容
// @apiGroup admin
//
// @apiRequest json
// @apiHeader Authorization xxx
//
// @apiSuccess 200 OK
// @apiParam id           int    id值
// @apiParam name         string 唯一名称,可以为空
// @apiParam title        string 标题
// @apiParam summary      string 文章摘要
// @apiParam content      string 文章内容
// @apiParam state        int    状态
// @apiParam order        int    排序
// @apiParam created      int    创建时间
// @apiParam modified     int    修改时间
// @apiParam template     string 所使用的模板
// @apiParam allowPing    bool   允许ping
// @apiParam allowComment bool   允许评论
// @apiParam tags         array  关联的标签。
func adminGetPost(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	p := &models.Post{ID: id}
	if err := db.Select(p); err != nil {
		logs.Error("adminGetPost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	tags, err := getPostTags(id)
	if err != nil {
		logs.Error("adminGetPost:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	obj := &struct {
		ID           int64         `json:"id"`
		Name         string        `json:"name"`
		Title        string        `json:"title"`
		Summary      string        `json:"summary"`
		Content      string        `json:"content"`
		State        int           `json:"state"`
		Order        int           `json:"order"`
		Created      int64         `json:"created"`
		Modified     int64         `json:"modified"`
		Template     string        `json:"template"`
		AllowPing    bool          `json:"allowPing"`
		AllowComment bool          `json:"allowComment"`
		Tags         []*models.Tag `json:"tags"`
	}{
		ID:           p.ID,
		Name:         p.Name,
		Title:        p.Title,
		Summary:      p.Summary,
		Content:      p.Content,
		State:        p.State,
		Order:        p.Order,
		Created:      p.Created,
		Modified:     p.Modified,
		Template:     p.Template,
		AllowPing:    p.AllowPing,
		AllowComment: p.AllowComment,
		Tags:         tags,
	}
	util.RenderJSON(w, http.StatusOK, obj, nil)
}
Beispiel #5
0
// @api get /admin/api/tags/{id} 获取指定id的标签内容
// @apiParam id int 标签的id
// @apiGroup admin
//
// @apiSuccess 200 OK
// @apiParam id          int 	标签的id
// @apiParam name        string 标签的唯一名称,可能为空
// @apiParam title       string 标签名称
// @apiParam description string 对标签的详细描述
func adminGetTag(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	t := &models.Tag{ID: id}
	if err := db.Select(t); err != nil {
		logs.Error("adminGetTag:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	util.RenderJSON(w, http.StatusOK, t, nil)
}
Beispiel #6
0
// @api delete /admin/api/comments/{id} 删除某条评论
// @apiParam id int 评论的id值
// @apiGroup admin
//
// @apiSuccess 204 no content
func adminDeleteComment(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	c := &models.Comment{ID: id}
	if _, err := db.Delete(c); err != nil {
		logs.Error("adminDeleteComment:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if err := stats.UpdateCommentsSize(); err != nil {
		logs.Error("admin.adminDeleteComment:", err)
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}
Beispiel #7
0
// @api put /admin/api/comments/{id} 修改评论,只能修改管理员发布的评论
// @apiParam id int 需要修改的评论id
// @apiGroup admin
//
// @apiRequest json
// @apiParam content string 新的评论内容
// @apiExample json
// { "content", "content..." }
//
// @apiSuccess 200 ok
func adminPutComment(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	c := &models.Comment{ID: id}
	cnt, err := db.Count(c)
	if err != nil {
		logs.Error("putComment:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}
	if cnt == 0 {
		util.RenderJSON(w, http.StatusNotFound, nil, nil)
		return
	}

	ct := &struct {
		Content string `json:"content"`
	}{}

	if !util.ReadJSON(w, r, ct) {
		return
	}

	c.Content = ct.Content

	if _, err = db.Update(c); err != nil {
		logs.Error("putComment", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if err := stats.UpdateCommentsSize(); err != nil {
		logs.Error("admin.adminPutComment:", err)
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}
Beispiel #8
0
// @api delete /admin/api/tags/{id} 删除该id的标签,也将被从relationships表中删除。
// @apiParam id int 需要删除的标签id
// @apiGroup admin
//
// @apiRequest json
// @apiHeader Authorization xxx
//
// @apiSuccess 204 no content
func adminDeleteTag(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	tx, err := db.Begin()
	if err != nil {
		logs.Error("adminDeleteMeta:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if _, err := tx.Delete(&models.Tag{ID: id}); err != nil {
		logs.Error("adminDeleteMeta:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	// 删除与之对应的关联数据。
	sql := "DELETE FROM #relationships WHERE {tagID}=?"
	if _, err := tx.Exec(true, sql, id); err != nil {
		logs.Error("adminDeleteMeta:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if err := tx.Commit(); err != nil {
		logs.Error("adminDeleteMeta:", err)
		tx.Rollback()
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}
Beispiel #9
0
// @api get /api/posts/{id}/comments
// @apiQuery page  int 页码
// @apiGroup front
//
// @apiSuccess 200 OK
// @apiParam comments array 当前页的评论
func frontGetPostComments(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	p := &models.Post{ID: id}
	if err := db.Select(p); err != nil {
		logs.Error("frontGetPostComments:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	if p.State != models.PostStatePublished {
		util.RenderJSON(w, http.StatusNotFound, nil, nil)
		return
	}

	sql := db.Where("{postID}=?", id).
		And("{state}=?", models.CommentStateApproved).
		Table("#comments")

	var page int
	if page, ok = util.QueryInt(w, r, "page", 0); !ok {
		return
	}
	sql.Limit(opt.PageSize, page*opt.PageSize)
	maps, err := sql.SelectMap(true, "*")
	if err != nil {
		logs.Error("frontGetComments:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	util.RenderJSON(w, http.StatusOK, map[string]interface{}{"comments": maps}, nil)
}
Beispiel #10
0
// @api put /admin/api/posts/{id} 修改文章
// @apiGroup admin
//
// @apiRequest json
// @apiHeader Authorization xxx
// @apiParam name         string 唯一名称,可以为空
// @apiParam title        string 标题
// @apiParam summary      string 文章摘要
// @apiParam content      string 文章内容
// @apiParam state        int    状态
// @apiParam order        int    排序
// @apiParam template     string 所使用的模板
// @apiParam allowPing    bool   允许ping
// @apiParam allowComment bool   允许评论
// @apiParam tags         array 关联的标签
//
// @apiSuccess 200 no content
func adminPutPost(w http.ResponseWriter, r *http.Request) {
	id, ok := util.ParamID(w, r, "id")
	if !ok {
		return
	}

	p := &struct {
		Name         string  `json:"name"`
		Title        string  `json:"title"`
		Summary      string  `json:"summary"`
		Content      string  `json:"content"`
		State        int     `json:"state"`
		Order        int     `json:"order"`
		Template     string  `json:"template"`
		AllowPing    bool    `json:"allowPing"`
		AllowComment bool    `json:"allowComment"`
		Tags         []int64 `json:"tags"`
	}{}
	if !util.ReadJSON(w, r, p) {
		return
	}
	op := &models.Post{ID: id}
	if err := db.Select(op); err != nil {
		logs.Error("adminPutPost-0:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		return
	}

	pp := &models.Post{
		ID:           id,
		Name:         p.Name,
		Title:        p.Title,
		Summary:      p.Summary,
		Content:      p.Content,
		State:        p.State,
		Order:        p.Order,
		Template:     p.Template,
		AllowPing:    p.AllowPing,
		AllowComment: p.AllowComment,
		Modified:     time.Now().Unix(),
		Created:      op.Created,
	}

	// TODO 是否有必要检测标签是否真实存在

	tx, err := db.Begin()
	if err != nil {
		logs.Error("adminPutPost-1:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	// 更新文档内容
	if _, err := tx.UpdateZero(pp); err != nil {
		logs.Error("adminPutPost-2:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	// 删除旧的关联内容
	sql := "DELETE FROM #relationships WHERE {postID}=?"
	if _, err := tx.Exec(true, sql, pp.ID); err != nil {
		logs.Error("adminPutPost-3:", err)
		util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
		tx.Rollback()
		return
	}

	// 添加新的关联
	if len(p.Tags) > 0 {
		rs := make([]interface{}, 0, len(p.Tags))
		for _, tag := range p.Tags {
			rs = append(rs, &models.Relationship{TagID: tag, PostID: pp.ID})
		}
		if err := tx.MultInsert(rs...); err != nil {
			logs.Error("adminPutPost-4:", err)
			util.RenderJSON(w, http.StatusInternalServerError, nil, nil)
			tx.Rollback()
			return
		}
	}

	if err := tx.Commit(); err != nil {
		logs.Error("adminPutPost-5:", err)
		tx.Rollback()
		return
	}

	if err := stats.UpdatePostsSize(); err != nil {
		logs.Error("admin.adminPutPost:", err)
	}
	lastUpdated()
	util.RenderJSON(w, http.StatusNoContent, nil, nil)
}