You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

339 lines
8.4 KiB

10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
  1. // Copyright 2014 The Gogs Authors. All rights reserved.
  2. // Use of this source code is governed by a MIT-style
  3. // license that can be found in the LICENSE file.
  4. package user
  5. import (
  6. "fmt"
  7. "net/url"
  8. "strings"
  9. "github.com/codegangsta/martini"
  10. "github.com/gogits/gogs/models"
  11. "github.com/gogits/gogs/modules/auth"
  12. "github.com/gogits/gogs/modules/base"
  13. "github.com/gogits/gogs/modules/log"
  14. "github.com/gogits/gogs/modules/mailer"
  15. "github.com/gogits/gogs/modules/middleware"
  16. )
  17. func Dashboard(ctx *middleware.Context) {
  18. ctx.Data["Title"] = "Dashboard"
  19. ctx.Data["PageIsUserDashboard"] = true
  20. repos, err := models.GetRepositories(&models.User{Id: ctx.User.Id})
  21. if err != nil {
  22. ctx.Handle(200, "user.Dashboard", err)
  23. return
  24. }
  25. ctx.Data["MyRepos"] = repos
  26. feeds, err := models.GetFeeds(ctx.User.Id, 0, false)
  27. if err != nil {
  28. ctx.Handle(200, "user.Dashboard", err)
  29. return
  30. }
  31. ctx.Data["Feeds"] = feeds
  32. ctx.HTML(200, "user/dashboard")
  33. }
  34. func Profile(ctx *middleware.Context, params martini.Params) {
  35. ctx.Data["Title"] = "Profile"
  36. // TODO: Need to check view self or others.
  37. user, err := models.GetUserByName(params["username"])
  38. if err != nil {
  39. ctx.Handle(200, "user.Profile", err)
  40. return
  41. }
  42. ctx.Data["Owner"] = user
  43. tab := ctx.Query("tab")
  44. ctx.Data["TabName"] = tab
  45. switch tab {
  46. case "activity":
  47. feeds, err := models.GetFeeds(user.Id, 0, true)
  48. if err != nil {
  49. ctx.Handle(200, "user.Profile", err)
  50. return
  51. }
  52. ctx.Data["Feeds"] = feeds
  53. default:
  54. repos, err := models.GetRepositories(user)
  55. if err != nil {
  56. ctx.Handle(200, "user.Profile", err)
  57. return
  58. }
  59. ctx.Data["Repos"] = repos
  60. }
  61. ctx.Data["PageIsUserProfile"] = true
  62. ctx.HTML(200, "user/profile")
  63. }
  64. func SignIn(ctx *middleware.Context, form auth.LogInForm) {
  65. ctx.Data["Title"] = "Log In"
  66. if ctx.Req.Method == "GET" {
  67. // Check auto-login.
  68. userName := ctx.GetCookie(base.CookieUserName)
  69. if len(userName) == 0 {
  70. ctx.HTML(200, "user/signin")
  71. return
  72. }
  73. isSucceed := false
  74. defer func() {
  75. if !isSucceed {
  76. log.Trace("%s auto-login cookie cleared: %s", ctx.Req.RequestURI, userName)
  77. ctx.SetCookie(base.CookieUserName, "", -1)
  78. ctx.SetCookie(base.CookieRememberName, "", -1)
  79. }
  80. }()
  81. user, err := models.GetUserByName(userName)
  82. if err != nil {
  83. ctx.HTML(200, "user/signin")
  84. return
  85. }
  86. secret := base.EncodeMd5(user.Rands + user.Passwd)
  87. value, _ := ctx.GetSecureCookie(secret, base.CookieRememberName)
  88. if value != user.Name {
  89. ctx.HTML(200, "user/signin")
  90. return
  91. }
  92. isSucceed = true
  93. ctx.Session.Set("userId", user.Id)
  94. ctx.Session.Set("userName", user.Name)
  95. redirectTo, _ := url.QueryUnescape(ctx.GetCookie("redirect_to"))
  96. if len(redirectTo) > 0 {
  97. ctx.SetCookie("redirect_to", "", -1)
  98. ctx.Redirect(redirectTo)
  99. } else {
  100. ctx.Redirect("/")
  101. }
  102. return
  103. }
  104. if hasErr, ok := ctx.Data["HasError"]; ok && hasErr.(bool) {
  105. ctx.HTML(200, "user/signin")
  106. return
  107. }
  108. user, err := models.LoginUserPlain(form.UserName, form.Password)
  109. if err != nil {
  110. if err == models.ErrUserNotExist {
  111. log.Trace("%s Log in failed: %s/%s", ctx.Req.RequestURI, form.UserName, form.Password)
  112. ctx.RenderWithErr("Username or password is not correct", "user/signin", &form)
  113. return
  114. }
  115. ctx.Handle(200, "user.SignIn", err)
  116. return
  117. }
  118. if form.Remember == "on" {
  119. secret := base.EncodeMd5(user.Rands + user.Passwd)
  120. days := 86400 * base.LogInRememberDays
  121. ctx.SetCookie(base.CookieUserName, user.Name, days)
  122. ctx.SetSecureCookie(secret, base.CookieRememberName, user.Name, days)
  123. }
  124. ctx.Session.Set("userId", user.Id)
  125. ctx.Session.Set("userName", user.Name)
  126. redirectTo, _ := url.QueryUnescape(ctx.GetCookie("redirect_to"))
  127. if len(redirectTo) > 0 {
  128. ctx.SetCookie("redirect_to", "", -1)
  129. ctx.Redirect(redirectTo)
  130. } else {
  131. ctx.Redirect("/")
  132. }
  133. }
  134. func SignOut(ctx *middleware.Context) {
  135. ctx.Session.Delete("userId")
  136. ctx.Session.Delete("userName")
  137. ctx.SetCookie(base.CookieUserName, "", -1)
  138. ctx.SetCookie(base.CookieRememberName, "", -1)
  139. ctx.Redirect("/")
  140. }
  141. func SignUp(ctx *middleware.Context, form auth.RegisterForm) {
  142. ctx.Data["Title"] = "Sign Up"
  143. ctx.Data["PageIsSignUp"] = true
  144. if base.Service.DisenableRegisteration {
  145. ctx.Data["DisenableRegisteration"] = true
  146. ctx.HTML(200, "user/signup")
  147. return
  148. }
  149. if ctx.Req.Method == "GET" {
  150. ctx.HTML(200, "user/signup")
  151. return
  152. }
  153. if form.Password != form.RetypePasswd {
  154. ctx.Data["HasError"] = true
  155. ctx.Data["Err_Password"] = true
  156. ctx.Data["Err_RetypePasswd"] = true
  157. ctx.Data["ErrorMsg"] = "Password and re-type password are not same"
  158. auth.AssignForm(form, ctx.Data)
  159. }
  160. if ctx.HasError() {
  161. ctx.HTML(200, "user/signup")
  162. return
  163. }
  164. u := &models.User{
  165. Name: form.UserName,
  166. Email: form.Email,
  167. Passwd: form.Password,
  168. IsActive: !base.Service.RegisterEmailConfirm,
  169. }
  170. var err error
  171. if u, err = models.RegisterUser(u); err != nil {
  172. switch err {
  173. case models.ErrUserAlreadyExist:
  174. ctx.RenderWithErr("Username has been already taken", "user/signup", &form)
  175. case models.ErrEmailAlreadyUsed:
  176. ctx.RenderWithErr("E-mail address has been already used", "user/signup", &form)
  177. case models.ErrUserNameIllegal:
  178. ctx.RenderWithErr(models.ErrRepoNameIllegal.Error(), "user/signup", &form)
  179. default:
  180. ctx.Handle(200, "user.SignUp", err)
  181. }
  182. return
  183. }
  184. log.Trace("%s User created: %s", ctx.Req.RequestURI, strings.ToLower(form.UserName))
  185. // Send confirmation e-mail.
  186. if base.Service.RegisterEmailConfirm && u.Id > 1 {
  187. mailer.SendRegisterMail(ctx.Render, u)
  188. ctx.Data["IsSendRegisterMail"] = true
  189. ctx.Data["Email"] = u.Email
  190. ctx.Data["Hours"] = base.Service.ActiveCodeLives / 60
  191. ctx.HTML(200, "user/active")
  192. if err = ctx.Cache.Put("MailResendLimit_"+u.LowerName, u.LowerName, 180); err != nil {
  193. log.Error("Set cache(MailResendLimit) fail: %v", err)
  194. }
  195. return
  196. }
  197. ctx.Redirect("/user/login")
  198. }
  199. func Delete(ctx *middleware.Context) {
  200. ctx.Data["Title"] = "Delete Account"
  201. ctx.Data["PageIsUserSetting"] = true
  202. ctx.Data["IsUserPageSettingDelete"] = true
  203. if ctx.Req.Method == "GET" {
  204. ctx.HTML(200, "user/delete")
  205. return
  206. }
  207. tmpUser := models.User{Passwd: ctx.Query("password")}
  208. tmpUser.EncodePasswd()
  209. if len(tmpUser.Passwd) == 0 || tmpUser.Passwd != ctx.User.Passwd {
  210. ctx.Data["HasError"] = true
  211. ctx.Data["ErrorMsg"] = "Password is not correct. Make sure you are owner of this account."
  212. } else {
  213. if err := models.DeleteUser(ctx.User); err != nil {
  214. ctx.Data["HasError"] = true
  215. switch err {
  216. case models.ErrUserOwnRepos:
  217. ctx.Data["ErrorMsg"] = "Your account still have ownership of repository, you have to delete or transfer them first."
  218. default:
  219. ctx.Handle(200, "user.Delete", err)
  220. return
  221. }
  222. } else {
  223. ctx.Redirect("/")
  224. return
  225. }
  226. }
  227. ctx.HTML(200, "user/delete")
  228. }
  229. const (
  230. TPL_FEED = `<i class="icon fa fa-%s"></i>
  231. <div class="info"><span class="meta">%s</span><br>%s</div>`
  232. )
  233. func Feeds(ctx *middleware.Context, form auth.FeedsForm) {
  234. actions, err := models.GetFeeds(form.UserId, form.Page*20, false)
  235. if err != nil {
  236. ctx.JSON(500, err)
  237. }
  238. feeds := make([]string, len(actions))
  239. for i := range actions {
  240. feeds[i] = fmt.Sprintf(TPL_FEED, base.ActionIcon(actions[i].OpType),
  241. base.TimeSince(actions[i].Created), base.ActionDesc(actions[i], ctx.User.AvatarLink()))
  242. }
  243. ctx.JSON(200, &feeds)
  244. }
  245. func Issues(ctx *middleware.Context) {
  246. ctx.Data["Title"] = "Your Issues"
  247. ctx.HTML(200, "issue/user")
  248. }
  249. func Pulls(ctx *middleware.Context) {
  250. ctx.HTML(200, "user/pulls")
  251. }
  252. func Stars(ctx *middleware.Context) {
  253. ctx.HTML(200, "user/stars")
  254. }
  255. func Activate(ctx *middleware.Context) {
  256. code := ctx.Query("code")
  257. if len(code) == 0 {
  258. ctx.Data["IsActivatePage"] = true
  259. if ctx.User.IsActive {
  260. ctx.Handle(404, "user.Activate", nil)
  261. return
  262. }
  263. // Resend confirmation e-mail.
  264. if base.Service.RegisterEmailConfirm {
  265. if ctx.Cache.IsExist("MailResendLimit_" + ctx.User.LowerName) {
  266. ctx.Data["ResendLimited"] = true
  267. } else {
  268. ctx.Data["Hours"] = base.Service.ActiveCodeLives / 60
  269. mailer.SendActiveMail(ctx.Render, ctx.User)
  270. }
  271. } else {
  272. ctx.Data["ServiceNotEnabled"] = true
  273. }
  274. ctx.HTML(200, "user/active")
  275. return
  276. }
  277. // Verify code.
  278. if user := models.VerifyUserActiveCode(code); user != nil {
  279. user.IsActive = true
  280. user.Rands = models.GetUserSalt()
  281. models.UpdateUser(user)
  282. log.Trace("%s User activated: %s", ctx.Req.RequestURI, user.LowerName)
  283. ctx.Session.Set("userId", user.Id)
  284. ctx.Session.Set("userName", user.Name)
  285. ctx.Redirect("/")
  286. return
  287. }
  288. ctx.Data["IsActivateFailed"] = true
  289. ctx.HTML(200, "user/active")
  290. }