diff --git a/app/cmd/main.go b/app/cmd/main.go index 7b9df89..4929262 100644 --- a/app/cmd/main.go +++ b/app/cmd/main.go @@ -1,9 +1,9 @@ package main import ( - "github.com/revel/revel" - "github.com/revel/cmd/harness" "fmt" + "github.com/revel/cmd/harness" + "github.com/revel/revel" ) func main() { @@ -15,5 +15,5 @@ func main() { panic(err) } fmt.Println("Ok") -// panicOnError(reverr, "Failed to build") -} \ No newline at end of file + // panicOnError(reverr, "Failed to build") +} diff --git a/app/controllers/AlbumController.go b/app/controllers/AlbumController.go index 43aa3fc..dcd097c 100644 --- a/app/controllers/AlbumController.go +++ b/app/controllers/AlbumController.go @@ -16,7 +16,7 @@ type Album struct { // 图片管理, iframe func (c Album) Index() revel.Result { - c.SetLocale(); + c.SetLocale() return c.RenderTemplate("album/index.html") } diff --git a/app/controllers/AttachController.go b/app/controllers/AttachController.go index 97d18f9..3852fad 100644 --- a/app/controllers/AttachController.go +++ b/app/controllers/AttachController.go @@ -2,18 +2,18 @@ package controllers import ( "github.com/revel/revel" -// "encoding/json" - "gopkg.in/mgo.v2/bson" - . "github.com/leanote/leanote/app/lea" + // "encoding/json" + "archive/tar" + "compress/gzip" + "fmt" "github.com/leanote/leanote/app/info" + . "github.com/leanote/leanote/app/lea" + "gopkg.in/mgo.v2/bson" + "io" "io/ioutil" "os" "strings" "time" - "io" - "fmt" - "archive/tar" - "compress/gzip" ) // 附件 @@ -31,44 +31,44 @@ func (c Attach) uploadAttach(noteId string) (re info.Re) { var resultMsg = "error" // 错误信息 var Ok = false var fileInfo info.Attach - + re = info.NewRe() - + defer func() { re.Id = fileId // 只是id, 没有其它信息 re.Msg = resultMsg re.Ok = Ok re.Item = fileInfo }() - + // 判断是否有权限为笔记添加附件 if !shareService.HasUpdateNotePerm(noteId, c.GetUserId()) { return re } - + file, handel, err := c.Request.FormFile("file") if err != nil { return re } defer file.Close() - + data, err := ioutil.ReadAll(file) if err != nil { return re } // > 5M? - maxFileSize := configService.GetUploadSize("uploadAttachSize"); + maxFileSize := configService.GetUploadSize("uploadAttachSize") if maxFileSize <= 0 { maxFileSize = 1000 } - if(float64(len(data)) > maxFileSize * float64(1024*1024)) { + if float64(len(data)) > maxFileSize*float64(1024*1024) { resultMsg = fmt.Sprintf("The file's size is bigger than %vM", maxFileSize) return re } - + // 生成上传路径 filePath := "files/" + c.GetUserId() + "/attachs" - dir := revel.BasePath + "/" + filePath + dir := revel.BasePath + "/" + filePath err = os.MkdirAll(dir, 0755) if err != nil { return re @@ -77,12 +77,12 @@ func (c Attach) uploadAttach(noteId string) (re info.Re) { filename := handel.Filename _, ext := SplitFilename(filename) // .doc filename = NewGuid() + ext - toPath := dir + "/" + filename; + toPath := dir + "/" + filename err = ioutil.WriteFile(toPath, data, 0777) if err != nil { return re } - + // add File to db fileType := "" if ext != "" { @@ -90,22 +90,22 @@ func (c Attach) uploadAttach(noteId string) (re info.Re) { } filesize := GetFilesize(toPath) fileInfo = info.Attach{Name: filename, - Title: handel.Filename, - NoteId: bson.ObjectIdHex(noteId), + Title: handel.Filename, + NoteId: bson.ObjectIdHex(noteId), UploadUserId: c.GetObjectUserId(), - Path: filePath + "/" + filename, - Type: fileType, - Size: filesize} - - id := bson.NewObjectId(); + Path: filePath + "/" + filename, + Type: fileType, + Size: filesize} + + id := bson.NewObjectId() fileInfo.AttachId = id fileId = id.Hex() Ok, resultMsg = attachService.AddAttach(fileInfo, false) if resultMsg != "" { resultMsg = c.Message(resultMsg) } - - fileInfo.Path = ""; // 不要返回 + + fileInfo.Path = "" // 不要返回 if Ok { resultMsg = "success" } @@ -130,15 +130,15 @@ func (c Attach) GetAttachs(noteId string) revel.Result { // 下载附件 // 权限判断 func (c Attach) Download(attachId string) revel.Result { - attach := attachService.GetAttach(attachId, c.GetUserId()); // 得到路径 + attach := attachService.GetAttach(attachId, c.GetUserId()) // 得到路径 path := attach.Path if path == "" { return c.RenderText("") } - fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") - file, _ := os.Open(fn) - return c.RenderBinary(file, attach.Title, revel.Attachment, time.Now()) // revel.Attachment - // return c.RenderFile(file, revel.Attachment) // revel.Attachment + fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") + file, _ := os.Open(fn) + return c.RenderBinary(file, attach.Title, revel.Attachment, time.Now()) // revel.Attachment + // return c.RenderFile(file, revel.Attachment) // revel.Attachment } func (c Attach) DownloadAll(noteId string) revel.Result { @@ -151,69 +151,69 @@ func (c Attach) DownloadAll(noteId string) revel.Result { if attachs == nil || len(attachs) == 0 { return c.RenderText("") } - + /* - dir := revel.BasePath + "/files/tmp" - err := os.MkdirAll(dir, 0755) - if err != nil { - return c.RenderText("") - } + dir := revel.BasePath + "/files/tmp" + err := os.MkdirAll(dir, 0755) + if err != nil { + return c.RenderText("") + } */ - + filename := note.Title + ".tar.gz" if note.Title == "" { filename = "all.tar.gz" } - + // file write - fw, err := os.Create(revel.BasePath + "/files/" + filename) - if err != nil { + fw, err := os.Create(revel.BasePath + "/files/" + filename) + if err != nil { return c.RenderText("") - } - // defer fw.Close() // 不需要关闭, 还要读取给用户下载 - - // gzip write - gw := gzip.NewWriter(fw) - defer gw.Close() - - // tar write - tw := tar.NewWriter(gw) - defer tw.Close() - - // 遍历文件列表 - for _, attach := range attachs { - fn := revel.BasePath + "/" + strings.TrimLeft(attach.Path, "/") - fr, err := os.Open(fn) - fileInfo, _ := fr.Stat() - if err != nil { + } + // defer fw.Close() // 不需要关闭, 还要读取给用户下载 + + // gzip write + gw := gzip.NewWriter(fw) + defer gw.Close() + + // tar write + tw := tar.NewWriter(gw) + defer tw.Close() + + // 遍历文件列表 + for _, attach := range attachs { + fn := revel.BasePath + "/" + strings.TrimLeft(attach.Path, "/") + fr, err := os.Open(fn) + fileInfo, _ := fr.Stat() + if err != nil { return c.RenderText("") - } - defer fr.Close() - - // 信息头 - h := new(tar.Header) - h.Name = attach.Title - h.Size = fileInfo.Size() - h.Mode = int64(fileInfo.Mode()) - h.ModTime = fileInfo.ModTime() - - // 写信息头 - err = tw.WriteHeader(h) - if err != nil { - panic(err) - } - - // 写文件 - _, err = io.Copy(tw, fr) - if err != nil { - panic(err) - } - } // for - -// tw.Close() -// gw.Close() -// fw.Close() -// file, _ := os.Open(dir + "/" + filename) + } + defer fr.Close() + + // 信息头 + h := new(tar.Header) + h.Name = attach.Title + h.Size = fileInfo.Size() + h.Mode = int64(fileInfo.Mode()) + h.ModTime = fileInfo.ModTime() + + // 写信息头 + err = tw.WriteHeader(h) + if err != nil { + panic(err) + } + + // 写文件 + _, err = io.Copy(tw, fr) + if err != nil { + panic(err) + } + } // for + + // tw.Close() + // gw.Close() + // fw.Close() + // file, _ := os.Open(dir + "/" + filename) // fw.Seek(0, 0) - return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachment + return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachment } diff --git a/app/controllers/AuthController.go b/app/controllers/AuthController.go index a13be7c..ecfe5ed 100644 --- a/app/controllers/AuthController.go +++ b/app/controllers/AuthController.go @@ -1,10 +1,10 @@ package controllers import ( - "github.com/revel/revel" "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" -// "strconv" + "github.com/revel/revel" + // "strconv" ) // 用户登录/注销/找回密码 @@ -21,14 +21,14 @@ func (c Auth) Login(email, from string) revel.Result { c.RenderArgs["email"] = email c.RenderArgs["from"] = from c.RenderArgs["openRegister"] = configService.IsOpenRegister() - + sessionId := c.Session.Id() if sessionService.LoginTimesIsOver(sessionId) { c.RenderArgs["needCaptcha"] = true } - + c.SetLocale() - + if c.Has("demo") { c.RenderArgs["demo"] = true c.RenderArgs["email"] = "demo@leanote.com" @@ -49,14 +49,14 @@ func (c Auth) doLogin(email, pwd string) revel.Result { c.SetSession(userInfo) sessionService.ClearLoginTimes(sessionId) return c.RenderJson(info.Re{Ok: true}) - } - - return c.RenderJson(info.Re{Ok: false, Item: sessionService.LoginTimesIsOver(sessionId) , Msg: c.Message(msg)}) + } + + return c.RenderJson(info.Re{Ok: false, Item: sessionService.LoginTimesIsOver(sessionId), Msg: c.Message(msg)}) } func (c Auth) DoLogin(email, pwd string, captcha string) revel.Result { sessionId := c.Session.Id() var msg = "" - + // > 5次需要验证码, 直到登录成功 if sessionService.LoginTimesIsOver(sessionId) && sessionService.GetCaptcha(sessionId) != captcha { msg = "captchaError" @@ -66,15 +66,16 @@ func (c Auth) DoLogin(email, pwd string, captcha string) revel.Result { // 登录错误, 则错误次数++ msg = "wrongUsernameOrPassword" sessionService.IncrLoginTimes(sessionId) - } else { + } else { c.SetSession(userInfo) sessionService.ClearLoginTimes(sessionId) return c.RenderJson(info.Re{Ok: true}) - } + } } - - return c.RenderJson(info.Re{Ok: false, Item: sessionService.LoginTimesIsOver(sessionId) , Msg: c.Message(msg)}) + + return c.RenderJson(info.Re{Ok: false, Item: sessionService.LoginTimesIsOver(sessionId), Msg: c.Message(msg)}) } + // 注销 func (c Auth) Logout() revel.Result { sessionId := c.Session.Id() @@ -90,8 +91,8 @@ func (c Auth) Demo() revel.Result { userInfo, err := authService.Login(email, pwd) if err != nil { - return c.RenderJson(info.Re{Ok: false}) - } else { + return c.RenderJson(info.Re{Ok: false}) + } else { c.SetSession(userInfo) return c.Redirect("/note") } @@ -107,7 +108,7 @@ func (c Auth) Register(from, iu string) revel.Result { c.SetLocale() c.RenderArgs["from"] = from c.RenderArgs["iu"] = iu - + c.RenderArgs["title"] = c.Message("register") c.RenderArgs["subTitle"] = c.Message("register") return c.RenderTemplate("home/register.html") @@ -116,24 +117,24 @@ func (c Auth) DoRegister(email, pwd, iu string) revel.Result { if !configService.IsOpenRegister() { return c.Redirect("/index") } - - re := info.NewRe(); - + + re := info.NewRe() + if re.Ok, re.Msg = Vd("email", email); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } if re.Ok, re.Msg = Vd("password", pwd); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } - + // 注册 re.Ok, re.Msg = authService.Register(email, pwd, iu) - + // 注册成功, 则立即登录之 if re.Ok { c.doLogin(email, pwd) } - + return c.RenderRe(re) } @@ -150,6 +151,7 @@ func (c Auth) DoFindPassword(email string) revel.Result { re.Ok = true return c.RenderJson(re) } + // 点击链接后, 先验证之 func (c Auth) FindPassword2(token string) revel.Result { c.RenderArgs["title"] = c.Message("findPassword") @@ -157,23 +159,24 @@ func (c Auth) FindPassword2(token string) revel.Result { if token == "" { return c.RenderTemplate("find_password2_timeout.html") } - ok, _, findPwd := tokenService.VerifyToken(token, info.TokenPwd); + ok, _, findPwd := tokenService.VerifyToken(token, info.TokenPwd) if !ok { return c.RenderTemplate("home/find_password2_timeout.html") } c.RenderArgs["findPwd"] = findPwd - + c.RenderArgs["title"] = c.Message("updatePassword") c.RenderArgs["subTitle"] = c.Message("updatePassword") - + return c.RenderTemplate("home/find_password2.html") } + // 找回密码修改密码 func (c Auth) FindPasswordUpdate(token, pwd string) revel.Result { - re := info.NewRe(); + re := info.NewRe() if re.Ok, re.Msg = Vd("password", pwd); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } // 修改之 diff --git a/app/controllers/BaseController.go b/app/controllers/BaseController.go index d9ab2cf..53a389e 100644 --- a/app/controllers/BaseController.go +++ b/app/controllers/BaseController.go @@ -1,17 +1,17 @@ package controllers import ( - "github.com/revel/revel" - "gopkg.in/mgo.v2/bson" "encoding/json" "github.com/leanote/leanote/app/info" -// . "github.com/leanote/leanote/app/lea" -// "io/ioutil" -// "fmt" + "github.com/revel/revel" + "gopkg.in/mgo.v2/bson" + // . "github.com/leanote/leanote/app/lea" + // "io/ioutil" + // "fmt" + "bytes" "math" "strconv" "strings" - "bytes" ) // 公用Controller, 其它Controller继承它 @@ -56,29 +56,29 @@ func (c BaseController) GetUsername() string { // 得到用户信息 func (c BaseController) GetUserInfo() info.User { if userId, ok := c.Session["UserId"]; ok && userId != "" { - return userService.GetUserInfo(userId); + return userService.GetUserInfo(userId) /* - notebookWidth, _ := strconv.Atoi(c.Session["NotebookWidth"]) - noteListWidth, _ := strconv.Atoi(c.Session["NoteListWidth"]) - mdEditorWidth, _ := strconv.Atoi(c.Session["MdEditorWidth"]) - LogJ(c.Session) - user := info.User{UserId: bson.ObjectIdHex(userId), - Email: c.Session["Email"], - Logo: c.Session["Logo"], - Username: c.Session["Username"], - UsernameRaw: c.Session["UsernameRaw"], - Theme: c.Session["Theme"], - NotebookWidth: notebookWidth, - NoteListWidth: noteListWidth, - MdEditorWidth: mdEditorWidth, + notebookWidth, _ := strconv.Atoi(c.Session["NotebookWidth"]) + noteListWidth, _ := strconv.Atoi(c.Session["NoteListWidth"]) + mdEditorWidth, _ := strconv.Atoi(c.Session["MdEditorWidth"]) + LogJ(c.Session) + user := info.User{UserId: bson.ObjectIdHex(userId), + Email: c.Session["Email"], + Logo: c.Session["Logo"], + Username: c.Session["Username"], + UsernameRaw: c.Session["UsernameRaw"], + Theme: c.Session["Theme"], + NotebookWidth: notebookWidth, + NoteListWidth: noteListWidth, + MdEditorWidth: mdEditorWidth, + } + if c.Session["Verified"] == "1" { + user.Verified = true } - if c.Session["Verified"] == "1" { - user.Verified = true - } - if c.Session["LeftIsMin"] == "1" { - user.LeftIsMin = true - } - return user + if c.Session["LeftIsMin"] == "1" { + user.LeftIsMin = true + } + return user */ } return info.User{} @@ -86,7 +86,7 @@ func (c BaseController) GetUserInfo() info.User { func (c BaseController) GetUserAndBlogUrl() info.UserAndBlogUrl { if userId, ok := c.Session["UserId"]; ok && userId != "" { - return userService.GetUserAndBlogUrl(userId); + return userService.GetUserAndBlogUrl(userId) } return info.UserAndBlogUrl{} } @@ -107,16 +107,16 @@ func (c BaseController) SetSession(userInfo info.User) { c.Session["UsernameRaw"] = userInfo.UsernameRaw c.Session["Theme"] = userInfo.Theme c.Session["Logo"] = userInfo.Logo - + c.Session["NotebookWidth"] = strconv.Itoa(userInfo.NotebookWidth) c.Session["NoteListWidth"] = strconv.Itoa(userInfo.NoteListWidth) - + if userInfo.Verified { c.Session["Verified"] = "1" } else { c.Session["Verified"] = "0" } - + if userInfo.LeftIsMin { c.Session["LeftIsMin"] = "1" } else { @@ -139,8 +139,8 @@ func (c BaseController) UpdateSession(key, value string) { // 返回json func (c BaseController) Json(i interface{}) string { -// b, _ := json.MarshalIndent(i, "", " ") - b, _ := json.Marshal(i) + // b, _ := json.MarshalIndent(i, "", " ") + b, _ := json.Marshal(i) return string(b) } @@ -157,9 +157,9 @@ func (c BaseController) GetPage() int { // 判断是否含有某参数 func (c BaseController) Has(key string) bool { if _, ok := c.Params.Values[key]; ok { - return true; + return true } - return false; + return false } /* @@ -169,12 +169,12 @@ func (c Blog) GetPage(page, count int, list interface{}) info.Page { */ func (c BaseController) GetTotalPage(page, count int) int { - return int(math.Ceil(float64(count)/float64(page))) + return int(math.Ceil(float64(count) / float64(page))) } //------------- func (c BaseController) E404() revel.Result { - c.RenderArgs["title"] = "404"; + c.RenderArgs["title"] = "404" return c.NotFound("", nil) } @@ -187,15 +187,15 @@ func (c BaseController) SetLocale() string { lang = locale[0:pos] } if lang != "zh" && lang != "en" { - lang = "en"; + lang = "en" } - c.RenderArgs["locale"] = lang; - c.RenderArgs["siteUrl"] = configService.GetSiteUrl(); - + c.RenderArgs["locale"] = lang + c.RenderArgs["siteUrl"] = configService.GetSiteUrl() + c.RenderArgs["blogUrl"] = configService.GetBlogUrl() c.RenderArgs["leaUrl"] = configService.GetLeaUrl() c.RenderArgs["noteUrl"] = configService.GetNoteUrl() - + return lang } @@ -203,7 +203,7 @@ func (c BaseController) SetLocale() string { func (c BaseController) SetUserInfo() info.User { userInfo := c.GetUserInfo() c.RenderArgs["userInfo"] = userInfo - if(userInfo.Username == configService.GetAdminUsername()) { + if userInfo.Username == configService.GetAdminUsername() { c.RenderArgs["isAdmin"] = true } return userInfo @@ -222,10 +222,10 @@ func (c BaseController) RenderTemplateStr(templatePath string) string { Template: template, RenderArgs: c.RenderArgs, // 把args给它 } - + var buffer bytes.Buffer tpl.Template.Render(&buffer, c.RenderArgs) - return buffer.String(); + return buffer.String() } // json, result @@ -234,7 +234,7 @@ func (c BaseController) RenderTemplateStr(templatePath string) string { func (c BaseController) RenderRe(re info.Re) revel.Result { oldMsg := re.Msg if re.Msg != "" { - if(strings.Contains(re.Msg, "-")) { + if strings.Contains(re.Msg, "-") { msgAndValues := strings.Split(re.Msg, "-") if len(msgAndValues) == 2 { re.Msg = c.Message(msgAndValues[0], msgAndValues[1]) diff --git a/app/controllers/BlogController.go b/app/controllers/BlogController.go index 196ace2..c2d6f13 100644 --- a/app/controllers/BlogController.go +++ b/app/controllers/BlogController.go @@ -57,9 +57,9 @@ func (c Blog) render(templateName string, themePath string) revel.Result { isPreview = true themePath = themePath2.(string) c.setPreviewUrl() - + // 因为common的themeInfo是从UserBlog.ThemeId来取的, 所以这里要fugai下 - c.RenderArgs["themeInfo"] = c.RenderArgs["themeInfoPreview"]; + c.RenderArgs["themeInfo"] = c.RenderArgs["themeInfoPreview"] } return blog.RenderTemplate(templateName, c.RenderArgs, revel.BasePath+"/"+themePath, isPreview) } @@ -119,9 +119,9 @@ func (c Blog) setPreviewUrl() { indexUrl = blogUrl + "/" + userIdOrEmail cateUrl = blogUrl + "/cate/" + userIdOrEmail // /notebookId - postUrl = blogUrl + "/post/" + userIdOrEmail // /xxxxx + postUrl = blogUrl + "/post/" + userIdOrEmail // /xxxxx searchUrl = blogUrl + "/search/" + userIdOrEmail // blog.leanote.com/search/userId - singleUrl = blogUrl + "/single/" + userIdOrEmail // blog.leanote.com/single/singleId + singleUrl = blogUrl + "/single/" + userIdOrEmail // blog.leanote.com/single/singleId archiveUrl = blogUrl + "/archives/" + userIdOrEmail // blog.leanote.com/archive/userId tagsUrl = blogUrl + "/tags/" + userIdOrEmail // blog.leanote.com/archive/userId @@ -220,7 +220,7 @@ func (c Blog) getCates(userBlog info.UserBlog) { } } } - + // 之后添加没有排序的 for _, n := range notebooks { id := n.NotebookId.Hex() @@ -234,19 +234,19 @@ func (c Blog) getCates(userBlog info.UserBlog) { i++ } } - -// LogJ(">>") -// LogJ(cates) - + + // LogJ(">>") + // LogJ(cates) + // 建立层级 hasParent := map[string]bool{} // 有父的cate for _, cate := range cates { parentCateId := cate.ParentCateId if parentCateId != "" { if parentCate, ok := cateMap[parentCateId]; ok { -// Log("________") -// LogJ(parentCate) -// LogJ(cate) + // Log("________") + // LogJ(parentCate) + // LogJ(cate) if parentCate.Children == nil { parentCate.Children = []*info.Cate{cate} } else { @@ -256,7 +256,7 @@ func (c Blog) getCates(userBlog info.UserBlog) { } } } - + // 得到没有父的cate, 作为第一级cate catesTree := []*info.Cate{} for _, cate := range cates { @@ -264,7 +264,7 @@ func (c Blog) getCates(userBlog info.UserBlog) { catesTree = append(catesTree, cate) } } - + c.RenderArgs["cates"] = cates c.RenderArgs["catesTree"] = catesTree } @@ -348,10 +348,10 @@ func (c Blog) blogCommon(userId string, userBlog info.UserBlog, userInfo info.Us // 得到主题信息 themeInfo := themeService.GetThemeInfo(userBlog.ThemeId.Hex(), userBlog.Style) c.RenderArgs["themeInfo"] = themeInfo - -// Log(">>") -// Log(userBlog.Style) -// Log(userBlog.ThemeId.Hex()) + + // Log(">>") + // Log(userBlog.Style) + // Log(userBlog.ThemeId.Hex()) return true, userBlog } @@ -507,6 +507,7 @@ func (c Blog) Archives(userIdOrEmail string, cateId string, year, month int) (re // 进入某个用户的博客 var blogPageSize = 5 var searchBlogPageSize = 30 + // 分类 /cate/xxxxxxxx?notebookId=1212 func (c Blog) Cate(userIdOrEmail string, notebookId string) (re revel.Result) { // 自定义域名 @@ -833,7 +834,7 @@ func (c Blog) GetComments(noteId string, callback string) revel.Result { result["comments"] = comments result["commentUserInfo"] = commentUserInfo re.Item = result - + if callback != "" { return c.RenderJsonP(callback, result) } diff --git a/app/controllers/CaptchaController.go b/app/controllers/CaptchaController.go index a4dd621..a1dbe9e 100644 --- a/app/controllers/CaptchaController.go +++ b/app/controllers/CaptchaController.go @@ -2,17 +2,17 @@ package controllers import ( "github.com/revel/revel" -// "encoding/json" -// "gopkg.in/mgo.v2/bson" + // "encoding/json" + // "gopkg.in/mgo.v2/bson" . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/lea/captcha" -// "github.com/leanote/leanote/app/types" -// "io/ioutil" -// "fmt" -// "math" -// "os" -// "path" -// "strconv" + // "github.com/leanote/leanote/app/types" + // "io/ioutil" + // "fmt" + // "math" + // "os" + // "path" + // "strconv" "net/http" ) @@ -22,22 +22,23 @@ type Captcha struct { } type Ca string + func (r Ca) Apply(req *revel.Request, resp *revel.Response) { - resp.WriteHeader(http.StatusOK, "image/png") + resp.WriteHeader(http.StatusOK, "image/png") } func (c Captcha) Get() revel.Result { c.Response.ContentType = "image/png" image, str := captcha.Fetch() image.WriteTo(c.Response.Out) - + sessionId := c.Session["_ID"] -// LogJ(c.Session) -// Log("------") -// Log(str) -// Log(sessionId) -Log("..") + // LogJ(c.Session) + // Log("------") + // Log(str) + // Log(sessionId) + Log("..") sessionService.SetCaptcha(sessionId, str) - + return c.Render() -} \ No newline at end of file +} diff --git a/app/controllers/FileController.go b/app/controllers/FileController.go index ce0e691..0f54e8f 100644 --- a/app/controllers/FileController.go +++ b/app/controllers/FileController.go @@ -2,15 +2,15 @@ package controllers import ( "github.com/revel/revel" -// "encoding/json" - "gopkg.in/mgo.v2/bson" + // "encoding/json" + "fmt" + "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/lea/netutil" - "github.com/leanote/leanote/app/info" + "gopkg.in/mgo.v2/bson" "io/ioutil" "os" - "fmt" -// "strconv" + // "strconv" "strings" ) @@ -22,8 +22,8 @@ type File struct { // 上传的是博客logo // TODO logo不要设置权限, 另外的目录 func (c File) UploadBlogLogo() revel.Result { - re := c.uploadImage("blogLogo", ""); - + re := c.uploadImage("blogLogo", "") + c.RenderArgs["fileUrlPath"] = re.Id c.RenderArgs["resultCode"] = re.Code c.RenderArgs["resultMsg"] = re.Msg @@ -34,8 +34,8 @@ func (c File) UploadBlogLogo() revel.Result { // 拖拉上传, pasteImage // noteId 是为了判断是否是协作的note, 如果是则需要复制一份到note owner中 func (c File) PasteImage(noteId string) revel.Result { - re := c.uploadImage("pasteImage", ""); - + re := c.uploadImage("pasteImage", "") + userId := c.GetUserId() note := noteService.GetNoteById(noteId) if note.UserId != "" { @@ -44,29 +44,29 @@ func (c File) PasteImage(noteId string) revel.Result { // 是否是有权限协作的 if shareService.HasUpdatePerm(noteUserId, userId, noteId) { // 复制图片之, 图片复制给noteUserId - _, re.Id = fileService.CopyImage(userId, re.Id, noteUserId) + _, re.Id = fileService.CopyImage(userId, re.Id, noteUserId) } else { // 怎么可能在这个笔记下paste图片呢? // 正常情况下不会 } } } - + return c.RenderJson(re) } // 头像设置 func (c File) UploadAvatar() revel.Result { - re := c.uploadImage("logo", ""); - + re := c.uploadImage("logo", "") + c.RenderArgs["fileUrlPath"] = re.Id c.RenderArgs["resultCode"] = re.Code c.RenderArgs["resultMsg"] = re.Msg - + if re.Ok { re.Ok = userService.UpdateAvatar(c.GetUserId(), re.Id) if re.Ok { - c.UpdateSession("Logo", re.Id); + c.UpdateSession("Logo", re.Id) } } @@ -100,13 +100,13 @@ func (c File) uploadImage(from, albumId string) (re info.Re) { return re } defer file.Close() - + // 生成上传路径 newGuid := NewGuid() - + userId := c.GetUserId() - - if(from == "logo" || from == "blogLogo") { + + if from == "logo" || from == "blogLogo" { fileUrlPath = "public/upload/" + Digest3(userId) + "/" + userId + "/images/logo" } else { fileUrlPath = "files/" + Digest3(userId) + "/" + userId + "/" + Digest2(newGuid) + "/images" @@ -180,8 +180,8 @@ func (c File) uploadImage(from, albumId string) (re info.Re) { id := bson.NewObjectId() fileInfo.FileId = id fileId = id.Hex() - - if(from == "logo" || from == "blogLogo") { + + if from == "logo" || from == "blogLogo" { fileId = fileUrlPath } @@ -217,13 +217,13 @@ func (c File) DeleteImage(fileId string) revel.Result { // 输出image // 权限判断 func (c File) OutputImage(noteId, fileId string) revel.Result { - path := fileService.GetFile(c.GetUserId(), fileId); // 得到路径 + path := fileService.GetFile(c.GetUserId(), fileId) // 得到路径 if path == "" { return c.RenderText("") } - fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") - file, _ := os.Open(fn) - return c.RenderFile(file, revel.Inline) // revel.Attachment + fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") + file, _ := os.Open(fn) + return c.RenderFile(file, revel.Inline) // revel.Attachment } // 协作时复制图片到owner @@ -265,7 +265,7 @@ func (c File) CopyHttpImage(src string) revel.Result { fileInfo.FileId = id re.Id = id.Hex() -// re.Item = fileInfo.Path + // re.Item = fileInfo.Path re.Ok, re.Msg = fileService.AddImage(fileInfo, "", c.GetUserId(), true) return c.RenderJson(re) diff --git a/app/controllers/IndexController.go b/app/controllers/IndexController.go index cc7188c..75c780b 100644 --- a/app/controllers/IndexController.go +++ b/app/controllers/IndexController.go @@ -1,9 +1,9 @@ package controllers import ( - "github.com/revel/revel" "github.com/leanote/leanote/app/info" -// . "github.com/leanote/leanote/app/lea" + "github.com/revel/revel" + // . "github.com/leanote/leanote/app/lea" ) // 首页 @@ -13,31 +13,32 @@ type Index struct { } func (c Index) Default() revel.Result { - if configService.HomePageIsAdminsBlog(){ + if configService.HomePageIsAdminsBlog() { blog := Blog{c.BaseController} - return blog.Index(configService.GetAdminUsername()); + return blog.Index(configService.GetAdminUsername()) } return c.Index() } + // leanote展示页, 没有登录的, 或已登录明确要进该页的 func (c Index) Index() revel.Result { c.SetUserInfo() c.RenderArgs["title"] = "leanote" c.RenderArgs["openRegister"] = configService.GlobalStringConfigs["openRegister"] c.SetLocale() - - return c.RenderTemplate("home/index.html"); + + return c.RenderTemplate("home/index.html") } // 建议 func (c Index) Suggestion(addr, suggestion string) revel.Result { re := info.NewRe() re.Ok = suggestionService.AddSuggestion(info.Suggestion{Addr: addr, UserId: c.GetObjectUserId(), Suggestion: suggestion}) - + // 发给我 go func() { - emailService.SendEmail("leanote@leanote.com", "建议", "UserId: " + c.GetUserId() + "
Suggestions: " + suggestion) - }(); - + emailService.SendEmail("leanote@leanote.com", "建议", "UserId: "+c.GetUserId()+"
Suggestions: "+suggestion) + }() + return c.RenderJson(re) -} \ No newline at end of file +} diff --git a/app/controllers/NoteContentHistoryController.go b/app/controllers/NoteContentHistoryController.go index f5b43ef..5ff1555 100644 --- a/app/controllers/NoteContentHistoryController.go +++ b/app/controllers/NoteContentHistoryController.go @@ -11,6 +11,6 @@ type NoteContentHistory struct { // 得到list func (c NoteContentHistory) ListHistories(noteId string) revel.Result { histories := noteContentHistoryService.ListHistories(noteId, c.GetUserId()) - + return c.RenderJson(histories) -} \ No newline at end of file +} diff --git a/app/controllers/NoteController.go b/app/controllers/NoteController.go index bc428ac..9a911e8 100644 --- a/app/controllers/NoteController.go +++ b/app/controllers/NoteController.go @@ -3,6 +3,7 @@ package controllers import ( "github.com/revel/revel" // "encoding/json" + "fmt" "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" @@ -11,7 +12,6 @@ import ( "regexp" "strings" "time" - "fmt" // "github.com/leanote/leanote/app/types" // "io/ioutil" // "bytes" @@ -30,51 +30,51 @@ func (c Note) Index(noteId, online string) revel.Result { userInfo := c.GetUserAndBlogUrl() userId := userInfo.UserId.Hex() - + // 没有登录 if userId == "" { return c.Redirect("/login") } - + c.RenderArgs["openRegister"] = configService.IsOpenRegister() // 已登录了, 那么得到所有信息 notebooks := notebookService.GetNotebooks(userId) shareNotebooks, sharedUserInfos := shareService.GetShareNotebooks(userId) - + // 还需要按时间排序(DESC)得到notes notes := []info.Note{} noteContent := info.NoteContent{} - + if len(notebooks) > 0 { // noteId是否存在 // 是否传入了正确的noteId hasRightNoteId := false if IsObjectId(noteId) { note := noteService.GetNoteById(noteId) - + if note.NoteId != "" { var noteOwner = note.UserId.Hex() noteContent = noteService.GetNoteContent(noteId, noteOwner) - + hasRightNoteId = true c.RenderArgs["curNoteId"] = noteId c.RenderArgs["curNotebookId"] = note.NotebookId.Hex() - + // 打开的是共享的笔记, 那么判断是否是共享给我的默认笔记 if noteOwner != c.GetUserId() { if shareService.HasReadPerm(noteOwner, c.GetUserId(), noteId) { // 不要获取notebook下的笔记 // 在前端下发请求 c.RenderArgs["curSharedNoteNotebookId"] = note.NotebookId.Hex() - c.RenderArgs["curSharedUserId"] = noteOwner; - // 没有读写权限 + c.RenderArgs["curSharedUserId"] = noteOwner + // 没有读写权限 } else { hasRightNoteId = false } } else { - _, notes = noteService.ListNotes(c.GetUserId(), note.NotebookId.Hex(), false, c.GetPage(), 50, defaultSortField, false, false); - + _, notes = noteService.ListNotes(c.GetUserId(), note.NotebookId.Hex(), false, c.GetPage(), 50, defaultSortField, false, false) + // 如果指定了某笔记, 则该笔记放在首位 lenNotes := len(notes) if lenNotes > 1 { @@ -84,7 +84,7 @@ func (c Note) Index(noteId, online string) revel.Result { for _, note := range notes { if note.NoteId.Hex() != noteId { if i == lenNotes { // 防止越界 - break; + break } notes2[i] = note i++ @@ -94,40 +94,40 @@ func (c Note) Index(noteId, online string) revel.Result { } } } - + // 得到最近的笔记 - _, latestNotes := noteService.ListNotes(c.GetUserId(), "", false, c.GetPage(), 50, defaultSortField, false, false); + _, latestNotes := noteService.ListNotes(c.GetUserId(), "", false, c.GetPage(), 50, defaultSortField, false, false) c.RenderArgs["latestNotes"] = latestNotes } - + // 没有传入笔记 // 那么得到最新笔记 if !hasRightNoteId { - _, notes = noteService.ListNotes(c.GetUserId(), "", false, c.GetPage(), 50, defaultSortField, false, false); + _, notes = noteService.ListNotes(c.GetUserId(), "", false, c.GetPage(), 50, defaultSortField, false, false) if len(notes) > 0 { noteContent = noteService.GetNoteContent(notes[0].NoteId.Hex(), userId) c.RenderArgs["curNoteId"] = notes[0].NoteId.Hex() } } } - + // 当然, 还需要得到第一个notes的content //... c.RenderArgs["isAdmin"] = configService.GetAdminUsername() == userInfo.Username - + c.RenderArgs["userInfo"] = userInfo c.RenderArgs["notebooks"] = notebooks c.RenderArgs["shareNotebooks"] = shareNotebooks // note信息在notes列表中 c.RenderArgs["sharedUserInfos"] = sharedUserInfos - + c.RenderArgs["notes"] = notes c.RenderArgs["noteContentJson"] = noteContent c.RenderArgs["noteContent"] = noteContent.Content - + c.RenderArgs["tags"] = tagService.GetTags(c.GetUserId()) - + c.RenderArgs["globalConfigs"] = configService.GetGlobalConfigForUser() - + // return c.RenderTemplate("note/note.html") if isDev, _ := revel.Config.Bool("mode.dev"); isDev && online == "" { @@ -167,93 +167,94 @@ func (c Note) GetNoteContent(noteId string) revel.Result { // 会传Title, Content, Tags, 一种或几种 type NoteOrContent struct { NotebookId string - NoteId string - UserId string - Title string - Desc string - ImgSrc string - Tags string - Content string - Abstract string - IsNew bool + NoteId string + UserId string + Title string + Desc string + ImgSrc string + Tags string + Content string + Abstract string + IsNew bool IsMarkdown bool FromUserId string // 为共享而新建 - IsBlog bool // 是否是blog, 更新note不需要修改, 添加note时才有可能用到, 此时需要判断notebook是否设为Blog + IsBlog bool // 是否是blog, 更新note不需要修改, 添加note时才有可能用到, 此时需要判断notebook是否设为Blog } + // 这里不能用json, 要用post func (c Note) UpdateNoteOrContent(noteOrContent NoteOrContent) revel.Result { // 新添加note if noteOrContent.IsNew { - userId := c.GetObjectUserId(); -// myUserId := userId + userId := c.GetObjectUserId() + // myUserId := userId // 为共享新建? if noteOrContent.FromUserId != "" { userId = bson.ObjectIdHex(noteOrContent.FromUserId) } - - note := info.Note{UserId: userId, - NoteId: bson.ObjectIdHex(noteOrContent.NoteId), - NotebookId: bson.ObjectIdHex(noteOrContent.NotebookId), - Title: noteOrContent.Title, - Tags: strings.Split(noteOrContent.Tags, ","), - Desc: noteOrContent.Desc, - ImgSrc: noteOrContent.ImgSrc, - IsBlog: noteOrContent.IsBlog, + + note := info.Note{UserId: userId, + NoteId: bson.ObjectIdHex(noteOrContent.NoteId), + NotebookId: bson.ObjectIdHex(noteOrContent.NotebookId), + Title: noteOrContent.Title, + Tags: strings.Split(noteOrContent.Tags, ","), + Desc: noteOrContent.Desc, + ImgSrc: noteOrContent.ImgSrc, + IsBlog: noteOrContent.IsBlog, IsMarkdown: noteOrContent.IsMarkdown, - }; - noteContent := info.NoteContent{NoteId: note.NoteId, - UserId: userId, - IsBlog: note.IsBlog, - Content: noteOrContent.Content, - Abstract: noteOrContent.Abstract}; - + } + noteContent := info.NoteContent{NoteId: note.NoteId, + UserId: userId, + IsBlog: note.IsBlog, + Content: noteOrContent.Content, + Abstract: noteOrContent.Abstract} + note = noteService.AddNoteAndContentForController(note, noteContent, c.GetUserId()) return c.RenderJson(note) } - + noteUpdate := bson.M{} needUpdateNote := false - + // Desc前台传来 if c.Has("Desc") { needUpdateNote = true - noteUpdate["Desc"] = noteOrContent.Desc; + noteUpdate["Desc"] = noteOrContent.Desc } if c.Has("ImgSrc") { needUpdateNote = true - noteUpdate["ImgSrc"] = noteOrContent.ImgSrc; + noteUpdate["ImgSrc"] = noteOrContent.ImgSrc } if c.Has("Title") { needUpdateNote = true - noteUpdate["Title"] = noteOrContent.Title; + noteUpdate["Title"] = noteOrContent.Title } - + if c.Has("Tags") { needUpdateNote = true - noteUpdate["Tags"] = strings.Split(noteOrContent.Tags, ","); + noteUpdate["Tags"] = strings.Split(noteOrContent.Tags, ",") } - + // web端不控制 - if needUpdateNote { - noteService.UpdateNote(c.GetUserId(), + if needUpdateNote { + noteService.UpdateNote(c.GetUserId(), noteOrContent.NoteId, noteUpdate, -1) } - + //------------- afterContentUsn := 0 contentOk := false contentMsg := "" if c.Has("Content") { -// noteService.UpdateNoteContent(noteOrContent.UserId, c.GetUserId(), -// noteOrContent.NoteId, noteOrContent.Content, noteOrContent.Abstract) + // noteService.UpdateNoteContent(noteOrContent.UserId, c.GetUserId(), + // noteOrContent.NoteId, noteOrContent.Content, noteOrContent.Abstract) contentOk, contentMsg, afterContentUsn = noteService.UpdateNoteContent(c.GetUserId(), noteOrContent.NoteId, noteOrContent.Content, noteOrContent.Abstract, needUpdateNote, -1) } - + Log(afterContentUsn) Log(contentOk) Log(contentMsg) - + return c.RenderJson(true) } @@ -347,14 +348,14 @@ func (c Note) ToPdf(noteId, appKey string) revel.Result { //------------------ // 将content的图片转换为base64 contentStr := content.Content - + siteUrlPattern := configService.GetSiteUrl() if strings.Contains(siteUrlPattern, "https") { siteUrlPattern = strings.Replace(siteUrlPattern, "https", "https*", 1) } else { siteUrlPattern = strings.Replace(siteUrlPattern, "http", "https*", 1) } - + regImage, _ := regexp.Compile(` 0 { if !InArray(okSorter, s2[0]) { - return sorterField, isAsc; + return sorterField, isAsc } } - + sorterField = strings.Title(s2[0]) if s2[1] == "up" { isAsc = true @@ -47,7 +47,7 @@ func (c AdminBaseController) getSorter(sorterField string, isAsc bool, okSorter isAsc = false } c.RenderArgs["sorter"] = sorter - return sorterField, isAsc; + return sorterField, isAsc } func (c AdminBaseController) updateConfig(keys []string) { @@ -56,4 +56,4 @@ func (c AdminBaseController) updateConfig(keys []string) { v := c.Params.Values.Get(key) configService.UpdateGlobalStringConfig(userId, key, v) } -} \ No newline at end of file +} diff --git a/app/controllers/admin/AdminBlogController.go b/app/controllers/admin/AdminBlogController.go index ca8a48d..e977f37 100644 --- a/app/controllers/admin/AdminBlogController.go +++ b/app/controllers/admin/AdminBlogController.go @@ -2,7 +2,7 @@ package admin import ( "github.com/revel/revel" -// . "github.com/leanote/leanote/app/lea" + // . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/info" ) @@ -15,16 +15,16 @@ type AdminBlog struct { // admin 主页 func (c AdminBlog) Index(sorter, keywords string) revel.Result { pageNumber := c.GetPage() - sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"title", "userId", "isRecommed", "createdTime"}); - pageInfo, blogs := blogService.ListAllBlogs("", "", keywords, false, pageNumber, userPageSize, sorterField, isAsc); + sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"title", "userId", "isRecommed", "createdTime"}) + pageInfo, blogs := blogService.ListAllBlogs("", "", keywords, false, pageNumber, userPageSize, sorterField, isAsc) c.RenderArgs["pageInfo"] = pageInfo c.RenderArgs["blogs"] = blogs c.RenderArgs["keywords"] = keywords - return c.RenderTemplate("admin/blog/list.html"); + return c.RenderTemplate("admin/blog/list.html") } func (c AdminBlog) SetRecommend(noteId string, recommend bool) revel.Result { re := info.NewRe() - re.Ok = blogService.SetRecommend(noteId, recommend); + re.Ok = blogService.SetRecommend(noteId, recommend) return c.RenderJson(re) } diff --git a/app/controllers/admin/AdminController.go b/app/controllers/admin/AdminController.go index c3215a5..c4360c8 100644 --- a/app/controllers/admin/AdminController.go +++ b/app/controllers/admin/AdminController.go @@ -13,15 +13,15 @@ type Admin struct { // admin 主页 func (c Admin) Index() revel.Result { c.SetUserInfo() - + c.RenderArgs["title"] = "leanote" c.SetLocale() - + c.RenderArgs["countUser"] = userService.CountUser() c.RenderArgs["countNote"] = noteService.CountNote("") c.RenderArgs["countBlog"] = noteService.CountBlog("") - - return c.RenderTemplate("admin/index.html"); + + return c.RenderTemplate("admin/index.html") } // 模板 @@ -35,5 +35,5 @@ func (c Admin) T(t string) revel.Result { } func (c Admin) GetView(view string) revel.Result { - return c.RenderTemplate("admin/" + view); -} \ No newline at end of file + return c.RenderTemplate("admin/" + view) +} diff --git a/app/controllers/admin/AdminData.go b/app/controllers/admin/AdminData.go index 8304c79..1ea9dfb 100644 --- a/app/controllers/admin/AdminData.go +++ b/app/controllers/admin/AdminData.go @@ -1,14 +1,14 @@ package admin import ( - "github.com/revel/revel" - . "github.com/leanote/leanote/app/lea" + "archive/tar" + "compress/gzip" "github.com/leanote/leanote/app/info" - "archive/tar" - "compress/gzip" - "os" - "io" - "time" + . "github.com/leanote/leanote/app/lea" + "github.com/revel/revel" + "io" + "os" + "time" ) // 数据管理, 备份和恢复 @@ -22,18 +22,18 @@ func (c AdminData) Index() revel.Result { // 逆序之 backups2 := make([]map[string]string, len(backups)) j := 0 - for i := len(backups)-1; i >= 0; i-- { + for i := len(backups) - 1; i >= 0; i-- { backups2[j] = backups[i] j++ } c.RenderArgs["backups"] = backups2 - return c.RenderTemplate("admin/data/index.html"); + return c.RenderTemplate("admin/data/index.html") } func (c AdminData) Backup() revel.Result { re := info.NewRe() re.Ok, re.Msg = configService.Backup("") - return c.RenderJson(re) + return c.RenderJson(re) } // 还原 @@ -51,7 +51,7 @@ func (c AdminData) Delete(createdTime string) revel.Result { func (c AdminData) UpdateRemark(createdTime, remark string) revel.Result { re := info.Re{} re.Ok, re.Msg = configService.UpdateBackupRemark(createdTime, remark) - + return c.RenderJson(re) } func (c AdminData) Download(createdTime string) revel.Result { @@ -59,56 +59,56 @@ func (c AdminData) Download(createdTime string) revel.Result { if !ok { return c.RenderText("") } - + dbname, _ := revel.Config.String("db.dbname") path := backup["path"] + "/" + dbname - allFiles := ListDir(path) - + allFiles := ListDir(path) + filename := "backup_" + dbname + "_" + backup["createdTime"] + ".tar.gz" - + // file write - fw, err := os.Create(revel.BasePath + "/files/" + filename) - if err != nil { + fw, err := os.Create(revel.BasePath + "/files/" + filename) + if err != nil { return c.RenderText("") - } - // defer fw.Close() // 不需要关闭, 还要读取给用户下载 - // gzip write - gw := gzip.NewWriter(fw) - defer gw.Close() - - // tar write - tw := tar.NewWriter(gw) - defer tw.Close() - - // 遍历文件列表 - for _, file := range allFiles { + } + // defer fw.Close() // 不需要关闭, 还要读取给用户下载 + // gzip write + gw := gzip.NewWriter(fw) + defer gw.Close() + + // tar write + tw := tar.NewWriter(gw) + defer tw.Close() + + // 遍历文件列表 + for _, file := range allFiles { fn := path + "/" + file - fr, err := os.Open(fn) - fileInfo, _ := fr.Stat() - if err != nil { + fr, err := os.Open(fn) + fileInfo, _ := fr.Stat() + if err != nil { return c.RenderText("") - } - defer fr.Close() - - // 信息头 - h := new(tar.Header) - h.Name = file - h.Size = fileInfo.Size() - h.Mode = int64(fileInfo.Mode()) - h.ModTime = fileInfo.ModTime() - - // 写信息头 - err = tw.WriteHeader(h) - if err != nil { - panic(err) - } - - // 写文件 - _, err = io.Copy(tw, fr) - if err != nil { - panic(err) - } - } // for - - return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachm + } + defer fr.Close() + + // 信息头 + h := new(tar.Header) + h.Name = file + h.Size = fileInfo.Size() + h.Mode = int64(fileInfo.Mode()) + h.ModTime = fileInfo.ModTime() + + // 写信息头 + err = tw.WriteHeader(h) + if err != nil { + panic(err) + } + + // 写文件 + _, err = io.Copy(tw, fr) + if err != nil { + panic(err) + } + } // for + + return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachm } diff --git a/app/controllers/admin/AdminEmailController.go b/app/controllers/admin/AdminEmailController.go index 86fc766..59fc409 100644 --- a/app/controllers/admin/AdminEmailController.go +++ b/app/controllers/admin/AdminEmailController.go @@ -1,11 +1,11 @@ package admin import ( - "github.com/revel/revel" - . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/info" - "strings" + . "github.com/leanote/leanote/app/lea" + "github.com/revel/revel" "strconv" + "strings" ) // admin 首页 @@ -25,14 +25,14 @@ func (c AdminEmail) Blog() revel.Result { newTags := configService.GetGlobalArrayConfig("newTags") c.RenderArgs["recommendTags"] = strings.Join(recommendTags, ",") c.RenderArgs["newTags"] = strings.Join(newTags, ",") - return c.RenderTemplate("admin/setting/blog.html"); + return c.RenderTemplate("admin/setting/blog.html") } func (c AdminEmail) DoBlogTag(recommendTags, newTags string) revel.Result { re := info.NewRe() - + re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "recommendTags", strings.Split(recommendTags, ",")) re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "newTags", strings.Split(newTags, ",")) - + return c.RenderJson(re) } @@ -41,24 +41,24 @@ func (c AdminEmail) DoBlogTag(recommendTags, newTags string) revel.Result { func (c AdminEmail) Demo() revel.Result { c.RenderArgs["demoUsername"] = configService.GetGlobalStringConfig("demoUsername") c.RenderArgs["demoPassword"] = configService.GetGlobalStringConfig("demoPassword") - return c.RenderTemplate("admin/setting/demo.html"); + return c.RenderTemplate("admin/setting/demo.html") } func (c AdminEmail) DoDemo(demoUsername, demoPassword string) revel.Result { re := info.NewRe() - + userInfo, err := authService.Login(demoUsername, demoPassword) if err != nil { return c.RenderJson(info.Re{Ok: false}) } if userInfo.UserId == "" { - re.Msg = "The User is Not Exists"; + re.Msg = "The User is Not Exists" return c.RenderJson(re) } - + re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoUserId", userInfo.UserId.Hex()) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoUsername", demoUsername) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoPassword", demoPassword) - + return c.RenderJson(re) } @@ -66,7 +66,7 @@ func (c AdminEmail) DoDemo(demoUsername, demoPassword string) revel.Result { // 长微博的bin路径phantomJs func (c AdminEmail) ToImage() revel.Result { c.RenderArgs["toImageBinPath"] = configService.GetGlobalStringConfig("toImageBinPath") - return c.RenderTemplate("admin/setting/toImage.html"); + return c.RenderTemplate("admin/setting/toImage.html") } func (c AdminEmail) DoToImage(toImageBinPath string) revel.Result { re := info.NewRe() @@ -80,13 +80,13 @@ func (c AdminEmail) Set(emailHost, emailPort, emailUsername, emailPassword strin re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "emailPort", emailPort) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "emailUsername", emailUsername) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "emailPassword", emailPassword) - + return c.RenderJson(re) } func (c AdminEmail) Template() revel.Result { re := info.NewRe() - - keys := []string{"emailTemplateHeader", "emailTemplateFooter", + + keys := []string{"emailTemplateHeader", "emailTemplateFooter", "emailTemplateRegisterSubject", "emailTemplateRegister", "emailTemplateFindPasswordSubject", @@ -98,7 +98,7 @@ func (c AdminEmail) Template() revel.Result { "emailTemplateCommentSubject", "emailTemplateComment", } - + userId := c.GetUserId() for _, key := range keys { v := c.Params.Values.Get(key) @@ -113,7 +113,7 @@ func (c AdminEmail) Template() revel.Result { } } } - + re.Ok = true return c.RenderJson(re) } @@ -121,100 +121,99 @@ func (c AdminEmail) Template() revel.Result { // 发送Email func (c AdminEmail) SendEmailToEmails(sendEmails, latestEmailSubject, latestEmailBody string, verified, saveAsOldEmail bool) revel.Result { re := info.NewRe() - + c.updateConfig([]string{"sendEmails", "latestEmailSubject", "latestEmailBody"}) - + if latestEmailSubject == "" || latestEmailBody == "" { re.Msg = "subject or body is blank" return c.RenderJson(re) } - + if saveAsOldEmail { oldEmails := configService.GetGlobalMapConfig("oldEmails") oldEmails[latestEmailSubject] = latestEmailBody - configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails); + configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails) } - + sendEmails = strings.Replace(sendEmails, "\r", "", -1) emails := strings.Split(sendEmails, "\n") - - re.Ok, re.Msg = emailService.SendEmailToEmails(emails, latestEmailSubject, latestEmailBody); + + re.Ok, re.Msg = emailService.SendEmailToEmails(emails, latestEmailSubject, latestEmailBody) return c.RenderJson(re) } // 发送Email func (c AdminEmail) SendToUsers2(emails, latestEmailSubject, latestEmailBody string, verified, saveAsOldEmail bool) revel.Result { re := info.NewRe() - + c.updateConfig([]string{"sendEmails", "latestEmailSubject", "latestEmailBody"}) - + if latestEmailSubject == "" || latestEmailBody == "" { re.Msg = "subject or body is blank" return c.RenderJson(re) } - + if saveAsOldEmail { oldEmails := configService.GetGlobalMapConfig("oldEmails") oldEmails[latestEmailSubject] = latestEmailBody - configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails); + configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails) } - + emails = strings.Replace(emails, "\r", "", -1) emailsArr := strings.Split(emails, "\n") - + users := userService.ListUserInfosByEmails(emailsArr) LogJ(emailsArr) - - - re.Ok, re.Msg = emailService.SendEmailToUsers(users, latestEmailSubject, latestEmailBody); - + + re.Ok, re.Msg = emailService.SendEmailToUsers(users, latestEmailSubject, latestEmailBody) + return c.RenderJson(re) } // send Email dialog -func (c AdminEmail) SendEmailDialog(emails string) revel.Result{ +func (c AdminEmail) SendEmailDialog(emails string) revel.Result { emailsArr := strings.Split(emails, ",") emailsNl := strings.Join(emailsArr, "\n") - + c.RenderArgs["emailsNl"] = emailsNl c.RenderArgs["str"] = configService.GlobalStringConfigs c.RenderArgs["map"] = configService.GlobalMapConfigs - - return c.RenderTemplate("admin/email/emailDialog.html"); + + return c.RenderTemplate("admin/email/emailDialog.html") } func (c AdminEmail) SendToUsers(userFilterEmail, userFilterWhiteList, userFilterBlackList, latestEmailSubject, latestEmailBody string, verified, saveAsOldEmail bool) revel.Result { re := info.NewRe() - + c.updateConfig([]string{"userFilterEmail", "userFilterWhiteList", "userFilterBlackList", "latestEmailSubject", "latestEmailBody"}) - + if latestEmailSubject == "" || latestEmailBody == "" { re.Msg = "subject or body is blank" return c.RenderJson(re) } - + if saveAsOldEmail { oldEmails := configService.GetGlobalMapConfig("oldEmails") oldEmails[latestEmailSubject] = latestEmailBody - configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails); + configService.UpdateGlobalMapConfig(c.GetUserId(), "oldEmails", oldEmails) } - + users := userService.GetAllUserByFilter(userFilterEmail, userFilterWhiteList, userFilterBlackList, verified) - - if(users == nil || len(users) == 0) { + + if users == nil || len(users) == 0 { re.Ok = false re.Msg = "no users" return c.RenderJson(re) } - - re.Ok, re.Msg = emailService.SendEmailToUsers(users, latestEmailSubject, latestEmailBody); - if(!re.Ok) { + + re.Ok, re.Msg = emailService.SendEmailToUsers(users, latestEmailSubject, latestEmailBody) + if !re.Ok { return c.RenderJson(re) } - + re.Ok = true re.Msg = "users:" + strconv.Itoa(len(users)) - + return c.RenderJson(re) } @@ -227,10 +226,10 @@ func (c AdminEmail) DeleteEmails(ids string) revel.Result { func (c AdminEmail) List(sorter, keywords string) revel.Result { pageNumber := c.GetPage() - sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"email", "ok", "subject", "createdTime"}); - pageInfo, emails := emailService.ListEmailLogs(pageNumber, userPageSize, sorterField, isAsc, keywords); + sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"email", "ok", "subject", "createdTime"}) + pageInfo, emails := emailService.ListEmailLogs(pageNumber, userPageSize, sorterField, isAsc, keywords) c.RenderArgs["pageInfo"] = pageInfo c.RenderArgs["emails"] = emails c.RenderArgs["keywords"] = keywords - return c.RenderTemplate("admin/email/list.html"); -} \ No newline at end of file + return c.RenderTemplate("admin/email/list.html") +} diff --git a/app/controllers/admin/AdminSettingController.go b/app/controllers/admin/AdminSettingController.go index 7a68416..759ba18 100644 --- a/app/controllers/admin/AdminSettingController.go +++ b/app/controllers/admin/AdminSettingController.go @@ -2,10 +2,10 @@ package admin import ( "github.com/revel/revel" -// . "github.com/leanote/leanote/app/lea" + // . "github.com/leanote/leanote/app/lea" + "fmt" "github.com/leanote/leanote/app/info" "strings" - "fmt" ) // admin 首页 @@ -25,24 +25,24 @@ func (c AdminSetting) Blog() revel.Result { newTags := configService.GetGlobalArrayConfig("newTags") c.RenderArgs["recommendTags"] = strings.Join(recommendTags, ",") c.RenderArgs["newTags"] = strings.Join(newTags, ",") - return c.RenderTemplate("admin/setting/blog.html"); + return c.RenderTemplate("admin/setting/blog.html") } func (c AdminSetting) DoBlogTag(recommendTags, newTags string) revel.Result { re := info.NewRe() - + re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "recommendTags", strings.Split(recommendTags, ",")) re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "newTags", strings.Split(newTags, ",")) - + return c.RenderJson(re) } // 共享设置 -func (c AdminSetting) ShareNote(registerSharedUserId string, - registerSharedNotebookPerms, registerSharedNotePerms []int, +func (c AdminSetting) ShareNote(registerSharedUserId string, + registerSharedNotebookPerms, registerSharedNotePerms []int, registerSharedNotebookIds, registerSharedNoteIds, registerCopyNoteIds []string) revel.Result { - + re := info.NewRe() - re.Ok, re.Msg = configService.UpdateShareNoteConfig(registerSharedUserId, registerSharedNotebookPerms, registerSharedNotePerms, registerSharedNotebookIds, registerSharedNoteIds, registerCopyNoteIds); + re.Ok, re.Msg = configService.UpdateShareNoteConfig(registerSharedUserId, registerSharedNotebookPerms, registerSharedNotePerms, registerSharedNotebookIds, registerSharedNoteIds, registerCopyNoteIds) return c.RenderJson(re) } @@ -51,25 +51,25 @@ func (c AdminSetting) ShareNote(registerSharedUserId string, func (c AdminSetting) Demo() revel.Result { c.RenderArgs["demoUsername"] = configService.GetGlobalStringConfig("demoUsername") c.RenderArgs["demoPassword"] = configService.GetGlobalStringConfig("demoPassword") - return c.RenderTemplate("admin/setting/demo.html"); + return c.RenderTemplate("admin/setting/demo.html") } func (c AdminSetting) DoDemo(demoUsername, demoPassword string) revel.Result { re := info.NewRe() - + userInfo, err := authService.Login(demoUsername, demoPassword) if err != nil { fmt.Println(err) return c.RenderJson(info.Re{Ok: false}) } if userInfo.UserId == "" { - re.Msg = "The User is Not Exists"; + re.Msg = "The User is Not Exists" return c.RenderJson(re) } - + re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoUserId", userInfo.UserId.Hex()) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoUsername", demoUsername) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "demoPassword", demoPassword) - + return c.RenderJson(re) } @@ -83,23 +83,23 @@ func (c AdminSetting) ExportPdf(path string) revel.Result { func (c AdminSetting) SubDomain() revel.Result { c.RenderArgs["str"] = configService.GlobalStringConfigs c.RenderArgs["arr"] = configService.GlobalArrayConfigs - + c.RenderArgs["noteSubDomain"] = configService.GetGlobalStringConfig("noteSubDomain") c.RenderArgs["blogSubDomain"] = configService.GetGlobalStringConfig("blogSubDomain") c.RenderArgs["leaSubDomain"] = configService.GetGlobalStringConfig("leaSubDomain") - - return c.RenderTemplate("admin/setting/subDomain.html"); + + return c.RenderTemplate("admin/setting/subDomain.html") } func (c AdminSetting) DoSubDomain(noteSubDomain, blogSubDomain, leaSubDomain, blackSubDomains, allowCustomDomain, blackCustomDomains string) revel.Result { re := info.NewRe() re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "noteSubDomain", noteSubDomain) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "blogSubDomain", blogSubDomain) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "leaSubDomain", leaSubDomain) - + re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "allowCustomDomain", allowCustomDomain) re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "blackSubDomains", strings.Split(blackSubDomains, ",")) re.Ok = configService.UpdateGlobalArrayConfig(c.GetUserId(), "blackCustomDomains", strings.Split(blackCustomDomains, ",")) - + return c.RenderJson(re) } @@ -133,4 +133,4 @@ func (c AdminSetting) UploadSize(uploadImageSize, uploadAvatarSize, uploadBlogLo re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "uploadBlogLogoSize", fmt.Sprintf("%v", uploadBlogLogoSize)) re.Ok = configService.UpdateGlobalStringConfig(c.GetUserId(), "uploadAttachSize", fmt.Sprintf("%v", uploadAttachSize)) return c.RenderJson(re) -} \ No newline at end of file +} diff --git a/app/controllers/admin/AdminUpgradeController.go b/app/controllers/admin/AdminUpgradeController.go index 8f8f2f3..0ca28fb 100644 --- a/app/controllers/admin/AdminUpgradeController.go +++ b/app/controllers/admin/AdminUpgradeController.go @@ -2,9 +2,9 @@ package admin import ( "github.com/revel/revel" -// "encoding/json" + // "encoding/json" "github.com/leanote/leanote/app/info" -// "io/ioutil" + // "io/ioutil" ) // Upgrade controller @@ -14,7 +14,7 @@ type AdminUpgrade struct { func (c AdminUpgrade) UpgradeBlog() revel.Result { upgradeService.UpgradeBlog() - return nil; + return nil } func (c AdminUpgrade) UpgradeBetaToBeta2() revel.Result { @@ -27,4 +27,4 @@ func (c AdminUpgrade) UpgradeBeta3ToBeta4() revel.Result { re := info.NewRe() re.Ok, re.Msg = upgradeService.Api(c.GetUserId()) return c.RenderJson(re) -} \ No newline at end of file +} diff --git a/app/controllers/admin/AdminUserController.go b/app/controllers/admin/AdminUserController.go index 8e2ba65..73bc1b9 100644 --- a/app/controllers/admin/AdminUserController.go +++ b/app/controllers/admin/AdminUserController.go @@ -1,9 +1,9 @@ package admin import ( - "github.com/revel/revel" . "github.com/leanote/leanote/app/lea" -// "time" + "github.com/revel/revel" + // "time" "github.com/leanote/leanote/app/info" ) @@ -15,37 +15,38 @@ type AdminUser struct { // admin 主页 var userPageSize = 10 + func (c AdminUser) Index(sorter, keywords string, pageSize int) revel.Result { pageNumber := c.GetPage() if userPageSize == 0 { pageSize = userPageSize } - sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"email", "username", "verified", "createdTime", "accountType"}); - pageInfo, users := userService.ListUsers(pageNumber, pageSize, sorterField, isAsc, keywords); + sorterField, isAsc := c.getSorter("CreatedTime", false, []string{"email", "username", "verified", "createdTime", "accountType"}) + pageInfo, users := userService.ListUsers(pageNumber, pageSize, sorterField, isAsc, keywords) c.RenderArgs["pageInfo"] = pageInfo c.RenderArgs["users"] = users c.RenderArgs["keywords"] = keywords - return c.RenderTemplate("admin/user/list.html"); + return c.RenderTemplate("admin/user/list.html") } func (c AdminUser) Add() revel.Result { - return c.RenderTemplate("admin/user/add.html"); + return c.RenderTemplate("admin/user/add.html") } // 添加 func (c AdminUser) Register(email, pwd string) revel.Result { - re := info.NewRe(); - + re := info.NewRe() + if re.Ok, re.Msg = Vd("email", email); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } if re.Ok, re.Msg = Vd("password", pwd); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } - + // 注册 re.Ok, re.Msg = authService.Register(email, pwd, "") - + return c.RenderRe(re) } @@ -53,14 +54,14 @@ func (c AdminUser) Register(email, pwd string) revel.Result { func (c AdminUser) ResetPwd(userId string) revel.Result { userInfo := userService.GetUserInfo(userId) c.RenderArgs["userInfo"] = userInfo - return c.RenderTemplate("admin/user/reset_pwd.html"); + return c.RenderTemplate("admin/user/reset_pwd.html") } func (c AdminUser) DoResetPwd(userId, pwd string) revel.Result { - re := info.NewRe(); + re := info.NewRe() if re.Ok, re.Msg = Vd("password", pwd); !re.Ok { - return c.RenderRe(re); + return c.RenderRe(re) } re.Ok, re.Msg = userService.ResetPwd(c.GetUserId(), userId, pwd) return c.RenderRe(re) -} \ No newline at end of file +} diff --git a/app/controllers/admin/init.go b/app/controllers/admin/init.go index bcd964c..bd97b48 100644 --- a/app/controllers/admin/init.go +++ b/app/controllers/admin/init.go @@ -1,11 +1,11 @@ package admin import ( - "github.com/leanote/leanote/app/service" "github.com/leanote/leanote/app/info" -// . "github.com/leanote/leanote/app/lea" + "github.com/leanote/leanote/app/service" + // . "github.com/leanote/leanote/app/lea" "github.com/revel/revel" -// "strings" + // "strings" ) var userService *service.UserService @@ -19,9 +19,9 @@ var blogService *service.BlogService var tagService *service.TagService var pwdService *service.PwdService var tokenService *service.TokenService -var suggestionService *service.SuggestionService -var albumService *service.AlbumService -var noteImageService *service.NoteImageService +var suggestionService *service.SuggestionService +var albumService *service.AlbumService +var noteImageService *service.NoteImageService var fileService *service.FileService var attachService *service.AttachService var configService *service.ConfigService @@ -31,31 +31,32 @@ var upgradeService *service.UpgradeService // 拦截器 // 不需要拦截的url // Index 除了Note之外都不需要 -var commonUrl = map[string]map[string]bool{"Index": map[string]bool{"Index": true, - "Login": true, - "DoLogin": true, - "Logout": true, - "Register": true, - "DoRegister": true, - "FindPasswword": true, - "DoFindPassword": true, - "FindPassword2": true, - "FindPasswordUpdate": true, - "Suggestion": true, - }, +var commonUrl = map[string]map[string]bool{"Index": map[string]bool{"Index": true, + "Login": true, + "DoLogin": true, + "Logout": true, + "Register": true, + "DoRegister": true, + "FindPasswword": true, + "DoFindPassword": true, + "FindPassword2": true, + "FindPasswordUpdate": true, + "Suggestion": true, +}, "Blog": map[string]bool{"Index": true, - "View": true, - "AboutMe": true, + "View": true, + "AboutMe": true, "SearchBlog": true, - }, + }, // 用户的激活与修改邮箱都不需要登录, 通过链接地址 "User": map[string]bool{"UpdateEmail": true, - "ActiveEmail":true, - }, - "Oauth": map[string]bool{"GithubCallback": true}, - "File": map[string]bool{"OutputImage": true, "OutputFile": true}, + "ActiveEmail": true, + }, + "Oauth": map[string]bool{"GithubCallback": true}, + "File": map[string]bool{"OutputImage": true, "OutputFile": true}, "Attach": map[string]bool{"Download": true, "DownloadAll": true}, } + func needValidate(controller, method string) bool { // 在里面 if v, ok := commonUrl[controller]; ok { @@ -66,33 +67,33 @@ func needValidate(controller, method string) bool { return true } else { // controller不在这里的, 肯定要验证 - return true; + return true } } func AuthInterceptor(c *revel.Controller) revel.Result { // 全部变成首字大写 /* - var controller = strings.Title(c.Name) - var method = strings.Title(c.MethodName) - // 是否需要验证? - if !needValidate(controller, method) { - return nil - } + var controller = strings.Title(c.Name) + var method = strings.Title(c.MethodName) + // 是否需要验证? + if !needValidate(controller, method) { + return nil + } */ - + // 验证是否已登录 // 必须是管理员 if username, ok := c.Session["Username"]; ok && username == configService.GetAdminUsername() { return nil // 已登录 } - + // 没有登录, 判断是否是ajax操作 if c.Request.Header.Get("X-Requested-With") == "XMLHttpRequest" { re := info.NewRe() re.Msg = "NOTLOGIN" return c.RenderJson(re) } - + return c.Redirect("/login") } @@ -110,7 +111,7 @@ func InitService() { tokenService = service.TokenS noteImageService = service.NoteImageS fileService = service.FileS - albumService= service.AlbumS + albumService = service.AlbumS attachService = service.AttachS pwdService = service.PwdS suggestionService = service.SuggestionS diff --git a/app/controllers/api/ApiAuthController.go b/app/controllers/api/ApiAuthController.go index 6f16a37..c651fd1 100644 --- a/app/controllers/api/ApiAuthController.go +++ b/app/controllers/api/ApiAuthController.go @@ -23,7 +23,7 @@ type ApiAuth struct { // 失败返回 {Ok: false, Msg: ""} func (c ApiAuth) Login(email, pwd string) revel.Result { var msg = "" - + userInfo, err := authService.Login(email, pwd) if err == nil { token := bson.NewObjectId().Hex() diff --git a/app/controllers/api/ApiBaseController.go b/app/controllers/api/ApiBaseController.go index b903cc6..1b975aa 100644 --- a/app/controllers/api/ApiBaseController.go +++ b/app/controllers/api/ApiBaseController.go @@ -4,11 +4,11 @@ import ( "github.com/revel/revel" "gopkg.in/mgo.v2/bson" // "encoding/json" - . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/controllers" "github.com/leanote/leanote/app/info" + . "github.com/leanote/leanote/app/lea" "os" -// "fmt" + // "fmt" "io/ioutil" // "fmt" // "math" @@ -43,75 +43,75 @@ func (c ApiBaseContrller) getUserInfo() info.User { // 上传附件 func (c ApiBaseContrller) uploadAttach(name string, noteId string) (ok bool, msg string, id string) { - userId := c.getUserId(); - + userId := c.getUserId() + // 判断是否有权限为笔记添加附件 // 如果笔记还没有添加是不是会有问题 /* - if !shareService.HasUpdateNotePerm(noteId, userId) { - return - } + if !shareService.HasUpdateNotePerm(noteId, userId) { + return + } */ - + file, handel, err := c.Request.FormFile(name) if err != nil { - return + return } defer file.Close() - + data, err := ioutil.ReadAll(file) if err != nil { - return + return } // > 5M? - maxFileSize := configService.GetUploadSize("uploadAttachSize"); + maxFileSize := configService.GetUploadSize("uploadAttachSize") if maxFileSize <= 0 { maxFileSize = 1000 } - if(float64(len(data)) > maxFileSize * float64(1024*1024)) { - msg = "fileIsTooLarge" - return + if float64(len(data)) > maxFileSize*float64(1024*1024) { + msg = "fileIsTooLarge" + return } - + // 生成上传路径 newGuid := NewGuid() - filePath := "files/" + Digest3(userId) + "/" + userId + "/" + Digest2(newGuid) + "/attachs" - - dir := revel.BasePath + "/" + filePath + filePath := "files/" + Digest3(userId) + "/" + userId + "/" + Digest2(newGuid) + "/attachs" + + dir := revel.BasePath + "/" + filePath err = os.MkdirAll(dir, 0755) if err != nil { - return + return } // 生成新的文件名 filename := handel.Filename _, ext := SplitFilename(filename) // .doc filename = newGuid + ext - toPath := dir + "/" + filename; + toPath := dir + "/" + filename err = ioutil.WriteFile(toPath, data, 0777) if err != nil { - return + return } - + // add File to db fileType := "" if ext != "" { fileType = strings.ToLower(ext[1:]) } filesize := GetFilesize(toPath) - fileInfo := info.Attach{AttachId: bson.NewObjectId(), - Name: filename, - Title: handel.Filename, - NoteId: bson.ObjectIdHex(noteId), + fileInfo := info.Attach{AttachId: bson.NewObjectId(), + Name: filename, + Title: handel.Filename, + NoteId: bson.ObjectIdHex(noteId), UploadUserId: bson.ObjectIdHex(userId), - Path: filePath + "/" + filename, - Type: fileType, - Size: filesize} - + Path: filePath + "/" + filename, + Type: fileType, + Size: filesize} + ok, msg = attachService.AddAttach(fileInfo, true) if !ok { return } - + id = fileInfo.AttachId.Hex() return } @@ -123,16 +123,16 @@ func (c ApiBaseContrller) upload(name string, noteId string, isAttach bool) (ok } file, handel, err := c.Request.FormFile(name) if err != nil { - return + return } defer file.Close() - + newGuid := NewGuid() // 生成上传路径 userId := c.getUserId() fileUrlPath := "files/" + Digest3(userId) + "/" + userId + "/" + Digest2(newGuid) + "/images" - - dir := revel.BasePath + "/" + fileUrlPath + + dir := revel.BasePath + "/" + fileUrlPath err = os.MkdirAll(dir, 0755) if err != nil { return @@ -140,7 +140,7 @@ func (c ApiBaseContrller) upload(name string, noteId string, isAttach bool) (ok // 生成新的文件名 filename := handel.Filename _, ext := SplitFilename(filename) - if(ext != ".gif" && ext != ".jpg" && ext != ".png" && ext != ".bmp" && ext != ".jpeg") { + if ext != ".gif" && ext != ".jpg" && ext != ".png" && ext != ".bmp" && ext != ".jpeg" { msg = "notImage" return } @@ -150,35 +150,35 @@ func (c ApiBaseContrller) upload(name string, noteId string, isAttach bool) (ok if err != nil { return } - - maxFileSize := configService.GetUploadSize("uploadImageSize"); + + maxFileSize := configService.GetUploadSize("uploadImageSize") if maxFileSize <= 0 { maxFileSize = 1000 } - + // > 2M? - if(float64(len(data)) > maxFileSize * float64(1024*1024)) { + if float64(len(data)) > maxFileSize*float64(1024*1024) { msg = "fileIsTooLarge" return } - - toPath := dir + "/" + filename; + + toPath := dir + "/" + filename err = ioutil.WriteFile(toPath, data, 0777) if err != nil { - return + return } // 改变成gif图片 _, toPathGif := TransToGif(toPath, 0, true) filename = GetFilename(toPathGif) filesize := GetFilesize(toPathGif) fileUrlPath += "/" + filename - + // File fileInfo := info.File{FileId: bson.NewObjectId(), - Name: filename, + Name: filename, Title: handel.Filename, - Path: fileUrlPath, - Size: filesize} + Path: fileUrlPath, + Size: filesize} ok, msg = fileService.AddImage(fileInfo, "", c.getUserId(), true) if ok { id = fileInfo.FileId.Hex() diff --git a/app/controllers/api/ApiFileController.go b/app/controllers/api/ApiFileController.go index 530e9fe..4432501 100644 --- a/app/controllers/api/ApiFileController.go +++ b/app/controllers/api/ApiFileController.go @@ -3,18 +3,18 @@ package api import ( "github.com/revel/revel" // "encoding/json" -// . "github.com/leanote/leanote/app/lea" -// "gopkg.in/mgo.v2/bson" + // . "github.com/leanote/leanote/app/lea" + // "gopkg.in/mgo.v2/bson" // "github.com/leanote/leanote/app/lea/netutil" -// "github.com/leanote/leanote/app/info" -// "io/ioutil" + // "github.com/leanote/leanote/app/info" + // "io/ioutil" "os" // "strconv" + "archive/tar" + "compress/gzip" "io" - "time" "strings" - "archive/tar" - "compress/gzip" + "time" ) // 文件操作, 图片, 头像上传, 输出 @@ -73,14 +73,14 @@ func (c ApiFile) GetImage(fileId string) revel.Result { // 下载附件 // [OK] func (c ApiFile) GetAttach(fileId string) revel.Result { - attach := attachService.GetAttach(fileId, c.getUserId()); // 得到路径 + attach := attachService.GetAttach(fileId, c.getUserId()) // 得到路径 path := attach.Path if path == "" { return c.RenderText("No Such File") } - fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") - file, _ := os.Open(fn) - return c.RenderBinary(file, attach.Title, revel.Attachment, time.Now()) // revel.Attachment + fn := revel.BasePath + "/" + strings.TrimLeft(path, "/") + file, _ := os.Open(fn) + return c.RenderBinary(file, attach.Title, revel.Attachment, time.Now()) // revel.Attachment } // 下载所有附件 @@ -95,70 +95,69 @@ func (c ApiFile) GetAllAttachs(noteId string) revel.Result { if attachs == nil || len(attachs) == 0 { return c.RenderText("") } - + /* - dir := revel.BasePath + "/files/tmp" - err := os.MkdirAll(dir, 0755) - if err != nil { - return c.RenderText("") - } + dir := revel.BasePath + "/files/tmp" + err := os.MkdirAll(dir, 0755) + if err != nil { + return c.RenderText("") + } */ - + filename := note.Title + ".tar.gz" if note.Title == "" { filename = "all.tar.gz" } - - // file write - fw, err := os.Create(revel.BasePath + "/files/" + filename) - if err != nil { - return c.RenderText("") - } - // defer fw.Close() // 不需要关闭, 还要读取给用户下载 - - // gzip write - gw := gzip.NewWriter(fw) - defer gw.Close() - - // tar write - tw := tar.NewWriter(gw) - defer tw.Close() - - // 遍历文件列表 - for _, attach := range attachs { - fn := revel.BasePath + "/" + strings.TrimLeft(attach.Path, "/") - fr, err := os.Open(fn) - fileInfo, _ := fr.Stat() - if err != nil { - return c.RenderText("") - } - defer fr.Close() - - // 信息头 - h := new(tar.Header) - h.Name = attach.Title - h.Size = fileInfo.Size() - h.Mode = int64(fileInfo.Mode()) - h.ModTime = fileInfo.ModTime() - - // 写信息头 - err = tw.WriteHeader(h) - if err != nil { - panic(err) - } - - // 写文件 - _, err = io.Copy(tw, fr) - if err != nil { - panic(err) - } - } // for - -// tw.Close() -// gw.Close() -// fw.Close() -// file, _ := os.Open(dir + "/" + filename) - // fw.Seek(0, 0) - return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachment -} + // file write + fw, err := os.Create(revel.BasePath + "/files/" + filename) + if err != nil { + return c.RenderText("") + } + // defer fw.Close() // 不需要关闭, 还要读取给用户下载 + + // gzip write + gw := gzip.NewWriter(fw) + defer gw.Close() + + // tar write + tw := tar.NewWriter(gw) + defer tw.Close() + + // 遍历文件列表 + for _, attach := range attachs { + fn := revel.BasePath + "/" + strings.TrimLeft(attach.Path, "/") + fr, err := os.Open(fn) + fileInfo, _ := fr.Stat() + if err != nil { + return c.RenderText("") + } + defer fr.Close() + + // 信息头 + h := new(tar.Header) + h.Name = attach.Title + h.Size = fileInfo.Size() + h.Mode = int64(fileInfo.Mode()) + h.ModTime = fileInfo.ModTime() + + // 写信息头 + err = tw.WriteHeader(h) + if err != nil { + panic(err) + } + + // 写文件 + _, err = io.Copy(tw, fr) + if err != nil { + panic(err) + } + } // for + + // tw.Close() + // gw.Close() + // fw.Close() + // file, _ := os.Open(dir + "/" + filename) + // fw.Seek(0, 0) + return c.RenderBinary(fw, filename, revel.Attachment, time.Now()) // revel.Attachment +} diff --git a/app/controllers/api/ApiNoteController.go b/app/controllers/api/ApiNoteController.go index be344fa..6c97c8c 100644 --- a/app/controllers/api/ApiNoteController.go +++ b/app/controllers/api/ApiNoteController.go @@ -6,11 +6,11 @@ import ( "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" + "os" + "os/exec" "regexp" "strings" "time" - "os/exec" - "os" // "github.com/leanote/leanote/app/types" // "io/ioutil" // "fmt" @@ -58,7 +58,7 @@ func (c ApiNote) GetSyncNotes(afterUsn, maxEntry int) revel.Result { // 得到笔记本下的笔记 // [OK] func (c ApiNote) GetNotes(notebookId string) revel.Result { - if notebookId != "" && !bson.IsObjectIdHex(notebookId) { + if notebookId != "" && !bson.IsObjectIdHex(notebookId) { re := info.NewApiRe() re.Msg = "notebookIdInvalid" return c.RenderJson(re) @@ -72,7 +72,7 @@ func (c ApiNote) GetNotes(notebookId string) revel.Result { func (c ApiNote) GetTrashNotes() revel.Result { _, notes := noteService.ListNotes(c.getUserId(), "", true, c.GetPage(), pageSize, defaultSortField, false, false) return c.RenderJson(noteService.ToApiNotes(notes)) - + } // get Note @@ -125,12 +125,12 @@ func (c ApiNote) GetTrashNotes() revel.Result { } */ func (c ApiNote) GetNote(noteId string) revel.Result { - if !bson.IsObjectIdHex(noteId) { + if !bson.IsObjectIdHex(noteId) { re := info.NewApiRe() re.Msg = "noteIdInvalid" return c.RenderJson(re) } - + note := noteService.GetNote(noteId, c.getUserId()) if note.NoteId == "" { re := info.NewApiRe() @@ -145,7 +145,7 @@ func (c ApiNote) GetNote(noteId string) revel.Result { // [OK] func (c ApiNote) GetNoteAndContent(noteId string) revel.Result { noteAndContent := noteService.GetNoteAndContent(noteId, c.getUserId()) - + apiNotes := noteService.ToApiNotes([]info.Note{noteAndContent.Note}) apiNote := apiNotes[0] apiNote.Content = noteAndContent.Content @@ -156,57 +156,57 @@ func (c ApiNote) GetNoteAndContent(noteId string) revel.Result { // 图片, 附件都替换 func (c ApiNote) fixContent(content string) string { // TODO, 这个url需要从config中取 -// baseUrl := "http://leanote.com" + // baseUrl := "http://leanote.com" baseUrl := configService.GetSiteUrl() -// baseUrl := "http://localhost:9000" - + // baseUrl := "http://localhost:9000" + patterns := []map[string]string{ map[string]string{"src": "src", "middle": "/file/outputImage", "param": "fileId", "to": "getImage?fileId="}, map[string]string{"src": "href", "middle": "/attach/download", "param": "attachId", "to": "getAttach?fileId="}, map[string]string{"src": "href", "middle": "/attach/downloadAll", "param": "noteId", "to": "getAllAttachs?noteId="}, } - + for _, eachPattern := range patterns { - + // src="http://leanote.com/file/outputImage?fileId=5503537b38f4111dcb0000d1" // href="http://leanote.com/attach/download?attachId=5504243a38f4111dcb00017d" // href="http://leanote.com/attach/downloadAll?noteId=55041b6a38f4111dcb000159" - - regImage, _ := regexp.Compile(eachPattern["src"] + `=('|")`+ baseUrl + eachPattern["middle"] + `\?` + eachPattern["param"] + `=([a-z0-9A-Z]{24})("|')`) + + regImage, _ := regexp.Compile(eachPattern["src"] + `=('|")` + baseUrl + eachPattern["middle"] + `\?` + eachPattern["param"] + `=([a-z0-9A-Z]{24})("|')`) findsImage := regImage.FindAllStringSubmatch(content, -1) // 查找所有的 - + // [[src='http://leanote.com/file/outputImage?fileId=54672e8d38f411286b000069" ' 54672e8d38f411286b000069 "] [src="http://leanote.com/file/outputImage?fileId=54672e8d38f411286b000069" " 54672e8d38f411286b000069 "] [src="http://leanote.com/file/outputImage?fileId=54672e8d38f411286b000069" " 54672e8d38f411286b000069 "] [src="http://leanote.com/file/outputImage?fileId=54672e8d38f411286b000069" " 54672e8d38f411286b000069 "]] for _, eachFind := range findsImage { // [src='http://leanote.com/file/outputImage?fileId=54672e8d38f411286b000069" ' 54672e8d38f411286b000069 "] if len(eachFind) == 4 { - content = strings.Replace(content, - eachFind[0], - eachPattern["src"] + "=\"" + baseUrl + "/api/file/" + eachPattern["to"] + eachFind[2] + "\"", - 1); + content = strings.Replace(content, + eachFind[0], + eachPattern["src"]+"=\""+baseUrl+"/api/file/"+eachPattern["to"]+eachFind[2]+"\"", + 1) } } - + // markdown处理 // ![](http://leanote.com/file/outputImage?fileId=5503537b38f4111dcb0000d1) // [selection 2.html](http://leanote.com/attach/download?attachId=5504262638f4111dcb00017f) // [all.tar.gz](http://leanote.com/attach/downloadAll?noteId=5503b57d59f81b4eb4000000) - - pre := "!" // 默认图片 + + pre := "!" // 默认图片 if eachPattern["src"] == "href" { // 是attach pre = "" } - - regImageMarkdown, _ := regexp.Compile(pre + `\[(.*?)\]\(`+ baseUrl + eachPattern["middle"] + `\?` + eachPattern["param"] + `=([a-z0-9A-Z]{24})\)`) + + regImageMarkdown, _ := regexp.Compile(pre + `\[(.*?)\]\(` + baseUrl + eachPattern["middle"] + `\?` + eachPattern["param"] + `=([a-z0-9A-Z]{24})\)`) findsImageMarkdown := regImageMarkdown.FindAllStringSubmatch(content, -1) // 查找所有的 // [[![](http://leanote.com/file/outputImage?fileId=5503537b38f4111dcb0000d1) 5503537b38f4111dcb0000d1] [![你好啊, 我很好, 为什么?](http://leanote.com/file/outputImage?fileId=5503537b38f4111dcb0000d1) 5503537b38f4111dcb0000d1]] for _, eachFind := range findsImageMarkdown { // [![你好啊, 我很好, 为什么?](http://leanote.com/file/outputImage?fileId=5503537b38f4111dcb0000d1) 你好啊, 我很好, 为什么? 5503537b38f4111dcb0000d1] if len(eachFind) == 3 { - content = strings.Replace(content, eachFind[0], pre + "[" + eachFind[1] + "](" + baseUrl + "/api/file/" + eachPattern["to"] + eachFind[2] + ")", 1); + content = strings.Replace(content, eachFind[0], pre+"["+eachFind[1]+"]("+baseUrl+"/api/file/"+eachPattern["to"]+eachFind[2]+")", 1) } } } - + return content } @@ -222,7 +222,7 @@ func (c ApiNote) fixPostNotecontent(noteOrContent *info.ApiNote) { if files != nil && len(files) > 0 { for _, file := range files { if file.LocalFileId != "" { - noteOrContent.Content = strings.Replace(noteOrContent.Content, "fileId=" + file.LocalFileId, "fileId=" + file.FileId, -1) + noteOrContent.Content = strings.Replace(noteOrContent.Content, "fileId="+file.LocalFileId, "fileId="+file.FileId, -1) } } } @@ -236,13 +236,13 @@ func (c ApiNote) GetNoteContent(noteId string) revel.Result { if noteContent.Content != "" { noteContent.Content = c.fixContent(noteContent.Content) } - + apiNoteContent := info.ApiNoteContent{ - NoteId: noteContent.NoteId, - UserId: noteContent.UserId, + NoteId: noteContent.NoteId, + UserId: noteContent.UserId, Content: noteContent.Content, } - + // re.Item = noteContent return c.RenderJson(apiNoteContent) } @@ -255,9 +255,9 @@ func (c ApiNote) AddNote(noteOrContent info.ApiNote) revel.Result { myUserId := userId // 为共享新建? /* - if noteOrContent.FromUserId != "" { - userId = bson.ObjectIdHex(noteOrContent.FromUserId) - } + if noteOrContent.FromUserId != "" { + userId = bson.ObjectIdHex(noteOrContent.FromUserId) + } */ // Log(noteOrContent.Title) // LogJ(noteOrContent) @@ -315,8 +315,8 @@ func (c ApiNote) AddNote(noteOrContent info.ApiNote) revel.Result { c.fixPostNotecontent(¬eOrContent) -// Log("Add") -// LogJ(noteOrContent) + // Log("Add") + // LogJ(noteOrContent) // return c.RenderJson(re) @@ -326,7 +326,7 @@ func (c ApiNote) AddNote(noteOrContent info.ApiNote) revel.Result { Title: noteOrContent.Title, Tags: noteOrContent.Tags, Desc: noteOrContent.Desc, -// ImgSrc: noteOrContent.ImgSrc, + // ImgSrc: noteOrContent.ImgSrc, IsBlog: noteOrContent.IsBlog, IsMarkdown: noteOrContent.IsMarkdown, AttachNum: attachNum, @@ -346,7 +346,7 @@ func (c ApiNote) AddNote(noteOrContent info.ApiNote) revel.Result { } note = noteService.AddNoteAndContentApi(note, noteContent, myUserId) - + if note.NoteId == "" { re.Ok = false return c.RenderJson(re) @@ -386,8 +386,8 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { return c.RenderJson(re) } -// Log("_____________") -// LogJ(noteOrContent) + // Log("_____________") + // LogJ(noteOrContent) /* LogJ(c.Params.Files) LogJ(c.Request.Header) @@ -410,14 +410,14 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { // 如果传了files // TODO 测试 /* - for key, v := range c.Params.Values { - Log(key) - Log(v) - } + for key, v := range c.Params.Values { + Log(key) + Log(v) + } */ -// Log(c.Has("Files[0]")) - if c.Has("Files[0][LocalFileId]") { -// LogJ(c.Params.Files) + // Log(c.Has("Files[0]")) + if c.Has("Files[0][LocalFileId]") { + // LogJ(c.Params.Files) if noteOrContent.Files != nil && len(noteOrContent.Files) > 0 { for i, file := range noteOrContent.Files { if file.HasBody { @@ -444,25 +444,25 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { } } } - -// Log("after upload") -// LogJ(noteOrContent.Files) + + // Log("after upload") + // LogJ(noteOrContent.Files) } - + // 移到外面来, 删除最后一个file时也要处理, 不然总删不掉 // 附件问题, 根据Files, 有些要删除的, 只留下这些 attachService.UpdateOrDeleteAttachApi(noteId, userId, noteOrContent.Files) - + // Desc前台传来 if c.Has("Desc") { needUpdateNote = true noteUpdate["Desc"] = noteOrContent.Desc } /* - if c.Has("ImgSrc") { - needUpdateNote = true - noteUpdate["ImgSrc"] = noteOrContent.ImgSrc - } + if c.Has("ImgSrc") { + needUpdateNote = true + noteUpdate["ImgSrc"] = noteOrContent.ImgSrc + } */ if c.Has("Title") { needUpdateNote = true @@ -472,7 +472,7 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { needUpdateNote = true noteUpdate["IsTrash"] = noteOrContent.IsTrash } - + // 是否是博客 if c.Has("IsBlog") { needUpdateNote = true @@ -532,8 +532,8 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { if noteOrContent.Abstract == "" { noteOrContent.Abstract = SubStringHTML(noteOrContent.Content, 200, "") } -// Log("--------> afte fixed") -// Log(noteOrContent.Content) + // Log("--------> afte fixed") + // Log(noteOrContent.Content) contentOk, contentMsg, afterContentUsn = noteService.UpdateNoteContent(c.getUserId(), noteOrContent.NoteId, noteOrContent.Content, noteOrContent.Abstract, needUpdateNote, noteOrContent.Usn) } @@ -556,8 +556,8 @@ func (c ApiNote) UpdateNote(noteOrContent info.ApiNote) revel.Result { noteOrContent.Usn = re.Usn noteOrContent.UpdatedTime = time.Now() -// Log("after upload") -// LogJ(noteOrContent.Files) + // Log("after upload") + // LogJ(noteOrContent.Files) noteOrContent.UserId = c.getUserId() return c.RenderJson(noteOrContent) @@ -593,7 +593,7 @@ func (c ApiNote) ExportPdf(noteId string) revel.Result { re.Msg = "noteNotExists" return c.RenderJson(re) } - + note := noteService.GetNoteById(noteId) if note.NoteId == "" { re.Msg = "noteNotExists" @@ -625,7 +625,7 @@ func (c ApiNote) ExportPdf(noteId string) revel.Result { if appKey == "" { appKey, _ = revel.Config.String("app.secret") } - + // 生成之 binPath := configService.GetGlobalStringConfig("exportPdfBinPath") // 默认路径 @@ -635,15 +635,15 @@ func (c ApiNote) ExportPdf(noteId string) revel.Result { url := configService.GetSiteUrl() + "/note/toPdf?noteId=" + noteId + "&appKey=" + appKey var cc string - if(note.IsMarkdown) { + if note.IsMarkdown { cc = binPath + " --window-status done \"" + url + "\" \"" + path + "\"" // \"" + cookieDomain + "\" \"" + cookieName + "\" \"" + cookieValue + "\"" } else { cc = binPath + " \"" + url + "\" \"" + path + "\"" // \"" + cookieDomain + "\" \"" + cookieName + "\" \"" + cookieValue + "\"" } - + cmd := exec.Command("/bin/sh", "-c", cc) _, err := cmd.Output() - if err != nil { + if err != nil { re.Msg = "sysError" return c.RenderJson(re) } @@ -660,5 +660,5 @@ func (c ApiNote) ExportPdf(noteId string) revel.Result { } else { filenameReturn += ".pdf" } - return c.RenderBinary(file, filenameReturn, revel.Attachment, time.Now()) // revel.Attachment + return c.RenderBinary(file, filenameReturn, revel.Attachment, time.Now()) // revel.Attachment } diff --git a/app/controllers/api/ApiNotebookController.go b/app/controllers/api/ApiNotebookController.go index 53e8c67..520a998 100644 --- a/app/controllers/api/ApiNotebookController.go +++ b/app/controllers/api/ApiNotebookController.go @@ -2,9 +2,9 @@ package api import ( "github.com/leanote/leanote/app/info" + . "github.com/leanote/leanote/app/lea" "github.com/revel/revel" "gopkg.in/mgo.v2/bson" - . "github.com/leanote/leanote/app/lea" // "io/ioutil" ) @@ -30,17 +30,17 @@ func (c ApiNotebook) fixNotebook(notebook *info.Notebook) info.ApiNotebook { return info.ApiNotebook{} } return info.ApiNotebook{ - NotebookId : notebook.NotebookId, - UserId : notebook.UserId, - ParentNotebookId : notebook.ParentNotebookId, - Seq : notebook.Seq, - Title : notebook.Title, - UrlTitle : notebook.UrlTitle, - IsBlog : notebook.IsBlog, - CreatedTime : notebook.CreatedTime, - UpdatedTime : notebook.UpdatedTime, - Usn: notebook.Usn, - IsDeleted: notebook.IsDeleted, + NotebookId: notebook.NotebookId, + UserId: notebook.UserId, + ParentNotebookId: notebook.ParentNotebookId, + Seq: notebook.Seq, + Title: notebook.Title, + UrlTitle: notebook.UrlTitle, + IsBlog: notebook.IsBlog, + CreatedTime: notebook.CreatedTime, + UpdatedTime: notebook.UpdatedTime, + Usn: notebook.Usn, + IsDeleted: notebook.IsDeleted, } } @@ -86,7 +86,7 @@ func (c ApiNotebook) AddNotebook(title, parentNotebookId string, seq int) revel. // [OK] func (c ApiNotebook) UpdateNotebook(notebookId, title, parentNotebookId string, seq, usn int) revel.Result { re := info.NewApiRe() - + ok, msg, notebook := notebookService.UpdateNotebookApi(c.getUserId(), notebookId, title, parentNotebookId, seq, usn) if !ok { re.Ok = false diff --git a/app/controllers/api/ApiTagController.go b/app/controllers/api/ApiTagController.go index 5b2c58f..14dbcea 100644 --- a/app/controllers/api/ApiTagController.go +++ b/app/controllers/api/ApiTagController.go @@ -3,7 +3,7 @@ package api import ( "github.com/leanote/leanote/app/info" "github.com/revel/revel" -// "gopkg.in/mgo.v2/bson" + // "gopkg.in/mgo.v2/bson" // . "github.com/leanote/leanote/app/lea" // "io/ioutil" ) @@ -53,4 +53,4 @@ func (c ApiTag) DeleteTag(tag string, usn int) revel.Result { re := info.NewReUpdate() re.Ok, re.Msg, re.Usn = tagService.DeleteTagApi(c.getUserId(), tag, usn) return c.RenderJson(re) -} \ No newline at end of file +} diff --git a/app/controllers/api/ApiUserController.go b/app/controllers/api/ApiUserController.go index 1601b4f..a0c5426 100644 --- a/app/controllers/api/ApiUserController.go +++ b/app/controllers/api/ApiUserController.go @@ -3,15 +3,15 @@ package api import ( "github.com/revel/revel" // "encoding/json" - "gopkg.in/mgo.v2/bson" "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" + "gopkg.in/mgo.v2/bson" "time" // "github.com/leanote/leanote/app/types" - "io/ioutil" + "io/ioutil" // "fmt" // "math" - "os" + "os" // "path" // "strconv" @@ -31,10 +31,10 @@ func (c ApiUser) Info() revel.Result { return c.RenderJson(re) } apiUser := info.ApiUser{ - UserId: userInfo.UserId.Hex(), + UserId: userInfo.UserId.Hex(), Username: userInfo.Username, - Email: userInfo.Email, - Logo: userInfo.Logo, + Email: userInfo.Email, + Logo: userInfo.Logo, Verified: userInfo.Verified, } return c.RenderJson(apiUser) @@ -82,7 +82,6 @@ func (c ApiUser) GetSyncState() revel.Result { return c.RenderJson(ret) } - // 头像设置 // 参数file=文件 // 成功返回{Logo: url} 头像新url @@ -112,7 +111,7 @@ func (c ApiUser) uploadImage() (ok bool, msg, url string) { defer file.Close() // 生成上传路径 fileUrlPath = "public/upload/" + c.getUserId() + "/images/logo" - + dir := revel.BasePath + "/" + fileUrlPath err = os.MkdirAll(dir, 0755) if err != nil { @@ -122,11 +121,11 @@ func (c ApiUser) uploadImage() (ok bool, msg, url string) { filename := handel.Filename var ext string - + _, ext = SplitFilename(filename) if ext != ".gif" && ext != ".jpg" && ext != ".png" && ext != ".bmp" && ext != ".jpeg" { msg = "notImage" - return + return } filename = NewGuid() + ext @@ -148,8 +147,8 @@ func (c ApiUser) uploadImage() (ok bool, msg, url string) { LogJ(err) return } - + ok = true url = configService.GetSiteUrl() + "/" + fileUrlPath + "/" + filename - return + return } diff --git a/app/controllers/api/init.go b/app/controllers/api/init.go index 28a9a69..37f9c1c 100644 --- a/app/controllers/api/init.go +++ b/app/controllers/api/init.go @@ -3,7 +3,7 @@ package api import ( "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/service" -// . "github.com/leanote/leanote/app/lea" + // . "github.com/leanote/leanote/app/lea" "github.com/revel/revel" "strings" ) @@ -46,10 +46,10 @@ const ( // 不需要拦截的url var commonUrl = map[string]map[string]bool{"ApiAuth": map[string]bool{"Login": true, "Register": true, - }, +}, // 文件的操作也不用登录, userId会从session中获取 "ApiFile": map[string]bool{"GetImage": true, - "GetAttach": true, + "GetAttach": true, "GetAllAttachs": true, }, } @@ -90,15 +90,15 @@ func AuthInterceptor(c *revel.Controller) revel.Result { if noToken && userId == "" { // 从session中获取, api/file/getImage, api/file/getAttach, api/file/getAllAttach // 客户端 - userId, _ = c.Session["UserId"]; + userId, _ = c.Session["UserId"] } c.Session["_userId"] = userId - + // 是否需要验证? if !needValidate(controller, method) { return nil } - + if userId != "" { return nil // 已登录 } diff --git a/app/controllers/init.go b/app/controllers/init.go index 7fba55a..790b453 100644 --- a/app/controllers/init.go +++ b/app/controllers/init.go @@ -1,10 +1,10 @@ package controllers import ( - "github.com/leanote/leanote/app/service" "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/lea/blog" -// . "github.com/leanote/leanote/app/lea" + "github.com/leanote/leanote/app/service" + // . "github.com/leanote/leanote/app/lea" "github.com/revel/revel" "strings" ) @@ -68,7 +68,7 @@ var commonUrl = map[string]map[string]bool{"Index": map[string]bool{"Index": tru }, "Oauth": map[string]bool{"GithubCallback": true}, "File": map[string]bool{"OutputImage": true, "OutputFile": true}, - "Attach": map[string]bool{"Download": true/*, "DownloadAll": true*/}, + "Attach": map[string]bool{"Download": true /*, "DownloadAll": true*/}, } func needValidate(controller, method string) bool { diff --git a/app/controllers/member/MemberBaseController.go b/app/controllers/member/MemberBaseController.go index 2fac5f4..4db0bb7 100644 --- a/app/controllers/member/MemberBaseController.go +++ b/app/controllers/member/MemberBaseController.go @@ -1,15 +1,15 @@ package member import ( -// "github.com/revel/revel" -// "gopkg.in/mgo.v2/bson" -// "encoding/json" - . "github.com/leanote/leanote/app/lea" + // "github.com/revel/revel" + // "gopkg.in/mgo.v2/bson" + // "encoding/json" "github.com/leanote/leanote/app/controllers" -// "io/ioutil" -// "fmt" -// "math" -// "strconv" + . "github.com/leanote/leanote/app/lea" + // "io/ioutil" + // "fmt" + // "math" + // "strconv" "strings" ) @@ -20,26 +20,26 @@ type MemberBaseController struct { // 得到sorterField 和 isAsc // okSorter = ['email', 'username'] -func (c MemberBaseController) getSorter(sorterField string, isAsc bool, okSorter []string) (string, bool){ +func (c MemberBaseController) getSorter(sorterField string, isAsc bool, okSorter []string) (string, bool) { sorter := "" c.Params.Bind(&sorter, "sorter") if sorter == "" { - return sorterField, isAsc; + return sorterField, isAsc } - + // sorter形式 email-up, email-down s2 := strings.Split(sorter, "-") if len(s2) != 2 { - return sorterField, isAsc; + return sorterField, isAsc } - + // 必须是可用的sorter if okSorter != nil && len(okSorter) > 0 { if !InArray(okSorter, s2[0]) { - return sorterField, isAsc; + return sorterField, isAsc } } - + sorterField = strings.Title(s2[0]) if s2[1] == "up" { isAsc = true @@ -47,7 +47,7 @@ func (c MemberBaseController) getSorter(sorterField string, isAsc bool, okSorter isAsc = false } c.RenderArgs["sorter"] = sorter - return sorterField, isAsc; + return sorterField, isAsc } func (c MemberBaseController) updateConfig(keys []string) { @@ -56,4 +56,4 @@ func (c MemberBaseController) updateConfig(keys []string) { v := c.Params.Values.Get(key) configService.UpdateGlobalStringConfig(userId, key, v) } -} \ No newline at end of file +} diff --git a/app/controllers/member/MemberGroupController.go b/app/controllers/member/MemberGroupController.go index 345a95d..dc6072a 100644 --- a/app/controllers/member/MemberGroupController.go +++ b/app/controllers/member/MemberGroupController.go @@ -1,8 +1,8 @@ package member import ( - "github.com/revel/revel" "github.com/leanote/leanote/app/info" + "github.com/revel/revel" ) // 分组管理 @@ -16,7 +16,7 @@ func (c MemberGroup) Index() revel.Result { c.SetLocale() c.RenderArgs["title"] = "My Group" c.RenderArgs["groups"] = groupService.GetGroupsAndUsers(c.GetUserId()) - return c.RenderTemplate("member/group/index.html"); + return c.RenderTemplate("member/group/index.html") } // 添加分组 diff --git a/app/controllers/member/MemberIndexController.go b/app/controllers/member/MemberIndexController.go index 6393450..50caac6 100644 --- a/app/controllers/member/MemberIndexController.go +++ b/app/controllers/member/MemberIndexController.go @@ -14,13 +14,13 @@ type MemberIndex struct { func (c MemberIndex) Index() revel.Result { c.SetUserInfo() c.RenderArgs["title"] = "Leanote Member Center" - + c.RenderArgs["countNote"] = noteService.CountNote(c.GetUserId()) c.RenderArgs["countBlog"] = noteService.CountBlog(c.GetUserId()) - + c.SetLocale() - - return c.RenderTemplate("member/index.html"); + + return c.RenderTemplate("member/index.html") } // 模板 @@ -33,5 +33,5 @@ func (c MemberIndex) T(t string) revel.Result { } func (c MemberIndex) GetView(view string) revel.Result { - return c.RenderTemplate("admin/" + view); -} \ No newline at end of file + return c.RenderTemplate("admin/" + view) +} diff --git a/app/controllers/member/MemberUserController.go b/app/controllers/member/MemberUserController.go index 4fdb2eb..408daf0 100644 --- a/app/controllers/member/MemberUserController.go +++ b/app/controllers/member/MemberUserController.go @@ -14,21 +14,21 @@ func (c MemberUser) Username() revel.Result { c.SetUserInfo() c.SetLocale() c.RenderArgs["title"] = "Username" - return c.RenderTemplate("member/user/username.html"); + return c.RenderTemplate("member/user/username.html") } func (c MemberUser) Email() revel.Result { c.SetUserInfo() c.SetLocale() c.RenderArgs["title"] = "Email" - return c.RenderTemplate("member/user/email.html"); + return c.RenderTemplate("member/user/email.html") } func (c MemberUser) Password() revel.Result { c.SetUserInfo() c.SetLocale() c.RenderArgs["title"] = "Password" - return c.RenderTemplate("member/user/password.html"); + return c.RenderTemplate("member/user/password.html") } func (c MemberUser) Avatar() revel.Result { @@ -36,11 +36,11 @@ func (c MemberUser) Avatar() revel.Result { c.SetLocale() c.RenderArgs["title"] = "Avatar" c.RenderArgs["globalConfigs"] = configService.GetGlobalConfigForUser() - return c.RenderTemplate("member/user/avatar.html"); + return c.RenderTemplate("member/user/avatar.html") } func (c MemberUser) AddAccount() revel.Result { c.SetUserInfo() c.SetLocale() c.RenderArgs["title"] = "Add Account" - return c.RenderTemplate("member/user/add_account.html"); -} \ No newline at end of file + return c.RenderTemplate("member/user/add_account.html") +} diff --git a/app/controllers/member/init.go b/app/controllers/member/init.go index b52edb0..eea26e6 100644 --- a/app/controllers/member/init.go +++ b/app/controllers/member/init.go @@ -1,11 +1,11 @@ package member import ( - "github.com/leanote/leanote/app/service" "github.com/leanote/leanote/app/info" -// . "github.com/leanote/leanote/app/lea" + "github.com/leanote/leanote/app/service" + // . "github.com/leanote/leanote/app/lea" "github.com/revel/revel" -// "strings" + // "strings" ) var userService *service.UserService @@ -20,9 +20,9 @@ var blogService *service.BlogService var tagService *service.TagService var pwdService *service.PwdService var tokenService *service.TokenService -var suggestionService *service.SuggestionService -var albumService *service.AlbumService -var noteImageService *service.NoteImageService +var suggestionService *service.SuggestionService +var albumService *service.AlbumService +var noteImageService *service.NoteImageService var fileService *service.FileService var attachService *service.AttachService var configService *service.ConfigService @@ -33,31 +33,32 @@ var themeService *service.ThemeService // 拦截器 // 不需要拦截的url // Index 除了Note之外都不需要 -var commonUrl = map[string]map[string]bool{"Index": map[string]bool{"Index": true, - "Login": true, - "DoLogin": true, - "Logout": true, - "Register": true, - "DoRegister": true, - "FindPasswword": true, - "DoFindPassword": true, - "FindPassword2": true, - "FindPasswordUpdate": true, - "Suggestion": true, - }, +var commonUrl = map[string]map[string]bool{"Index": map[string]bool{"Index": true, + "Login": true, + "DoLogin": true, + "Logout": true, + "Register": true, + "DoRegister": true, + "FindPasswword": true, + "DoFindPassword": true, + "FindPassword2": true, + "FindPasswordUpdate": true, + "Suggestion": true, +}, "Blog": map[string]bool{"Index": true, - "View": true, - "AboutMe": true, + "View": true, + "AboutMe": true, "SearchBlog": true, - }, + }, // 用户的激活与修改邮箱都不需要登录, 通过链接地址 "User": map[string]bool{"UpdateEmail": true, - "ActiveEmail":true, - }, - "Oauth": map[string]bool{"GithubCallback": true}, - "File": map[string]bool{"OutputImage": true, "OutputFile": true}, + "ActiveEmail": true, + }, + "Oauth": map[string]bool{"GithubCallback": true}, + "File": map[string]bool{"OutputImage": true, "OutputFile": true}, "Attach": map[string]bool{"Download": true, "DownloadAll": true}, } + func needValidate(controller, method string) bool { // 在里面 if v, ok := commonUrl[controller]; ok { @@ -68,33 +69,33 @@ func needValidate(controller, method string) bool { return true } else { // controller不在这里的, 肯定要验证 - return true; + return true } } func AuthInterceptor(c *revel.Controller) revel.Result { // 全部变成首字大写 /* - var controller = strings.Title(c.Name) - var method = strings.Title(c.MethodName) - // 是否需要验证? - if !needValidate(controller, method) { - return nil - } + var controller = strings.Title(c.Name) + var method = strings.Title(c.MethodName) + // 是否需要验证? + if !needValidate(controller, method) { + return nil + } */ - + // 验证是否已登录 // 必须是管理员 if _, ok := c.Session["Username"]; ok { return nil // 已登录 } - + // 没有登录, 判断是否是ajax操作 if c.Request.Header.Get("X-Requested-With") == "XMLHttpRequest" { re := info.NewRe() re.Msg = "NOTLOGIN" return c.RenderJson(re) } - + return c.Redirect("/login") } @@ -113,7 +114,7 @@ func InitService() { tokenService = service.TokenS noteImageService = service.NoteImageS fileService = service.FileS - albumService= service.AlbumS + albumService = service.AlbumS attachService = service.AttachS pwdService = service.PwdS suggestionService = service.SuggestionS @@ -131,4 +132,4 @@ func init() { revel.InterceptFunc(AuthInterceptor, revel.BEFORE, &MemberGroup{}) revel.OnAppStart(func() { }) -} \ No newline at end of file +} diff --git a/app/db/Mgo.go b/app/db/Mgo.go index 958d345..7f8c181 100644 --- a/app/db/Mgo.go +++ b/app/db/Mgo.go @@ -2,8 +2,8 @@ package db import ( "fmt" - "github.com/revel/revel" . "github.com/leanote/leanote/app/lea" + "github.com/revel/revel" "gopkg.in/mgo.v2" "gopkg.in/mgo.v2/bson" "strings" @@ -61,7 +61,7 @@ var Sessions *mgo.Collection func Init(url, dbname string) { ok := true config := revel.Config - if url == "" { + if url == "" { url, ok = config.String("db.url") if !ok { url, ok = config.String("db.urlEnv") @@ -71,7 +71,7 @@ func Init(url, dbname string) { } else { Log("get db conf from db.url: " + url) } - + if ok { // get dbname from urlEnv urls := strings.Split(url, "/") @@ -81,7 +81,7 @@ func Init(url, dbname string) { if dbname == "" { dbname, _ = config.String("db.dbname") } - + // get db config from host, port, username, password if !ok { host, _ := revel.Config.String("db.host") @@ -124,7 +124,7 @@ func Init(url, dbname string) { // user Users = Session.DB(dbname).C("users") - // group + // group Groups = Session.DB(dbname).C("groups") GroupUsers = Session.DB(dbname).C("group_users") @@ -360,15 +360,15 @@ func Err(err error) bool { // 每个请求之前都要检查!! func CheckMongoSessionLost() { // fmt.Println("检查CheckMongoSessionLostErr") - err := Session.Ping() - if err != nil { - Log("Lost connection to db!") - Session.Refresh() - err = Session.Ping() - if err == nil { - Log("Reconnect to db successful.") - } else { - Log("重连失败!!!! 警告") - } - } + err := Session.Ping() + if err != nil { + Log("Lost connection to db!") + Session.Refresh() + err = Session.Ping() + if err == nil { + Log("Reconnect to db successful.") + } else { + Log("重连失败!!!! 警告") + } + } } diff --git a/app/i18n/i18n.go b/app/i18n/i18n.go index 4df311f..8b257d3 100644 --- a/app/i18n/i18n.go +++ b/app/i18n/i18n.go @@ -1,17 +1,18 @@ package main import ( + "bufio" + "encoding/json" "fmt" "os" - "bufio" "strings" - "encoding/json" ) // convert revel msg to js msg var msgBasePath = "/Users/life/Documents/Go/package2/src/github.com/leanote/leanote/messages/" var targetBasePath = "/Users/life/Documents/Go/package2/src/github.com/leanote/leanote/public/js/i18n/" + func parse(filename string) { file, err := os.Open(msgBasePath + filename) reader := bufio.NewReader(file) @@ -22,41 +23,41 @@ func parse(filename string) { } for true { line, _, err := reader.ReadLine() - + if err != nil { break } - + if len(line) == 0 { continue } // 对每一行进行处理 if line[0] == '#' || line[1] == '#' { - continue; + continue } lineStr := string(line) - + // 找到第一个=位置 pos := strings.Index(lineStr, "=") - + if pos < 0 { - continue; + continue } - + key := string(line[0:pos]) value := string(line[pos+1:]) - -// fmt.Println(lineStr) -// fmt.Println(value) - + + // fmt.Println(lineStr) + // fmt.Println(value) + msg[key] = value } - + // JSON b, _ := json.Marshal(msg) str := string(b) - fmt.Println(str); - + fmt.Println(str) + targetName := targetBasePath + filename + ".js" file2, err2 := os.OpenFile(targetName, os.O_RDWR|os.O_CREATE, 0644) if err2 != nil { diff --git a/app/info/Api.go b/app/info/Api.go index 5b19413..2610c93 100644 --- a/app/info/Api.go +++ b/app/info/Api.go @@ -1,20 +1,20 @@ package info import ( - "time" "gopkg.in/mgo.v2/bson" + "time" ) //--------- // 数据结构 //--------- type NoteFile struct { - FileId string // 服务器端Id + FileId string // 服务器端Id LocalFileId string // 客户端Id - Type string // images/png, doc, xls, 根据fileName确定 - Title string - HasBody bool // 传过来的值是否要更新内容 - IsAttach bool // 是否是附件, 不是附件就是图片 + Type string // images/png, doc, xls, 根据fileName确定 + Title string + HasBody bool // 传过来的值是否要更新内容 + IsAttach bool // 是否是附件, 不是附件就是图片 } type ApiNote struct { NoteId string @@ -22,32 +22,31 @@ type ApiNote struct { UserId string Title string Desc string -// ImgSrc string + // ImgSrc string Tags []string Abstract string Content string IsMarkdown bool -// FromUserId string // 为共享而新建 - IsBlog bool // 是否是blog, 更新note不需要修改, 添加note时才有可能用到, 此时需要判断notebook是否设为Blog - IsTrash bool - IsDeleted bool - Usn int - Files []NoteFile + // FromUserId string // 为共享而新建 + IsBlog bool // 是否是blog, 更新note不需要修改, 添加note时才有可能用到, 此时需要判断notebook是否设为Blog + IsTrash bool + IsDeleted bool + Usn int + Files []NoteFile CreatedTime time.Time UpdatedTime time.Time - PublicTime time.Time + PublicTime time.Time } - // 内容 type ApiNoteContent struct { NoteId bson.ObjectId `bson:"_id,omitempty"` UserId bson.ObjectId `bson:"UserId"` - Content string `Content` + Content string `Content` -// CreatedTime time.Time `CreatedTime` -// UpdatedTime time.Time `UpdatedTime` + // CreatedTime time.Time `CreatedTime` + // UpdatedTime time.Time `UpdatedTime` } // 转换 @@ -61,11 +60,11 @@ func NoteToApiNote(note Note, files []NoteFile) ApiNote { //---------- type ApiUser struct { - UserId string + UserId string Username string - Email string + Email string Verified bool - Logo string + Logo string } //---------- @@ -81,8 +80,8 @@ type ApiNotebook struct { IsBlog bool `IsBlog,omitempty` // 是否是Blog 2013/12/29 新加 CreatedTime time.Time `CreatedTime,omitempty` UpdatedTime time.Time `UpdatedTime,omitempty` - Usn int `Usn` // UpdateSequenceNum - IsDeleted bool `IsDeleted` + Usn int `Usn` // UpdateSequenceNum + IsDeleted bool `IsDeleted` } //--------- @@ -91,7 +90,7 @@ type ApiNotebook struct { // 一般返回 type ApiRe struct { - Ok bool + Ok bool Msg string } @@ -101,19 +100,20 @@ func NewApiRe() ApiRe { // auth type AuthOk struct { - Ok bool - Token string - UserId bson.ObjectId - Email string + Ok bool + Token string + UserId bson.ObjectId + Email string Username string } // 供notebook, note, tag更新的返回数据用 type ReUpdate struct { - Ok bool + Ok bool Msg string Usn int } + func NewReUpdate() ReUpdate { return ReUpdate{Ok: false} -} \ No newline at end of file +} diff --git a/app/info/AttachInfo.go b/app/info/AttachInfo.go index 4dc39ef..a276d1c 100644 --- a/app/info/AttachInfo.go +++ b/app/info/AttachInfo.go @@ -7,15 +7,15 @@ import ( // Attach belongs to note type Attach struct { - AttachId bson.ObjectId `bson:"_id,omitempty"` // - NoteId bson.ObjectId `bson:"NoteId"` // - UploadUserId bson.ObjectId `bson:"UploadUserId"` // 可以不是note owner, 协作者userId - Name string `Name` // file name, md5, such as 13232312.doc - Title string `Title` // raw file name - Size int64 `Size` // file size (byte) - Type string `Type` // file type, "doc" = word - Path string `Path` // the file path such as: files/userId/attachs/adfadf.doc - CreatedTime time.Time `CreatedTime` - + AttachId bson.ObjectId `bson:"_id,omitempty"` // + NoteId bson.ObjectId `bson:"NoteId"` // + UploadUserId bson.ObjectId `bson:"UploadUserId"` // 可以不是note owner, 协作者userId + Name string `Name` // file name, md5, such as 13232312.doc + Title string `Title` // raw file name + Size int64 `Size` // file size (byte) + Type string `Type` // file type, "doc" = word + Path string `Path` // the file path such as: files/userId/attachs/adfadf.doc + CreatedTime time.Time `CreatedTime` + // FromFileId bson.ObjectId `bson:"FromFileId,omitempty"` // copy from fileId, for collaboration } diff --git a/app/info/BlogCustom.go b/app/info/BlogCustom.go index aed4b24..6853465 100644 --- a/app/info/BlogCustom.go +++ b/app/info/BlogCustom.go @@ -7,51 +7,52 @@ import ( // 仅仅为了博客的主题 type BlogInfoCustom struct { - UserId string - Username string - UserLogo string - Title string - SubTitle string - Logo string + UserId string + Username string + UserLogo string + Title string + SubTitle string + Logo string OpenComment bool CommentType string - ThemeId string - SubDomain string - Domain string + ThemeId string + SubDomain string + Domain string } type Post struct { - NoteId string - Title string - UrlTitle string - ImgSrc string + NoteId string + Title string + UrlTitle string + ImgSrc string CreatedTime time.Time UpdatedTime time.Time - PublicTime time.Time - Desc string - Abstract string - Content string - Tags []string - CommentNum int - ReadNum int - LikeNum int - IsMarkdown bool + PublicTime time.Time + Desc string + Abstract string + Content string + Tags []string + CommentNum int + ReadNum int + LikeNum int + IsMarkdown bool } + // 归档 type ArchiveMonth struct { Month int Posts []*Post } type Archive struct { - Year int + Year int MonthAchives []ArchiveMonth - Posts []*Post + Posts []*Post } type Cate struct { - CateId string + CateId string ParentCateId string - Title string - UrlTitle string - Children []*Cate + Title string + UrlTitle string + Children []*Cate } diff --git a/app/info/BlogInfo.go b/app/info/BlogInfo.go index 24dafae..4be64c8 100644 --- a/app/info/BlogInfo.go +++ b/app/info/BlogInfo.go @@ -9,17 +9,17 @@ import ( type BlogItem struct { Note - Abstract string - Content string // 可能是content的一部分, 截取. 点击more后就是整个信息了 - HasMore bool // 是否是否还有 - User User // 用户信息 + Abstract string + Content string // 可能是content的一部分, 截取. 点击more后就是整个信息了 + HasMore bool // 是否是否还有 + User User // 用户信息 } type UserBlogBase struct { Logo string `Logo` Title string `Title` // 标题 SubTitle string `SubTitle` // 副标题 -// AboutMe string `AboutMe` // 关于我 + // AboutMe string `AboutMe` // 关于我 } type UserBlogComment struct { @@ -49,32 +49,32 @@ type UserBlog struct { Style string `Style` // 风格 Css string `Css` // 自定义css - ThemeId bson.ObjectId `ThemeId,omitempty` // 主题Id - ThemePath string `bson:"ThemePath" json:"-"` // 不存值, 从Theme中获取, 相对路径 public/ + ThemeId bson.ObjectId `ThemeId,omitempty` // 主题Id + ThemePath string `bson:"ThemePath" json:"-"` // 不存值, 从Theme中获取, 相对路径 public/ CateIds []string `CateIds,omitempty` // 分类Id, 排序好的 - Singles []map[string]string `Singles,omitempty` // 单页, 排序好的, map包含: ["Title"], ["SingleId"] - - PerPageSize int `PerPageSize,omitempty` - SortField string `SortField` // 排序字段 - IsAsc bool `IsAsc,omitempty` // 排序类型, 降序, 升序, 默认是false, 表示降序 + Singles []map[string]string `Singles,omitempty` // 单页, 排序好的, map包含: ["Title"], ["SingleId"] + + PerPageSize int `PerPageSize,omitempty` + SortField string `SortField` // 排序字段 + IsAsc bool `IsAsc,omitempty` // 排序类型, 降序, 升序, 默认是false, 表示降序 SubDomain string `SubDomain` // 二级域名 Domain string `Domain` // 自定义域名 - + } // 博客统计信息 type BlogStat struct { - NoteId bson.ObjectId `bson:"_id,omitempty"` - ReadNum int `ReadNum,omitempty` // 阅读次数 2014/9/28 - LikeNum int `LikeNum,omitempty` // 点赞次数 2014/9/28 - CommentNum int `CommentNum,omitempty` // 评论次数 2014/9/28 + NoteId bson.ObjectId `bson:"_id,omitempty"` + ReadNum int `ReadNum,omitempty` // 阅读次数 2014/9/28 + LikeNum int `LikeNum,omitempty` // 点赞次数 2014/9/28 + CommentNum int `CommentNum,omitempty` // 评论次数 2014/9/28 } // 单页 type BlogSingle struct { - SingleId bson.ObjectId `bson:"_id,omitempty"` + SingleId bson.ObjectId `bson:"_id,omitempty"` UserId bson.ObjectId `UserId` Title string `Title` UrlTitle string `UrlTitle` // 2014/11/11 @@ -117,12 +117,12 @@ type BlogCommentPublic struct { } type BlogUrls struct { - IndexUrl string - CateUrl string - SearchUrl string - SingleUrl string - PostUrl string - ArchiveUrl string - TagsUrl string + IndexUrl string + CateUrl string + SearchUrl string + SingleUrl string + PostUrl string + ArchiveUrl string + TagsUrl string TagPostsUrl string } diff --git a/app/info/Configinfo.go b/app/info/Configinfo.go index 1fbecd5..7ddf4b8 100644 --- a/app/info/Configinfo.go +++ b/app/info/Configinfo.go @@ -10,9 +10,9 @@ type Config struct { ConfigId bson.ObjectId `bson:"_id"` UserId bson.ObjectId `UserId` Key string `Key` - ValueStr string `ValueStr,omitempty` // "1" - ValueArr []string `ValueArr,omitempty` // ["1","b","c"] - ValueMap map[string]string `ValueMap,omitempty` // {"a":"bb", "CC":"xx"} + ValueStr string `ValueStr,omitempty` // "1" + ValueArr []string `ValueArr,omitempty` // ["1","b","c"] + ValueMap map[string]string `ValueMap,omitempty` // {"a":"bb", "CC":"xx"} ValueArrMap []map[string]string `ValueArrMap,omitempty` // [{"a":"B"}, {}, {}] IsArr bool `IsArr` // 是否是数组 IsMap bool `IsMap` // 是否是Map diff --git a/app/info/NoteImage.go b/app/info/NoteImage.go index 38643cf..3ad349c 100644 --- a/app/info/NoteImage.go +++ b/app/info/NoteImage.go @@ -9,4 +9,4 @@ type NoteImage struct { NoteImageId bson.ObjectId `bson:"_id,omitempty"` // 必须要设置bson:"_id" 不然mgo不会认为是主键 NoteId bson.ObjectId `bson:"NoteId"` // 笔记 ImageId bson.ObjectId `bson:"ImageId"` // 图片fileId -} \ No newline at end of file +} diff --git a/app/info/NoteInfo.go b/app/info/NoteInfo.go index 1dd31f5..01eaa15 100644 --- a/app/info/NoteInfo.go +++ b/app/info/NoteInfo.go @@ -34,15 +34,15 @@ type Note struct { IsMarkdown bool `IsMarkdown` // 是否是markdown笔记, 默认是false AttachNum int `AttachNum` // 2014/9/21, attachments num - + CreatedTime time.Time `CreatedTime` UpdatedTime time.Time `UpdatedTime` RecommendTime time.Time `RecommendTime,omitempty` // 推荐时间 PublicTime time.Time `PublicTime,omitempty` // 发表时间, 公开为博客则设置 UpdatedUserId bson.ObjectId `bson:"UpdatedUserId"` // 如果共享了, 并可写, 那么可能是其它他修改了 - + // 2015/1/15, 更新序号 - Usn int `Usn` // UpdateSequenceNum + Usn int `Usn` // UpdateSequenceNum IsDeleted bool `IsDeleted` // 删除位 } diff --git a/app/info/NotebookInfo.go b/app/info/NotebookInfo.go index baeb2a0..39719da 100644 --- a/app/info/NotebookInfo.go +++ b/app/info/NotebookInfo.go @@ -19,9 +19,9 @@ type Notebook struct { IsBlog bool `IsBlog,omitempty` // 是否是Blog 2013/12/29 新加 CreatedTime time.Time `CreatedTime,omitempty` UpdatedTime time.Time `UpdatedTime,omitempty` - + // 2015/1/15, 更新序号 - Usn int `Usn` // UpdateSequenceNum + Usn int `Usn` // UpdateSequenceNum IsDeleted bool `IsDeleted` } diff --git a/app/info/Re.go b/app/info/Re.go index 19951a8..a415edd 100644 --- a/app/info/Re.go +++ b/app/info/Re.go @@ -1,18 +1,17 @@ package info -import ( -) +import () // controller ajax返回 type Re struct { - Ok bool + Ok bool Code int - Msg string - Id string + Msg string + Id string List interface{} Item interface{} } func NewRe() Re { return Re{Ok: false} -} \ No newline at end of file +} diff --git a/app/info/SessionInfo.go b/app/info/SessionInfo.go index d08386d..d054c31 100644 --- a/app/info/SessionInfo.go +++ b/app/info/SessionInfo.go @@ -13,8 +13,8 @@ type Session struct { LoginTimes int `LoginTimes` // 登录错误时间 Captcha string `Captcha` // 验证码 - - UserId string `UserId` // API时有值UserId + + UserId string `UserId` // API时有值UserId CreatedTime time.Time `CreatedTime` UpdatedTime time.Time `UpdatedTime` // 更新时间, expire这个时间会自动清空 diff --git a/app/info/TagInfo.go b/app/info/TagInfo.go index c7e67de..fe96dda 100644 --- a/app/info/TagInfo.go +++ b/app/info/TagInfo.go @@ -18,28 +18,28 @@ type TagNote struct { // 每个用户一条记录, 存储用户的所有tags type Tag struct { - UserId bson.ObjectId `bson:"_id"` - Tags []string `Tags` + UserId bson.ObjectId `bson:"_id"` + Tags []string `Tags` } // v2 版标签 type NoteTag struct { - TagId bson.ObjectId `bson:"_id"` - UserId bson.ObjectId `UserId` // 谁的 - Tag string `Tag` // UserId, Tag是唯一索引 - Usn int `Usn` // Update Sequence Number - Count int `Count` // 笔记数 - CreatedTime time.Time `CreatedTime` - UpdatedTime time.Time `UpdatedTime` - IsDeleted bool `IsDeleted` // 删除位 + TagId bson.ObjectId `bson:"_id"` + UserId bson.ObjectId `UserId` // 谁的 + Tag string `Tag` // UserId, Tag是唯一索引 + Usn int `Usn` // Update Sequence Number + Count int `Count` // 笔记数 + CreatedTime time.Time `CreatedTime` + UpdatedTime time.Time `UpdatedTime` + IsDeleted bool `IsDeleted` // 删除位 } type TagCount struct { TagCountId bson.ObjectId `bson:"_id,omitempty"` - UserId bson.ObjectId `UserId` // 谁的 - Tag string `Tag` - IsBlog bool `IsBlog` // 是否是博客的tag统计 - Count int `Count` // 统计数量 + UserId bson.ObjectId `UserId` // 谁的 + Tag string `Tag` + IsBlog bool `IsBlog` // 是否是博客的tag统计 + Count int `Count` // 统计数量 } /* diff --git a/app/info/ThemeInfo.go b/app/info/ThemeInfo.go index 2f96f72..5ab1013 100644 --- a/app/info/ThemeInfo.go +++ b/app/info/ThemeInfo.go @@ -18,7 +18,7 @@ type Theme struct { Info map[string]interface{} `Info` // 所有信息 IsActive bool `IsActive` // 是否在用 - IsDefault bool `IsDefault` // leanote默认主题, 如果用户修改了默认主题, 则先copy之. 也是admin用户的主题 + IsDefault bool `IsDefault` // leanote默认主题, 如果用户修改了默认主题, 则先copy之. 也是admin用户的主题 Style string `Style,omitempty` // 之前的, 只有default的用户才有blog_default, blog_daqi, blog_left_fixed CreatedTime time.Time `CreatedTime` diff --git a/app/info/TokenInfo.go b/app/info/TokenInfo.go index a27a58b..c43b295 100644 --- a/app/info/TokenInfo.go +++ b/app/info/TokenInfo.go @@ -18,7 +18,7 @@ const ( // 过期时间 const ( - PwdOverHours = 2.0 + PwdOverHours = 2.0 ActiveEmailOverHours = 48.0 UpdateEmailOverHours = 2.0 ) @@ -29,4 +29,4 @@ type Token struct { Token string `Token` Type int `Type` CreatedTime time.Time `CreatedTime` -} \ No newline at end of file +} diff --git a/app/info/UserInfo.go b/app/info/UserInfo.go index 11d83e2..c4b5df0 100644 --- a/app/info/UserInfo.go +++ b/app/info/UserInfo.go @@ -73,8 +73,8 @@ type UserAccount struct { // note主页需要 type UserAndBlogUrl struct { User - BlogUrl string `BlogUrl` - PostUrl string `PostUrl` + BlogUrl string `BlogUrl` + PostUrl string `PostUrl` } // 用户与博客信息结合, 公开 diff --git a/app/info/common.go b/app/info/common.go index 25ef0e0..0e05447 100644 --- a/app/info/common.go +++ b/app/info/common.go @@ -4,14 +4,13 @@ import ( "math" ) - // 分页数据 type Page struct { - CurPage int // 当前页码 - TotalPage int // 总页 + CurPage int // 当前页码 + TotalPage int // 总页 PerPageSize int - Count int // 总记录数 - List interface{} + Count int // 总记录数 + List interface{} } func NewPage(page, perPageSize, count int, list interface{}) Page { diff --git a/app/init.go b/app/init.go index 0adf5b3..1bf7c62 100644 --- a/app/init.go +++ b/app/init.go @@ -1,77 +1,77 @@ package app import ( - "github.com/revel/revel" - . "github.com/leanote/leanote/app/lea" - "github.com/leanote/leanote/app/service" - "github.com/leanote/leanote/app/db" + "encoding/json" + "fmt" "github.com/leanote/leanote/app/controllers" - "github.com/leanote/leanote/app/controllers/api" "github.com/leanote/leanote/app/controllers/admin" + "github.com/leanote/leanote/app/controllers/api" "github.com/leanote/leanote/app/controllers/member" + "github.com/leanote/leanote/app/db" + . "github.com/leanote/leanote/app/lea" _ "github.com/leanote/leanote/app/lea/binder" "github.com/leanote/leanote/app/lea/route" - "reflect" - "fmt" + "github.com/leanote/leanote/app/service" + "github.com/revel/revel" "html/template" "math" - "strings" - "strconv" - "time" - "encoding/json" "net/url" + "reflect" + "strconv" + "strings" + "time" ) func init() { // Filters is the default set of global filters. revel.Filters = []revel.Filter{ - revel.PanicFilter, // Recover from panics and display an error page instead. + revel.PanicFilter, // Recover from panics and display an error page instead. route.RouterFilter, // revel.RouterFilter, // Use the routing table to select the right Action // AuthFilter, // Invoke the action. revel.FilterConfiguringFilter, // A hook for adding or removing per-Action filters. revel.ParamsFilter, // Parse parameters into Controller.Params. revel.SessionFilter, // Restore and write the session cookie. - + // 使用SessionFilter标准版从cookie中得到sessionID, 然后通过MssessionFilter从Memcache中得到 // session, 之后MSessionFilter将session只存sessionID然后返回给SessionFilter返回到web - // session.SessionFilter, // leanote session - // session.MSessionFilter, // leanote memcache session - - revel.FlashFilter, // Restore and write the flash cookie. - revel.ValidationFilter, // Restore kept validation errors and save new ones from cookie. - revel.I18nFilter, // Resolve the requested language - revel.InterceptorFilter, // Run interceptors around the action. - revel.CompressFilter, // Compress the result. - revel.ActionInvoker, // Invoke the action. + // session.SessionFilter, // leanote session + // session.MSessionFilter, // leanote memcache session + + revel.FlashFilter, // Restore and write the flash cookie. + revel.ValidationFilter, // Restore kept validation errors and save new ones from cookie. + revel.I18nFilter, // Resolve the requested language + revel.InterceptorFilter, // Run interceptors around the action. + revel.CompressFilter, // Compress the result. + revel.ActionInvoker, // Invoke the action. } - + revel.TemplateFuncs["raw"] = func(str string) template.HTML { return template.HTML(str) } revel.TemplateFuncs["trim"] = func(str string) string { str = strings.Trim(str, " ") str = strings.Trim(str, " ") - + str = strings.Trim(str, "\n") str = strings.Trim(str, " ") - + // 以下两个空格不一样 str = strings.Trim(str, " ") str = strings.Trim(str, " ") return str } revel.TemplateFuncs["add"] = func(i int) string { - i = i + 1; + i = i + 1 return fmt.Sprintf("%v", i) } revel.TemplateFuncs["sub"] = func(i int) int { - i = i - 1; + i = i - 1 return i } // 增加或减少 revel.TemplateFuncs["incr"] = func(n, i int) int { - n = n + i; + n = n + i return n } revel.TemplateFuncs["join"] = func(arr []string) template.HTML { @@ -95,11 +95,11 @@ func init() { return v.Get("a") } revel.TemplateFuncs["json"] = func(i interface{}) string { - b, _ := json.Marshal(i) + b, _ := json.Marshal(i) return string(b) } revel.TemplateFuncs["jsonJs"] = func(i interface{}) template.JS { - b, _ := json.Marshal(i) + b, _ := json.Marshal(i) return template.JS(string(b)) } revel.TemplateFuncs["datetime"] = func(t time.Time) template.HTML { @@ -113,10 +113,10 @@ func init() { t := time.Unix(int64(sec), 0) return template.HTML(t.Format("2006-01-02 15:04:05")) } - + // interface是否有该字段 revel.TemplateFuncs["has"] = func(i interface{}, key string) bool { - t := reflect.TypeOf(i) + t := reflect.TypeOf(i) _, ok := t.FieldByName(key) return ok } @@ -130,9 +130,9 @@ func init() { locale, _ := renderArgs[revel.CurrentLocaleRenderArg].(string) tagStr := "" lenTags := len(tags) - + tagPostUrl, _ := renderArgs["tagPostsUrl"].(string) - + for i, tag := range tags { str := revel.Message(locale, tag) var classes = "label" @@ -144,24 +144,24 @@ func init() { } else { classes += " label-default" } - + classes += " label-post" var url = tagPostUrl + "/" + url.QueryEscape(tag) - tagStr += "" + str + ""; - if i != lenTags - 1 { + tagStr += "" + str + "" + if i != lenTags-1 { tagStr += " " } } return template.HTML(tagStr) } - + revel.TemplateFuncs["blogTagsForExport"] = func(renderArgs map[string]interface{}, tags []string) template.HTML { if tags == nil || len(tags) == 0 { return "" } tagStr := "" lenTags := len(tags) - + for i, tag := range tags { str := tag var classes = "label" @@ -170,16 +170,16 @@ func init() { } else { classes += " label-default" } - + classes += " label-post" - tagStr += "" + str + ""; - if i != lenTags - 1 { + tagStr += "" + str + "" + if i != lenTags-1 { tagStr += " " } } return template.HTML(tagStr) } - + // 不用revel的msg revel.TemplateFuncs["leaMsg"] = func(renderArgs map[string]interface{}, key string) template.HTML { locale, _ := renderArgs[revel.CurrentLocaleRenderArg].(string) @@ -187,7 +187,7 @@ func init() { if strings.HasPrefix(str, "???") { str = key } - return template.HTML(str); + return template.HTML(str) } // lea++ @@ -198,16 +198,16 @@ func init() { locale, _ := renderArgs[revel.CurrentLocaleRenderArg].(string) tagStr := "" lenTags := len(tags) - + tagPostUrl := "http://lea.leanote.com/" if typeStr == "recommend" { - tagPostUrl += "?tag="; + tagPostUrl += "?tag=" } else if typeStr == "latest" { - tagPostUrl += "latest?tag="; + tagPostUrl += "latest?tag=" } else { - tagPostUrl += "subscription?tag="; + tagPostUrl += "subscription?tag=" } - + for i, tag := range tags { str := revel.Message(locale, tag) var classes = "label" @@ -221,66 +221,66 @@ func init() { } classes += " label-post" var url = tagPostUrl + url.QueryEscape(tag) - tagStr += "" + str + ""; - if i != lenTags - 1 { + tagStr += "" + str + "" + if i != lenTags-1 { tagStr += " " } } return template.HTML(tagStr) } - + /* - revel.TemplateFuncs["blogTags"] = func(tags []string) template.HTML { - if tags == nil || len(tags) == 0 { - return "" - } - // TODO 这里判断语言, 从语言包中拿 - tagMap := map[string]string{"red": "红色", "yellow": "黄色", "blue": "蓝色", "green": "绿色"} - tagStr := "" - lenTags := len(tags) - for i, tag := range tags { - if text, ok := tagMap[tag]; ok { - tagStr += text - } else { - tagStr += tag + revel.TemplateFuncs["blogTags"] = func(tags []string) template.HTML { + if tags == nil || len(tags) == 0 { + return "" } - if i != lenTags - 1 { - tagStr += "," + // TODO 这里判断语言, 从语言包中拿 + tagMap := map[string]string{"red": "红色", "yellow": "黄色", "blue": "蓝色", "green": "绿色"} + tagStr := "" + lenTags := len(tags) + for i, tag := range tags { + if text, ok := tagMap[tag]; ok { + tagStr += text + } else { + tagStr += tag + } + if i != lenTags - 1 { + tagStr += "," + } } + return template.HTML(tagStr) } - return template.HTML(tagStr) - } */ revel.TemplateFuncs["li"] = func(a string) string { return "" } // str连接 - revel.TemplateFuncs["urlConcat"] = func(url string, v... interface{}) string { + revel.TemplateFuncs["urlConcat"] = func(url string, v ...interface{}) string { html := "" for i := 0; i < len(v); i = i + 2 { item := v[i] if i+1 == len(v) { - break; + break } value := v[i+1] if item != nil && value != nil { - keyStr, _ := item.(string) - valueStr, err := value.(string) - if !err { - valueInt, _ := value.(int) - valueStr = strconv.Itoa(valueInt) - } - if keyStr != "" && valueStr != "" { - s := keyStr + "=" + valueStr - if html != "" { - html += "&" + s - } else { - html += s - } - } - } + keyStr, _ := item.(string) + valueStr, err := value.(string) + if !err { + valueInt, _ := value.(int) + valueStr = strconv.Itoa(valueInt) + } + if keyStr != "" && valueStr != "" { + s := keyStr + "=" + valueStr + if html != "" { + html += "&" + s + } else { + html += s + } + } + } } - + if html != "" { if strings.Index(url, "?") >= 0 { return url + "&" + html @@ -290,11 +290,11 @@ func init() { } return url } - + revel.TemplateFuncs["urlCond"] = func(url string, sorterI, keyords interface{}) template.HTML { return "" } - + // http://stackoverflow.com/questions/14226416/go-lang-templates-always-quotes-a-string-and-removes-comments revel.TemplateFuncs["rawMsg"] = func(renderArgs map[string]interface{}, message string, args ...interface{}) template.JS { str, ok := renderArgs[revel.CurrentLocaleRenderArg].(string) @@ -303,38 +303,38 @@ func init() { } return template.JS(revel.Message(str, message, args...)) } - + // 为后台管理sorter th使用 // 必须要返回HTMLAttr, 返回html, golang 会执行安全检查返回ZgotmplZ // sorterI 可能是nil, 所以用interfalce{}来接收 /* - data-url="/adminUser/index" - data-sorter="email" - class="th-sortable {{if eq .sorter "email-up"}}th-sort-up{{else}}{{if eq .sorter "email-down"}}th-sort-down{{end}}{{end}}" + data-url="/adminUser/index" + data-sorter="email" + class="th-sortable {{if eq .sorter "email-up"}}th-sort-up{{else}}{{if eq .sorter "email-down"}}th-sort-down{{end}}{{end}}" */ revel.TemplateFuncs["sorterTh"] = func(url, sorterField string, sorterI interface{}) template.HTMLAttr { sorter := "" if sorterI != nil { sorter, _ = sorterI.(string) } - html := "data-url=\"" + url + "\" data-sorter=\"" + sorterField + "\""; - html += " class=\"th-sortable "; - if sorter == sorterField + "-up" { - html += "th-sort-up\""; - } else if(sorter == sorterField + "-down") { - html += "th-sort-down"; + html := "data-url=\"" + url + "\" data-sorter=\"" + sorterField + "\"" + html += " class=\"th-sortable " + if sorter == sorterField+"-up" { + html += "th-sort-up\"" + } else if sorter == sorterField+"-down" { + html += "th-sort-down" } - html += "\""; + html += "\"" return template.HTMLAttr(html) } - + // pagination revel.TemplateFuncs["page"] = func(urlBase string, page, pageSize, count int) template.HTML { if count == 0 { - return ""; + return "" } - totalPage := int(math.Ceil(float64(count)/float64(pageSize))) - + totalPage := int(math.Ceil(float64(count) / float64(pageSize))) + preClass := "" prePage := page - 1 if prePage == 0 { @@ -343,10 +343,10 @@ func init() { nextClass := "" nextPage := page + 1 var preUrl, nextUrl string - - preUrl = urlBase + "?page=" + strconv.Itoa(prePage) + + preUrl = urlBase + "?page=" + strconv.Itoa(prePage) nextUrl = urlBase + "?page=" + strconv.Itoa(nextPage) - + // 没有上一页了 if page == 1 { preClass = "disabled" @@ -364,49 +364,49 @@ func init() { // http://play.golang.org/p/snygrVpQva // http://grokbase.com/t/gg/golang-nuts/142a6dhfh3/go-nuts-text-template-using-comparison-operators-eq-gt-etc-on-non-existent-variable-causes-the-template-to-stop-outputting-but-with-no-error-correct-behaviour /* - revel.TemplateFuncs["gt"] = func(a1, a2 interface{}) bool { - switch a1.(type) { - case string: - switch a2.(type) { + revel.TemplateFuncs["gt"] = func(a1, a2 interface{}) bool { + switch a1.(type) { case string: - return reflect.ValueOf(a1).String() > reflect.ValueOf(a2).String() - } - case int, int8, int16, int32, int64: - switch a2.(type) { + switch a2.(type) { + case string: + return reflect.ValueOf(a1).String() > reflect.ValueOf(a2).String() + } case int, int8, int16, int32, int64: - return reflect.ValueOf(a1).Int() > reflect.ValueOf(a2).Int() - } - case uint, uint8, uint16, uint32, uint64: - switch a2.(type) { + switch a2.(type) { + case int, int8, int16, int32, int64: + return reflect.ValueOf(a1).Int() > reflect.ValueOf(a2).Int() + } case uint, uint8, uint16, uint32, uint64: - return reflect.ValueOf(a1).Uint() > reflect.ValueOf(a2).Uint() - } - case float32, float64: - switch a2.(type) { + switch a2.(type) { + case uint, uint8, uint16, uint32, uint64: + return reflect.ValueOf(a1).Uint() > reflect.ValueOf(a2).Uint() + } case float32, float64: - return reflect.ValueOf(a1).Float() > reflect.ValueOf(a2).Float() + switch a2.(type) { + case float32, float64: + return reflect.ValueOf(a1).Float() > reflect.ValueOf(a2).Float() + } } + return false } - return false - } */ - + /* - {{range $i := N 1 10}} -
{{$i}}
- {{end}} - */ + {{range $i := N 1 10}} +
{{$i}}
+ {{end}} + */ revel.TemplateFuncs["N"] = func(start, end int) (stream chan int) { - stream = make(chan int) - go func() { - for i := start; i <= end; i++ { - stream <- i - } - close(stream) - }() - return + stream = make(chan int) + go func() { + for i := start; i <= end; i++ { + stream <- i + } + close(stream) + }() + return } - + // init Email revel.OnAppStart(func() { // 数据库 diff --git a/app/lea/Debug.go b/app/lea/Debug.go index 7684521..70fbf51 100644 --- a/app/lea/Debug.go +++ b/app/lea/Debug.go @@ -2,8 +2,8 @@ package lea import ( "encoding/json" - "github.com/revel/revel" "fmt" + "github.com/revel/revel" ) func Log(i interface{}) { @@ -11,7 +11,7 @@ func Log(i interface{}) { } func LogJ(i interface{}) { - b, _ := json.MarshalIndent(i, "", " ") + b, _ := json.MarshalIndent(i, "", " ") revel.INFO.Println(string(b)) } @@ -21,6 +21,6 @@ func L(i interface{}) { } func LJ(i interface{}) { - b, _ := json.MarshalIndent(i, "", " ") + b, _ := json.MarshalIndent(i, "", " ") fmt.Println(string(b)) } diff --git a/app/lea/Email.go b/app/lea/Email.go index 7f5812c..ab9fd88 100644 --- a/app/lea/Email.go +++ b/app/lea/Email.go @@ -1,10 +1,11 @@ package lea import ( + "github.com/revel/revel" "net/smtp" "strings" - "github.com/revel/revel" ) + // 发送邮件 var host = "smtp.ym.163.com" var port = "25" @@ -12,7 +13,7 @@ var username = "noreply@leanote.com" var password = "---" func InitEmail() { - config := revel.Config; + config := revel.Config host, _ = config.String("email.host") port, _ = config.String("email.port") username, _ = config.String("email.username") @@ -56,26 +57,27 @@ var bodyTpl = ` ` + func SendEmailOld(to, subject, body string) bool { hp := strings.Split(host, ":") auth := smtp.PlainAuth("", username, password, hp[0]) - + var content_type string - + mailtype := "html" if mailtype == "html" { - content_type = "Content-Type: text/"+ mailtype + "; charset=UTF-8" - } else{ + content_type = "Content-Type: text/" + mailtype + "; charset=UTF-8" + } else { content_type = "Content-Type: text/plain" + "; charset=UTF-8" } - + //body = strings.Replace(bodyTpl, "$body", body, 1) //body = strings.Replace(body, "$title", title, 1) - msg := []byte("To: " + to + "\r\nFrom: " + username + "<"+ username +">\r\nSubject: " + subject + "\r\n" + content_type + "\r\n\r\n" + body) + msg := []byte("To: " + to + "\r\nFrom: " + username + "<" + username + ">\r\nSubject: " + subject + "\r\n" + content_type + "\r\n\r\n" + body) send_to := strings.Split(to, ";") err := smtp.SendMail(host+":"+port, auth, username, send_to, msg) - + if err != nil { Log(err) return false @@ -85,5 +87,5 @@ func SendEmailOld(to, subject, body string) bool { func SendToLeanoteOld(subject, title, body string) { to := "leanote@leanote.com" - SendEmailOld(to, subject, body); -} \ No newline at end of file + SendEmailOld(to, subject, body) +} diff --git a/app/lea/File.go b/app/lea/File.go index 13ddb62..8b54944 100644 --- a/app/lea/File.go +++ b/app/lea/File.go @@ -116,13 +116,13 @@ func CopyDir(source string, dest string) (err error) { // create sub-directories - recursively err = CopyDir(sourcefilepointer, destinationfilepointer) if err != nil { -// fmt.Println(err) + // fmt.Println(err) } } else { // perform copy _, err = CopyFile(sourcefilepointer, destinationfilepointer) if err != nil { -// fmt.Println(err) + // fmt.Println(err) } } } diff --git a/app/lea/Image.go b/app/lea/Image.go index f79d195..2f47b55 100644 --- a/app/lea/Image.go +++ b/app/lea/Image.go @@ -16,7 +16,7 @@ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPat transPath = path wand.Genesis() defer wand.Terminus() - + w := wand.NewMagickWand() defer w.Destroy() @@ -24,7 +24,7 @@ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPat fmt.Println(err); return; } - + width := w.ImageWidth() height := w.ImageHeight() if maxWidth != 0 { @@ -34,14 +34,14 @@ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPat width = maxWidth } } - + w.SetImageFormat("GIF"); if err := paint.Thumbnail(w, width, height); err != nil { fmt.Println(err); return; } - + // 判断是否是gif图片, 是就不用转换了 baseName, ext := SplitFilename(path) var toPath string @@ -50,19 +50,19 @@ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPat } else { toPath = TransferExt(path, ".gif"); } - + if err := w.WriteImage(toPath); err != nil { fmt.Println(err); return; } - + if afterDelete { os.Remove(path) } - + ok = true transPath = toPath - + return } @@ -71,7 +71,7 @@ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPat func Reset(path string, maxWidth uint) (ok bool, transPath string){ wand.Genesis() defer wand.Terminus() - + w := wand.NewMagickWand() defer w.Destroy() @@ -79,7 +79,7 @@ func Reset(path string, maxWidth uint) (ok bool, transPath string){ fmt.Println(err); return; } - + width := w.ImageWidth() height := w.ImageHeight() if maxWidth != 0 { @@ -93,20 +93,20 @@ func Reset(path string, maxWidth uint) (ok bool, transPath string){ fmt.Println(err); return; } - + toPath := TransferExt(path, ".gif"); if err := w.WriteImage(toPath); err != nil { fmt.Println(err); return; } - + ok = true transPath = toPath - + return } */ func TransToGif(path string, maxWidth uint, afterDelete bool) (ok bool, transPath string) { return ok, path -} \ No newline at end of file +} diff --git a/app/lea/Pwd.go b/app/lea/Pwd.go index 290e343..21cfe36 100644 --- a/app/lea/Pwd.go +++ b/app/lea/Pwd.go @@ -7,7 +7,7 @@ func ComparePwd(rawPwd, dbPwd string) bool { if len(dbPwd) == 32 { return Md5(rawPwd) == dbPwd } - + hex := []byte(dbPwd) return CompareHash(hex, rawPwd) } @@ -19,4 +19,4 @@ func GenPwd(rawPwd string) string { return "" } return string(digest) -} \ No newline at end of file +} diff --git a/app/lea/Util.go b/app/lea/Util.go index f366762..4ff66f7 100644 --- a/app/lea/Util.go +++ b/app/lea/Util.go @@ -1,19 +1,19 @@ package lea import ( - "fmt" - "regexp" + "bytes" "crypto/md5" "crypto/rand" "encoding/base64" "encoding/hex" - "io" - "gopkg.in/mgo.v2/bson" - "time" - "strings" + "fmt" "github.com/PuerkitoBio/goquery" - "bytes" - math_rand "math/rand" + "gopkg.in/mgo.v2/bson" + "io" + math_rand "math/rand" + "regexp" + "strings" + "time" ) // 字符串 @@ -31,14 +31,14 @@ func Digest3(str string) string { for _, k := range str { b += k } - return fmt.Sprintf("%d", b % 1000) + return fmt.Sprintf("%d", b%1000) } func Digest2(str string) string { var b rune = 0 for _, k := range str { b += k } - return fmt.Sprintf("%d", b % 100) + return fmt.Sprintf("%d", b%100) } // Guid @@ -77,7 +77,7 @@ func Substr(str string, start, length int) string { func substr(str string, start, length int, isRune bool) string { rs := []rune(str) rs2 := []byte(str) - + rl := len(rs) if !isRune { rl = len(rs2) @@ -161,7 +161,7 @@ func SubStringHTMLToRaw(param string, length int) string { continue } else if temp == '>' { isCode = false - resultRune[n] = ' '; + resultRune[n] = ' ' n++ if n >= length { @@ -170,7 +170,7 @@ func SubStringHTMLToRaw(param string, length int) string { continue } if !isCode { - resultRune[n] = temp; + resultRune[n] = temp // s += string(temp) n++ if n >= length { @@ -192,13 +192,13 @@ func fixHtml(result string) string { // 把
]*>", "<$1>") - + // 3 只能用正则,+stack来去有结束的 // golang的正则暂不支持back reference, 以后可以用它来去掉重复的标签 p, _ := regexp.Compile("<(/?[a-zA-Z]+)[^<>]*>") // 得到所有的
,
... strs := p.FindAllString(tempResult, -1) -// fmt.Println(strs) + // fmt.Println(strs) stack := make([]string, len(strs)) stackP := -1 for _, each := range strs { @@ -215,14 +215,14 @@ func fixHtml(result string) string { // 补全tag if stackP != -1 { fmt.Println(stack[0 : stackP+1]) - + for _, each := range stack[0 : stackP+1] { if each[1] != '/' { result += "", "", 1) html = strings.Replace(html, "", "", 1) - + // TODO 把style="float: left"去掉 return html - - // 如果有错误, 则使用自己的方法补全, 有风险 + + // 如果有错误, 则使用自己的方法补全, 有风险 } else { return fixHtml(result) } @@ -305,7 +305,7 @@ func IsGoodPwd(pwd string) (bool, string) { // 是否是email func IsEmail(email string) bool { if email == "" { - return false; + return false } ok, _ := regexp.MatchString(`^([a-zA-Z0-9]+[_|\_|\.|\-]?)*[_a-z\-A-Z0-9]+@([a-zA-Z0-9]+[_|\_|\.|\-]?)*[a-zA-Z0-9\-]+\.[0-9a-zA-Z]{2,6}$`, email) return ok @@ -314,7 +314,7 @@ func IsEmail(email string) bool { // 是否只包含数字, 字母 -, _ func IsUsername(username string) bool { if username == "" { - return false; + return false } ok, _ := regexp.MatchString(`[^0-9a-zA-Z_\-]`, username) return !ok @@ -351,15 +351,15 @@ func RandomPwd(num int) string { chars[j] = byte(i) j++ } - j--; - + j-- + str := "" math_rand.Seed(time.Now().UnixNano()) for i := 0; i < num; i++ { x := math_rand.Intn(j) str += string(chars[x]) } - + return str } @@ -379,14 +379,14 @@ func InArray(arr []string, str string) bool { func FixFilename(filename string) string { if filename != "" { // 把特殊字段给替换掉 -// str := `life "%&()+,/:;<>=?@\|` + // str := `life "%&()+,/:;<>=?@\|` // . == \\. // $ === \\$ reg, _ := regexp.Compile("\\.|/|#|\\$|!|\\^|\\*|'| |\"|%|&|\\(|\\)|\\+|\\,|/|:|;|<|>|=|\\?|@|\\||\\\\") filename = reg.ReplaceAllString(filename, "-") filename = strings.Trim(filename, "-") // 左右单独的-去掉 // 把空格替换成- -// filename = strings.Replace(filename, " ", "-", -1) + // filename = strings.Replace(filename, " ", "-", -1) for strings.Index(filename, "--") >= 0 { // 防止出现连续的-- filename = strings.Replace(filename, "--", "-", -1) } diff --git a/app/lea/Vd.go b/app/lea/Vd.go index 6dcf409..0f6effb 100644 --- a/app/lea/Vd.go +++ b/app/lea/Vd.go @@ -2,8 +2,8 @@ package lea import ( "encoding/json" - "strconv" "regexp" + "strconv" ) // 验证 @@ -38,15 +38,15 @@ var rulesStr = `{ ` var rulesMap map[string][]map[string]string -var rules = map[string]func(string, map[string]string)(bool, string) { - "required": func(value string, rule map[string]string)(ok bool, msg string) { +var rules = map[string]func(string, map[string]string) (bool, string){ + "required": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } ok = true - return + return }, - "minLength": func(value string, rule map[string]string)(ok bool, msg string) { + "minLength": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } @@ -55,7 +55,7 @@ var rules = map[string]func(string, map[string]string)(bool, string) { ok = len(value) >= dataI return }, - "min": func(value string, rule map[string]string)(ok bool, msg string) { + "min": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } @@ -65,8 +65,8 @@ var rules = map[string]func(string, map[string]string)(bool, string) { ok = vI >= dataI return }, - - "sortField": func(value string, rule map[string]string)(ok bool, msg string) { + + "sortField": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } @@ -74,22 +74,22 @@ var rules = map[string]func(string, map[string]string)(bool, string) { ok = InArray(sortFields, value) return }, - - "password": func(value string, rule map[string]string)(ok bool, msg string) { + + "password": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } ok = len(value) >= 6 return }, - "email": func(value string, rule map[string]string)(ok bool, msg string) { + "email": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } ok = IsEmail(value) return }, - "noSpecialChars": func(value string, rule map[string]string)(ok bool, msg string) { + "noSpecialChars": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { return } @@ -97,8 +97,8 @@ var rules = map[string]func(string, map[string]string)(bool, string) { return }, // www.baidu.com - // - "domain": func(value string, rule map[string]string)(ok bool, msg string) { + // + "domain": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { ok = true return // 可为空 @@ -106,16 +106,16 @@ var rules = map[string]func(string, map[string]string)(bool, string) { ok2, _ := regexp.MatchString(`[^0-9a-zA-Z_\.\-]`, value) ok = !ok2 if !ok { - return + return } ok = true return }, // abcd - "subDomain": func(value string, rule map[string]string)(ok bool, msg string) { + "subDomain": func(value string, rule map[string]string) (ok bool, msg string) { if value == "" { ok = true - return // 可为空 + return // 可为空 } if len(value) < 4 { ok = false @@ -137,7 +137,7 @@ func InitVd() { func Vd(name, value string) (ok bool, msg string) { rs, _ := rulesMap[name] - + for _, rule := range rs { ruleFunc, _ := rules[rule["rule"]] if ok2, msg2 := ruleFunc(value, rule); !ok2 { @@ -151,11 +151,11 @@ func Vd(name, value string) (ok bool, msg string) { if msgData != "" { msg += "-" + msgData } - return + return } } ok = true - return + return } func Vds(m map[string]string) (ok bool, msg string) { @@ -166,5 +166,5 @@ func Vds(m map[string]string) (ok bool, msg string) { } } ok = true - return + return } diff --git a/app/lea/archive/tar.go b/app/lea/archive/tar.go index 3bb914f..13cfe72 100644 --- a/app/lea/archive/tar.go +++ b/app/lea/archive/tar.go @@ -1,12 +1,12 @@ package archive import ( - "archive/tar" - "compress/gzip" - "fmt" - "io" - "os" - "path" + "archive/tar" + "compress/gzip" + "fmt" + "io" + "os" + "path" ) // main functions shows how to TarGz a directory/file and @@ -16,66 +16,66 @@ import ( func main() { /* - os.Mkdir("/home/ty4z2008/tar", 0777) - w, err := CopyFile("/home/ty4z2008/tar/1.pdf", "/home/ty4z2008/src/1.pdf") - //targetfile,sourcefile - if err != nil { - fmt.Println(err.Error()) - } - fmt.Println(w) + os.Mkdir("/home/ty4z2008/tar", 0777) + w, err := CopyFile("/home/ty4z2008/tar/1.pdf", "/home/ty4z2008/src/1.pdf") + //targetfile,sourcefile + if err != nil { + fmt.Println(err.Error()) + } + fmt.Println(w) - TarGz("/home/ty4z2008/tar/1.pdf", "/home/ty4z2008/test.tar.gz") //压缩 - //UnTarGz("/home/ty4z2008/1.tar.gz", "/home/ty4z2008") //解压 - os.RemoveAll("/home/ty4z2008/tar") - */ -// TaZip("/Users/life/Desktop/j", "/Users/life/Desktop/aaa.tar.gz") - Zip("/Users/life/Desktop/j", "/Users/life/Desktop/aaa.zip") - fmt.Println("ok") + TarGz("/home/ty4z2008/tar/1.pdf", "/home/ty4z2008/test.tar.gz") //压缩 + //UnTarGz("/home/ty4z2008/1.tar.gz", "/home/ty4z2008") //解压 + os.RemoveAll("/home/ty4z2008/tar") + */ + // TaZip("/Users/life/Desktop/j", "/Users/life/Desktop/aaa.tar.gz") + Zip("/Users/life/Desktop/j", "/Users/life/Desktop/aaa.zip") + fmt.Println("ok") } func TarGz(srcDirPath string, destFilePath string) (ok bool) { - defer func() { //必须要先声明defer,否则不能捕获到panic异常 + defer func() { //必须要先声明defer,否则不能捕获到panic异常 if err := recover(); err != nil { ok = false } - + }() - fw, err := os.Create(destFilePath) - - if err != nil { - panic(err) - } - defer fw.Close() + fw, err := os.Create(destFilePath) - // Gzip writer - gw := gzip.NewWriter(fw) - defer gw.Close() + if err != nil { + panic(err) + } + defer fw.Close() - // Tar writer - tw := tar.NewWriter(gw) - defer tw.Close() + // Gzip writer + gw := gzip.NewWriter(fw) + defer gw.Close() - // Check if it's a file or a directory - f, err := os.Open(srcDirPath) - if err != nil { - panic(err) - } - fi, err := f.Stat() - if err != nil { - panic(err) - } - if fi.IsDir() { - // handle source directory -// fmt.Println("Cerating tar.gz from directory...") - tarGzDir(srcDirPath, path.Base(srcDirPath), tw) - } else { - // handle file directly -// fmt.Println("Cerating tar.gz from " + fi.Name() + "...") - tarGzFile(srcDirPath, fi.Name(), tw, fi) - } - ok = true - return + // Tar writer + tw := tar.NewWriter(gw) + defer tw.Close() + + // Check if it's a file or a directory + f, err := os.Open(srcDirPath) + if err != nil { + panic(err) + } + fi, err := f.Stat() + if err != nil { + panic(err) + } + if fi.IsDir() { + // handle source directory + // fmt.Println("Cerating tar.gz from directory...") + tarGzDir(srcDirPath, path.Base(srcDirPath), tw) + } else { + // handle file directly + // fmt.Println("Cerating tar.gz from " + fi.Name() + "...") + tarGzFile(srcDirPath, fi.Name(), tw, fi) + } + ok = true + return } // Deal with directories @@ -83,148 +83,148 @@ func TarGz(srcDirPath string, destFilePath string) (ok bool) { // Every recurrence append the base path to the recPath // recPath is the path inside of tar.gz func tarGzDir(srcDirPath string, recPath string, tw *tar.Writer) { - // Open source diretory - dir, err := os.Open(srcDirPath) - if err != nil { - panic(err) - } - defer dir.Close() + // Open source diretory + dir, err := os.Open(srcDirPath) + if err != nil { + panic(err) + } + defer dir.Close() - // Get file info slice - fis, err := dir.Readdir(0) - if err != nil { - panic(err) - } - for _, fi := range fis { - // Append path - curPath := srcDirPath + "/" + fi.Name() - // Check it is directory or file - if fi.IsDir() { - // Directory - // (Directory won't add unitl all subfiles are added) -// fmt.Printf("Adding path...%s\n", curPath) - tarGzDir(curPath, recPath+"/"+fi.Name(), tw) - } else { - // File -// fmt.Printf("Adding file...%s\n", curPath) - } + // Get file info slice + fis, err := dir.Readdir(0) + if err != nil { + panic(err) + } + for _, fi := range fis { + // Append path + curPath := srcDirPath + "/" + fi.Name() + // Check it is directory or file + if fi.IsDir() { + // Directory + // (Directory won't add unitl all subfiles are added) + // fmt.Printf("Adding path...%s\n", curPath) + tarGzDir(curPath, recPath+"/"+fi.Name(), tw) + } else { + // File + // fmt.Printf("Adding file...%s\n", curPath) + } - tarGzFile(curPath, recPath+"/"+fi.Name(), tw, fi) - } + tarGzFile(curPath, recPath+"/"+fi.Name(), tw, fi) + } } // Deal with files func tarGzFile(srcFile string, recPath string, tw *tar.Writer, fi os.FileInfo) { - if fi.IsDir() { -// fmt.Println("??") - // Create tar header - hdr := new(tar.Header) - // if last character of header name is '/' it also can be directory - // but if you don't set Typeflag, error will occur when you untargz - hdr.Name = recPath // + "/" -// fmt.Println(hdr.Name) - hdr.Typeflag = tar.TypeDir -// hdr.Size = 0 - //hdr.Mode = 0755 | c_ISDIR -// hdr.Mode = int64(fi.Mode()) // 加这个会有错误!!! -// hdr.ModTime = fi.ModTime() // 加这个会有错误!! + if fi.IsDir() { + // fmt.Println("??") + // Create tar header + hdr := new(tar.Header) + // if last character of header name is '/' it also can be directory + // but if you don't set Typeflag, error will occur when you untargz + hdr.Name = recPath // + "/" + // fmt.Println(hdr.Name) + hdr.Typeflag = tar.TypeDir + // hdr.Size = 0 + //hdr.Mode = 0755 | c_ISDIR + // hdr.Mode = int64(fi.Mode()) // 加这个会有错误!!! + // hdr.ModTime = fi.ModTime() // 加这个会有错误!! - // Write hander - err := tw.WriteHeader(hdr) - if err != nil { - panic(err) - } - } else { - // File reader - fr, err := os.Open(srcFile) - if err != nil { - panic(err) - } - defer fr.Close() + // Write hander + err := tw.WriteHeader(hdr) + if err != nil { + panic(err) + } + } else { + // File reader + fr, err := os.Open(srcFile) + if err != nil { + panic(err) + } + defer fr.Close() - // Create tar header - hdr := new(tar.Header) - hdr.Name = recPath -// fmt.Println(hdr.Name) - hdr.Size = fi.Size() - hdr.Mode = int64(fi.Mode()) - hdr.ModTime = fi.ModTime() + // Create tar header + hdr := new(tar.Header) + hdr.Name = recPath + // fmt.Println(hdr.Name) + hdr.Size = fi.Size() + hdr.Mode = int64(fi.Mode()) + hdr.ModTime = fi.ModTime() - // Write hander - err = tw.WriteHeader(hdr) - if err != nil { - panic(err) - } + // Write hander + err = tw.WriteHeader(hdr) + if err != nil { + panic(err) + } - // Write file data - _, err = io.Copy(tw, fr) - if err != nil { - panic(err) - } - } + // Write file data + _, err = io.Copy(tw, fr) + if err != nil { + panic(err) + } + } } // Ungzip and untar from source file to destination directory // you need check file exist before you call this function func UnTarGz(srcFilePath string, destDirPath string) { -// fmt.Println("UnTarGzing " + srcFilePath + "...") - // Create destination directory - os.Mkdir(destDirPath, os.ModePerm) + // fmt.Println("UnTarGzing " + srcFilePath + "...") + // Create destination directory + os.Mkdir(destDirPath, os.ModePerm) - fr, err := os.Open(srcFilePath) - if err != nil { - panic(err) - } - defer fr.Close() + fr, err := os.Open(srcFilePath) + if err != nil { + panic(err) + } + defer fr.Close() - // Gzip reader - gr, err := gzip.NewReader(fr) - if err != nil { - panic(err) - } - defer gr.Close() + // Gzip reader + gr, err := gzip.NewReader(fr) + if err != nil { + panic(err) + } + defer gr.Close() - // Tar reader - tr := tar.NewReader(gr) + // Tar reader + tr := tar.NewReader(gr) - for { - hdr, err := tr.Next() - if err == io.EOF { - // End of tar archive - break - } - //handleError(err) -// fmt.Println("UnTarGzing file..." + hdr.Name) - // Check if it is diretory or file - if hdr.Typeflag != tar.TypeDir { - // Get files from archive - // Create diretory before create file - os.MkdirAll(destDirPath+"/"+path.Dir(hdr.Name), os.ModePerm) - // Write data to file - fw, _ := os.Create(destDirPath + "/" + hdr.Name) - if err != nil { - panic(err) - } - _, err = io.Copy(fw, tr) - if err != nil { - panic(err) - } - } - } -// fmt.Println("Well done!") + for { + hdr, err := tr.Next() + if err == io.EOF { + // End of tar archive + break + } + //handleError(err) + // fmt.Println("UnTarGzing file..." + hdr.Name) + // Check if it is diretory or file + if hdr.Typeflag != tar.TypeDir { + // Get files from archive + // Create diretory before create file + os.MkdirAll(destDirPath+"/"+path.Dir(hdr.Name), os.ModePerm) + // Write data to file + fw, _ := os.Create(destDirPath + "/" + hdr.Name) + if err != nil { + panic(err) + } + _, err = io.Copy(fw, tr) + if err != nil { + panic(err) + } + } + } + // fmt.Println("Well done!") } // Copyfile func CopyFile(dstName, srcName string) (written int64, err error) { - src, err := os.Open(srcName) - if err != nil { - return - } - defer src.Close() - dst, err := os.OpenFile(dstName, os.O_WRONLY|os.O_CREATE, 0644) - if err != nil { - return - } - defer dst.Close() - return io.Copy(dst, src) -} \ No newline at end of file + src, err := os.Open(srcName) + if err != nil { + return + } + defer src.Close() + dst, err := os.OpenFile(dstName, os.O_WRONLY|os.O_CREATE, 0644) + if err != nil { + return + } + defer dst.Close() + return io.Copy(dst, src) +} diff --git a/app/lea/archive/zip.go b/app/lea/archive/zip.go index c1a705c..2f5346f 100644 --- a/app/lea/archive/zip.go +++ b/app/lea/archive/zip.go @@ -1,12 +1,12 @@ package archive import ( - "archive/zip" - "fmt" + "archive/zip" + "fmt" + "io" + "os" + "path" "strings" - "io" - "os" - "path" ) // main functions shows how to TarGz a directory/file and @@ -15,43 +15,43 @@ import ( // you need check file exist before you call this function func Zip(srcDirPath string, destFilePath string) (ok bool) { - defer func() { //必须要先声明defer,否则不能捕获到panic异常 + defer func() { //必须要先声明defer,否则不能捕获到panic异常 if err := recover(); err != nil { ok = false } }() - fw, err := os.Create(destFilePath) - - if err != nil { - panic(err) - } - defer fw.Close() + fw, err := os.Create(destFilePath) - // Tar writer - tw := zip.NewWriter(fw) - defer tw.Close() + if err != nil { + panic(err) + } + defer fw.Close() - // Check if it's a file or a directory - f, err := os.Open(srcDirPath) - if err != nil { - panic(err) - } - fi, err := f.Stat() - if err != nil { - panic(err) - } - if fi.IsDir() { - // handle source directory -// fmt.Println("Cerating tar.gz from directory...") - zipDir(srcDirPath, path.Base(srcDirPath), tw) - } else { - // handle file directly -// fmt.Println("Cerating tar.gz from " + fi.Name() + "...") - zipFile(srcDirPath, fi.Name(), tw, fi) - } - ok = true - return + // Tar writer + tw := zip.NewWriter(fw) + defer tw.Close() + + // Check if it's a file or a directory + f, err := os.Open(srcDirPath) + if err != nil { + panic(err) + } + fi, err := f.Stat() + if err != nil { + panic(err) + } + if fi.IsDir() { + // handle source directory + // fmt.Println("Cerating tar.gz from directory...") + zipDir(srcDirPath, path.Base(srcDirPath), tw) + } else { + // handle file directly + // fmt.Println("Cerating tar.gz from " + fi.Name() + "...") + zipFile(srcDirPath, fi.Name(), tw, fi) + } + ok = true + return } // Deal with directories @@ -59,69 +59,69 @@ func Zip(srcDirPath string, destFilePath string) (ok bool) { // Every recurrence append the base path to the recPath // recPath is the path inside of tar.gz func zipDir(srcDirPath string, recPath string, tw *zip.Writer) { - // Open source diretory - dir, err := os.Open(srcDirPath) - if err != nil { - panic(err) - } - defer dir.Close() + // Open source diretory + dir, err := os.Open(srcDirPath) + if err != nil { + panic(err) + } + defer dir.Close() - // Get file info slice - fis, err := dir.Readdir(0) - if err != nil { - panic(err) - } - for _, fi := range fis { - // Append path - curPath := srcDirPath + "/" + fi.Name() - // Check it is directory or file - if fi.IsDir() { - // Directory - // (Directory won't add unitl all subfiles are added) -// fmt.Printf("Adding path...%s\n", curPath) - zipDir(curPath, recPath+"/"+fi.Name(), tw) - } else { - // File -// fmt.Printf("Adding file...%s\n", curPath) - } + // Get file info slice + fis, err := dir.Readdir(0) + if err != nil { + panic(err) + } + for _, fi := range fis { + // Append path + curPath := srcDirPath + "/" + fi.Name() + // Check it is directory or file + if fi.IsDir() { + // Directory + // (Directory won't add unitl all subfiles are added) + // fmt.Printf("Adding path...%s\n", curPath) + zipDir(curPath, recPath+"/"+fi.Name(), tw) + } else { + // File + // fmt.Printf("Adding file...%s\n", curPath) + } - zipFile(curPath, recPath+"/"+fi.Name(), tw, fi) - } + zipFile(curPath, recPath+"/"+fi.Name(), tw, fi) + } } // Deal with files func zipFile(srcFile string, recPath string, tw *zip.Writer, fi os.FileInfo) { - if fi.IsDir() { -// fmt.Println("??") - // Create tar header - /* - fh, err := zip.FileInfoHeader(fi) - if err != nil { - panic(err) - } - fh.Name = recPath // + "/" - err = tw.WriteHeader(hdr) - tw.Create(recPath) - */ - } else { - // File reader - fr, err := os.Open(srcFile) - if err != nil { - panic(err) - } - defer fr.Close() + if fi.IsDir() { + // fmt.Println("??") + // Create tar header + /* + fh, err := zip.FileInfoHeader(fi) + if err != nil { + panic(err) + } + fh.Name = recPath // + "/" + err = tw.WriteHeader(hdr) + tw.Create(recPath) + */ + } else { + // File reader + fr, err := os.Open(srcFile) + if err != nil { + panic(err) + } + defer fr.Close() - // Write hander - w, err2 := tw.Create(recPath) - if err2 != nil { - panic(err) - } - // Write file data - _, err = io.Copy(w, fr) - if err != nil { - panic(err) - } - } + // Write hander + w, err2 := tw.Create(recPath) + if err2 != nil { + panic(err) + } + // Write file data + _, err = io.Copy(w, fr) + if err != nil { + panic(err) + } + } } // Ungzip and untar from source file to destination directory @@ -129,33 +129,33 @@ func zipFile(srcFile string, recPath string, tw *zip.Writer, fi os.FileInfo) { func Unzip(srcFilePath string, destDirPath string) (ok bool, msg string) { ok = false msg = "" - - defer func() { //必须要先声明defer,否则不能捕获到panic异常 + + defer func() { //必须要先声明defer,否则不能捕获到panic异常 if err := recover(); err != nil { msg = fmt.Sprintf("%v", err) ok = false } }() - + os.Mkdir(destDirPath, os.ModePerm) - r, err := zip.OpenReader(srcFilePath); + r, err := zip.OpenReader(srcFilePath) if err != nil { panic(err) } - defer r.Close(); + defer r.Close() for _, f := range r.File { -// fmt.Println("FileName : ", f.Name); // j/aaa.zip - rc, err := f.Open(); - if err!=nil { + // fmt.Println("FileName : ", f.Name); // j/aaa.zip + rc, err := f.Open() + if err != nil { panic(err) } - + // 把首文件夹去掉, 即j去掉, 分离出文件夹和文件名 paths := strings.Split(f.Name, "/") prePath := "" filename := "" l := len(paths) -// fmt.Println(l) + // fmt.Println(l) if l > 1 { // 去掉第1个文件夹 if l == 2 { @@ -167,26 +167,26 @@ func Unzip(srcFilePath string, destDirPath string) (ok bool, msg string) { } else { filename = f.Name } -// fmt.Println(prePath) - + // fmt.Println(prePath) + // 相对于目标文件件下的路径 - destPath := destDirPath + "/" + filename + destPath := destDirPath + "/" + filename if prePath != "" { - os.MkdirAll(destDirPath + "/" + prePath, os.ModePerm) + os.MkdirAll(destDirPath+"/"+prePath, os.ModePerm) destPath = destDirPath + "/" + prePath + "/" + filename } - // Write data to file -// fmt.Println(destPath) - fw, _ := os.Create(destPath) - if err != nil { - panic(err) - } - _, err = io.Copy(fw, rc) - if err != nil { - panic(err) - } + // Write data to file + // fmt.Println(destPath) + fw, _ := os.Create(destPath) + if err != nil { + panic(err) + } + _, err = io.Copy(fw, rc) + if err != nil { + panic(err) + } } - + ok = true return -} \ No newline at end of file +} diff --git a/app/lea/binder/binder.go b/app/lea/binder/binder.go index 3087478..63f0431 100644 --- a/app/lea/binder/binder.go +++ b/app/lea/binder/binder.go @@ -1,10 +1,10 @@ package binder import ( - "github.com/revel/revel" - "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/controllers" -// "github.com/leanote/leanote/app/controllers/api" + "github.com/leanote/leanote/app/info" + "github.com/revel/revel" + // "github.com/leanote/leanote/app/controllers/api" "fmt" "reflect" "strings" @@ -12,7 +12,7 @@ import ( // leanote binder struct // rewrite revel struct binder -// not need the struct name as prefix, +// not need the struct name as prefix, // eg: // type Note struct {Name} // func (c Controller) List(note Note) revel.Result {} @@ -34,13 +34,13 @@ var MSSBinder = revel.Binder{ } return result }, - + Unbind: func(output map[string]string, name string, val interface{}) { mapValue := reflect.ValueOf(val) for _, key := range mapValue.MapKeys() { revel.Unbind(output, fmt.Sprintf("%v", key.Interface()), mapValue.MapIndex(key).Interface()) - } + } }, } @@ -54,55 +54,56 @@ func nextKey(key string) string { } return key[:fieldLen] } + var leanoteStructBinder = revel.Binder{ // name == "noteOrContent" Bind: func(params *revel.Params, name string, typ reflect.Type) reflect.Value { result := reflect.New(typ).Elem() // 创建一个该类型的, 然后其field从所有的param去取 fieldValues := make(map[string]reflect.Value) -// fmt.Println(name) + // fmt.Println(name) // fmt.Println(typ) // api.NoteFiles // name = files[0], files[1], noteContent -// fmt.Println(params.Values) + // fmt.Println(params.Values) /* -map[Title:[test1] METHOD:[POST] NotebookId:[54c4f51705fcd14031000002] -files[1][FileId]:[] -controller:[note] -files[1][LocalFileId]:[54c7ae27d98d0329dd000000] files[1][HasBody]:[true] files[0][FileId]:[] files[0][LocalFileId]:[54c7ae855e94ea2dba000000] action:[addNote] Content:[

lifedddddd




] IsBlog:[false] token:[user1] -files[0][HasBody]:[true]] + map[Title:[test1] METHOD:[POST] NotebookId:[54c4f51705fcd14031000002] + files[1][FileId]:[] + controller:[note] + files[1][LocalFileId]:[54c7ae27d98d0329dd000000] files[1][HasBody]:[true] files[0][FileId]:[] files[0][LocalFileId]:[54c7ae855e94ea2dba000000] action:[addNote] Content:[

lifedddddd




] IsBlog:[false] token:[user1] + files[0][HasBody]:[true]] */ nameIsSlice := strings.Contains(name, "[") -// fmt.Println(params.Values["files[1]"]) -// fmt.Println(params.Values["Title"]) - for key, _ := range params.Values {// Title, Content, Files + // fmt.Println(params.Values["files[1]"]) + // fmt.Println(params.Values["Title"]) + for key, _ := range params.Values { // Title, Content, Files // 这里, 如果没有点, 默认就是a. // life -// fmt.Println("key:" + key); // files[0][LocalFileId] -// fmt.Println("name:" + name); // files[0][LocalFileId] + // fmt.Println("key:" + key); // files[0][LocalFileId] + // fmt.Println("name:" + name); // files[0][LocalFileId] var suffix string var noPrefix = false if nameIsSlice && strings.HasPrefix(key, name) { - suffix = key[len(name)+1:len(key)-1] // files[0][LocalFileId] 去掉 => LocalFileId - } else if !strings.HasPrefix(key, name + ".") { + suffix = key[len(name)+1 : len(key)-1] // files[0][LocalFileId] 去掉 => LocalFileId + } else if !strings.HasPrefix(key, name+".") { noPrefix = true suffix = key - // continue + // continue } else { // Get the name of the struct property. // Strip off the prefix. e.g. foo.bar.baz => bar.baz suffix = key[len(name)+1:] } -// fmt.Println(suffix); - + // fmt.Println(suffix); + fieldName := nextKey(suffix) // e.g. bar => "bar", bar.baz => "bar", bar[0] => "bar" -// fmt.Println(fieldName); + // fmt.Println(fieldName); fieldLen := len(fieldName) - + if _, ok := fieldValues[fieldName]; !ok { // Time to bind this field. Get it and make sure we can set it. fieldName = strings.Title(fieldName) // 传过来title, 但struct是Title -// fmt.Println("xx: " + fieldName) + // fmt.Println("xx: " + fieldName) fieldValue := result.FieldByName(fieldName) -// fmt.Println(fieldValue) + // fmt.Println(fieldValue) if !fieldValue.IsValid() { continue } @@ -111,14 +112,14 @@ files[0][HasBody]:[true]] } var boundVal reflect.Value // 没有name前缀 - if(noPrefix) { + if noPrefix { // life -// fmt.Println("<<") -// fmt.Println(strings.Title(key[:fieldLen])); + // fmt.Println("<<") + // fmt.Println(strings.Title(key[:fieldLen])); boundVal = revel.Bind(params, key[:fieldLen], fieldValue.Type()) } else { -// fmt.Println("final") -// fmt.Println(key[:len(name)+1+fieldLen]) // files[0][HasBody + // fmt.Println("final") + // fmt.Println(key[:len(name)+1+fieldLen]) // files[0][HasBody if nameIsSlice { fieldLen += 1 } @@ -153,4 +154,4 @@ func init() { revel.TypeBinders[reflect.TypeOf(controllers.NoteOrContent{})] = leanoteStructBinder revel.TypeBinders[reflect.TypeOf(info.ApiNote{})] = leanoteStructBinder revel.TypeBinders[reflect.TypeOf(info.NoteFile{})] = leanoteStructBinder -} \ No newline at end of file +} diff --git a/app/lea/blog/Template.go b/app/lea/blog/Template.go index 39ae3ee..908ec40 100644 --- a/app/lea/blog/Template.go +++ b/app/lea/blog/Template.go @@ -6,8 +6,8 @@ import ( "html/template" "io/ioutil" // "os" - "fmt" "bytes" + "fmt" "io" "net/http" "regexp" @@ -40,8 +40,8 @@ type RenderTemplateResult struct { Template *template.Template PathContent map[string]string RenderArgs map[string]interface{} - - IsPreview bool // 是否是预览 + + IsPreview bool // 是否是预览 CurBlogTpl *BlogTpl } @@ -87,7 +87,7 @@ func (r *RenderTemplateResult) render(req *revel.Request, resp *revel.Response, Line: line, SourceLines: templateContent, } - + // 这里, 错误!! // 这里应该导向到本主题的错误页面 resp.Status = 500 @@ -117,7 +117,7 @@ func (r *RenderTemplateResult) Apply(req *revel.Request, resp *revel.Response) { r.render(req, resp, out) // 这里!!! return } - + // Render the template into a temporary buffer, to see if there was an error // rendering the template. If not, then copy it into the response buffer. // Otherwise, template render errors may result in unpredictable HTML (and @@ -139,7 +139,7 @@ func Init() { fileBytes, _ := ioutil.ReadFile(revel.ViewsPath + "/Blog/" + path) fileStr := string(fileBytes) path := "blog/" + path -// path := path + // path := path BlogTplObject.PathContent[path] = fileStr BlogTplObject.Template.New(path).Parse(fileStr) // 以blog为根 } @@ -157,7 +157,7 @@ func RenderTemplate(name string, args map[string]interface{}, basePath string, i // 都不会为空的 if basePath == "" { path := "blog/" + name -// path := name + // path := name t := BlogTplObject.Template.Lookup(path) r = &RenderTemplateResult{ Template: t, @@ -181,7 +181,7 @@ func RenderTemplate(name string, args map[string]interface{}, basePath string, i files := ListDir(basePath) for _, t := range files { if !strings.Contains(t, ".html") { - continue; + continue } fileBytes, err := ioutil.ReadFile(basePath + "/" + t) if err != nil { @@ -194,7 +194,7 @@ func RenderTemplate(name string, args map[string]interface{}, basePath string, i // 如果本主题下没有, 则用系统的 t := newBlogTplObject.Template.Lookup(name) - + if t == nil { path := "blog/" + name t = BlogTplObject.Template.Lookup(path) @@ -203,23 +203,21 @@ func RenderTemplate(name string, args map[string]interface{}, basePath string, i Template: t, PathContent: newBlogTplObject.PathContent, // 为了显示错误 RenderArgs: args, - CurBlogTpl: newBlogTplObject, - IsPreview: isPreview, + CurBlogTpl: newBlogTplObject, + IsPreview: isPreview, } } return r } - //////////////////// // - type ErrorResult struct { RenderArgs map[string]interface{} Error error - IsPreview bool + IsPreview bool CurBlogTpl *BlogTpl } @@ -240,7 +238,7 @@ func (r ErrorResult) Apply(req *revel.Request, resp *revel.Response) { var err error templatePath := fmt.Sprintf("errors/%d.%s", status, format) err = nil -// tmpl, err := revel.MainTemplateLoader.Template("index.html") // 这里找到错误页面主题 + // tmpl, err := revel.MainTemplateLoader.Template("index.html") // 这里找到错误页面主题 // This func shows a plaintext error message, in case the template rendering // doesn't work. @@ -297,4 +295,4 @@ func (r ErrorResult) Apply(req *revel.Request, resp *revel.Response) { resp.WriteHeader(http.StatusOK, "text/html; charset=utf-8") b.WriteTo(out) } -} \ No newline at end of file +} diff --git a/app/lea/captcha/Captcha.go b/app/lea/captcha/Captcha.go index 6348d2a..f7a7fd7 100644 --- a/app/lea/captcha/Captcha.go +++ b/app/lea/captcha/Captcha.go @@ -1,399 +1,401 @@ package captcha import ( - "image" - "image/color" - "image/png" - "io" - "math/rand" - crand "crypto/rand" - "time" - "strconv" -) -const ( - stdWidth = 100 - stdHeight = 40 - maxSkew = 2 + crand "crypto/rand" + "image" + "image/color" + "image/png" + "io" + "math/rand" + "strconv" + "time" ) const ( - fontWidth = 5 - fontHeight = 8 - blackChar = 1 + stdWidth = 100 + stdHeight = 40 + maxSkew = 2 ) - + +const ( + fontWidth = 5 + fontHeight = 8 + blackChar = 1 +) + var font = [][]byte{ - { // 0 - 0, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 0, 1, 1, 1, 0, - }, - { // 1 - 0, 0, 1, 0, 0, - 0, 1, 1, 0, 0, - 1, 0, 1, 0, 0, - 0, 0, 1, 0, 0, - 0, 0, 1, 0, 0, - 0, 0, 1, 0, 0, - 0, 0, 1, 0, 0, - 1, 1, 1, 1, 1, - }, - { // 2 - 0, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 0, 0, 0, 1, 1, - 0, 1, 1, 0, 0, - 1, 0, 0, 0, 0, - 1, 0, 0, 0, 0, - 1, 1, 1, 1, 1, - }, - { // 3 - 1, 1, 1, 1, 0, - 0, 0, 0, 0, 1, - 0, 0, 0, 1, 0, - 0, 1, 1, 1, 0, - 0, 0, 0, 1, 0, - 0, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 1, 1, 1, 1, 0, - }, - { // 4 - 1, 0, 0, 1, 0, - 1, 0, 0, 1, 0, - 1, 0, 0, 1, 0, - 1, 0, 0, 1, 0, - 1, 1, 1, 1, 1, - 0, 0, 0, 1, 0, - 0, 0, 0, 1, 0, - 0, 0, 0, 1, 0, - }, - { // 5 - 1, 1, 1, 1, 1, - 1, 0, 0, 0, 0, - 1, 0, 0, 0, 0, - 1, 1, 1, 1, 0, - 0, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 1, 1, 1, 1, 0, - }, - { // 6 - 0, 0, 1, 1, 1, - 0, 1, 0, 0, 0, - 1, 0, 0, 0, 0, - 1, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 0, 1, 1, 1, 0, - }, - { // 7 - 1, 1, 1, 1, 1, - 0, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 0, 0, 0, 1, 0, - 0, 0, 1, 0, 0, - 0, 1, 0, 0, 0, - 0, 1, 0, 0, 0, - 0, 1, 0, 0, 0, - }, - { // 8 - 0, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 0, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 0, 1, 1, 1, 0, - }, - { // 9 - 0, 1, 1, 1, 0, - 1, 0, 0, 0, 1, - 1, 0, 0, 0, 1, - 1, 1, 0, 0, 1, - 0, 1, 1, 1, 1, - 0, 0, 0, 0, 1, - 0, 0, 0, 0, 1, - 1, 1, 1, 1, 0, - }, + { // 0 + 0, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 0, 1, 1, 1, 0, + }, + { // 1 + 0, 0, 1, 0, 0, + 0, 1, 1, 0, 0, + 1, 0, 1, 0, 0, + 0, 0, 1, 0, 0, + 0, 0, 1, 0, 0, + 0, 0, 1, 0, 0, + 0, 0, 1, 0, 0, + 1, 1, 1, 1, 1, + }, + { // 2 + 0, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 0, 0, 0, 1, 1, + 0, 1, 1, 0, 0, + 1, 0, 0, 0, 0, + 1, 0, 0, 0, 0, + 1, 1, 1, 1, 1, + }, + { // 3 + 1, 1, 1, 1, 0, + 0, 0, 0, 0, 1, + 0, 0, 0, 1, 0, + 0, 1, 1, 1, 0, + 0, 0, 0, 1, 0, + 0, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 1, 1, 1, 1, 0, + }, + { // 4 + 1, 0, 0, 1, 0, + 1, 0, 0, 1, 0, + 1, 0, 0, 1, 0, + 1, 0, 0, 1, 0, + 1, 1, 1, 1, 1, + 0, 0, 0, 1, 0, + 0, 0, 0, 1, 0, + 0, 0, 0, 1, 0, + }, + { // 5 + 1, 1, 1, 1, 1, + 1, 0, 0, 0, 0, + 1, 0, 0, 0, 0, + 1, 1, 1, 1, 0, + 0, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 1, 1, 1, 1, 0, + }, + { // 6 + 0, 0, 1, 1, 1, + 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, + 1, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 0, 1, 1, 1, 0, + }, + { // 7 + 1, 1, 1, 1, 1, + 0, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, + 0, 1, 0, 0, 0, + 0, 1, 0, 0, 0, + 0, 1, 0, 0, 0, + }, + { // 8 + 0, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 0, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 0, 1, 1, 1, 0, + }, + { // 9 + 0, 1, 1, 1, 0, + 1, 0, 0, 0, 1, + 1, 0, 0, 0, 1, + 1, 1, 0, 0, 1, + 0, 1, 1, 1, 1, + 0, 0, 0, 0, 1, + 0, 0, 0, 0, 1, + 1, 1, 1, 1, 0, + }, } - + type Image struct { - *image.NRGBA - color *color.NRGBA - width int //a digit width - height int //a digit height - dotsize int + *image.NRGBA + color *color.NRGBA + width int //a digit width + height int //a digit height + dotsize int } -func init(){ - rand.Seed(int64(time.Second)) + +func init() { + rand.Seed(int64(time.Second)) } - + func NewImage(digits []byte, width, height int) *Image { - img := new(Image) - r := image.Rect(img.width, img.height, stdWidth, stdHeight) - img.NRGBA = image.NewNRGBA(r) - - img.color = &color.NRGBA{ - uint8(rand.Intn(129)), - uint8(rand.Intn(129)), - uint8(rand.Intn(129)), - 0xFF, - } - // Draw background (10 random circles of random brightness) - img.calculateSizes(width, height, len(digits)) - img.fillWithCircles(10, img.dotsize) - - maxx := width - (img.width+img.dotsize)*len(digits) - img.dotsize - maxy := height - img.height - img.dotsize*2 - - x := rnd(img.dotsize*2, maxx) - y := rnd(img.dotsize*2, maxy) - - // Draw digits. - for _, n := range digits { - img.drawDigit(font[n], x, y) - x += img.width + img.dotsize - } - - // Draw strike-through line. - // 中间线不要 - //img.strikeThrough() - - return img + img := new(Image) + r := image.Rect(img.width, img.height, stdWidth, stdHeight) + img.NRGBA = image.NewNRGBA(r) + + img.color = &color.NRGBA{ + uint8(rand.Intn(129)), + uint8(rand.Intn(129)), + uint8(rand.Intn(129)), + 0xFF, + } + // Draw background (10 random circles of random brightness) + img.calculateSizes(width, height, len(digits)) + img.fillWithCircles(10, img.dotsize) + + maxx := width - (img.width+img.dotsize)*len(digits) - img.dotsize + maxy := height - img.height - img.dotsize*2 + + x := rnd(img.dotsize*2, maxx) + y := rnd(img.dotsize*2, maxy) + + // Draw digits. + for _, n := range digits { + img.drawDigit(font[n], x, y) + x += img.width + img.dotsize + } + + // Draw strike-through line. + // 中间线不要 + //img.strikeThrough() + + return img } - + func (img *Image) WriteTo(w io.Writer) (int64, error) { - return 0, png.Encode(w, img) + return 0, png.Encode(w, img) } - + func (img *Image) calculateSizes(width, height, ncount int) { - - // Goal: fit all digits inside the image. - var border int - if width > height { - border = height / 5 - } else { - border = width / 5 - } - // Convert everything to floats for calculations. - w := float64(width - border*2) //268 - h := float64(height - border*2) //48 - // fw takes into account 1-dot spacing between digits. - - fw := float64(fontWidth) + 1 //6 - - fh := float64(fontHeight) //8 - nc := float64(ncount) //7 - - // Calculate the width of a single digit taking into account only the - // width of the image. - nw := w / nc //38 - // Calculate the height of a digit from this width. - nh := nw * fh / fw //51 - - // Digit too high? - - if nh > h { - // Fit digits based on height. - nh = h //nh = 44 - nw = fw / fh * nh - } - // Calculate dot size. - img.dotsize = int(nh / fh) - // Save everything, making the actual width smaller by 1 dot to account - // for spacing between digits. - img.width = int(nw) - img.height = int(nh) - img.dotsize + + // Goal: fit all digits inside the image. + var border int + if width > height { + border = height / 5 + } else { + border = width / 5 + } + // Convert everything to floats for calculations. + w := float64(width - border*2) //268 + h := float64(height - border*2) //48 + // fw takes into account 1-dot spacing between digits. + + fw := float64(fontWidth) + 1 //6 + + fh := float64(fontHeight) //8 + nc := float64(ncount) //7 + + // Calculate the width of a single digit taking into account only the + // width of the image. + nw := w / nc //38 + // Calculate the height of a digit from this width. + nh := nw * fh / fw //51 + + // Digit too high? + + if nh > h { + // Fit digits based on height. + nh = h //nh = 44 + nw = fw / fh * nh + } + // Calculate dot size. + img.dotsize = int(nh / fh) + // Save everything, making the actual width smaller by 1 dot to account + // for spacing between digits. + img.width = int(nw) + img.height = int(nh) - img.dotsize } - + func (img *Image) fillWithCircles(n, maxradius int) { - color := img.color - maxx := img.Bounds().Max.X - maxy := img.Bounds().Max.Y - for i := 0; i < n; i++ { - setRandomBrightness(color, 255) - r := rnd(1, maxradius) - img.drawCircle(color, rnd(r, maxx-r), rnd(r, maxy-r), r) - } + color := img.color + maxx := img.Bounds().Max.X + maxy := img.Bounds().Max.Y + for i := 0; i < n; i++ { + setRandomBrightness(color, 255) + r := rnd(1, maxradius) + img.drawCircle(color, rnd(r, maxx-r), rnd(r, maxy-r), r) + } } - + func (img *Image) drawHorizLine(color color.Color, fromX, toX, y int) { - for x := fromX; x <= toX; x++ { - img.Set(x, y, color) - } + for x := fromX; x <= toX; x++ { + img.Set(x, y, color) + } } - + func (img *Image) drawCircle(color color.Color, x, y, radius int) { - f := 1 - radius - dfx := 1 - dfy := -2 * radius - xx := 0 - yy := radius - - img.Set(x, y+radius, color) - img.Set(x, y-radius, color) - img.drawHorizLine(color, x-radius, x+radius, y) - - for xx < yy { - if f >= 0 { - yy-- - dfy += 2 - f += dfy - } - xx++ - dfx += 2 - f += dfx - img.drawHorizLine(color, x-xx, x+xx, y+yy) - img.drawHorizLine(color, x-xx, x+xx, y-yy) - img.drawHorizLine(color, x-yy, x+yy, y+xx) - img.drawHorizLine(color, x-yy, x+yy, y-xx) - } + f := 1 - radius + dfx := 1 + dfy := -2 * radius + xx := 0 + yy := radius + + img.Set(x, y+radius, color) + img.Set(x, y-radius, color) + img.drawHorizLine(color, x-radius, x+radius, y) + + for xx < yy { + if f >= 0 { + yy-- + dfy += 2 + f += dfy + } + xx++ + dfx += 2 + f += dfx + img.drawHorizLine(color, x-xx, x+xx, y+yy) + img.drawHorizLine(color, x-xx, x+xx, y-yy) + img.drawHorizLine(color, x-yy, x+yy, y+xx) + img.drawHorizLine(color, x-yy, x+yy, y-xx) + } } - + func (img *Image) strikeThrough() { - r := 0 - maxx := img.Bounds().Max.X - maxy := img.Bounds().Max.Y - y := rnd(maxy/3, maxy-maxy/3) - for x := 0; x < maxx; x += r { - r = rnd(1, img.dotsize/3) - y += rnd(-img.dotsize/2, img.dotsize/2) - if y <= 0 || y >= maxy { - y = rnd(maxy/3, maxy-maxy/3) - } - img.drawCircle(img.color, x, y, r) - } + r := 0 + maxx := img.Bounds().Max.X + maxy := img.Bounds().Max.Y + y := rnd(maxy/3, maxy-maxy/3) + for x := 0; x < maxx; x += r { + r = rnd(1, img.dotsize/3) + y += rnd(-img.dotsize/2, img.dotsize/2) + if y <= 0 || y >= maxy { + y = rnd(maxy/3, maxy-maxy/3) + } + img.drawCircle(img.color, x, y, r) + } } - + func (img *Image) drawDigit(digit []byte, x, y int) { - skf := rand.Float64() * float64(rnd(-maxSkew, maxSkew)) - xs := float64(x) - minr := img.dotsize / 2 // minumum radius - maxr := img.dotsize/2 + img.dotsize/4 // maximum radius - y += rnd(-minr, minr) - for yy := 0; yy < fontHeight; yy++ { - for xx := 0; xx < fontWidth; xx++ { - if digit[yy*fontWidth+xx] != blackChar { - continue - } - // Introduce random variations. - or := rnd(minr, maxr) - ox := x + (xx * img.dotsize) + rnd(0, or/2) - oy := y + (yy * img.dotsize) + rnd(0, or/2) - - img.drawCircle(img.color, ox, oy, or) - } - xs += skf - x = int(xs) - } + skf := rand.Float64() * float64(rnd(-maxSkew, maxSkew)) + xs := float64(x) + minr := img.dotsize / 2 // minumum radius + maxr := img.dotsize/2 + img.dotsize/4 // maximum radius + y += rnd(-minr, minr) + for yy := 0; yy < fontHeight; yy++ { + for xx := 0; xx < fontWidth; xx++ { + if digit[yy*fontWidth+xx] != blackChar { + continue + } + // Introduce random variations. + or := rnd(minr, maxr) + ox := x + (xx * img.dotsize) + rnd(0, or/2) + oy := y + (yy * img.dotsize) + rnd(0, or/2) + + img.drawCircle(img.color, ox, oy, or) + } + xs += skf + x = int(xs) + } } - + func setRandomBrightness(c *color.NRGBA, max uint8) { - minc := min3(c.R, c.G, c.B) - maxc := max3(c.R, c.G, c.B) - if maxc > max { - return - } - n := rand.Intn(int(max-maxc)) - int(minc) - c.R = uint8(int(c.R) + n) - c.G = uint8(int(c.G) + n) - c.B = uint8(int(c.B) + n) + minc := min3(c.R, c.G, c.B) + maxc := max3(c.R, c.G, c.B) + if maxc > max { + return + } + n := rand.Intn(int(max-maxc)) - int(minc) + c.R = uint8(int(c.R) + n) + c.G = uint8(int(c.G) + n) + c.B = uint8(int(c.B) + n) } - + func min3(x, y, z uint8) (o uint8) { - o = x - if y < o { - o = y - } - if z < o { - o = z - } - return + o = x + if y < o { + o = y + } + if z < o { + o = z + } + return } - + func max3(x, y, z uint8) (o uint8) { - o = x - if y > o { - o = y - } - if z > o { - o = z - } - return + o = x + if y > o { + o = y + } + if z > o { + o = z + } + return } - + // rnd returns a random number in range [from, to]. func rnd(from, to int) int { - //println(to+1-from) - return rand.Intn(to+1-from) + from + //println(to+1-from) + return rand.Intn(to+1-from) + from } - + const ( - // Standard length of uniuri string to achive ~95 bits of entropy. - StdLen = 16 - // Length of uniurl string to achive ~119 bits of entropy, closest - // to what can be losslessly converted to UUIDv4 (122 bits). - UUIDLen = 20 + // Standard length of uniuri string to achive ~95 bits of entropy. + StdLen = 16 + // Length of uniurl string to achive ~119 bits of entropy, closest + // to what can be losslessly converted to UUIDv4 (122 bits). + UUIDLen = 20 ) - + // Standard characters allowed in uniuri string. var StdChars = []byte("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789") - + // New returns a new random string of the standard length, consisting of // standard characters. func New() string { - return NewLenChars(StdLen, StdChars) + return NewLenChars(StdLen, StdChars) } - + // NewLen returns a new random string of the provided length, consisting of // standard characters. func NewLen(length int) string { - return NewLenChars(length, StdChars) + return NewLenChars(length, StdChars) } - + // NewLenChars returns a new random string of the provided length, consisting // of the provided byte slice of allowed characters (maximum 256). func NewLenChars(length int, chars []byte) string { - b := make([]byte, length) - r := make([]byte, length+(length/4)) // storage for random bytes. - clen := byte(len(chars)) - maxrb := byte(256 - (256 % len(chars))) - i := 0 - for { - if _, err := io.ReadFull(crand.Reader, r); err != nil { - panic("error reading from random source: " + err.Error()) - } - for _, c := range r { - if c >= maxrb { - // Skip this number to avoid modulo bias. - continue - } - b[i] = chars[c%clen] - i++ - if i == length { - return string(b) - } - } - } - panic("unreachable") + b := make([]byte, length) + r := make([]byte, length+(length/4)) // storage for random bytes. + clen := byte(len(chars)) + maxrb := byte(256 - (256 % len(chars))) + i := 0 + for { + if _, err := io.ReadFull(crand.Reader, r); err != nil { + panic("error reading from random source: " + err.Error()) + } + for _, c := range r { + if c >= maxrb { + // Skip this number to avoid modulo bias. + continue + } + b[i] = chars[c%clen] + i++ + if i == length { + return string(b) + } + } + } + panic("unreachable") } func Fetch() (*Image, string) { - d := make([]byte, 4) - s := NewLen(4) - ss := "" - d = []byte(s) - for v := range d { - d[v] %= 10 - ss += strconv.FormatInt(int64(d[v]), 32) - } - return NewImage(d, 100, 40), ss -} \ No newline at end of file + d := make([]byte, 4) + s := NewLen(4) + ss := "" + d = []byte(s) + for v := range d { + d[v] %= 10 + ss += strconv.FormatInt(int64(d[v]), 32) + } + return NewImage(d, 100, 40), ss +} diff --git a/app/lea/html2image/Html2Image.go b/app/lea/html2image/Html2Image.go index 748f785..c250e15 100644 --- a/app/lea/html2image/Html2Image.go +++ b/app/lea/html2image/Html2Image.go @@ -24,29 +24,29 @@ import ( type Html2Image struct { image *image.RGBA gc *draw2d.ImageGraphicContext - + // 试探 gc2 *draw2d.ImageGraphicContext - + width float64 // 图片宽度 height float64 - + painWidth float64 // 画布宽度 - + startX float64 x float64 y float64 - + isFirstP bool // 是否是第一个段落? - + // 换行和段落的高度 brY float64 pY float64 - + // 字体 normalFontFamily draw2d.FontData boldFontFamily draw2d.FontData - + // preTag 之前的标签 preTag *html.Node } @@ -58,23 +58,23 @@ func NewHtml2Image() *Html2Image { i, gc := h.InitGc(h.width, h.height) h.gc = gc; h.image = i - + // 试探 _, h.gc2 = h.InitGc(h.width, 100) - - h.startX = 10 - + + h.startX = 10 + // 最初位置 h.x = h.startX h.y = 80 - + h.isFirstP = true - + h.normalFontFamily = draw2d.FontData{"xihei", 4, draw2d.FontStyleNormal}; h.boldFontFamily = draw2d.FontData{"heiti", 5, draw2d.FontStyleNormal}; - + h.SetNormalFont() - + return h } @@ -86,12 +86,12 @@ func (this *Html2Image) InitGc(w, h float64) (* image.RGBA, *draw2d.ImageGraphic gc.SetFillColor(image.White) // fill the background // gc.Clear() - + draw2d.SetFontFolder(revel.BasePath + "/public/fonts/weibo") draw2d.Rect(gc, 0, 0, w, h) // 设置背景 gc.FillStroke() gc.SetFillColor(image.Black) - + // 这个很耗时 // gc.Translate(0, 0) return i, gc @@ -101,7 +101,7 @@ func (this *Html2Image) SaveToPngFile(filePath string) bool { // m := this.image; m := this.image.SubImage(image.Rect(0, 0, int(this.width), int(this.y + 20))) // 需要截断之 - + f, err := os.Create(filePath) if err != nil { return false @@ -124,14 +124,14 @@ func (this *Html2Image) SaveToPngFile(filePath string) bool { func (this *Html2Image) SetSmallFont() { this.gc.SetFontData(this.normalFontFamily) this.gc2.SetFontData(this.normalFontFamily) - + this.gc.SetFillColor(color.NRGBA{60, 60, 60, 255}) this.gc.SetFontSize(12) this.gc2.SetFontSize(12) - + this.brY = 16 this.pY = 30 - + this.painWidth = this.width - 10 } @@ -139,13 +139,13 @@ func (this *Html2Image) SetNormalFont() { this.gc.SetFillColor(image.Black) this.gc.SetFontData(this.normalFontFamily) this.gc2.SetFontData(this.normalFontFamily) - + this.gc.SetFontSize(14) this.gc2.SetFontSize(14) - + this.brY = 20 this.pY = 30 - + this.painWidth = this.width - 10 } func (this *Html2Image) SetAColor() { @@ -155,16 +155,16 @@ func (this *Html2Image) SetAColor() { // 标题 func (this *Html2Image) SetTitleFont() { this.gc.SetFillColor(image.Black) - + this.gc.SetFontData(this.boldFontFamily) this.gc2.SetFontData(this.boldFontFamily) - + this.gc.SetFontSize(24) this.gc2.SetFontSize(24) - + this.brY = 30 this.pY = 60 - + this.painWidth = this.width - 100 } @@ -175,9 +175,9 @@ func (this *Html2Image) SetHeadFont(h string) { this.gc.SetFontData(this.boldFontFamily) this.gc2.SetFontData(this.boldFontFamily) - + this.painWidth = this.width - 50 - + if h == "h1" { this.gc.SetFontSize(20) this.gc2.SetFontSize(20) @@ -229,7 +229,7 @@ func (this *Html2Image) IsOver(r []rune) bool { // 以下的方法可以极大节约时间 // a, b, c, d := this.gc2.GetStringBounds(string(r)) // width2 := c - a + 2 - + // fmt.Println(width2) // fmt.Println(c - a) @@ -268,7 +268,7 @@ func (this *Html2Image) InsertText(text string, needTest bool, prefix string) { this.InsertText(text, true, prefix) return; } - + r := []rune(text) // 试探吧, 可能需要截取 if !needTest || !this.IsOver(r) { @@ -316,17 +316,17 @@ func (this *Html2Image) InsertText(text string, needTest bool, prefix string) { end = i } } - + // 这一段写上 // println("------>" + string(r[0:end])) - + // 这里, 判断后面一个是否是标点符号 end = this.includePunctuation(r, end) this.InsertText(string(r[0:end]), false, prefix) this.NewBr() // 之后的 this.InsertText(string(r[end:]), true, prefix) - + return; } else { // 没超出, 不用计算, 但出要看是否是结尾了 @@ -351,17 +351,17 @@ func (this *Html2Image) InsertText(text string, needTest bool, prefix string) { end = maxRI + 1 } } - + // 这一段写上 // println("-e----->" + string(r[0:end])) - + // 这里, 判断后面一个是否是标点符号 end = this.includePunctuation(r, end) this.InsertText(string(r[0:end]), false, prefix) this.NewBr() // 之后的 this.InsertText(string(r[end:]), true, prefix) - + return; } } @@ -376,9 +376,9 @@ func (this *Html2Image) SetBottom(username, url string) { this.gc.SetStrokeColor(color.NRGBA{200, 0, 0, 255}) this.gc.SetLineWidth(2) this.gc.FillStroke() - + this.SetSmallFont() - + // 左侧写字 this.NewP() this.InsertText("本文来自 " + username + " 的leanote笔记", true, " ") @@ -389,11 +389,11 @@ func (this *Html2Image) SetBottom(username, url string) { siteUrl = "http://leanote.com" } this.InsertA(siteUrl + "/blog/" + username, false) - + this.setLogo() // this.painWidth = this.width - 100 // this.NewP() -// this.InsertText("leanote, 不一样的笔记.", false, " ") +// this.InsertText("leanote, 不一样的笔记.", false, " ") // this.NewBr() // this.InsertText("在这里你可以管理自己的知识", false, " ") // this.NewBr() @@ -401,7 +401,7 @@ func (this *Html2Image) SetBottom(username, url string) { // this.NewBr() // this.InsertText("并且还可以将笔记设为博客公开", false, " ") // this.InsertText(". 赶紧加入吧! leanote.com", false, "") -// +// // Logo } @@ -411,7 +411,7 @@ func (this *Html2Image) setImage(path string, x, y float64) { return; panic(err) } - + var m1 image.Image _, ext := lea.SplitFilename(path) if ext == ".png" { @@ -424,8 +424,8 @@ func (this *Html2Image) setImage(path string, x, y float64) { if err != nil { return panic(err) - } - + } + this.gc.Translate(x, y) this.gc.DrawImage(m1) this.gc.Translate(-x, -y) @@ -448,10 +448,10 @@ func (this *Html2Image) InsertA(text string, isNormal bool) { if text == "" { return } - + this.SetAColor() this.InsertText(text, true, "") - + // 还原 if isNormal { this.SetNormalFont() @@ -464,17 +464,17 @@ func (this *Html2Image) InsertA(text string, isNormal bool) { func (this *Html2Image) InsertTitle(title string) { oldX := this.x oldY := this.y - 35 - + // 插入之 this.SetTitleFont() - + this.InsertText(title, true, " ") - + // 还原字体大小 this.SetNormalFont() - + this.NewBr() - + this.gc.MoveTo(oldX, oldY) this.gc.LineTo(this.x, this.y - 10) this.gc.SetStrokeColor(color.NRGBA{200, 0, 0, 255}) @@ -512,7 +512,7 @@ func (this *Html2Image) InsertCode(n *html.Node) { } } this.NewBr() - + this.gc.MoveTo(oldX, oldY) this.gc.LineTo(this.x, this.y - 20) this.gc.SetStrokeColor(color.NRGBA{0, 200, 0, 255}) @@ -521,14 +521,14 @@ func (this *Html2Image) InsertCode(n *html.Node) { } // 插入图片 -// 这个path应该是url, +// 这个path应该是url, // http://abc.com/a.gif 需要先下载 // 或 /upload/a.gif func (this *Html2Image) InsertImage(path string, needTrans bool, width uint) { if path == "" { return; } - + // 是url, 那么取网络图片之 var ok bool if strings.HasPrefix(path, "http") || strings.HasPrefix(path, "//") { @@ -539,7 +539,7 @@ func (this *Html2Image) InsertImage(path string, needTrans bool, width uint) { } else { path = revel.BasePath + "/public/" + path } - + // 需要转换, logo不需要转换 if(needTrans) { painWidth := uint(this.painWidth - 10) @@ -557,7 +557,7 @@ func (this *Html2Image) InsertImage(path string, needTrans bool, width uint) { return; panic(err) } - + var m1 image.Image _, ext := lea.SplitFilename(path) if ext == ".png" { @@ -568,8 +568,8 @@ func (this *Html2Image) InsertImage(path string, needTrans bool, width uint) { if err != nil { return panic(err) - } - + } + // 如果之前是p, 那么不要有
if this.preTag.Data != "p" { this.NewBr() @@ -580,9 +580,9 @@ func (this *Html2Image) InsertImage(path string, needTrans bool, width uint) { this.gc.Translate(-this.x, -this.y) // 这个有用些 this.y += float64(m1.Bounds().Dy()) - 20 this.NewP() - + os.Remove(path) - + // 如果图片是文章第一个的话, 之后的需要p this.isFirstP = false } @@ -605,7 +605,7 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { this.preTag = n } }() - + // 标签 if n.Type == html.ElementNode { if n.Data == "p" { @@ -616,7 +616,7 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { } return; } - + // 也是一个段落, 只是要缩进 if n.Data == "ul" || n.Data == "ol" { this.NewP() @@ -637,7 +637,7 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { } else { f(c, n, "") } - + if c.Type == html.ElementNode { if c.Data == "br" || c.Data == "p" { needPrefix = true @@ -650,19 +650,19 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { this.NewBr() return; } - + // 标题 if n.Data == "h1" || n.Data == "h2" || n.Data == "h3" || n.Data == "h4" { this.InsertHead(n) return; } - + if n.Data == "pre" { // 把之后的全拿过来 this.InsertCode(n) return; } - + // 图片 // 得到src if n.Data == "img" { @@ -680,22 +680,22 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { } return; } - + // 链接 // 如果链接里只有文本, 那么单独处理, 如果还有其它的, 不作链接处理 if n.Data == "a" { if n.FirstChild == n.LastChild { this.InsertA(n.FirstChild.Data, true) return; - } + } } - + // 空行 if n.Data == "br" { // || n.Data == "div" this.NewBr() } } - + // 是文本, 输出之 if n.Type == html.TextNode { data := strings.TrimSpace(n.Data); @@ -705,36 +705,36 @@ func (this *Html2Image) InsertBody(htmlStr string) (ok bool) { } return; } - + // 其余的 - + for c := n.FirstChild; c != nil; c = c.NextSibling { f(c, n, prefix) } - + return; } f(doc, nil, "") - + return true } // 主函数 func ToImage(uid, username, noteId, title, htmlStr, toPath string) (ok bool) { h := NewHtml2Image() - + // 标题 h.InsertTitle(title) - + // 主体 ok = h.InsertBody(htmlStr) if(!ok) { return } - + // 页眉与页脚 h.SetBottom(username, "") - + // 保存成png图片 ok = h.SaveToPngFile(toPath) return @@ -757,4 +757,4 @@ func TestFillString() { func ToImage(uid, username, noteId, title, htmlStr, toPath string) (ok bool) { return false -} \ No newline at end of file +} diff --git a/app/lea/html2image/ToImage.go b/app/lea/html2image/ToImage.go index e6730f7..5facd32 100644 --- a/app/lea/html2image/ToImage.go +++ b/app/lea/html2image/ToImage.go @@ -7,4 +7,3 @@ import ( func Html2Image(userInfo info.User, note info.Note, content, toPath string) bool { return true } - diff --git a/app/lea/netutil/NetUtil.go b/app/lea/netutil/NetUtil.go index c27af89..817ce6b 100644 --- a/app/lea/netutil/NetUtil.go +++ b/app/lea/netutil/NetUtil.go @@ -1,12 +1,13 @@ package netutil + import ( - "strings" "os" -// "path/filepath" + "strings" + // "path/filepath" + . "github.com/leanote/leanote/app/lea" + "io/ioutil" "net" "net/http" - "io/ioutil" - . "github.com/leanote/leanote/app/lea" ) // net的util @@ -16,33 +17,33 @@ import ( // 返回文件的完整目录 func WriteUrl(url string, toPath string) (length int64, newFilename, path string, ok bool) { if url == "" { - return; + return } content, err := GetContent(url) if err != nil { - return; + return } - + length = int64(len(content)) - + // a.html?a=a11&xxx url = trimQueryParams(url) _, ext := SplitFilename(url) if toPath == "" { toPath = "/tmp" } -// dir := filepath.Dir(toPath) + // dir := filepath.Dir(toPath) newFilename = NewGuid() + ext fullPath := toPath + "/" + newFilename - + // 写到文件中 file, err := os.Create(fullPath) - defer file.Close() - if err != nil { - return + defer file.Close() + if err != nil { + return } file.Write(content) - + path = fullPath ok = true return @@ -53,43 +54,43 @@ func GetContent(url string) (content []byte, err error) { var resp *http.Response resp, err = http.Get(url) Log(err) - if(resp != nil && resp.Body != nil) { + if resp != nil && resp.Body != nil { defer resp.Body.Close() } else { } - if resp == nil || resp.Body == nil || err != nil || resp.StatusCode != http.StatusOK { - return - } - - var buf []byte - buf, err = ioutil.ReadAll(resp.Body) - if(err != nil) { - Log(err) + if resp == nil || resp.Body == nil || err != nil || resp.StatusCode != http.StatusOK { return } - - content = buf; - err = nil - return + + var buf []byte + buf, err = ioutil.ReadAll(resp.Body) + if err != nil { + Log(err) + return + } + + content = buf + err = nil + return } // 将url ?, #后面的字符串去掉 func trimQueryParams(url string) string { - pos := strings.Index(url, "?"); + pos := strings.Index(url, "?") if pos != -1 { - url = Substr(url, 0, pos); + url = Substr(url, 0, pos) } - - pos = strings.Index(url, "#"); + + pos = strings.Index(url, "#") if pos != -1 { - url = Substr(url, 0, pos); + url = Substr(url, 0, pos) } - - pos = strings.Index(url, "!"); + + pos = strings.Index(url, "!") if pos != -1 { - url = Substr(url, 0, pos); + url = Substr(url, 0, pos) } - return url; + return url } // 通过domain得到ip @@ -99,4 +100,4 @@ func GetIpFromDomain(domain string) string { return ip[0].String() } return "" -} \ No newline at end of file +} diff --git a/app/lea/route/Route.go b/app/lea/route/Route.go index b927d6f..c694001 100644 --- a/app/lea/route/Route.go +++ b/app/lea/route/Route.go @@ -1,9 +1,9 @@ package route import ( - "github.com/revel/revel" "github.com/leanote/leanote/app/db" -// . "github.com/leanote/leanote/app/lea" + "github.com/revel/revel" + // . "github.com/leanote/leanote/app/lea" "net/url" "strings" ) @@ -11,10 +11,11 @@ import ( // overwite revel RouterFilter // /api/user/Info => ApiUser.Info() var staticPrefix = []string{"/public", "/favicon.ico", "/css", "/js", "/images", "/tinymce", "/upload", "/fonts"} + func RouterFilter(c *revel.Controller, fc []revel.Filter) { // 补全controller部分 path := c.Request.Request.URL.Path - + // Figure out the Controller/Action var route *revel.RouteMatch = revel.MainRouter.Route(c.Request.Request) if route == nil { @@ -27,29 +28,29 @@ func RouterFilter(c *revel.Controller, fc []revel.Filter) { c.Result = c.NotFound("(intentionally)") return } - + //---------- // life start /* - type URL struct { - Scheme string - Opaque string // encoded opaque data - User *Userinfo // username and password information - Host string // host or host:port - Path string - RawQuery string // encoded query values, without '?' - Fragment string // fragment for references, without '#' - } + type URL struct { + Scheme string + Opaque string // encoded opaque data + User *Userinfo // username and password information + Host string // host or host:port + Path string + RawQuery string // encoded query values, without '?' + Fragment string // fragment for references, without '#' + } */ if route.ControllerName != "Static" { // 检查mongodb 是否lost db.CheckMongoSessionLost() - + // api设置 // leanote.com/api/user/get => ApiUser::Get //* /api/login ApiAuth.Login, 这里的设置, 其实已经转成了ApiAuth了 - if strings.HasPrefix(path, "/api") && !strings.HasPrefix(route.ControllerName, "Api"){ + if strings.HasPrefix(path, "/api") && !strings.HasPrefix(route.ControllerName, "Api") { route.ControllerName = "Api" + route.ControllerName } else if strings.HasPrefix(path, "/member") && !strings.HasPrefix(route.ControllerName, "Member") { // member设置 @@ -57,7 +58,7 @@ func RouterFilter(c *revel.Controller, fc []revel.Filter) { } // end } - + // Set the action. if err := c.SetAction(route.ControllerName, route.MethodName); err != nil { c.Result = c.NotFound(err.Error()) @@ -84,4 +85,3 @@ func RouterFilter(c *revel.Controller, fc []revel.Filter) { fc[0](c, fc[1:]) } - diff --git a/app/release/release.go b/app/release/release.go index 1912c4a..74ee887 100644 --- a/app/release/release.go +++ b/app/release/release.go @@ -2,11 +2,11 @@ package main import ( "fmt" + "io/ioutil" "os" "os/exec" - "io/ioutil" "strings" -// "time" + // "time" ) /* @@ -31,10 +31,10 @@ import ( */ //var jss = []string{"js/jquery-cookie", "js/bootstrap"} -var jss = []string{"js/jquery-cookie", "js/bootstrap", - "js/common", "js/app/note", "js/app/tag", "js/app/notebook", "js/app/share", +var jss = []string{"js/jquery-cookie", "js/bootstrap", + "js/common", "js/app/note", "js/app/tag", "js/app/notebook", "js/app/share", "js/object_id", "js/ZeroClipboard/ZeroClipboard"} - + var base1 = "/Users/life/Documents/Go/package2/src/github.com/leanote/leanote/" var base = "/Users/life/Documents/Go/package2/src/github.com/leanote/leanote/public/" var cmdPath = "/usr/local/bin/uglifyjs" @@ -54,26 +54,26 @@ func compressJs(filename string) { to := base + filename + "-min.js" cmd := exec.Command(cmdPath, source, "-o", to) _, err := cmd.CombinedOutput() - fmt.Println(source); + fmt.Println(source) cmdError(err) } - + func combineJs() { // 生成一个总文件 - cmd := exec.Command("rm", base + "js/all.js") + cmd := exec.Command("rm", base+"js/all.js") _, err := cmd.CombinedOutput() cmdError(err) - + for _, js := range jss { to := base + js + "-min.js" fmt.Println(to) compressJs(js) - + // 每个压缩后的文件放入之 - cmd2 := exec.Command("/bin/sh", "-c", "cat " + to + " >> " + base + "js/all.js") + cmd2 := exec.Command("/bin/sh", "-c", "cat "+to+" >> "+base+"js/all.js") _, err := cmd2.CombinedOutput() cmdError(err) - cmd2 = exec.Command("/bin/sh", "-c", "cat \n >> " + base + "js/all.js") + cmd2 = exec.Command("/bin/sh", "-c", "cat \n >> "+base+"js/all.js") _, err = cmd2.CombinedOutput() cmdError(err) } @@ -82,57 +82,57 @@ func combineJs() { // 改note-dev->note func dev() { // 即替换note.js->note-min.js - m := map[string]string{"tinymce.dev.js": "tinymce.min.js", - "tinymce.js": "tinymce.min.js", - "jquery.ztree.all-3.5.js": "jquery.ztree.all-3.5-min.js", - "note.js": "note-min.js", - "app.js": "app-min.js", - "page.js": "page-min.js", - "common.js": "common-min.js", - "notebook.js": "notebook-min.js", - "share.js": "share-min.js", - "tag.js": "tag-min.js", - "jquery.slimscroll.js": "jquery.slimscroll-min.js", - "jquery.contextmenu.js": "jquery.contextmenu-min.js", - "editor/editor.js": "editor/editor-min.js", + m := map[string]string{"tinymce.dev.js": "tinymce.min.js", + "tinymce.js": "tinymce.min.js", + "jquery.ztree.all-3.5.js": "jquery.ztree.all-3.5-min.js", + "note.js": "note-min.js", + "app.js": "app-min.js", + "page.js": "page-min.js", + "common.js": "common-min.js", + "notebook.js": "notebook-min.js", + "share.js": "share-min.js", + "tag.js": "tag-min.js", + "jquery.slimscroll.js": "jquery.slimscroll-min.js", + "jquery.contextmenu.js": "jquery.contextmenu-min.js", + "editor/editor.js": "editor/editor-min.js", "/public/mdeditor/editor/scrollLink.js": "/public/mdeditor/editor/scrollLink-min.js", - "console.log(o);": "", - } + "console.log(o);": "", + } path := base1 + "/src/views/note/note-dev.html" target := base1 + "/src/views/note/note.html" - + bs, _ := ioutil.ReadFile(path) content := string(bs) print(content) for key, value := range m { content = strings.Replace(content, key, value, -1) } - -// var time = time.Now().Unix() % 1000 - -// content = strings.Replace(content, "-min.js", fmt.Sprintf("-min.js?r=%d", time), -1) -// content = strings.Replace(content, "default{{end}}.css", fmt.Sprintf("default{{end}}.css?r=%d", time), 1) -// content = strings.Replace(content, "writting-overwrite.css", fmt.Sprintf("writting-overwrite.css?r=%d", time), 1) - + + // var time = time.Now().Unix() % 1000 + + // content = strings.Replace(content, "-min.js", fmt.Sprintf("-min.js?r=%d", time), -1) + // content = strings.Replace(content, "default{{end}}.css", fmt.Sprintf("default{{end}}.css?r=%d", time), 1) + // content = strings.Replace(content, "writting-overwrite.css", fmt.Sprintf("writting-overwrite.css?r=%d", time), 1) + ioutil.WriteFile(target, []byte(content), os.ModeAppend) } // 压缩js成一块 func tinymce() { -// cmdStr := "node_modules/jake/bin/cli.js minify bundle[themes:modern,plugins:table,paste,advlist,autolink,link,image,lists,charmap,hr,searchreplace,visualblocks,visualchars,code,nav,tabfocus,contextmenu,directionality,codemirror,codesyntax,textcolor,fullpage]" -// cmd := exec.Command("/Users/life/Documents/eclipse-workspace/go/leanote_release/tinymce-master/node_modules/jake/bin/cli.js", "minify", "bundle[themes:modern,plugins:table,paste,advlist,autolink,link,image,lists,charmap,hr,searchreplace,visualblocks,visualchars,code,nav,tabfocus,contextmenu,directionality,codemirror,codesyntax,textcolor,fullpage]") - cmd := exec.Command("/bin/sh", "-c", "grunt minify"); + // cmdStr := "node_modules/jake/bin/cli.js minify bundle[themes:modern,plugins:table,paste,advlist,autolink,link,image,lists,charmap,hr,searchreplace,visualblocks,visualchars,code,nav,tabfocus,contextmenu,directionality,codemirror,codesyntax,textcolor,fullpage]" + // cmd := exec.Command("/Users/life/Documents/eclipse-workspace/go/leanote_release/tinymce-master/node_modules/jake/bin/cli.js", "minify", "bundle[themes:modern,plugins:table,paste,advlist,autolink,link,image,lists,charmap,hr,searchreplace,visualblocks,visualchars,code,nav,tabfocus,contextmenu,directionality,codemirror,codesyntax,textcolor,fullpage]") + cmd := exec.Command("/bin/sh", "-c", "grunt minify") cmd.Dir = base + "/tinymce_4.1.9" - - fmt.Println("正在build tinymce"); - + + fmt.Println("正在build tinymce") + // 必须要先删除 - cmd2 := exec.Command("/bin/sh", "-c", "rm " + cmd.Dir + "/js/tinymce/tinymce.dev.js") + cmd2 := exec.Command("/bin/sh", "-c", "rm "+cmd.Dir+"/js/tinymce/tinymce.dev.js") cmd2.CombinedOutput() - cmd2 = exec.Command("/bin/sh", "-c", "rm " + cmd.Dir + "/js/tinymce/tinymce.jquery.dev.js") + cmd2 = exec.Command("/bin/sh", "-c", "rm "+cmd.Dir+"/js/tinymce/tinymce.jquery.dev.js") c, _ := cmd2.CombinedOutput() fmt.Println(string(c)) - + c, _ = cmd.CombinedOutput() fmt.Println(string(c)) } @@ -140,19 +140,19 @@ func tinymce() { func main() { // 压缩tinymce // tinymce() - - dev(); - + + dev() + // 其它零散的需要压缩的js - otherJss := []string{"js/main", "js/app/page", "js/contextmenu/jquery.contextmenu", + otherJss := []string{"js/main", "js/app/page", "js/contextmenu/jquery.contextmenu", "js/jquery.ztree.all-3.5", "js/jQuery-slimScroll-1.3.0/jquery.slimscroll", - } - + } + for _, js := range otherJss { compressJs(js) } - + // 先压缩后合并 combineJs() diff --git a/app/service/AlbumService.go b/app/service/AlbumService.go index 992b7bf..f5a1f67 100644 --- a/app/service/AlbumService.go +++ b/app/service/AlbumService.go @@ -2,7 +2,7 @@ package service import ( "github.com/leanote/leanote/app/info" -// . "github.com/leanote/leanote/app/lea" + // . "github.com/leanote/leanote/app/lea" "github.com/leanote/leanote/app/db" "gopkg.in/mgo.v2/bson" "time" @@ -30,9 +30,9 @@ func (this *AlbumService) GetAlbums(userId string) []info.Album { // delete album // presupposition: has no images under this ablum func (this *AlbumService) DeleteAlbum(userId, albumId string) (bool, string) { - if db.Count(db.Files, bson.M{"AlbumId": bson.ObjectIdHex(albumId), + if db.Count(db.Files, bson.M{"AlbumId": bson.ObjectIdHex(albumId), "UserId": bson.ObjectIdHex(userId), - }) == 0 { + }) == 0 { return db.DeleteByIdAndUserId(db.Albums, albumId, userId), "" } return false, "has images" @@ -41,4 +41,4 @@ func (this *AlbumService) DeleteAlbum(userId, albumId string) (bool, string) { // update album name func (this *AlbumService) UpdateAlbum(albumId, userId, name string) bool { return db.UpdateByIdAndUserIdField(db.Albums, albumId, userId, "Name", name) -} \ No newline at end of file +} diff --git a/app/service/AttachService.go b/app/service/AttachService.go index e736dda..31d1c0c 100644 --- a/app/service/AttachService.go +++ b/app/service/AttachService.go @@ -20,9 +20,9 @@ type AttachService struct { func (this *AttachService) AddAttach(attach info.Attach, fromApi bool) (ok bool, msg string) { attach.CreatedTime = time.Now() ok = db.Insert(db.Attachs, attach) - + note := noteService.GetNoteById(attach.NoteId.Hex()) - + // api调用时, 添加attach之前是没有note的 var userId string if note.NoteId != "" { @@ -35,13 +35,13 @@ func (this *AttachService) AddAttach(attach info.Attach, fromApi bool) (ok bool, // 更新笔记的attachs num this.updateNoteAttachNum(attach.NoteId, 1) } - + if !fromApi { // 增长note's usn noteService.IncrNoteUsn(attach.NoteId.Hex(), userId) } - - return + + return } // 更新笔记的附件个数 @@ -49,13 +49,13 @@ func (this *AttachService) AddAttach(attach info.Attach, fromApi bool) (ok bool, func (this *AttachService) updateNoteAttachNum(noteId bson.ObjectId, addNum int) bool { num := db.Count(db.Attachs, bson.M{"NoteId": noteId}) /* - note := info.Note{} - note = noteService.GetNoteById(noteId.Hex()) - note.AttachNum += addNum - if note.AttachNum < 0 { - note.AttachNum = 0 - } - Log(note.AttachNum) + note := info.Note{} + note = noteService.GetNoteById(noteId.Hex()) + note.AttachNum += addNum + if note.AttachNum < 0 { + note.AttachNum = 0 + } + Log(note.AttachNum) */ return db.UpdateByQField(db.Notes, bson.M{"_id": noteId}, "AttachNum", num) } @@ -63,18 +63,18 @@ func (this *AttachService) updateNoteAttachNum(noteId bson.ObjectId, addNum int) // list attachs func (this *AttachService) ListAttachs(noteId, userId string) []info.Attach { attachs := []info.Attach{} - + // 判断是否有权限为笔记添加附件, userId为空时表示是分享笔记的附件 if userId != "" && !shareService.HasUpdateNotePerm(noteId, userId) { return attachs } - + // 笔记是否是自己的 note := noteService.GetNoteByIdAndUserId(noteId, userId) if note.NoteId == "" { return attachs } - + // TODO 这里, 优化权限控制 db.ListByQ(db.Attachs, bson.M{"NoteId": bson.ObjectIdHex(noteId)}, &attachs) @@ -122,13 +122,13 @@ func (this *AttachService) DeleteAllAttachs(noteId, userId string) bool { func (this *AttachService) DeleteAttach(attachId, userId string) (bool, string) { attach := info.Attach{} db.Get(db.Attachs, attachId, &attach) - - if(attach.AttachId != "") { + + if attach.AttachId != "" { // 判断是否有权限为笔记添加附件 if !shareService.HasUpdateNotePerm(attach.NoteId.Hex(), userId) { return false, "No Perm" } - + if db.Delete(db.Attachs, bson.M{"_id": bson.ObjectIdHex(attachId)}) { this.updateNoteAttachNum(attach.NoteId, -1) attach.Path = strings.TrimLeft(attach.Path, "/") @@ -137,7 +137,7 @@ func (this *AttachService) DeleteAttach(attachId, userId string) (bool, string) // userService.UpdateAttachSize(note.UserId.Hex(), -attach.Size) // 修改note Usn noteService.IncrNoteUsn(attach.NoteId.Hex(), userId) - + return true, "delete file success" } return false, "delete file error" diff --git a/app/service/BlogService.go b/app/service/BlogService.go index d50e2f6..a4bbe27 100644 --- a/app/service/BlogService.go +++ b/app/service/BlogService.go @@ -421,7 +421,7 @@ func (this *BlogService) PreNextBlog(userId string, sorterField string, isAsc bo // Log(sortFieldR2) q = db.Notes.Find(query) q.Sort(sortFieldR2).Limit(1).One(¬e2) - + return this.FixNote(note), this.FixNote(note2) } diff --git a/app/service/ConfigService.go b/app/service/ConfigService.go index e7c2082..c1a49d1 100644 --- a/app/service/ConfigService.go +++ b/app/service/ConfigService.go @@ -1,32 +1,33 @@ package service import ( + "fmt" + "github.com/leanote/leanote/app/db" "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" - "github.com/leanote/leanote/app/db" - "gopkg.in/mgo.v2/bson" "github.com/revel/revel" - "time" + "gopkg.in/mgo.v2/bson" "os" "os/exec" - "fmt" - "strings" "strconv" + "strings" + "time" ) // 配置服务 // 只是全局的, 用户的配置没有 type ConfigService struct { - adminUserId string - siteUrl string + adminUserId string + siteUrl string adminUsername string // 全局的 - GlobalAllConfigs map[string]interface{} + GlobalAllConfigs map[string]interface{} GlobalStringConfigs map[string]string - GlobalArrayConfigs map[string][]string - GlobalMapConfigs map[string]map[string]string + GlobalArrayConfigs map[string][]string + GlobalMapConfigs map[string]map[string]string GlobalArrMapConfigs map[string][]map[string]string } + // appStart时 将全局的配置从数据库中得到作为全局 func (this *ConfigService) InitGlobalConfigs() bool { this.GlobalAllConfigs = map[string]interface{}{} @@ -34,22 +35,22 @@ func (this *ConfigService) InitGlobalConfigs() bool { this.GlobalArrayConfigs = map[string][]string{} this.GlobalMapConfigs = map[string]map[string]string{} this.GlobalArrMapConfigs = map[string][]map[string]string{} - + this.adminUsername, _ = revel.Config.String("adminUsername") if this.adminUsername == "" { this.adminUsername = "admin" } this.siteUrl, _ = revel.Config.String("site.url") - + userInfo := userService.GetUserInfoByAny(this.adminUsername) if userInfo.UserId == "" { return false } this.adminUserId = userInfo.UserId.Hex() - + configs := []info.Config{} db.ListByQ(db.Configs, bson.M{"UserId": userInfo.UserId}, &configs) - + for _, config := range configs { if config.IsArr { this.GlobalArrayConfigs[config.Key] = config.ValueArr @@ -65,12 +66,12 @@ func (this *ConfigService) InitGlobalConfigs() bool { this.GlobalAllConfigs[config.Key] = config.ValueStr } } - + return true } func (this *ConfigService) GetSiteUrl() string { - return this.siteUrl; + return this.siteUrl } func (this *ConfigService) GetAdminUsername() string { return this.adminUsername @@ -84,15 +85,15 @@ func (this *ConfigService) updateGlobalConfig(userId, key string, value interfac // 判断是否存在 if _, ok := this.GlobalAllConfigs[key]; !ok { // 需要添加 - config := info.Config{ConfigId: bson.NewObjectId(), - UserId: bson.ObjectIdHex(userId), - Key: key, - IsArr: isArr, - IsMap: isMap, - IsArrMap: isArrMap, + config := info.Config{ConfigId: bson.NewObjectId(), + UserId: bson.ObjectIdHex(userId), + Key: key, + IsArr: isArr, + IsMap: isMap, + IsArrMap: isArrMap, UpdatedTime: time.Now(), } - if(isArr) { + if isArr { v, _ := value.([]string) config.ValueArr = v this.GlobalArrayConfigs[key] = v @@ -113,7 +114,7 @@ func (this *ConfigService) updateGlobalConfig(userId, key string, value interfac } else { i := bson.M{"UpdatedTime": time.Now()} this.GlobalAllConfigs[key] = value - if(isArr) { + if isArr { v, _ := value.([]string) i["ValueArr"] = v this.GlobalArrayConfigs[key] = v @@ -177,25 +178,26 @@ func (this *ConfigService) GetGlobalArrMapConfig(key string) []map[string]string func (this *ConfigService) IsOpenRegister() bool { return this.GetGlobalStringConfig("openRegister") != "" } + //------- // 修改共享笔记的配置 -func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, - registerSharedNotebookPerms, registerSharedNotePerms []int, +func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, + registerSharedNotebookPerms, registerSharedNotePerms []int, registerSharedNotebookIds, registerSharedNoteIds, registerCopyNoteIds []string) (ok bool, msg string) { - - defer func() { + + defer func() { if err := recover(); err != nil { ok = false msg = fmt.Sprint(err) } - }(); - + }() + // 用户是否存在? if registerSharedUserId == "" { ok = true msg = "share userId is blank, So it share nothing to register" this.UpdateGlobalStringConfig(this.adminUserId, "registerSharedUserId", "") - return + return } else { user := userService.GetUserInfo(registerSharedUserId) if user.UserId == "" { @@ -206,7 +208,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, this.UpdateGlobalStringConfig(this.adminUserId, "registerSharedUserId", registerSharedUserId) } } - + notebooks := []map[string]string{} // 共享笔记本 if len(registerSharedNotebookIds) > 0 { @@ -222,7 +224,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, msg = "The user has no such notebook: " + notebookId return } else { - perm := "0"; + perm := "0" if registerSharedNotebookPerms[i] == 1 { perm = "1" } @@ -231,7 +233,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, } } this.UpdateGlobalArrMapConfig(this.adminUserId, "registerSharedNotebooks", notebooks) - + notes := []map[string]string{} // 共享笔记 if len(registerSharedNoteIds) > 0 { @@ -247,7 +249,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, msg = "The user has no such note: " + noteId return } else { - perm := "0"; + perm := "0" if registerSharedNotePerms[i] == 1 { perm = "1" } @@ -256,7 +258,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, } } this.UpdateGlobalArrMapConfig(this.adminUserId, "registerSharedNotes", notes) - + // 复制 noteIds := []string{} if len(registerCopyNoteIds) > 0 { @@ -277,7 +279,7 @@ func (this *ConfigService) UpdateShareNoteConfig(registerSharedUserId string, } } this.UpdateGlobalArrayConfig(this.adminUserId, "registerCopyNoteIds", noteIds) - + ok = true return } @@ -298,7 +300,7 @@ func (this *ConfigService) getBackupDirname() string { } func (this *ConfigService) Backup(remark string) (ok bool, msg string) { binPath := configService.GetGlobalStringConfig("mongodumpPath") - config := revel.Config; + config := revel.Config dbname, _ := config.String("db.dbname") host, _ := revel.Config.String("db.host") port, _ := revel.Config.String("db.port") @@ -318,20 +320,21 @@ func (this *ConfigService) Backup(remark string) (ok bool, msg string) { msg = fmt.Sprintf("%v", err) return } - + cmd := exec.Command("/bin/sh", "-c", binPath) - Log(binPath); + Log(binPath) b, err := cmd.Output() - if err != nil { - msg = fmt.Sprintf("%v", err) + if err != nil { + msg = fmt.Sprintf("%v", err) ok = false - Log("error:......") - Log(string(b)) - return - } + Log("error:......") + Log(string(b)) + return + } ok = configService.AddBackup(dir, remark) - return ok, msg + return ok, msg } + // 还原 func (this *ConfigService) Restore(createdTime string) (ok bool, msg string) { backups := this.GetGlobalArrMapConfig("backups") // [{}, {}] @@ -339,22 +342,22 @@ func (this *ConfigService) Restore(createdTime string) (ok bool, msg string) { var backup map[string]string for i, backup = range backups { if backup["createdTime"] == createdTime { - break; + break } } if i == len(backups) { return false, "Backup Not Found" } - + // 先备份当前 - ok, msg = this.Backup("Auto backup when restore from " + backup["createdTime"] ) + ok, msg = this.Backup("Auto backup when restore from " + backup["createdTime"]) if !ok { return } - + // mongorestore -h localhost -d leanote --directoryperdb /home/user1/gopackage/src/github.com/leanote/leanote/mongodb_backup/leanote_install_data/ binPath := configService.GetGlobalStringConfig("mongorestorePath") - config := revel.Config; + config := revel.Config dbname, _ := config.String("db.dbname") host, _ := revel.Config.String("db.host") port, _ := revel.Config.String("db.port") @@ -365,26 +368,26 @@ func (this *ConfigService) Restore(createdTime string) (ok bool, msg string) { if username != "" { binPath += " -u " + username + " -p " + password } - + path := backup["path"] + "/" + dbname // 判断路径是否存在 if !IsDirExists(path) { return false, path + " Is Not Exists" } - + binPath += " " + path - + cmd := exec.Command("/bin/sh", "-c", binPath) - Log(binPath); + Log(binPath) b, err := cmd.Output() - if err != nil { - msg = fmt.Sprintf("%v", err) + if err != nil { + msg = fmt.Sprintf("%v", err) ok = false - Log("error:......") - Log(string(b)) - return - } - + Log("error:......") + Log(string(b)) + return + } + return true, "" } func (this *ConfigService) DeleteBackup(createdTime string) (bool, string) { @@ -393,22 +396,22 @@ func (this *ConfigService) DeleteBackup(createdTime string) (bool, string) { var backup map[string]string for i, backup = range backups { if backup["createdTime"] == createdTime { - break; + break } } if i == len(backups) { return false, "Backup Not Found" } - + // 删除文件夹之 err := os.RemoveAll(backups[i]["path"]) if err != nil { return false, fmt.Sprintf("%v", err) } - + // 删除之 backups = append(backups[0:i], backups[i+1:]...) - + ok := this.UpdateGlobalArrMapConfig(this.adminUserId, "backups", backups) return ok, "" } @@ -419,14 +422,14 @@ func (this *ConfigService) UpdateBackupRemark(createdTime, remark string) (bool, var backup map[string]string for i, backup = range backups { if backup["createdTime"] == createdTime { - break; + break } } if i == len(backups) { return false, "Backup Not Found" } - backup["remark"] = remark; - + backup["remark"] = remark + ok := this.UpdateGlobalArrMapConfig(this.adminUserId, "backups", backups) return ok, "" } @@ -438,7 +441,7 @@ func (this *ConfigService) GetBackup(createdTime string) (map[string]string, boo var backup map[string]string for i, backup = range backups { if backup["createdTime"] == createdTime { - break; + break } } if i == len(backups) { @@ -456,15 +459,15 @@ var port string func init() { revel.OnAppStart(func() { /* - 不用配置的, 因为最终通过命令可以改, 而且有的使用nginx代理 - port = strconv.Itoa(revel.HttpPort) - if port != "80" { - port = ":" + port - } else { - port = ""; - } + 不用配置的, 因为最终通过命令可以改, 而且有的使用nginx代理 + port = strconv.Itoa(revel.HttpPort) + if port != "80" { + port = ":" + port + } else { + port = ""; + } */ - + siteUrl, _ := revel.Config.String("site.url") // 已包含:9000, http, 去掉成 leanote.com if strings.HasPrefix(siteUrl, "http://") { defaultDomain = siteUrl[len("http://"):] @@ -472,7 +475,7 @@ func init() { defaultDomain = siteUrl[len("https://"):] schema = "https://" } - + // port localhost:9000 ports := strings.Split(defaultDomain, ":") if len(ports) == 2 { @@ -487,49 +490,53 @@ func init() { } func (this *ConfigService) GetSchema() string { - return schema; + return schema } + // 默认 func (this *ConfigService) GetDefaultDomain() string { return defaultDomain } + // 包含http:// func (this *ConfigService) GetDefaultUrl() string { return schema + defaultDomain } + // note func (this *ConfigService) GetNoteDomain() string { - subDomain := this.GetGlobalStringConfig("noteSubDomain"); + subDomain := this.GetGlobalStringConfig("noteSubDomain") if subDomain != "" { return subDomain + port } return this.GetDefaultDomain() + "/note" } func (this *ConfigService) GetNoteUrl() string { - return schema + this.GetNoteDomain(); + return schema + this.GetNoteDomain() } // blog func (this *ConfigService) GetBlogDomain() string { - subDomain := this.GetGlobalStringConfig("blogSubDomain"); + subDomain := this.GetGlobalStringConfig("blogSubDomain") if subDomain != "" { return subDomain + port } return this.GetDefaultDomain() + "/blog" } func (this *ConfigService) GetBlogUrl() string { - return schema + this.GetBlogDomain(); + return schema + this.GetBlogDomain() } + // lea func (this *ConfigService) GetLeaDomain() string { - subDomain := this.GetGlobalStringConfig("leaSubDomain"); + subDomain := this.GetGlobalStringConfig("leaSubDomain") if subDomain != "" { return subDomain + port } return this.GetDefaultDomain() + "/lea" } func (this *ConfigService) GetLeaUrl() string { - return schema + this.GetLeaDomain(); + return schema + this.GetLeaDomain() } func (this *ConfigService) GetUserUrl(domain string) string { @@ -543,6 +550,7 @@ func (this *ConfigService) GetUserSubUrl(subDomain string) string { func (this *ConfigService) AllowCustomDomain() bool { return configService.GetGlobalStringConfig("allowCustomDomain") != "" } + // 是否是好的自定义域名 func (this *ConfigService) IsGoodCustomDomain(domain string) bool { blacks := this.GetGlobalArrayConfig("blackCustomDomains") @@ -567,20 +575,21 @@ func (this *ConfigService) IsGoodSubDomain(domain string) bool { // 上传大小 func (this *ConfigService) GetUploadSize(key string) float64 { f, _ := strconv.ParseFloat(this.GetGlobalStringConfig(key), 64) - return f; + return f } func (this *ConfigService) GetUploadSizeLimit() map[string]float64 { return map[string]float64{ - "uploadImageSize": this.GetUploadSize("uploadImageSize"), - "uploadBlogLogoSize":this.GetUploadSize("uploadBlogLogoSize"), - "uploadAttachSize":this.GetUploadSize("uploadAttachSize"), - "uploadAvatarSize":this.GetUploadSize("uploadAvatarSize"), + "uploadImageSize": this.GetUploadSize("uploadImageSize"), + "uploadBlogLogoSize": this.GetUploadSize("uploadBlogLogoSize"), + "uploadAttachSize": this.GetUploadSize("uploadAttachSize"), + "uploadAvatarSize": this.GetUploadSize("uploadAvatarSize"), } } + // 为用户得到全局的配置 // NoteController调用 func (this *ConfigService) GetGlobalConfigForUser() map[string]interface{} { - uploadSizeConfigs := this.GetUploadSizeLimit(); + uploadSizeConfigs := this.GetUploadSizeLimit() config := map[string]interface{}{} for k, v := range uploadSizeConfigs { config[k] = v diff --git a/app/service/EmailService.go b/app/service/EmailService.go index ad71306..3753703 100644 --- a/app/service/EmailService.go +++ b/app/service/EmailService.go @@ -1,17 +1,17 @@ package service import ( - "github.com/leanote/leanote/app/info" + "bytes" + "fmt" "github.com/leanote/leanote/app/db" + "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" - "time" - "strings" + "html/template" "net/smtp" "strconv" - "fmt" - "html/template" - "bytes" + "strings" + "time" ) // 发送邮件 @@ -20,7 +20,7 @@ type EmailService struct { tpls map[string]*template.Template } -func NewEmailService() (*EmailService) { +func NewEmailService() *EmailService { return &EmailService{tpls: map[string]*template.Template{}} } @@ -39,32 +39,32 @@ func InitEmailFromDb() { func (this *EmailService) SendEmail(to, subject, body string) (ok bool, e string) { InitEmailFromDb() - + if host == "" || emailPort == "" || username == "" || password == "" { - return + return } hp := strings.Split(host, ":") auth := smtp.PlainAuth("", username, password, hp[0]) - + var content_type string - + mailtype := "html" if mailtype == "html" { - content_type = "Content-Type: text/"+ mailtype + "; charset=UTF-8" - } else{ + content_type = "Content-Type: text/" + mailtype + "; charset=UTF-8" + } else { content_type = "Content-Type: text/plain" + "; charset=UTF-8" } - - msg := []byte("To: " + to + "\r\nFrom: " + username + "<"+ username +">\r\nSubject: " + subject + "\r\n" + content_type + "\r\n\r\n" + body) + + msg := []byte("To: " + to + "\r\nFrom: " + username + "<" + username + ">\r\nSubject: " + subject + "\r\n" + content_type + "\r\n\r\n" + body) send_to := strings.Split(to, ";") err := smtp.SendMail(host+":"+emailPort, auth, username, send_to, msg) - + if err != nil { e = fmt.Sprint(err) - return + return } ok = true - return + return } // AddUser调用 @@ -74,20 +74,20 @@ func (this *EmailService) RegisterSendActiveEmail(userInfo info.User, email stri if token == "" { return false } - - subject := configService.GetGlobalStringConfig("emailTemplateRegisterSubject"); - tpl := configService.GetGlobalStringConfig("emailTemplateRegister"); - - if(tpl == "") { + + subject := configService.GetGlobalStringConfig("emailTemplateRegisterSubject") + tpl := configService.GetGlobalStringConfig("emailTemplateRegister") + + if tpl == "" { return false } - + tokenUrl := configService.GetSiteUrl() + "/user/activeEmail?token=" + token // {siteUrl} {tokenUrl} {token} {tokenTimeout} {user.id} {user.email} {user.username} token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "tokenUrl": tokenUrl, "token": token, "tokenTimeout": strconv.Itoa(int(tokenService.GetOverHours(info.TokenActiveEmail))), "user": map[string]interface{}{ - "userId": userInfo.UserId.Hex(), - "email": userInfo.Email, + "userId": userInfo.UserId.Hex(), + "email": userInfo.Email, "username": userInfo.Username, }, } @@ -97,7 +97,7 @@ func (this *EmailService) RegisterSendActiveEmail(userInfo info.User, email stri if !ok { return false } - + // 发送邮件 ok, _ = this.SendEmail(email, subject, tpl) return ok @@ -113,66 +113,66 @@ func (this *EmailService) UpdateEmailSendActiveEmail(userInfo info.User, email s } token := tokenService.NewToken(userInfo.UserId.Hex(), email, info.TokenUpdateEmail) - + if token == "" { return } - - subject := configService.GetGlobalStringConfig("emailTemplateUpdateEmailSubject"); - tpl := configService.GetGlobalStringConfig("emailTemplateUpdateEmail"); - + + subject := configService.GetGlobalStringConfig("emailTemplateUpdateEmailSubject") + tpl := configService.GetGlobalStringConfig("emailTemplateUpdateEmail") + // 发送邮件 tokenUrl := configService.GetSiteUrl() + "/user/updateEmail?token=" + token // {siteUrl} {tokenUrl} {token} {tokenTimeout} {user.userId} {user.email} {user.username} token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "tokenUrl": tokenUrl, "token": token, "tokenTimeout": strconv.Itoa(int(tokenService.GetOverHours(info.TokenActiveEmail))), "newEmail": email, "user": map[string]interface{}{ - "userId": userInfo.UserId.Hex(), - "email": userInfo.Email, + "userId": userInfo.UserId.Hex(), + "email": userInfo.Email, "username": userInfo.Username, }, } ok, msg, subject, tpl = this.renderEmail(subject, tpl, token2Value) if !ok { - return + return } - + // 发送邮件 ok, msg = this.SendEmail(email, subject, tpl) return } func (this *EmailService) FindPwdSendEmail(token, email string) (ok bool, msg string) { - subject := configService.GetGlobalStringConfig("emailTemplateFindPasswordSubject"); - tpl := configService.GetGlobalStringConfig("emailTemplateFindPassword"); - + subject := configService.GetGlobalStringConfig("emailTemplateFindPasswordSubject") + tpl := configService.GetGlobalStringConfig("emailTemplateFindPassword") + // 发送邮件 tokenUrl := configService.GetSiteUrl() + "/findPassword/" + token // {siteUrl} {tokenUrl} {token} {tokenTimeout} {user.id} {user.email} {user.username} - token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "tokenUrl": tokenUrl, + token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "tokenUrl": tokenUrl, "token": token, "tokenTimeout": strconv.Itoa(int(tokenService.GetOverHours(info.TokenActiveEmail)))} - + ok, msg, subject, tpl = this.renderEmail(subject, tpl, token2Value) if !ok { - return + return } // 发送邮件 ok, msg = this.SendEmail(email, subject, tpl) - return + return } // 发送邀请链接 func (this *EmailService) SendInviteEmail(userInfo info.User, email, content string) bool { - subject := configService.GetGlobalStringConfig("emailTemplateInviteSubject"); - tpl := configService.GetGlobalStringConfig("emailTemplateInvite"); - + subject := configService.GetGlobalStringConfig("emailTemplateInviteSubject") + tpl := configService.GetGlobalStringConfig("emailTemplateInvite") + token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "registerUrl": configService.GetSiteUrl() + "/register?from=" + userInfo.Username, - "content": content, + "content": content, "user": map[string]interface{}{ "username": userInfo.Username, - "email": userInfo.Email, + "email": userInfo.Email, }, } var ok bool @@ -187,32 +187,32 @@ func (this *EmailService) SendInviteEmail(userInfo info.User, email, content str // 发送评论 func (this *EmailService) SendCommentEmail(note info.Note, comment info.BlogComment, userId, content string) bool { - subject := configService.GetGlobalStringConfig("emailTemplateCommentSubject"); - tpl := configService.GetGlobalStringConfig("emailTemplateComment"); - + subject := configService.GetGlobalStringConfig("emailTemplateCommentSubject") + tpl := configService.GetGlobalStringConfig("emailTemplateComment") + // title := "评论提醒" - + /* - toUserId := note.UserId.Hex() - // title := "评论提醒" - - // 表示回复回复的内容, 那么发送给之前回复的 - if comment.CommentId != "" { - toUserId = comment.UserId.Hex() - } - toUserInfo := userService.GetUserInfo(toUserId) - sendUserInfo := userService.GetUserInfo(userId) - - subject := note.Title + " 收到 " + sendUserInfo.Username + " 的评论"; - if comment.CommentId != "" { - subject = "您在 " + note.Title + " 发表的评论收到 " + sendUserInfo.Username; - if userId == note.UserId.Hex() { - subject += "(作者)"; + toUserId := note.UserId.Hex() + // title := "评论提醒" + + // 表示回复回复的内容, 那么发送给之前回复的 + if comment.CommentId != "" { + toUserId = comment.UserId.Hex() + } + toUserInfo := userService.GetUserInfo(toUserId) + sendUserInfo := userService.GetUserInfo(userId) + + subject := note.Title + " 收到 " + sendUserInfo.Username + " 的评论"; + if comment.CommentId != "" { + subject = "您在 " + note.Title + " 发表的评论收到 " + sendUserInfo.Username; + if userId == note.UserId.Hex() { + subject += "(作者)"; + } + subject += " 的评论"; } - subject += " 的评论"; - } */ - + toUserId := note.UserId.Hex() // 表示回复回复的内容, 那么发送给之前回复的 if comment.CommentId != "" { @@ -220,28 +220,28 @@ func (this *EmailService) SendCommentEmail(note info.Note, comment info.BlogComm } toUserInfo := userService.GetUserInfo(toUserId) // 被评论者 sendUserInfo := userService.GetUserInfo(userId) // 评论者 - - // {siteUrl} {blogUrl} + + // {siteUrl} {blogUrl} // {blog.id} {blog.title} {blog.url} - // {commentUser.userId} {commentUser.username} {commentUser.email} + // {commentUser.userId} {commentUser.username} {commentUser.email} // {commentedUser.userId} {commentedUser.username} {commentedUser.email} token2Value := map[string]interface{}{"siteUrl": configService.GetSiteUrl(), "blogUrl": configService.GetBlogUrl(), "blog": map[string]string{ - "id": note.NoteId.Hex(), + "id": note.NoteId.Hex(), "title": note.Title, - "url": configService.GetBlogUrl() + "/view/" + note.NoteId.Hex(), + "url": configService.GetBlogUrl() + "/view/" + note.NoteId.Hex(), }, "commentContent": content, // 评论者信息 - "commentUser": map[string]interface{}{"userId": sendUserInfo.UserId.Hex(), - "username": sendUserInfo.Username, - "email": sendUserInfo.Email, + "commentUser": map[string]interface{}{"userId": sendUserInfo.UserId.Hex(), + "username": sendUserInfo.Username, + "email": sendUserInfo.Email, "isBlogAuthor": userId == note.UserId.Hex(), }, // 被评论者信息 "commentedUser": map[string]interface{}{"userId": toUserId, - "username": toUserInfo.Username, - "email": toUserInfo.Email, + "username": toUserInfo.Username, + "email": toUserInfo.Email, "isBlogAuthor": toUserId == note.UserId.Hex(), }, } @@ -251,53 +251,52 @@ func (this *EmailService) SendCommentEmail(note info.Note, comment info.BlogComm if !ok { return false } - + // 发送邮件 ok, _ = this.SendEmail(toUserInfo.Email, subject, tpl) return ok } - // 验证模板是否正确 -func (this *EmailService) ValidTpl(str string) (ok bool, msg string){ - defer func() { +func (this *EmailService) ValidTpl(str string) (ok bool, msg string) { + defer func() { if err := recover(); err != nil { ok = false msg = fmt.Sprint(err) } - }(); - header := configService.GetGlobalStringConfig("emailTemplateHeader"); - footer := configService.GetGlobalStringConfig("emailTemplateFooter"); + }() + header := configService.GetGlobalStringConfig("emailTemplateHeader") + footer := configService.GetGlobalStringConfig("emailTemplateFooter") str = strings.Replace(str, "{{header}}", header, -1) str = strings.Replace(str, "{{footer}}", footer, -1) _, err := template.New("tpl name").Parse(str) - if err != nil { + if err != nil { msg = fmt.Sprint(err) - return - } - ok = true + return + } + ok = true return } // ok, msg, subject, tpl -func (this *EmailService) getTpl(str string) (ok bool, msg string, tpl *template.Template){ - defer func() { +func (this *EmailService) getTpl(str string) (ok bool, msg string, tpl *template.Template) { + defer func() { if err := recover(); err != nil { ok = false msg = fmt.Sprint(err) } - }(); - + }() + var err error var has bool - + if tpl, has = this.tpls[str]; !has { - tpl, err = template.New("tpl name").Parse(str) - if err != nil { + tpl, err = template.New("tpl name").Parse(str) + if err != nil { msg = fmt.Sprint(err) - return - } - this.tpls[str] = tpl + return + } + this.tpls[str] = tpl } ok = true return @@ -310,67 +309,67 @@ func (this *EmailService) renderEmail(subject, body string, values map[string]in defer func() { // 必须要先声明defer,否则不能捕获到panic异常 if err := recover(); err != nil { ok = false - msg = fmt.Sprint(err) // 这里的err其实就是panic传入的内容, + msg = fmt.Sprint(err) // 这里的err其实就是panic传入的内容, } - }(); - + }() + var tpl *template.Template - - values["siteUrl"] = configService.GetSiteUrl(); - + + values["siteUrl"] = configService.GetSiteUrl() + // subject if subject != "" { ok, msg, tpl = this.getTpl(subject) - if(!ok) { + if !ok { return } var buffer bytes.Buffer - err := tpl.Execute(&buffer, values) - if err != nil { + err := tpl.Execute(&buffer, values) + if err != nil { msg = fmt.Sprint(err) return - } - o = buffer.String() - } else { - o = "" - } - - // content - header := configService.GetGlobalStringConfig("emailTemplateHeader"); - footer := configService.GetGlobalStringConfig("emailTemplateFooter"); + } + o = buffer.String() + } else { + o = "" + } + + // content + header := configService.GetGlobalStringConfig("emailTemplateHeader") + footer := configService.GetGlobalStringConfig("emailTemplateFooter") body = strings.Replace(body, "{{header}}", header, -1) body = strings.Replace(body, "{{footer}}", footer, -1) values["subject"] = o ok, msg, tpl = this.getTpl(body) - if(!ok) { + if !ok { return } var buffer2 bytes.Buffer - err := tpl.Execute(&buffer2, values) - if err != nil { + err := tpl.Execute(&buffer2, values) + if err != nil { msg = fmt.Sprint(err) return - } - b = buffer2.String() - - return + } + b = buffer2.String() + + return } // 发送email给用户 // 需要记录 func (this *EmailService) SendEmailToUsers(users []info.User, subject, body string) (ok bool, msg string) { - if(users == nil || len(users) == 0) { + if users == nil || len(users) == 0 { msg = "no users" - return + return } - + // 尝试renderHtml ok, msg, _, _ = this.renderEmail(subject, body, map[string]interface{}{}) - if(!ok) { + if !ok { Log(msg) - return + return } - + go func() { for _, user := range users { LogJ(user) @@ -381,8 +380,8 @@ func (this *EmailService) SendEmailToUsers(users []info.User, subject, body stri ok2, msg2, subject2, body2 := this.renderEmail(subject, body, m) ok = ok2 msg = msg2 - if(ok2) { - sendOk, msg := this.SendEmail(user.Email, subject2, body2); + if ok2 { + sendOk, msg := this.SendEmail(user.Email, subject2, body2) this.AddEmailLog(user.Email, subject, body, sendOk, msg) // 把模板记录下 // 记录到Email Log if sendOk { @@ -395,47 +394,47 @@ func (this *EmailService) SendEmailToUsers(users []info.User, subject, body stri } } }() - - return + + return } func (this *EmailService) SendEmailToEmails(emails []string, subject, body string) (ok bool, msg string) { - if(emails == nil || len(emails) == 0) { + if emails == nil || len(emails) == 0 { msg = "no emails" - return + return } - + // 尝试renderHtml ok, msg, _, _ = this.renderEmail(subject, body, map[string]interface{}{}) - if(!ok) { + if !ok { Log(msg) - return + return } - -// go func() { - for _, email := range emails { - if email == "" { - continue - } - m := map[string]interface{}{} - m["email"] = email - ok, msg, subject, body = this.renderEmail(subject, body, m) - if(ok) { - sendOk, msg := this.SendEmail(email, subject, body); - this.AddEmailLog(email, subject, body, sendOk, msg) - // 记录到Email Log - if sendOk { - Log("ok " + email) - } else { - Log("no " + email) - } - } else { - Log(msg); - } + + // go func() { + for _, email := range emails { + if email == "" { + continue } -// }() - - return + m := map[string]interface{}{} + m["email"] = email + ok, msg, subject, body = this.renderEmail(subject, body, m) + if ok { + sendOk, msg := this.SendEmail(email, subject, body) + this.AddEmailLog(email, subject, body, sendOk, msg) + // 记录到Email Log + if sendOk { + Log("ok " + email) + } else { + Log("no " + email) + } + } else { + Log(msg) + } + } + // }() + + return } // 添加邮件日志 @@ -443,6 +442,7 @@ func (this *EmailService) AddEmailLog(email, subject, body string, ok bool, msg log := info.EmailLog{LogId: bson.NewObjectId(), Email: email, Subject: subject, Body: body, Ok: ok, Msg: msg, CreatedTime: time.Now()} db.Insert(db.EmailLogs, log) } + // 展示邮件日志 func (this *EmailService) DeleteEmails(ids []string) bool { @@ -451,7 +451,7 @@ func (this *EmailService) DeleteEmails(ids []string) bool { idsO[i] = bson.ObjectIdHex(id) } db.DeleteAll(db.EmailLogs, bson.M{"_id": bson.M{"$in": idsO}}) - + return true } func (this *EmailService) ListEmailLogs(pageNumber, pageSize int, sortField string, isAsc bool, email string) (page info.Page, emailLogs []info.EmailLog) { @@ -461,7 +461,7 @@ func (this *EmailService) ListEmailLogs(pageNumber, pageSize int, sortField stri if email != "" { query["Email"] = bson.M{"$regex": bson.RegEx{".*?" + email + ".*", "i"}} } - q := db.EmailLogs.Find(query); + q := db.EmailLogs.Find(query) // 总记录数 count, _ := q.Count() // 列表 @@ -471,4 +471,4 @@ func (this *EmailService) ListEmailLogs(pageNumber, pageSize int, sortField stri All(&emailLogs) page = info.NewPage(pageNumber, pageSize, count, nil) return -} \ No newline at end of file +} diff --git a/app/service/FileService.go b/app/service/FileService.go index b8b1867..9e3569a 100644 --- a/app/service/FileService.go +++ b/app/service/FileService.go @@ -30,7 +30,7 @@ func (this *FileService) AddImage(image info.File, albumId, userId string, needC image.IsDefaultAlbum = true } image.UserId = bson.ObjectIdHex(userId) - + ok = db.Insert(db.Files, image) return } @@ -40,28 +40,28 @@ func (this *FileService) AddImage(image info.File, albumId, userId string, needC func (this *FileService) ListImagesWithPage(userId, albumId, key string, pageNumber, pageSize int) info.Page { skipNum, sortFieldR := parsePageAndSort(pageNumber, pageSize, "CreatedTime", false) files := []info.File{} - + q := bson.M{"UserId": bson.ObjectIdHex(userId), "Type": ""} // life if albumId != "" { - q["AlbumId"] = bson.ObjectIdHex(albumId); + q["AlbumId"] = bson.ObjectIdHex(albumId) } else { q["IsDefaultAlbum"] = true } if key != "" { - q["Title"] = bson.M{"$regex": bson.RegEx{".*?" + key + ".*", "i"}} + q["Title"] = bson.M{"$regex": bson.RegEx{".*?" + key + ".*", "i"}} } - -// LogJ(q) - - count := db.Count(db.Files, q); - + + // LogJ(q) + + count := db.Count(db.Files, q) + db.Files. Find(q). Sort(sortFieldR). Skip(skipNum). Limit(pageSize). All(&files) - + return info.Page{Count: count, List: files} } @@ -75,12 +75,12 @@ func (this *FileService) GetAllImageNamesMap(userId string) (m map[string]bool) q := bson.M{"UserId": bson.ObjectIdHex(userId)} files := []info.File{} db.ListByQWithFields(db.Files, q, []string{"Name"}, &files) - + m = make(map[string]bool) if len(files) == 0 { return } - + for _, file := range files { m[file.Name] = true } @@ -91,8 +91,8 @@ func (this *FileService) GetAllImageNamesMap(userId string) (m map[string]bool) func (this *FileService) DeleteImage(userId, fileId string) (bool, string) { file := info.File{} db.GetByIdAndUserId(db.Files, fileId, userId, &file) - - if(file.FileId != "") { + + if file.FileId != "" { if db.DeleteByIdAndUserId(db.Files, fileId, userId) { // delete image // TODO @@ -173,63 +173,63 @@ func (this *FileService) GetFile(userId, fileId string) string { if fileId == "" { return "" } - + file := info.File{} db.Get(db.Files, fileId, &file) path := file.Path if path == "" { return "" } - + // 1. 判断权限 - + // 是否是我的文件 if userId != "" && file.UserId.Hex() == userId { return path } - + // 得到使用过该fileId的所有笔记NoteId // 这些笔记是否有public的, 若有则ok // 这些笔记(笔记本)是否有共享给我的, 若有则ok - + noteIds := noteImageService.GetNoteIds(fileId) if noteIds != nil && len(noteIds) > 0 { // 这些笔记是否有public的 if db.Has(db.Notes, bson.M{"_id": bson.M{"$in": noteIds}, "IsBlog": true}) { return path } - + // 2014/12/28 修复, 如果是分享给用户组, 那就不行, 这里可以实现 for _, noteId := range noteIds { note := noteService.GetNoteById(noteId.Hex()) if shareService.HasReadPerm(note.UserId.Hex(), userId, noteId.Hex()) { - return path; - } - } - /* - // 若有共享给我的笔记? - // 对该笔记可读? - if db.Has(db.ShareNotes, bson.M{"ToUserId": bson.ObjectIdHex(userId), "NoteId": bson.M{"$in": noteIds}}) { - return path - } - - // 笔记本是否共享给我? - // 通过笔记得到笔记本 - notes := []info.Note{} - db.ListByQWithFields(db.Notes, bson.M{"_id": bson.M{"$in": noteIds}}, []string{"NotebookId"}, ¬es) - if notes != nil && len(notes) > 0 { - notebookIds := make([]bson.ObjectId, len(notes)) - for i := 0; i < len(notes); i++ { - notebookIds[i] = notes[i].NotebookId - } - - if db.Has(db.ShareNotebooks, bson.M{"ToUserId": bson.ObjectIdHex(userId), "NotebookId": bson.M{"$in": notebookIds}}) { return path } } + /* + // 若有共享给我的笔记? + // 对该笔记可读? + if db.Has(db.ShareNotes, bson.M{"ToUserId": bson.ObjectIdHex(userId), "NoteId": bson.M{"$in": noteIds}}) { + return path + } + + // 笔记本是否共享给我? + // 通过笔记得到笔记本 + notes := []info.Note{} + db.ListByQWithFields(db.Notes, bson.M{"_id": bson.M{"$in": noteIds}}, []string{"NotebookId"}, ¬es) + if notes != nil && len(notes) > 0 { + notebookIds := make([]bson.ObjectId, len(notes)) + for i := 0; i < len(notes); i++ { + notebookIds[i] = notes[i].NotebookId + } + + if db.Has(db.ShareNotebooks, bson.M{"ToUserId": bson.ObjectIdHex(userId), "NotebookId": bson.M{"$in": notebookIds}}) { + return path + } + } */ } - + // 可能是刚复制到owner上, 但内容又没有保存, 所以没有note->imageId的映射, 此时看是否有fromFileId if file.FromFileId != "" { fromFile := info.File{} @@ -238,7 +238,7 @@ func (this *FileService) GetFile(userId, fileId string) string { return fromFile.Path } } - + return "" } @@ -248,44 +248,44 @@ func (this *FileService) CopyImage(userId, fileId, toUserId string) (bool, strin file2 := info.File{} db.GetByQ(db.Files, bson.M{"UserId": bson.ObjectIdHex(toUserId), "FromFileId": bson.ObjectIdHex(fileId)}, &file2) if file2.FileId != "" { - return true, file2.FileId.Hex(); + return true, file2.FileId.Hex() } // 复制之 - + file := info.File{} db.GetByIdAndUserId(db.Files, fileId, userId, &file) - + if file.FileId == "" || file.UserId.Hex() != userId { return false, "" } - + _, ext := SplitFilename(file.Name) newFilename := NewGuid() + ext - + dir := "files/" + toUserId + "/images" filePath := dir + "/" + newFilename err := os.MkdirAll(dir, 0755) if err != nil { return false, "" } - - _, err = CopyFile(revel.BasePath + "/" + file.Path, revel.BasePath + "/" + filePath) + + _, err = CopyFile(revel.BasePath+"/"+file.Path, revel.BasePath+"/"+filePath) if err != nil { Log(err) return false, "" } - + fileInfo := info.File{Name: newFilename, - Title: file.Title, - Path: filePath, - Size: file.Size, + Title: file.Title, + Path: filePath, + Size: file.Size, FromFileId: file.FileId} - id := bson.NewObjectId(); + id := bson.NewObjectId() fileInfo.FileId = id fileId = id.Hex() Ok, _ := this.AddImage(fileInfo, "", toUserId, false) - + if Ok { return Ok, id.Hex() } @@ -296,7 +296,7 @@ func (this *FileService) CopyImage(userId, fileId, toUserId string) (bool, strin func (this *FileService) IsMyFile(userId, fileId string) bool { // 如果有问题会panic if !bson.IsObjectIdHex(fileId) || !bson.IsObjectIdHex(userId) { - return false; + return false } return db.Has(db.Files, bson.M{"UserId": bson.ObjectIdHex(userId), "_id": bson.ObjectIdHex(fileId)}) } diff --git a/app/service/GroupService.go b/app/service/GroupService.go index 86641b6..a2cab44 100644 --- a/app/service/GroupService.go +++ b/app/service/GroupService.go @@ -1,12 +1,12 @@ package service import ( - "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/db" -// . "github.com/leanote/leanote/app/lea" + "github.com/leanote/leanote/app/info" + // . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" "time" -// "strings" + // "strings" ) // 用户组, 用户组用户管理 @@ -16,34 +16,35 @@ type GroupService struct { // 添加分组 func (this *GroupService) AddGroup(userId, title string) (bool, info.Group) { - group := info.Group { - GroupId: bson.NewObjectId(), - UserId: bson.ObjectIdHex(userId), - Title: title, + group := info.Group{ + GroupId: bson.NewObjectId(), + UserId: bson.ObjectIdHex(userId), + Title: title, CreatedTime: time.Now(), } return db.Insert(db.Groups, group), group } + // 删除分组 // 判断是否有好友 func (this *GroupService) DeleteGroup(userId, groupId string) (ok bool, msg string) { /* - if db.Has(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId)}) { - return false, "groupHasUsers" - } + if db.Has(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId)}) { + return false, "groupHasUsers" + } */ if !this.isMyGroup(userId, groupId) { return false, "notMyGroup" } - + // 删除分组后, 需要删除所有用户分享到该组的笔记本, 笔记 - - shareService.DeleteAllShareNotebookGroup(groupId); - shareService.DeleteAllShareNoteGroup(groupId); - + + shareService.DeleteAllShareNotebookGroup(groupId) + shareService.DeleteAllShareNoteGroup(groupId) + db.DeleteAll(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId)}) return db.DeleteByIdAndUserId(db.Groups, groupId, userId), "" - + // TODO 删除分组后, 在shareNote, shareNotebook中也要删除 } @@ -53,15 +54,15 @@ func (this *GroupService) UpdateGroupTitle(userId, groupId, title string) (ok bo } // 得到用户的所有分组(包括下的所有用户) -func (this *GroupService) GetGroupsAndUsers(userId string) ([]info.Group) { -/* - // 得到我的分组 - groups := []info.Group{} - db.ListByQ(db.Groups, bson.M{"UserId": bson.ObjectIdHex(userId)}, &groups) -*/ +func (this *GroupService) GetGroupsAndUsers(userId string) []info.Group { + /* + // 得到我的分组 + groups := []info.Group{} + db.ListByQ(db.Groups, bson.M{"UserId": bson.ObjectIdHex(userId)}, &groups) + */ // 我的分组, 及我所属的分组 - groups := this.GetGroupsContainOf(userId); - + groups := this.GetGroupsContainOf(userId) + // 得到其下的用户 for i, group := range groups { group.Users = this.GetUsers(group.GroupId.Hex()) @@ -69,8 +70,9 @@ func (this *GroupService) GetGroupsAndUsers(userId string) ([]info.Group) { } return groups } + // 仅仅得到所有分组 -func (this *GroupService) GetGroups(userId string) ([]info.Group) { +func (this *GroupService) GetGroups(userId string) []info.Group { // 得到分组s groups := []info.Group{} db.ListByQ(db.Groups, bson.M{"UserId": bson.ObjectIdHex(userId)}, &groups) @@ -78,24 +80,24 @@ func (this *GroupService) GetGroups(userId string) ([]info.Group) { } // 得到我的和我所属组的ids -func (this *GroupService) GetMineAndBelongToGroupIds(userId string) ([]bson.ObjectId) { +func (this *GroupService) GetMineAndBelongToGroupIds(userId string) []bson.ObjectId { // 所属组 groupIds := this.GetBelongToGroupIds(userId) - + m := map[bson.ObjectId]bool{} for _, groupId := range groupIds { m[groupId] = true } - + // 我的组 myGroups := this.GetGroups(userId) - + for _, group := range myGroups { if !m[group.GroupId] { groupIds = append(groupIds, group.GroupId) } } - + return groupIds } @@ -105,28 +107,28 @@ func (this *GroupService) GetGroupsContainOf(userId string) []info.Group { // 我的组 myGroups := this.GetGroups(userId) myGroupMap := map[bson.ObjectId]bool{} - + for _, group := range myGroups { myGroupMap[group.GroupId] = true } - + // 所属组 groupIds := this.GetBelongToGroupIds(userId) groups := []info.Group{} db.ListByQ(db.Groups, bson.M{"_id": bson.M{"$in": groupIds}}, &groups) - + for _, group := range groups { if !myGroupMap[group.GroupId] { myGroups = append(myGroups, group) } } - + return myGroups } // 得到分组, shareService用 -func (this *GroupService) GetGroup(userId, groupId string) (info.Group) { +func (this *GroupService) GetGroup(userId, groupId string) info.Group { // 得到分组s group := info.Group{} db.GetByIdAndUserId(db.Groups, groupId, userId, &group) @@ -134,7 +136,7 @@ func (this *GroupService) GetGroup(userId, groupId string) (info.Group) { } // 得到某分组下的用户 -func (this *GroupService) GetUsers(groupId string) ([]info.User) { +func (this *GroupService) GetUsers(groupId string) []info.User { // 得到UserIds groupUsers := []info.GroupUser{} db.ListByQWithFields(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId)}, []string{"UserId"}, &groupUsers) @@ -150,7 +152,7 @@ func (this *GroupService) GetUsers(groupId string) ([]info.User) { } // 得到我所属的所有分组ids -func (this *GroupService) GetBelongToGroupIds(userId string) ([]bson.ObjectId) { +func (this *GroupService) GetBelongToGroupIds(userId string) []bson.ObjectId { // 得到UserIds groupUsers := []info.GroupUser{} db.ListByQWithFields(db.GroupUsers, bson.M{"UserId": bson.ObjectIdHex(userId)}, []string{"GroupId"}, &groupUsers) @@ -182,23 +184,23 @@ func (this *GroupService) IsExistsGroupUser(userId, groupId string) (ok bool) { func (this *GroupService) AddUser(ownUserId, groupId, userId string) (ok bool, msg string) { // groupId是否是ownUserId的? /* - if !this.IsExistsGroupUser(ownUserId, groupId) { - return false, "forbidden" - } + if !this.IsExistsGroupUser(ownUserId, groupId) { + return false, "forbidden" + } */ if !this.isMyGroup(ownUserId, groupId) { return false, "forbidden" } - + // 是否已存在 if db.Has(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId), "UserId": bson.ObjectIdHex(userId)}) { return false, "hasUsers" } - + return db.Insert(db.GroupUsers, info.GroupUser{ GroupUserId: bson.NewObjectId(), - GroupId: bson.ObjectIdHex(groupId), - UserId: bson.ObjectIdHex(userId), + GroupId: bson.ObjectIdHex(groupId), + UserId: bson.ObjectIdHex(userId), CreatedTime: time.Now(), }), "" } @@ -207,17 +209,17 @@ func (this *GroupService) AddUser(ownUserId, groupId, userId string) (ok bool, m func (this *GroupService) DeleteUser(ownUserId, groupId, userId string) (ok bool, msg string) { // groupId是否是ownUserId的? /* - if !this.IsExistsGroupUser(ownUserId, groupId) { - return false, "forbidden" - } + if !this.IsExistsGroupUser(ownUserId, groupId) { + return false, "forbidden" + } */ if !this.isMyGroup(ownUserId, groupId) { return false, "forbidden" } - + // 删除该用户分享到本组的笔记本, 笔记 - shareService.DeleteShareNotebookGroupWhenDeleteGroupUser(userId, groupId); - shareService.DeleteShareNoteGroupWhenDeleteGroupUser(userId, groupId); - + shareService.DeleteShareNotebookGroupWhenDeleteGroupUser(userId, groupId) + shareService.DeleteShareNoteGroupWhenDeleteGroupUser(userId, groupId) + return db.Delete(db.GroupUsers, bson.M{"GroupId": bson.ObjectIdHex(groupId), "UserId": bson.ObjectIdHex(userId)}), "" } diff --git a/app/service/NoteContentHistoryService.go b/app/service/NoteContentHistoryService.go index 803feb6..c4175f3 100644 --- a/app/service/NoteContentHistoryService.go +++ b/app/service/NoteContentHistoryService.go @@ -1,11 +1,11 @@ package service import ( - "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/db" -// . "github.com/leanote/leanote/app/lea" + "github.com/leanote/leanote/app/info" + // . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" -// "time" + // "time" ) // 历史记录 @@ -22,7 +22,7 @@ func (this *NoteContentHistoryService) AddHistory(noteId, userId string, eachHis if eachHistory.Content == "" { return } - + // 先查是否存在历史记录, 没有则添加之 history := info.NoteContentHistory{} db.GetByIdAndUserId(db.NoteContentHistories, noteId, userId, &history) @@ -38,8 +38,8 @@ func (this *NoteContentHistoryService) AddHistory(noteId, userId string, eachHis } newHistory := []info.EachHistory{eachHistory} newHistory = append(newHistory, history.Histories...) // 在开头加了, 最近的在最前 - history.Histories = newHistory - + history.Histories = newHistory + // 更新之 db.UpdateByIdAndUserId(db.NoteContentHistories, noteId, userId, history) } @@ -48,13 +48,13 @@ func (this *NoteContentHistoryService) AddHistory(noteId, userId string, eachHis // 新建历史 func (this *NoteContentHistoryService) newHistory(noteId, userId string, eachHistory info.EachHistory) { - history := info.NoteContentHistory{NoteId: bson.ObjectIdHex(noteId), - UserId: bson.ObjectIdHex(userId), + history := info.NoteContentHistory{NoteId: bson.ObjectIdHex(noteId), + UserId: bson.ObjectIdHex(userId), Histories: []info.EachHistory{eachHistory}, } - + // 保存之 - db.Insert(db.NoteContentHistories, history) + db.Insert(db.NoteContentHistories, history) } // 列表展示 diff --git a/app/service/NoteImageService.go b/app/service/NoteImageService.go index cbf538b..4cb7317 100644 --- a/app/service/NoteImageService.go +++ b/app/service/NoteImageService.go @@ -1,22 +1,22 @@ package service import ( - "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/db" + "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" "regexp" -// "time" + // "time" ) type NoteImageService struct { } // 通过id, userId得到noteIds -func (this *NoteImageService) GetNoteIds(imageId string) ([]bson.ObjectId) { +func (this *NoteImageService) GetNoteIds(imageId string) []bson.ObjectId { noteImages := []info.NoteImage{} - db.ListByQWithFields(db.NoteImages, bson.M{"ImageId": bson.ObjectIdHex(imageId)}, []string{"NoteId"}, ¬eImages) - + db.ListByQWithFields(db.NoteImages, bson.M{"ImageId": bson.ObjectIdHex(imageId)}, []string{"NoteId"}, ¬eImages) + if noteImages != nil && len(noteImages) > 0 { noteIds := make([]bson.ObjectId, len(noteImages)) cnt := len(noteImages) @@ -25,7 +25,7 @@ func (this *NoteImageService) GetNoteIds(imageId string) ([]bson.ObjectId) { } return noteIds } - + return nil } @@ -67,7 +67,7 @@ func (this *NoteImageService) UpdateNoteImages(userId, noteId, imgSrc, content s } } } - + return true } @@ -101,7 +101,7 @@ func (this *NoteImageService) CopyNoteImages(fromNoteId, fromUserId, newNoteId, // each = getImage?fileId=541bd2f599c37b4f3r000003 fileId := each[len(each)-24:] // 得到后24位, 也即id - + if _, ok := replaceMap[fileId]; !ok { if bson.IsObjectIdHex(fileId) { ok2, newImageId := fileService.CopyImage(fromUserId, fileId, toUserId) @@ -123,25 +123,25 @@ func (this *NoteImageService) CopyNoteImages(fromNoteId, fromUserId, newNoteId, return "getImage?fileId=" + replaceFileId } return each - }); + }) - return content; + return content } -// +// func (this *NoteImageService) getImagesByNoteIds(noteIds []bson.ObjectId) map[string][]info.File { noteNoteImages := []info.NoteImage{} db.ListByQ(db.NoteImages, bson.M{"NoteId": bson.M{"$in": noteIds}}, ¬eNoteImages) - + // 得到imageId, 再去files表查所有的Files imageIds := []bson.ObjectId{} - + // 图片1 => N notes imageIdNotes := map[string][]string{} // imageId => [noteId1, noteId2, ...] for _, noteImage := range noteNoteImages { imageId := noteImage.ImageId imageIds = append(imageIds, imageId) - + imageIdHex := imageId.Hex() noteId := noteImage.NoteId.Hex() if notes, ok := imageIdNotes[imageIdHex]; ok { @@ -150,11 +150,11 @@ func (this *NoteImageService) getImagesByNoteIds(noteIds []bson.ObjectId) map[st imageIdNotes[imageIdHex] = []string{noteId} } } - + // 得到所有files files := []info.File{} db.ListByQ(db.Files, bson.M{"_id": bson.M{"$in": imageIds}}, &files) - + // 建立note->file关联 noteImages := make(map[string][]info.File) for _, file := range files { diff --git a/app/service/NoteService.go b/app/service/NoteService.go index e600923..fa3225e 100644 --- a/app/service/NoteService.go +++ b/app/service/NoteService.go @@ -1,8 +1,8 @@ package service import ( - "github.com/leanote/leanote/app/info" "github.com/leanote/leanote/app/db" + "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" "gopkg.in/mgo.v2/bson" "time" @@ -17,6 +17,7 @@ func (this *NoteService) GetNote(noteId, userId string) (note info.Note) { db.GetByIdAndUserId(db.Notes, noteId, userId, ¬e) return } + // fileService调用 // 不能是已经删除了的, life bug, 客户端删除后, 竟然还能在web上打开 func (this *NoteService) GetNoteById(noteId string) (note info.Note) { @@ -35,14 +36,16 @@ func (this *NoteService) GetNoteByIdAndUserId(noteId, userId string) (note info. db.GetByQ(db.Notes, bson.M{"_id": bson.ObjectIdHex(noteId), "UserId": bson.ObjectIdHex(userId), "IsDeleted": false}, ¬e) return } + // 得到blog, blogService用 // 不要传userId, 因为是公开的 func (this *NoteService) GetBlogNote(noteId string) (note info.Note) { note = info.Note{} - db.GetByQ(db.Notes, bson.M{"_id": bson.ObjectIdHex(noteId), + db.GetByQ(db.Notes, bson.M{"_id": bson.ObjectIdHex(noteId), "IsBlog": true, "IsTrash": false, "IsDeleted": false}, ¬e) return } + // 通过id, userId得到noteContent func (this *NoteService) GetNoteContent(noteContentId, userId string) (noteContent info.NoteContent) { noteContent = info.NoteContent{} @@ -62,11 +65,11 @@ func (this *NoteService) GetNoteAndContent(noteId, userId string) (noteAndConten func (this *NoteService) GetSyncNotes(userId string, afterUsn, maxEntry int) []info.ApiNote { notes := []info.Note{} q := db.Notes.Find(bson.M{ - "UserId": bson.ObjectIdHex(userId), - "Usn": bson.M{"$gt": afterUsn}, - }); + "UserId": bson.ObjectIdHex(userId), + "Usn": bson.M{"$gt": afterUsn}, + }) q.Sort("Usn").Limit(maxEntry).All(¬es) - + return this.ToApiNotes(notes) } @@ -75,7 +78,7 @@ func (this *NoteService) ToApiNotes(notes []info.Note) []info.ApiNote { // 2, 得到所有图片, 附件信息 // 查images表, attachs表 if len(notes) > 0 { - noteIds := make([]bson.ObjectId, len(notes)); + noteIds := make([]bson.ObjectId, len(notes)) for i, note := range notes { noteIds[i] = note.NoteId } @@ -92,24 +95,23 @@ func (this *NoteService) ToApiNotes(notes []info.Note) []info.ApiNote { return []info.ApiNote{} } - // note与apiNote的转换 func (this *NoteService) ToApiNote(note *info.Note, files []info.NoteFile) info.ApiNote { apiNote := info.ApiNote{ - NoteId: note.NoteId.Hex(), - NotebookId: note.NotebookId.Hex(), - UserId : note.UserId.Hex(), - Title : note.Title, - Tags : note.Tags, - IsMarkdown : note.IsMarkdown, - IsBlog : note.IsBlog, - IsTrash : note.IsTrash, - IsDeleted : note.IsDeleted, - Usn : note.Usn, - CreatedTime : note.CreatedTime, - UpdatedTime : note.UpdatedTime, - PublicTime : note.PublicTime, - Files: files, + NoteId: note.NoteId.Hex(), + NotebookId: note.NotebookId.Hex(), + UserId: note.UserId.Hex(), + Title: note.Title, + Tags: note.Tags, + IsMarkdown: note.IsMarkdown, + IsBlog: note.IsBlog, + IsTrash: note.IsTrash, + IsDeleted: note.IsDeleted, + Usn: note.Usn, + CreatedTime: note.CreatedTime, + UpdatedTime: note.UpdatedTime, + PublicTime: note.PublicTime, + Files: files, } return apiNote } @@ -121,11 +123,11 @@ func (this *NoteService) ToApiNote(note *info.Note, files []info.NoteFile) info. // 查images表, attachs表 // [待测] func (this *NoteService) getFiles(noteIds []bson.ObjectId) map[string][]info.NoteFile { - noteImages := noteImageService.getImagesByNoteIds(noteIds); + noteImages := noteImageService.getImagesByNoteIds(noteIds) noteAttachs := attachService.getAttachsByNoteIds(noteIds) - + noteFilesMap := map[string][]info.NoteFile{} - + for _, noteId := range noteIds { noteIdHex := noteId.Hex() noteFiles := []info.NoteFile{} @@ -134,36 +136,36 @@ func (this *NoteService) getFiles(noteIds []bson.ObjectId) map[string][]info.Not for _, image := range images { noteFiles = append(noteFiles, info.NoteFile{ FileId: image.FileId.Hex(), - Type: image.Type, - }); + Type: image.Type, + }) } } - + // attach if attachs, ok := noteAttachs[noteIdHex]; ok { for _, attach := range attachs { noteFiles = append(noteFiles, info.NoteFile{ - FileId: attach.AttachId.Hex(), - Type: attach.Type, - Title: attach.Title, + FileId: attach.AttachId.Hex(), + Type: attach.Type, + Title: attach.Title, IsAttach: true, - }); + }) } } - + noteFilesMap[noteIdHex] = noteFiles } - + return noteFilesMap } // 列出note, 排序规则, 还有分页 // CreatedTime, UpdatedTime, title 来排序 func (this *NoteService) ListNotes(userId, notebookId string, - isTrash bool, pageNumber, pageSize int, sortField string, isAsc bool, isBlog bool) (count int, notes []info.Note) { + isTrash bool, pageNumber, pageSize int, sortField string, isAsc bool, isBlog bool) (count int, notes []info.Note) { notes = []info.Note{} skipNum, sortFieldR := parsePageAndSort(pageNumber, pageSize, sortField, isAsc) - + // 不是trash的 query := bson.M{"UserId": bson.ObjectIdHex(userId), "IsTrash": isTrash, "IsDeleted": false} if isBlog { @@ -172,12 +174,12 @@ func (this *NoteService) ListNotes(userId, notebookId string, if notebookId != "" { query["NotebookId"] = bson.ObjectIdHex(notebookId) } - - q := db.Notes.Find(query); - + + q := db.Notes.Find(query) + // 总记录数 count, _ = q.Count() - + q.Sort(sortFieldR). Skip(skipNum). Limit(pageSize). @@ -187,11 +189,11 @@ func (this *NoteService) ListNotes(userId, notebookId string, // 通过noteIds来查询 // ShareService调用 -func (this *NoteService) ListNotesByNoteIdsWithPageSort(noteIds []bson.ObjectId, userId string, - pageNumber, pageSize int, sortField string, isAsc bool, isBlog bool) (notes []info.Note) { +func (this *NoteService) ListNotesByNoteIdsWithPageSort(noteIds []bson.ObjectId, userId string, + pageNumber, pageSize int, sortField string, isAsc bool, isBlog bool) (notes []info.Note) { skipNum, sortFieldR := parsePageAndSort(pageNumber, pageSize, sortField, isAsc) notes = []info.Note{} - + // 不是trash db.Notes. Find(bson.M{"_id": bson.M{"$in": noteIds}, "IsTrash": false}). @@ -201,24 +203,27 @@ func (this *NoteService) ListNotesByNoteIdsWithPageSort(noteIds []bson.ObjectId, All(¬es) return } + // shareService调用 func (this *NoteService) ListNotesByNoteIds(noteIds []bson.ObjectId) (notes []info.Note) { notes = []info.Note{} - + db.Notes. Find(bson.M{"_id": bson.M{"$in": noteIds}}). All(¬es) return } + // blog需要 func (this *NoteService) ListNoteContentsByNoteIds(noteIds []bson.ObjectId) (notes []info.NoteContent) { notes = []info.NoteContent{} - + db.NoteContents. Find(bson.M{"_id": bson.M{"$in": noteIds}}). All(¬es) return } + // 只得到abstract, 不需要content func (this *NoteService) ListNoteAbstractsByNoteIds(noteIds []bson.ObjectId) (notes []info.NoteContent) { notes = []info.NoteContent{} @@ -236,9 +241,9 @@ func (this *NoteService) ListNoteContentByNoteIds(noteIds []bson.ObjectId) (note // [ok] func (this *NoteService) AddNote(note info.Note, fromApi bool) info.Note { - if(note.NoteId.Hex() == "") { - noteId := bson.NewObjectId(); - note.NoteId = noteId; + if note.NoteId.Hex() == "" { + noteId := bson.NewObjectId() + note.NoteId = noteId } note.CreatedTime = time.Now() note.UpdatedTime = note.CreatedTime @@ -246,26 +251,26 @@ func (this *NoteService) AddNote(note info.Note, fromApi bool) info.Note { note.UpdatedUserId = note.UserId note.UrlTitle = GetUrTitle(note.UserId.Hex(), note.Title, "note") note.Usn = userService.IncrUsn(note.UserId.Hex()) - + notebookId := note.NotebookId.Hex() - + // api会传IsBlog, web不会传 if !fromApi { // 设为blog note.IsBlog = notebookService.IsBlog(notebookId) } -// if note.IsBlog { + // if note.IsBlog { note.PublicTime = note.UpdatedTime -// } - + // } + db.Insert(db.Notes, note) - + // tag1 tagService.AddTags(note.UserId.Hex(), note.Tags) - + // recount notebooks' notes number notebookService.ReCountNotebookNumberNotes(notebookId) - + return note } @@ -279,19 +284,18 @@ func (this *NoteService) AddSharedNote(note info.Note, myUserId bson.ObjectId) i return info.Note{} } - // 添加笔记本内容 // [ok] func (this *NoteService) AddNoteContent(noteContent info.NoteContent) info.NoteContent { noteContent.CreatedTime = time.Now() - noteContent.UpdatedTime = noteContent.CreatedTime + noteContent.UpdatedTime = noteContent.CreatedTime noteContent.UpdatedUserId = noteContent.UserId db.Insert(db.NoteContents, noteContent) - + // 更新笔记图片 noteImageService.UpdateNoteImages(noteContent.UserId.Hex(), noteContent.NoteId.Hex(), "", noteContent.Content) - - return noteContent; + + return noteContent } // API, abstract, desc需要这里获取 @@ -308,7 +312,7 @@ func (this *NoteService) AddNoteAndContentApi(note info.Note, noteContent info.N note.UpdatedUserId = note.UserId note.UrlTitle = GetUrTitle(note.UserId.Hex(), note.Title, "note") note.Usn = userService.IncrUsn(note.UserId.Hex()) - + // desc这里获取 desc := SubStringHTMLToRaw(noteContent.Content, 50) note.Desc = desc; @@ -316,24 +320,24 @@ func (this *NoteService) AddNoteAndContentApi(note info.Note, noteContent info.N // 设为blog notebookId := note.NotebookId.Hex() note.IsBlog = notebookService.IsBlog(notebookId) - + if note.IsBlog { note.PublicTime = note.UpdatedTime } - + db.Insert(db.Notes, note) - + // tag1, 不需要了 // tagService.AddTags(note.UserId.Hex(), note.Tags) - + // recount notebooks' notes number notebookService.ReCountNotebookNumberNotes(notebookId) - + // 这里, 添加到内容中 abstract := SubStringHTML(noteContent.Content, 200, "") noteContent.Abstract = abstract this.AddNoteContent(noteContent) - + return note }*/ @@ -348,15 +352,15 @@ func (this *NoteService) AddNoteAndContentForController(note info.Note, noteCont Log("HAS AUTH -----------") } } - return this.AddNoteAndContent(note, noteContent, bson.ObjectIdHex(updatedUserId)); + return this.AddNoteAndContent(note, noteContent, bson.ObjectIdHex(updatedUserId)) } func (this *NoteService) AddNoteAndContent(note info.Note, noteContent info.NoteContent, myUserId bson.ObjectId) info.Note { - if(note.NoteId.Hex() == "") { + if note.NoteId.Hex() == "" { noteId := bson.NewObjectId() note.NoteId = noteId } noteContent.NoteId = note.NoteId - if note.UserId != myUserId { + if note.UserId != myUserId { note = this.AddSharedNote(note, myUserId) } else { note = this.AddNote(note, false) @@ -368,12 +372,12 @@ func (this *NoteService) AddNoteAndContent(note info.Note, noteContent info.Note } func (this *NoteService) AddNoteAndContentApi(note info.Note, noteContent info.NoteContent, myUserId bson.ObjectId) info.Note { - if(note.NoteId.Hex() == "") { + if note.NoteId.Hex() == "" { noteId := bson.NewObjectId() note.NoteId = noteId } noteContent.NoteId = note.NoteId - if note.UserId != myUserId { + if note.UserId != myUserId { note = this.AddSharedNote(note, myUserId) } else { note = this.AddNote(note, true) @@ -392,7 +396,7 @@ func (this *NoteService) UpdateNote(updatedUserId, noteId string, needUpdate bso if note.NoteId == "" { return false, "notExists", 0 } - + userId := note.UserId.Hex() // updatedUserId 要修改userId的note, 此时需要判断是否有修改权限 if userId != updatedUserId { @@ -403,34 +407,34 @@ func (this *NoteService) UpdateNote(updatedUserId, noteId string, needUpdate bso Log("HAS AUTH -----------") } } - - if usn > 0 && note.Usn != usn { + + if usn > 0 && note.Usn != usn { return false, "conflict", 0 } - + // 是否已自定义 if note.IsBlog && note.HasSelfDefined { delete(needUpdate, "ImgSrc") delete(needUpdate, "Desc") } - - needUpdate["UpdatedUserId"] = bson.ObjectIdHex(updatedUserId); - needUpdate["UpdatedTime"] = time.Now(); - afterUsn := userService.IncrUsn(userId); + + needUpdate["UpdatedUserId"] = bson.ObjectIdHex(updatedUserId) + needUpdate["UpdatedTime"] = time.Now() + afterUsn := userService.IncrUsn(userId) needUpdate["Usn"] = afterUsn - + // 添加tag2 // TODO 这个tag去掉, 添加tag另外添加, 不要这个 if tags, ok := needUpdate["Tags"]; ok { tagService.AddTagsI(userId, tags) } - + // 是否修改了isBlog // 也要修改noteContents的IsBlog if isBlog, ok := needUpdate["IsBlog"]; ok { isBlog2 := isBlog.(bool) if note.IsBlog != isBlog2 { - this.UpdateNoteContentIsBlog(noteId, userId, isBlog2); + this.UpdateNoteContentIsBlog(noteId, userId, isBlog2) // 重新发布成博客 if !note.IsBlog { @@ -438,17 +442,17 @@ func (this *NoteService) UpdateNote(updatedUserId, noteId string, needUpdate bso } } } - + ok := db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, needUpdate) if !ok { return ok, "", 0 } - + // 重新获取之 note = this.GetNoteById(noteId) - + hasRecount := false - + // 如果修改了notebookId, 则更新notebookId'count // 两方的notebook也要修改 notebookIdI := needUpdate["NotebookId"] @@ -460,14 +464,14 @@ func (this *NoteService) UpdateNote(updatedUserId, noteId string, needUpdate bso notebookService.ReCountNotebookNumberNotes(notebookId.Hex()) } } - + // 不要多次更新, isTrash = false, = true都要重新统计 if !hasRecount { if _, ok := needUpdate["IsTrash"]; ok { notebookService.ReCountNotebookNumberNotes(note.NotebookId.Hex()) } } - + return true, "", afterUsn } @@ -479,7 +483,7 @@ func (this *NoteService) UpdateNoteContentIsBlog(noteId, userId string, isBlog b // 附件修改, 增加noteIncr func (this *NoteService) IncrNoteUsn(noteId, userId string) int { afterUsn := userService.IncrUsn(userId) - db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, + db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, bson.M{"UpdatedTime": time.Now(), "Usn": afterUsn}) return afterUsn } @@ -495,7 +499,7 @@ func (this *NoteService) UpdateNoteTitle(userId, updatedUserId, noteId, title st } } - return db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, + return db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, bson.M{"UpdatedUserId": bson.ObjectIdHex(updatedUserId), "Title": title, "UpdatedTime": time.Now(), "Usn": userService.IncrUsn(userId)}) } @@ -517,17 +521,17 @@ func (this *NoteService) UpdateNoteContent(updatedUserId, noteId, content, abstr return false, "noAuth", 0 } } - + // abstract重置 - data := bson.M{"UpdatedUserId": bson.ObjectIdHex(updatedUserId), - "Content": content, - "Abstract": abstract, + data := bson.M{"UpdatedUserId": bson.ObjectIdHex(updatedUserId), + "Content": content, + "Abstract": abstract, "UpdatedTime": time.Now()} - + if note.IsBlog && note.HasSelfDefined { delete(data, "Abstract") } - + // usn, 修改笔记不可能单独修改内容 afterUsn := 0 // 如果之前没有修改note其它信息, 那么usn++ @@ -542,14 +546,14 @@ func (this *NoteService) UpdateNoteContent(updatedUserId, noteId, content, abstr if db.UpdateByIdAndUserIdMap(db.NoteContents, noteId, userId, data) { // 这里, 添加历史记录 - noteContentHistoryService.AddHistory(noteId, userId, info.EachHistory{UpdatedUserId: bson.ObjectIdHex(updatedUserId), - Content: content, + noteContentHistoryService.AddHistory(noteId, userId, info.EachHistory{UpdatedUserId: bson.ObjectIdHex(updatedUserId), + Content: content, UpdatedTime: time.Now(), }) - + // 更新笔记图片 noteImageService.UpdateNoteImages(userId, noteId, note.ImgSrc, content) - + return true, "", afterUsn } return false, "", 0 @@ -585,12 +589,12 @@ func (this *NoteService) ToBlog(userId, noteId string, isBlog, isTop bool) bool noteUpdate["HasSelfDefined"] = false } noteUpdate["Usn"] = userService.IncrUsn(userId) - + ok := db.UpdateByIdAndUserIdMap(db.Notes, noteId, userId, noteUpdate) // 重新计算tags go (func() { - this.UpdateNoteContentIsBlog(noteId, userId, isBlog); - + this.UpdateNoteContentIsBlog(noteId, userId, isBlog) + blogService.ReCountBlogTags(userId) })() return ok @@ -604,17 +608,17 @@ func (this *NoteService) MoveNote(noteId, notebookId, userId string) info.Note { if notebookService.IsMyNotebook(notebookId, userId) { note := this.GetNote(noteId, userId) preNotebookId := note.NotebookId.Hex() - - re := db.UpdateByIdAndUserId(db.Notes, noteId, userId, - bson.M{"$set": bson.M{"IsTrash": false, + + re := db.UpdateByIdAndUserId(db.Notes, noteId, userId, + bson.M{"$set": bson.M{"IsTrash": false, "NotebookId": bson.ObjectIdHex(notebookId), - "Usn": userService.IncrUsn(userId), - }}) - + "Usn": userService.IncrUsn(userId), + }}) + if re { // 更新blog状态 this.updateToNotebookBlog(noteId, notebookId, userId) - + // recount notebooks' notes number notebookService.ReCountNotebookNumberNotes(notebookId) // 之前不是trash才统计, trash本不在统计中的 @@ -622,13 +626,13 @@ func (this *NoteService) MoveNote(noteId, notebookId, userId string) info.Note { notebookService.ReCountNotebookNumberNotes(preNotebookId) } } - - return this.GetNote(noteId, userId); + + return this.GetNote(noteId, userId) } return info.Note{} } -// 如果自己的blog状态是true, 不用改变, +// 如果自己的blog状态是true, 不用改变, // 否则, 如果notebookId的blog是true, 则改为true之 // 返回blog状态 // move, copy时用 @@ -637,16 +641,17 @@ func (this *NoteService) updateToNotebookBlog(noteId, notebookId, userId string) return true } if notebookService.IsBlog(notebookId) { - db.UpdateByIdAndUserId(db.Notes, noteId, userId, + db.UpdateByIdAndUserId(db.Notes, noteId, userId, bson.M{"$set": bson.M{"IsBlog": true, "PublicTime": time.Now()}}) // life return true } return false } + // 判断是否是blog func (this *NoteService) IsBlog(noteId string) bool { note := info.Note{} - db.GetByQWithFields(db.Notes, bson.M{"_id": bson.ObjectIdHex(noteId)}, []string{"IsBlog"}, ¬e); + db.GetByQWithFields(db.Notes, bson.M{"_id": bson.ObjectIdHex(noteId)}, []string{"IsBlog"}, ¬e) return note.IsBlog } @@ -658,25 +663,25 @@ func (this *NoteService) CopyNote(noteId, notebookId, userId string) info.Note { if notebookService.IsMyNotebook(notebookId, userId) { note := this.GetNote(noteId, userId) noteContent := this.GetNoteContent(noteId, userId) - + // 重新生成noteId - note.NoteId = bson.NewObjectId(); + note.NoteId = bson.NewObjectId() note.NotebookId = bson.ObjectIdHex(notebookId) - + noteContent.NoteId = note.NoteId - note = this.AddNoteAndContent(note, noteContent, note.UserId); + note = this.AddNoteAndContent(note, noteContent, note.UserId) // 更新blog状态 isBlog := this.updateToNotebookBlog(note.NoteId.Hex(), notebookId, userId) // recount notebookService.ReCountNotebookNumberNotes(notebookId) - + note.IsBlog = isBlog - + return note } - + return info.Note{} } @@ -693,37 +698,37 @@ func (this *NoteService) CopySharedNote(noteId, notebookId, fromUserId, myUserId noteContent := this.GetNoteContent(noteId, fromUserId) // 重新生成noteId - note.NoteId = bson.NewObjectId(); + note.NoteId = bson.NewObjectId() note.NotebookId = bson.ObjectIdHex(notebookId) note.UserId = bson.ObjectIdHex(myUserId) note.IsTop = false note.IsBlog = false // 别人的可能是blog - + note.ImgSrc = "" // 为什么清空, 因为图片需要复制, 先清空 - + // content noteContent.NoteId = note.NoteId noteContent.UserId = note.UserId - + // 复制图片, 把note的图片都copy给我, 且修改noteContent图片路径 noteContent.Content = noteImageService.CopyNoteImages(noteId, fromUserId, note.NoteId.Hex(), noteContent.Content, myUserId) - + // 复制附件 attachService.CopyAttachs(noteId, note.NoteId.Hex(), myUserId) - + // 添加之 - note = this.AddNoteAndContent(note, noteContent, note.UserId); - + note = this.AddNoteAndContent(note, noteContent, note.UserId) + // 更新blog状态 isBlog := this.updateToNotebookBlog(note.NoteId.Hex(), notebookId, myUserId) - + // recount notebookService.ReCountNotebookNumberNotes(notebookId) - + note.IsBlog = isBlog return note } - + return info.Note{} } @@ -743,31 +748,31 @@ func (this *NoteService) GetNotebookId(noteId string) bson.ObjectId { func (this *NoteService) SearchNote(key, userId string, pageNumber, pageSize int, sortField string, isAsc, isBlog bool) (count int, notes []info.Note) { notes = []info.Note{} skipNum, sortFieldR := parsePageAndSort(pageNumber, pageSize, sortField, isAsc) - + // 利用标题和desc, 不用content orQ := []bson.M{ bson.M{"Title": bson.M{"$regex": bson.RegEx{".*?" + key + ".*", "i"}}}, bson.M{"Desc": bson.M{"$regex": bson.RegEx{".*?" + key + ".*", "i"}}}, } // 不是trash的 - query := bson.M{"UserId": bson.ObjectIdHex(userId), - "IsTrash": false, + query := bson.M{"UserId": bson.ObjectIdHex(userId), + "IsTrash": false, "IsDeleted": false, // 不能搜索已删除了的 - "$or": orQ, + "$or": orQ, } if isBlog { query["IsBlog"] = true } - q := db.Notes.Find(query); - + q := db.Notes.Find(query) + // 总记录数 count, _ = q.Count() - + q.Sort(sortFieldR). Skip(skipNum). Limit(pageSize). All(¬es) - + // 如果 < pageSize 那么搜索content, 且id不在这些id之间的 if len(notes) < pageSize { notes = this.searchNoteFromContent(notes, userId, key, pageSize, sortFieldR, isBlog) @@ -794,19 +799,19 @@ func (this *NoteService) searchNoteFromContent(notes []info.Note, userId, key st Select(bson.M{"_id": true}). All(¬eContents) var lenContent = len(noteContents) - if(lenContent == 0) { + if lenContent == 0 { return notes } - + // 收集ids noteIds2 := make([]bson.ObjectId, lenContent) for i, content := range noteContents { noteIds2[i] = content.NoteId } - + // 得到notes notes2 := this.ListNotesByNoteIds(noteIds2) - + // 合并之 notes = append(notes, notes2...) return notes @@ -817,17 +822,17 @@ func (this *NoteService) searchNoteFromContent(notes []info.Note, userId, key st func (this *NoteService) SearchNoteByTags(tags []string, userId string, pageNumber, pageSize int, sortField string, isAsc bool) (count int, notes []info.Note) { notes = []info.Note{} skipNum, sortFieldR := parsePageAndSort(pageNumber, pageSize, sortField, isAsc) - + // 不是trash的 - query := bson.M{"UserId": bson.ObjectIdHex(userId), - "IsTrash": false, - "Tags": bson.M{"$all": tags}} - - q := db.Notes.Find(query); - + query := bson.M{"UserId": bson.ObjectIdHex(userId), + "IsTrash": false, + "Tags": bson.M{"$all": tags}} + + q := db.Notes.Find(query) + // 总记录数 count, _ = q.Count() - + q.Sort(sortFieldR). Skip(skipNum). Limit(pageSize). @@ -857,17 +862,17 @@ func (this *NoteService) CountNoteByTag(userId string, tag string) int { if tag == "" { return 0 } - query := bson.M{"UserId": bson.ObjectIdHex(userId), -// "IsTrash": false, + query := bson.M{"UserId": bson.ObjectIdHex(userId), + // "IsTrash": false, "IsDeleted": false, - "Tags": bson.M{"$in": []string{tag}}} + "Tags": bson.M{"$in": []string{tag}}} return db.Count(db.Notes, query) } // 删除tag // 返回所有note的Usn func (this *NoteService) UpdateNoteToDeleteTag(userId string, targetTag string) map[string]int { - query := bson.M{"UserId": bson.ObjectIdHex(userId), + query := bson.M{"UserId": bson.ObjectIdHex(userId), "Tags": bson.M{"$in": []string{targetTag}}} notes := []info.Note{} db.ListByQ(db.Notes, query, ¬es) @@ -881,7 +886,7 @@ func (this *NoteService) UpdateNoteToDeleteTag(userId string, targetTag string) if tag == targetTag { tags = tags tags = append(tags[:i], tags[i+1:]...) - break; + break } } usn := userService.IncrUsn(userId) diff --git a/app/service/NotebookService.go b/app/service/NotebookService.go index dad005d..a437004 100644 --- a/app/service/NotebookService.go +++ b/app/service/NotebookService.go @@ -1,15 +1,15 @@ package service import ( -// "fmt" - "gopkg.in/mgo.v2/bson" + // "fmt" "github.com/leanote/leanote/app/db" "github.com/leanote/leanote/app/info" . "github.com/leanote/leanote/app/lea" + "gopkg.in/mgo.v2/bson" "sort" - "time" "strings" -// "html" + "time" + // "html" ) // 笔记本 @@ -42,8 +42,8 @@ func ParseAndSortNotebooks(userNotebooks []info.Notebook, noParentDelete, needSo for _, each := range userNotebooks { newNotebooks := info.Notebooks{Subs: info.SubNotebooks{}} newNotebooks.NotebookId = each.NotebookId - newNotebooks.Title = each.Title; -// newNotebooks.Title = html.EscapeString(each.Title) + newNotebooks.Title = each.Title + // newNotebooks.Title = html.EscapeString(each.Title) newNotebooks.Title = strings.Replace(strings.Replace(each.Title, "