npc.go 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. package main
  2. import (
  3. "ehang.io/nps/client"
  4. "ehang.io/nps/lib/common"
  5. "ehang.io/nps/lib/daemon"
  6. "ehang.io/nps/lib/version"
  7. "fmt"
  8. "fyne.io/fyne"
  9. "fyne.io/fyne/app"
  10. "fyne.io/fyne/layout"
  11. "fyne.io/fyne/widget"
  12. "github.com/astaxie/beego/logs"
  13. "io/ioutil"
  14. "os"
  15. "path"
  16. "runtime"
  17. "strings"
  18. "time"
  19. )
  20. func main() {
  21. daemon.InitDaemon("npc", common.GetRunPath(), common.GetTmpPath())
  22. logs.SetLogger("store")
  23. application := app.New()
  24. window := application.NewWindow("Npc " + version.VERSION)
  25. window.SetContent(WidgetScreen())
  26. window.Resize(fyne.NewSize(910, 350))
  27. window.ShowAndRun()
  28. }
  29. var (
  30. start bool
  31. status = "Start!"
  32. connType = "tcp"
  33. cl = new(client.TRPClient)
  34. refreshCh = make(chan struct{})
  35. )
  36. func WidgetScreen() fyne.CanvasObject {
  37. return fyne.NewContainerWithLayout(layout.NewBorderLayout(nil, nil, nil, nil),
  38. makeMainTab(),
  39. )
  40. }
  41. func makeMainTab() fyne.Widget {
  42. serverPort := widget.NewEntry()
  43. serverPort.SetPlaceHolder("Server:Port")
  44. vKey := widget.NewEntry()
  45. vKey.SetPlaceHolder("Vkey")
  46. radio := widget.NewRadio([]string{"tcp", "kcp"}, func(s string) { connType = s })
  47. radio.Horizontal = true
  48. button := widget.NewButton(status, func() {
  49. onclick(serverPort.Text, vKey.Text, connType)
  50. })
  51. go func() {
  52. for {
  53. <-refreshCh
  54. button.SetText(status)
  55. }
  56. }()
  57. lo := widget.NewMultiLineEntry()
  58. lo.Disable()
  59. lo.Resize(fyne.NewSize(910, 250))
  60. slo := widget.NewScrollContainer(lo)
  61. slo.Resize(fyne.NewSize(910, 250))
  62. go func() {
  63. for {
  64. time.Sleep(time.Second)
  65. lo.SetText(common.GetLogMsg())
  66. slo.Resize(fyne.NewSize(910, 250))
  67. }
  68. }()
  69. sp, vk, ct := loadConfig()
  70. if sp != "" && vk != "" && ct != "" {
  71. serverPort.SetText(sp)
  72. vKey.SetText(vk)
  73. connType = ct
  74. radio.SetSelected(ct)
  75. onclick(sp, vk, ct)
  76. }
  77. return widget.NewVBox(
  78. widget.NewLabel("Npc "+version.VERSION),
  79. serverPort,
  80. vKey,
  81. radio,
  82. button,
  83. slo,
  84. )
  85. }
  86. func onclick(s, v, c string) {
  87. start = !start
  88. if start {
  89. status = "Stop!"
  90. // init the npc
  91. fmt.Println("submit", s, v, c)
  92. sp, vk, ct := loadConfig()
  93. if sp != s || vk != v || ct != c {
  94. saveConfig(s, v, c)
  95. }
  96. cl = client.NewRPClient(s, v, c, "", nil, 60)
  97. go cl.Start()
  98. } else {
  99. // close the npc
  100. status = "Start!"
  101. if cl != nil {
  102. go cl.Close()
  103. cl = nil
  104. }
  105. }
  106. refreshCh <- struct{}{}
  107. }
  108. func getDir() (dir string, err error) {
  109. if runtime.GOOS != "android" {
  110. dir, err = os.UserConfigDir()
  111. if err != nil {
  112. return
  113. }
  114. } else {
  115. dir = "/data/data/org.nps.client/files"
  116. }
  117. return
  118. }
  119. func saveConfig(host, vkey, connType string) {
  120. data := strings.Join([]string{host, vkey, connType}, "\n")
  121. ph, err := getDir()
  122. if err != nil {
  123. logs.Warn("not found config dir")
  124. return
  125. }
  126. _ = os.Remove(path.Join(ph, "npc.conf"))
  127. f, err := os.OpenFile(path.Join(ph, "npc.conf"), os.O_CREATE|os.O_WRONLY, 0644)
  128. defer f.Close()
  129. if err != nil {
  130. logs.Error(err)
  131. return
  132. }
  133. if _, err := f.Write([]byte(data)); err != nil {
  134. f.Close() // ignore error; Write error takes precedence
  135. logs.Error(err)
  136. return
  137. }
  138. }
  139. func loadConfig() (host, vkey, connType string) {
  140. ph, err := getDir()
  141. if err != nil {
  142. logs.Warn("not found config dir")
  143. return
  144. }
  145. f, err := os.OpenFile(path.Join(ph, "npc.conf"), os.O_RDONLY, 0644)
  146. defer f.Close()
  147. if err != nil {
  148. logs.Error(err)
  149. return
  150. }
  151. data, err := ioutil.ReadAll(f)
  152. if err != nil {
  153. logs.Error(err)
  154. return
  155. }
  156. li := strings.Split(string(data), "\n")
  157. host = li[0]
  158. vkey = li[1]
  159. connType = li[2]
  160. return
  161. }