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.

template.go 5.5 kB

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
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
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
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267
  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 base
  5. import (
  6. "container/list"
  7. "encoding/json"
  8. "fmt"
  9. "html/template"
  10. "runtime"
  11. "strings"
  12. "time"
  13. "golang.org/x/net/html/charset"
  14. "golang.org/x/text/transform"
  15. "github.com/gogits/chardet"
  16. "github.com/gogits/gogs/modules/setting"
  17. )
  18. func Str2html(raw string) template.HTML {
  19. return template.HTML(Sanitizer.Sanitize(raw))
  20. }
  21. func Range(l int) []int {
  22. return make([]int, l)
  23. }
  24. func List(l *list.List) chan interface{} {
  25. e := l.Front()
  26. c := make(chan interface{})
  27. go func() {
  28. for e != nil {
  29. c <- e.Value
  30. e = e.Next()
  31. }
  32. close(c)
  33. }()
  34. return c
  35. }
  36. func ShortSha(sha1 string) string {
  37. if len(sha1) == 40 {
  38. return sha1[:10]
  39. }
  40. return sha1
  41. }
  42. func DetectEncoding(content []byte) (string, error) {
  43. detector := chardet.NewTextDetector()
  44. result, err := detector.DetectBest(content)
  45. return result.Charset, err
  46. }
  47. func ToUtf8WithErr(content []byte) (error, string) {
  48. charsetLabel, err := DetectEncoding(content)
  49. if err != nil {
  50. return err, ""
  51. }
  52. if charsetLabel == "utf8" {
  53. return nil, string(content)
  54. }
  55. encoding, _ := charset.Lookup(charsetLabel)
  56. if encoding == nil {
  57. return fmt.Errorf("unknow char decoder %s", charsetLabel), string(content)
  58. }
  59. result, n, err := transform.String(encoding.NewDecoder(), string(content))
  60. // If there is an error, we concatenate the nicely decoded part and the
  61. // original left over. This way we won't loose data.
  62. if err != nil {
  63. result = result + string(content[n:])
  64. }
  65. return err, result
  66. }
  67. func ToUtf8(content string) string {
  68. _, res := ToUtf8WithErr([]byte(content))
  69. return res
  70. }
  71. // RenderCommitMessage renders commit message with XSS-safe and special links.
  72. func RenderCommitMessage(msg, urlPrefix string) template.HTML {
  73. return template.HTML(string(RenderIssueIndexPattern([]byte(template.HTMLEscapeString(msg)), urlPrefix)))
  74. }
  75. var mailDomains = map[string]string{
  76. "gmail.com": "gmail.com",
  77. }
  78. var TemplateFuncs template.FuncMap = map[string]interface{}{
  79. "GoVer": func() string {
  80. return strings.Title(runtime.Version())
  81. },
  82. "AppName": func() string {
  83. return setting.AppName
  84. },
  85. "AppSubUrl": func() string {
  86. return setting.AppSubUrl
  87. },
  88. "AppVer": func() string {
  89. return setting.AppVer
  90. },
  91. "AppDomain": func() string {
  92. return setting.Domain
  93. },
  94. "CdnMode": func() bool {
  95. return setting.ProdMode && !setting.OfflineMode
  96. },
  97. "LoadTimes": func(startTime time.Time) string {
  98. return fmt.Sprint(time.Since(startTime).Nanoseconds()/1e6) + "ms"
  99. },
  100. "AvatarLink": AvatarLink,
  101. "Str2html": Str2html,
  102. "TimeSince": TimeSince,
  103. "FileSize": FileSize,
  104. "Subtract": Subtract,
  105. "Add": func(a, b int) int {
  106. return a + b
  107. },
  108. "ActionIcon": ActionIcon,
  109. "DateFormat": DateFormat,
  110. "List": List,
  111. "Mail2Domain": func(mail string) string {
  112. if !strings.Contains(mail, "@") {
  113. return "try.gogs.io"
  114. }
  115. suffix := strings.SplitN(mail, "@", 2)[1]
  116. domain, ok := mailDomains[suffix]
  117. if !ok {
  118. return "mail." + suffix
  119. }
  120. return domain
  121. },
  122. "SubStr": func(str string, start, length int) string {
  123. if len(str) == 0 {
  124. return ""
  125. }
  126. end := start + length
  127. if length == -1 {
  128. end = len(str)
  129. }
  130. if len(str) < end {
  131. return str
  132. }
  133. return str[start:end]
  134. },
  135. "DiffTypeToStr": DiffTypeToStr,
  136. "DiffLineTypeToStr": DiffLineTypeToStr,
  137. "ShortSha": ShortSha,
  138. "Md5": EncodeMd5,
  139. "ActionContent2Commits": ActionContent2Commits,
  140. "Oauth2Icon": Oauth2Icon,
  141. "Oauth2Name": Oauth2Name,
  142. "ToUtf8": ToUtf8,
  143. "EscapePound": func(str string) string {
  144. return strings.Replace(str, "#", "%23", -1)
  145. },
  146. "RenderCommitMessage": RenderCommitMessage,
  147. }
  148. type Actioner interface {
  149. GetOpType() int
  150. GetActUserName() string
  151. GetActEmail() string
  152. GetRepoUserName() string
  153. GetRepoName() string
  154. GetBranch() string
  155. GetContent() string
  156. }
  157. // ActionIcon accepts a int that represents action operation type
  158. // and returns a icon class name.
  159. func ActionIcon(opType int) string {
  160. switch opType {
  161. case 1, 8: // Create, transfer repository.
  162. return "repo"
  163. case 5, 9: // Commit repository.
  164. return "git-commit"
  165. case 6: // Create issue.
  166. return "issue-opened"
  167. case 10: // Comment issue.
  168. return "comment"
  169. default:
  170. return "invalid type"
  171. }
  172. }
  173. type PushCommit struct {
  174. Sha1 string
  175. Message string
  176. AuthorEmail string
  177. AuthorName string
  178. }
  179. type PushCommits struct {
  180. Len int
  181. Commits []*PushCommit
  182. CompareUrl string
  183. }
  184. func ActionContent2Commits(act Actioner) *PushCommits {
  185. var push *PushCommits
  186. if err := json.Unmarshal([]byte(act.GetContent()), &push); err != nil {
  187. return nil
  188. }
  189. return push
  190. }
  191. func DiffTypeToStr(diffType int) string {
  192. diffTypes := map[int]string{
  193. 1: "add", 2: "modify", 3: "del",
  194. }
  195. return diffTypes[diffType]
  196. }
  197. func DiffLineTypeToStr(diffType int) string {
  198. switch diffType {
  199. case 2:
  200. return "add"
  201. case 3:
  202. return "del"
  203. case 4:
  204. return "tag"
  205. }
  206. return "same"
  207. }
  208. func Oauth2Icon(t int) string {
  209. switch t {
  210. case 1:
  211. return "fa-github-square"
  212. case 2:
  213. return "fa-google-plus-square"
  214. case 3:
  215. return "fa-twitter-square"
  216. case 4:
  217. return "fa-qq"
  218. case 5:
  219. return "fa-weibo"
  220. }
  221. return ""
  222. }
  223. func Oauth2Name(t int) string {
  224. switch t {
  225. case 1:
  226. return "GitHub"
  227. case 2:
  228. return "Google+"
  229. case 3:
  230. return "Twitter"
  231. case 4:
  232. return "腾讯 QQ"
  233. case 5:
  234. return "Weibo"
  235. }
  236. return ""
  237. }