// @api patch /admin/api/options/{key} 修改设置项的值 // @apiParam key string 需要修改项的key // @apiGroup admin // // @apiRequest json // @apiHeader Authorization xxx // @apiParam value string 新值 // @apiExample json // { "value": "abcdef" } // @apiSuccess 204 no content func adminPatchOption(w http.ResponseWriter, r *http.Request) { key, ok := util.ParamString(w, r, "key") if !ok { return } if _, found := app.GetOption(key); !found { util.RenderJSON(w, http.StatusNotFound, nil, nil) return } data := &struct { Value string `json:"value"` }{} if !util.ReadJSON(w, r, data) { return } if err := app.SetOption(key, data.Value, false); err != nil { logs.Error("adminPatchOption:", err) util.RenderJSON(w, http.StatusInternalServerError, nil, nil) return } lastUpdated() util.RenderJSON(w, http.StatusNoContent, nil, nil) }
// /tags/1.html func pageTag(w http.ResponseWriter, r *http.Request) { tagName, ok := util.ParamString(w, r, "id") if !ok { return } tagName = strings.TrimSuffix(tagName, opt.Suffix) sql := `SELECT {id} AS {ID}, {name} AS {Name}, {title} AS {Title}, {description} AS {Description} FROM #tags WHERE {name}=?` rows, err := db.Query(true, sql, tagName) if err != nil { logs.Error("pageTag:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } defer rows.Close() tag := &Tag{} if _, err = fetch.Obj(tag, rows); err != nil { logs.Error("pageTag:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } info, err := getInfo() if err != nil { logs.Error("pageTag:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } info.Canonical = app.URL(tag.Permalink()) info.Title = tag.Title page := conv.MustInt(r.FormValue("page"), 1) if page < 1 { // 不能小于1 page = 1 } else if page > 1 { // 为1的时候,不需要prev info.PrevPage = &Anchor{Title: "上一页", Link: app.TagURL(tagName, page-1)} } if page*opt.SidebarSize < tag.Count() { info.NextPage = &Anchor{Title: "下一页", Link: app.TagURL(tagName, page+1)} } posts, err := getTagPosts(page-1, tag.ID) if err != nil { logs.Error("pageTag:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } data := map[string]interface{}{ "info": info, "tag": tag, "posts": posts, } render(w, r, "tag", data, map[string]string{"Content-Type": "text/html"}) }
// @api get /admin/api/options/{key} 获取设置项的值,不能获取password字段。 // @apiParam key string 名称 // // @apiRequest json // @apiHeader Authorization xxx // // @apiSuccess 200 ok // @api value any 设置项的值 // @apiExample json // { "value": "20" } func adminGetOption(w http.ResponseWriter, r *http.Request) { key, ok := util.ParamString(w, r, "key") if !ok { return } if key == "password" { util.RenderJSON(w, http.StatusNotFound, nil, nil) return } val, found := app.GetOption(key) if !found { util.RenderJSON(w, http.StatusNotFound, nil, nil) return } util.RenderJSON(w, http.StatusOK, map[string]interface{}{"value": val}, nil) }
// 从请求参数中解析出模块实例。 func getModule(w http.ResponseWriter, r *http.Request) *web.Module { name, ok := util.ParamString(w, r, "name") if name == moduleName { // 当前模块不能被控制 util.RenderJSON(w, http.StatusBadRequest, &util.ErrorResult{Message: "无法控制该模块!"}, nil) return nil } if !ok { util.RenderJSON(w, http.StatusNotFound, nil, nil) return nil } m := web.GetModule(name) if m == nil { util.RenderJSON(w, http.StatusNotFound, nil, nil) return nil } return m }
// /posts/1.html // /posts/about.html func pagePost(w http.ResponseWriter, r *http.Request) { idStr, ok := util.ParamString(w, r, "id") if !ok { return } idStr = strings.TrimSuffix(idStr, opt.Suffix) var rows *sql.Rows var err error postID, err := strconv.ParseInt(idStr, 10, 64) if err != nil { sql := `SELECT * FROM #posts WHERE {name}=?` rows, err = db.Query(true, sql, idStr) } else { sql := `SELECT * FROM #posts WHERE {id}=?` rows, err = db.Query(true, sql, postID) } if err != nil { logs.Error("pagePost:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } defer rows.Close() mp := &models.Post{} if _, err = fetch.Obj(mp, rows); err != nil { logs.Error("pagePost:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } if len(mp.Title) == 0 || mp.State != models.PostStatePublished { pageHttpStatusCode(w, r, http.StatusNotFound) return } if r.Method == "POST" { if err := insertComment(mp.ID, r); err != nil { logs.Error("pagePost:", err) } else { stats.WaitingCommentsSize++ stats.CommentsSize++ } } post := &Post{ ID: mp.ID, Name: mp.Name, Title: mp.Title, Summary: mp.Summary, Content: mp.Content, Author: opt.ScreenName, Created: mp.Created, Modified: mp.Modified, AllowComment: mp.AllowComment, } info, err := getInfo() if err != nil { logs.Error("pagePost:", err) pageHttpStatusCode(w, r, http.StatusInternalServerError) return } info.Canonical = app.URL(post.Permalink()) info.Title = post.Title info.Description = post.Summary info.Keywords = post.Keywords() data := map[string]interface{}{ "info": info, "post": post, } render(w, r, "post", data, map[string]string{"Content-Type": "text/html"}) }