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.

232 lines
5.3 KiB

5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
  1. package govue
  2. //go-bindata-assetfs --pkg=govue govue-runtime/...
  3. import (
  4. "fmt"
  5. "git.ouxuan.net/3136352472/go-service-template/jsruntime"
  6. "git.ouxuan.net/3136352472/go-service-template/pool"
  7. "github.com/elazarl/go-bindata-assetfs"
  8. "io/ioutil"
  9. "log"
  10. "net/http"
  11. "os"
  12. "path/filepath"
  13. "strings"
  14. "time"
  15. )
  16. type GoVue struct {
  17. StaticPath string
  18. UseJsPath string
  19. ErrorPage404 string
  20. Resources *assetfs.AssetFS
  21. jsRuntimePool *pool.JsRuntimePool
  22. }
  23. func NewGoVueDefaultConfig(debug bool) (gv *GoVue, err error) {
  24. gv = &GoVue{
  25. Resources: assetFS(),
  26. }
  27. err = gv.initRender(debug)
  28. return
  29. }
  30. func NewGoVue(useJsPath string, staticPath string, debug bool) (gv *GoVue, err error) {
  31. gv = &GoVue{
  32. StaticPath: staticPath,
  33. UseJsPath: useJsPath,
  34. Resources: assetFS(),
  35. }
  36. err = gv.initRender(debug)
  37. return
  38. }
  39. func (gv *GoVue) SetErrorPage404(page string) {
  40. gv.ErrorPage404 = page
  41. }
  42. func SetPoolConfig(config pool.Config) {
  43. pool.DefaultConfig = config
  44. }
  45. func (gv *GoVue) initRender(debug bool) (err error) {
  46. if gv.StaticPath == "" {
  47. gv.StaticPath = filepath.Join(getSelfFilePath(), "static")
  48. }
  49. if gv.UseJsPath == "" {
  50. gv.UseJsPath = filepath.Join(gv.StaticPath, "use.js")
  51. }
  52. //vuessr, err := ioutil.ReadFile(filepath.Join("govue", "govue-runtime", "vuessr.js"))
  53. //if err != nil {
  54. // return
  55. //}
  56. //polyfill, err := ioutil.ReadFile(filepath.Join("govue", "govue-runtime", "polyfill.js"))
  57. //if err != nil {
  58. // return
  59. //}
  60. //
  61. //mainScript, err := ioutil.ReadFile(filepath.Join("govue", "govue-runtime", "runtime.js"))
  62. //if err != nil {
  63. // return
  64. //}
  65. //
  66. //headerScript, err := ioutil.ReadFile(filepath.Join("govue", "govue-runtime", "header.js"))
  67. //if err != nil {
  68. // return
  69. //}
  70. //
  71. //govueScript, err := ioutil.ReadFile(filepath.Join("govue", "govue-js-src", "dist", "index.js"))
  72. //if err != nil {
  73. // return
  74. //}
  75. vuessr, err := gv.Resources.Asset(filepath.Join("govue-runtime", "vuessr.js"))
  76. if err != nil {
  77. return
  78. }
  79. polyfill, err := gv.Resources.Asset(filepath.Join("govue-runtime", "polyfill.js"))
  80. if err != nil {
  81. return
  82. }
  83. mainScript, err := gv.Resources.Asset(filepath.Join("govue-runtime", "runtime.js"))
  84. if err != nil {
  85. return
  86. }
  87. govueScript, err := gv.Resources.Asset(filepath.Join("govue-runtime", "govue.js"))
  88. if err != nil {
  89. return
  90. }
  91. headerScript, err := gv.Resources.Asset(filepath.Join("govue-runtime", "header.js"))
  92. if err != nil {
  93. return
  94. }
  95. gv.jsRuntimePool = pool.NewJsRuntimePool(string(mainScript), gv.UseJsPath, gv.StaticPath, jsruntime.Relys{
  96. jsruntime.Rely{
  97. Src: string(polyfill),
  98. },
  99. jsruntime.Rely{
  100. Src: string(headerScript),
  101. },
  102. jsruntime.Rely{
  103. Src: string(vuessr),
  104. },
  105. jsruntime.Rely{
  106. Src: string(govueScript),
  107. },
  108. }, jsruntime.ModeSync, debug)
  109. return
  110. }
  111. func (gv *GoVue) PoolLog() {
  112. gv.jsRuntimePool.Log()
  113. }
  114. func (gv *GoVue) StartPoolLog() {
  115. go func() {
  116. defer func() {
  117. recover()
  118. log.Println("统计协程异常")
  119. }()
  120. lastidle := 0
  121. lastactive := 0
  122. for {
  123. all, idle, active := gv.jsRuntimePool.NumInfo()
  124. if idle != lastidle || active != lastactive {
  125. fmt.Println("渲染协程数量变动变动:所有:", all, "空闲:", idle, "活动:", active)
  126. }
  127. lastidle = idle
  128. lastactive = active
  129. time.Sleep(time.Second)
  130. }
  131. }()
  132. }
  133. func (gv *GoVue) LoadStaticResources(request *http.Request, goExtDataS ...interface{}) (result []byte, err error) {
  134. var staticDir string
  135. var filePath = request.URL.Path
  136. if gv.StaticPath == "" {
  137. staticDir = filepath.Join(getSelfFilePath(), "static")
  138. } else {
  139. staticDir = gv.StaticPath
  140. }
  141. filePath = filepath.Join(staticDir, filePath)
  142. fi, err := os.Stat(filePath)
  143. if err == nil {
  144. if fi.IsDir() {
  145. defaultPath := []string{"index.vue", "index.html"}
  146. for e := range defaultPath {
  147. path := filepath.Join(filePath, defaultPath[e])
  148. _, err := os.Stat(path)
  149. if err == nil {
  150. filePath = path
  151. break
  152. }
  153. }
  154. }
  155. } else {
  156. if filepath.Ext(filePath) == ".html" {
  157. split := strings.Split(filePath, ".")
  158. split[len(split)-1] = "vue"
  159. vuePath := strings.Join(split, ".")
  160. _, err := os.Stat(vuePath)
  161. if err == nil {
  162. filePath = vuePath
  163. }
  164. }
  165. }
  166. result, err = ioutil.ReadFile(filePath)
  167. if err != nil {
  168. return gv.renderErrPage(404, request, goExtDataS...)
  169. }
  170. if filepath.Ext(filePath) != ".html" && filepath.Ext(filePath) != ".vue" {
  171. return
  172. }
  173. var goExtData interface{}
  174. if len(goExtDataS) > 0 {
  175. goExtData = goExtDataS[0]
  176. }
  177. err = gv.jsRuntimePool.JsRuntimeCall(func(jr *jsruntime.JsRuntime) {
  178. if filepath.Ext(filePath) == ".vue" {
  179. jr.SetVariable("IS_VUE_SSR", true)
  180. } else {
  181. jr.SetVariable("IS_VUE_SSR", false)
  182. }
  183. err = jr.Render(filePath, fmt.Sprintf("http://%s%s", request.Host, request.RequestURI), string(result), goExtData, func(data string) {
  184. result = []byte(data)
  185. })
  186. })
  187. return
  188. }
  189. func (gv *GoVue) renderErrPage(errCode int, request *http.Request, goExtDataS ...interface{}) (result []byte, err error) {
  190. filePath := gv.ErrorPage404
  191. if filePath == "" {
  192. return []byte("页面不存在"), err
  193. }
  194. result, _ = ioutil.ReadFile(filePath)
  195. var goExtData interface{}
  196. if len(goExtDataS) > 0 {
  197. goExtData = goExtDataS[0]
  198. }
  199. err = gv.jsRuntimePool.JsRuntimeCall(func(jr *jsruntime.JsRuntime) {
  200. err = jr.Render(filePath, fmt.Sprintf("http://%s%s", request.Host, request.RequestURI), string(result), goExtData, func(data string) {
  201. result = []byte(data)
  202. })
  203. })
  204. return
  205. }