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

context.go 8.6 kB

11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
9 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
9 years ago
Add lang specific font stacks for CJK (#6007) * Add lang specific font stacks * Force font changes Signed-off-by: Andrew Thornton <art27@cantab.net> * Fix icons Signed-off-by: Andrew Thornton <art27@cantab.net> * Fix octicons and icons Signed-off-by: Andrew Thornton <art27@cantab.net> * Just override the semantic ui fonts only Signed-off-by: Andrew Thornton <art27@cantab.net> * Missed the headers... override them too * Missed some more semantic ui stuff * Fix PT Sans Signed-off-by: Andrew Thornton <art27@cantab.net> * More changes Signed-off-by: Andrew Thornton <art27@cantab.net> * Squashed commit of the following: commit 7d1679e9079541359869c9e677ba7412bfcc59f3 Author: Mike L <cl.jeremy@qq.com> Date: Wed Mar 13 13:53:49 2019 +0100 Remove missed YaHei leftover from _home.less commit 0079121ea91860a323ed4e5cc1a9c0d490d9cefd Author: Mike L <cl.jeremy@qq.com> Date: Wed Mar 13 12:03:54 2019 +0100 Fix overdone fixes (inherit, :lang) commit 62c919915928ec1db4731d547e95885f91a0618d Author: Mike L <cl.jeremy@qq.com> Date: Wed Mar 13 02:29:10 2019 +0100 Fix elements w/ explicit lang (language chooser) commit b3117587aa2eb8570d60bed583a11ee5565418be Author: Mike L <cl.jeremy@qq.com> Date: Tue Mar 12 20:17:26 2019 +0100 Fix textarea also (to match body) commit 81cedf2c3012c4dd05a7680782b4a98e1b947f67 Author: Mike L <cl.jeremy@qq.com> Date: Tue Mar 12 19:41:39 2019 +0100 Revert css temporarily to fix conflict commit 80ff82797f3203cbeaf866f22e961334e137df89 Author: Mike L <cl.jeremy@qq.com> Date: Tue Mar 12 19:15:30 2019 +0100 Tweak CJK, fix Yu Gothic, more monospace inherits commit 581dceb9a869646c2c486dabb925c88c2680d70c Author: Mike L <cl.jeremy@qq.com> Date: Mon Mar 11 13:09:26 2019 +0100 Add Lato for latin extd. & cyrillic, improve CJK * update stylesheet
6 years ago
11 years ago
11 years ago
11 years ago
11 years ago
11 years ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280
  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 context
  5. import (
  6. "html"
  7. "html/template"
  8. "io"
  9. "net/http"
  10. "net/url"
  11. "path"
  12. "strings"
  13. "time"
  14. "code.gitea.io/gitea/models"
  15. "code.gitea.io/gitea/modules/auth"
  16. "code.gitea.io/gitea/modules/base"
  17. "code.gitea.io/gitea/modules/log"
  18. "code.gitea.io/gitea/modules/setting"
  19. "code.gitea.io/gitea/modules/util"
  20. "github.com/Unknwon/com"
  21. "github.com/go-macaron/cache"
  22. "github.com/go-macaron/csrf"
  23. "github.com/go-macaron/i18n"
  24. "github.com/go-macaron/session"
  25. macaron "gopkg.in/macaron.v1"
  26. )
  27. // Context represents context of a request.
  28. type Context struct {
  29. *macaron.Context
  30. Cache cache.Cache
  31. csrf csrf.CSRF
  32. Flash *session.Flash
  33. Session session.Store
  34. Link string // current request URL
  35. EscapedLink string
  36. User *models.User
  37. IsSigned bool
  38. IsBasicAuth bool
  39. Repo *Repository
  40. Org *Organization
  41. }
  42. // HasAPIError returns true if error occurs in form validation.
  43. func (ctx *Context) HasAPIError() bool {
  44. hasErr, ok := ctx.Data["HasError"]
  45. if !ok {
  46. return false
  47. }
  48. return hasErr.(bool)
  49. }
  50. // GetErrMsg returns error message
  51. func (ctx *Context) GetErrMsg() string {
  52. return ctx.Data["ErrorMsg"].(string)
  53. }
  54. // HasError returns true if error occurs in form validation.
  55. func (ctx *Context) HasError() bool {
  56. hasErr, ok := ctx.Data["HasError"]
  57. if !ok {
  58. return false
  59. }
  60. ctx.Flash.ErrorMsg = ctx.Data["ErrorMsg"].(string)
  61. ctx.Data["Flash"] = ctx.Flash
  62. return hasErr.(bool)
  63. }
  64. // HasValue returns true if value of given name exists.
  65. func (ctx *Context) HasValue(name string) bool {
  66. _, ok := ctx.Data[name]
  67. return ok
  68. }
  69. // RedirectToFirst redirects to first not empty URL
  70. func (ctx *Context) RedirectToFirst(location ...string) {
  71. for _, loc := range location {
  72. if len(loc) == 0 {
  73. continue
  74. }
  75. u, err := url.Parse(loc)
  76. if err != nil || (u.Scheme != "" && !strings.HasPrefix(strings.ToLower(loc), strings.ToLower(setting.AppURL))) {
  77. continue
  78. }
  79. ctx.Redirect(loc)
  80. return
  81. }
  82. ctx.Redirect(setting.AppSubURL + "/")
  83. return
  84. }
  85. // HTML calls Context.HTML and converts template name to string.
  86. func (ctx *Context) HTML(status int, name base.TplName) {
  87. log.Debug("Template: %s", name)
  88. ctx.Context.HTML(status, string(name))
  89. }
  90. // RenderWithErr used for page has form validation but need to prompt error to users.
  91. func (ctx *Context) RenderWithErr(msg string, tpl base.TplName, form interface{}) {
  92. if form != nil {
  93. auth.AssignForm(form, ctx.Data)
  94. }
  95. ctx.Flash.ErrorMsg = msg
  96. ctx.Data["Flash"] = ctx.Flash
  97. ctx.HTML(200, tpl)
  98. }
  99. // NotFound displays a 404 (Not Found) page and prints the given error, if any.
  100. func (ctx *Context) NotFound(title string, err error) {
  101. if err != nil {
  102. log.Error(4, "%s: %v", title, err)
  103. if macaron.Env != macaron.PROD {
  104. ctx.Data["ErrorMsg"] = err
  105. }
  106. }
  107. ctx.Data["IsRepo"] = ctx.Repo.Repository != nil
  108. ctx.Data["Title"] = "Page Not Found"
  109. ctx.HTML(http.StatusNotFound, base.TplName("status/404"))
  110. }
  111. // ServerError displays a 500 (Internal Server Error) page and prints the given
  112. // error, if any.
  113. func (ctx *Context) ServerError(title string, err error) {
  114. if err != nil {
  115. log.Error(4, "%s: %v", title, err)
  116. if macaron.Env != macaron.PROD {
  117. ctx.Data["ErrorMsg"] = err
  118. }
  119. }
  120. ctx.Data["Title"] = "Internal Server Error"
  121. ctx.HTML(http.StatusInternalServerError, base.TplName("status/500"))
  122. }
  123. // NotFoundOrServerError use error check function to determine if the error
  124. // is about not found. It responses with 404 status code for not found error,
  125. // or error context description for logging purpose of 500 server error.
  126. func (ctx *Context) NotFoundOrServerError(title string, errck func(error) bool, err error) {
  127. if errck(err) {
  128. ctx.NotFound(title, err)
  129. return
  130. }
  131. ctx.ServerError(title, err)
  132. }
  133. // HandleText handles HTTP status code
  134. func (ctx *Context) HandleText(status int, title string) {
  135. if (status/100 == 4) || (status/100 == 5) {
  136. log.Error(4, "%s", title)
  137. }
  138. ctx.PlainText(status, []byte(title))
  139. }
  140. // ServeContent serves content to http request
  141. func (ctx *Context) ServeContent(name string, r io.ReadSeeker, params ...interface{}) {
  142. modtime := time.Now()
  143. for _, p := range params {
  144. switch v := p.(type) {
  145. case time.Time:
  146. modtime = v
  147. }
  148. }
  149. ctx.Resp.Header().Set("Content-Description", "File Transfer")
  150. ctx.Resp.Header().Set("Content-Type", "application/octet-stream")
  151. ctx.Resp.Header().Set("Content-Disposition", "attachment; filename="+name)
  152. ctx.Resp.Header().Set("Content-Transfer-Encoding", "binary")
  153. ctx.Resp.Header().Set("Expires", "0")
  154. ctx.Resp.Header().Set("Cache-Control", "must-revalidate")
  155. ctx.Resp.Header().Set("Pragma", "public")
  156. http.ServeContent(ctx.Resp, ctx.Req.Request, name, modtime, r)
  157. }
  158. // Contexter initializes a classic context for a request.
  159. func Contexter() macaron.Handler {
  160. return func(c *macaron.Context, l i18n.Locale, cache cache.Cache, sess session.Store, f *session.Flash, x csrf.CSRF) {
  161. ctx := &Context{
  162. Context: c,
  163. Cache: cache,
  164. csrf: x,
  165. Flash: f,
  166. Session: sess,
  167. Link: setting.AppSubURL + strings.TrimSuffix(c.Req.URL.EscapedPath(), "/"),
  168. Repo: &Repository{
  169. PullRequest: &PullRequest{},
  170. },
  171. Org: &Organization{},
  172. }
  173. ctx.Data["Language"] = ctx.Locale.Language()
  174. c.Data["Link"] = ctx.Link
  175. ctx.Data["PageStartTime"] = time.Now()
  176. // Quick responses appropriate go-get meta with status 200
  177. // regardless of if user have access to the repository,
  178. // or the repository does not exist at all.
  179. // This is particular a workaround for "go get" command which does not respect
  180. // .netrc file.
  181. if ctx.Query("go-get") == "1" {
  182. ownerName := c.Params(":username")
  183. repoName := c.Params(":reponame")
  184. branchName := "master"
  185. repo, err := models.GetRepositoryByOwnerAndName(ownerName, repoName)
  186. if err == nil && len(repo.DefaultBranch) > 0 {
  187. branchName = repo.DefaultBranch
  188. }
  189. prefix := setting.AppURL + path.Join(url.PathEscape(ownerName), url.PathEscape(repoName), "src", "branch", util.PathEscapeSegments(branchName))
  190. c.Header().Set("Content-Type", "text/html")
  191. c.WriteHeader(http.StatusOK)
  192. c.Write([]byte(com.Expand(`<!doctype html>
  193. <html>
  194. <head>
  195. <meta name="go-import" content="{GoGetImport} git {CloneLink}">
  196. <meta name="go-source" content="{GoGetImport} _ {GoDocDirectory} {GoDocFile}">
  197. </head>
  198. <body>
  199. go get {GoGetImport}
  200. </body>
  201. </html>
  202. `, map[string]string{
  203. "GoGetImport": ComposeGoGetImport(ownerName, strings.TrimSuffix(repoName, ".git")),
  204. "CloneLink": models.ComposeHTTPSCloneURL(ownerName, repoName),
  205. "GoDocDirectory": prefix + "{/dir}",
  206. "GoDocFile": prefix + "{/dir}/{file}#L{line}",
  207. })))
  208. return
  209. }
  210. // Get user from session if logged in.
  211. ctx.User, ctx.IsBasicAuth = auth.SignedInUser(ctx.Context, ctx.Session)
  212. if ctx.User != nil {
  213. ctx.IsSigned = true
  214. ctx.Data["IsSigned"] = ctx.IsSigned
  215. ctx.Data["SignedUser"] = ctx.User
  216. ctx.Data["SignedUserID"] = ctx.User.ID
  217. ctx.Data["SignedUserName"] = ctx.User.Name
  218. ctx.Data["IsAdmin"] = ctx.User.IsAdmin
  219. } else {
  220. ctx.Data["SignedUserID"] = int64(0)
  221. ctx.Data["SignedUserName"] = ""
  222. }
  223. // If request sends files, parse them here otherwise the Query() can't be parsed and the CsrfToken will be invalid.
  224. if ctx.Req.Method == "POST" && strings.Contains(ctx.Req.Header.Get("Content-Type"), "multipart/form-data") {
  225. if err := ctx.Req.ParseMultipartForm(setting.AttachmentMaxSize << 20); err != nil && !strings.Contains(err.Error(), "EOF") { // 32MB max size
  226. ctx.ServerError("ParseMultipartForm", err)
  227. return
  228. }
  229. }
  230. ctx.Resp.Header().Set(`X-Frame-Options`, `SAMEORIGIN`)
  231. ctx.Data["CsrfToken"] = html.EscapeString(x.GetToken())
  232. ctx.Data["CsrfTokenHtml"] = template.HTML(`<input type="hidden" name="_csrf" value="` + ctx.Data["CsrfToken"].(string) + `">`)
  233. log.Debug("Session ID: %s", sess.ID())
  234. log.Debug("CSRF Token: %v", ctx.Data["CsrfToken"])
  235. ctx.Data["IsLandingPageHome"] = setting.LandingPageURL == setting.LandingPageHome
  236. ctx.Data["IsLandingPageExplore"] = setting.LandingPageURL == setting.LandingPageExplore
  237. ctx.Data["IsLandingPageOrganizations"] = setting.LandingPageURL == setting.LandingPageOrganizations
  238. ctx.Data["ShowRegistrationButton"] = setting.Service.ShowRegistrationButton
  239. ctx.Data["ShowFooterBranding"] = setting.ShowFooterBranding
  240. ctx.Data["ShowFooterVersion"] = setting.ShowFooterVersion
  241. ctx.Data["EnableSwagger"] = setting.API.EnableSwagger
  242. ctx.Data["EnableOpenIDSignIn"] = setting.Service.EnableOpenIDSignIn
  243. c.Map(ctx)
  244. }
  245. }