module_blog.go 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338
  1. package modules
  2. import (
  3. "database/sql"
  4. "html"
  5. "strings"
  6. "golang-fave/assets"
  7. "golang-fave/consts"
  8. "golang-fave/engine/builder"
  9. "golang-fave/engine/wrapper"
  10. "golang-fave/utils"
  11. )
  12. func (this *Modules) blog_GetCategorySelectOptions(wrap *wrapper.Wrapper, id int) string {
  13. result := ``
  14. rows, err := wrap.DB.Query(
  15. `SELECT
  16. node.id,
  17. node.user,
  18. node.name,
  19. node.alias,
  20. (COUNT(parent.id) - 1) AS depth
  21. FROM
  22. blog_cats AS node,
  23. blog_cats AS parent
  24. WHERE
  25. node.lft BETWEEN parent.lft AND parent.rgt
  26. GROUP BY
  27. node.id
  28. ORDER BY
  29. node.lft ASC
  30. ;`,
  31. )
  32. if err == nil {
  33. values := make([]string, 5)
  34. scan := make([]interface{}, len(values))
  35. for i := range values {
  36. scan[i] = &values[i]
  37. }
  38. idStr := utils.IntToStr(id)
  39. for rows.Next() {
  40. err = rows.Scan(scan...)
  41. if err == nil {
  42. selected := ""
  43. if string(values[0]) == idStr {
  44. selected = " selected"
  45. }
  46. sub := strings.Repeat("— ", utils.StrToInt(string(values[4])))
  47. result += `<option value="` + html.EscapeString(string(values[0])) + `"` + selected + `>` + sub + html.EscapeString(string(values[2])) + `</option>`
  48. }
  49. }
  50. }
  51. return result
  52. }
  53. func (this *Modules) blog_GetCategoryParentId(wrap *wrapper.Wrapper, id int) int {
  54. var result int
  55. _ = wrap.DB.QueryRow(`
  56. SELECT
  57. parent.id
  58. FROM
  59. blog_cats AS node,
  60. blog_cats AS parent
  61. WHERE
  62. node.lft BETWEEN parent.lft AND parent.rgt AND
  63. node.id = ? AND
  64. parent.id <> ?
  65. ORDER BY
  66. parent.lft DESC
  67. LIMIT 1;`,
  68. id,
  69. id,
  70. ).Scan(
  71. &result,
  72. )
  73. return result
  74. }
  75. func (this *Modules) RegisterModule_Blog() *Module {
  76. return this.newModule(MInfo{
  77. WantDB: true,
  78. Mount: "blog",
  79. Name: "Blog",
  80. Order: 1,
  81. System: false,
  82. Icon: assets.SysSvgIconList,
  83. Sub: &[]MISub{
  84. {Mount: "default", Name: "List of posts", Show: true, Icon: assets.SysSvgIconList},
  85. {Mount: "add", Name: "Add new post", Show: true, Icon: assets.SysSvgIconPlus},
  86. {Mount: "modify", Name: "Modify post", Show: false},
  87. {Sep: true, Show: true},
  88. {Mount: "categories", Name: "List of categories", Show: true, Icon: assets.SysSvgIconList},
  89. {Mount: "categories-add", Name: "Add new category", Show: true, Icon: assets.SysSvgIconPlus},
  90. {Mount: "categories-modify", Name: "Modify category", Show: false},
  91. },
  92. }, nil, func(wrap *wrapper.Wrapper) (string, string, string) {
  93. content := ""
  94. sidebar := ""
  95. if wrap.CurrSubModule == "" || wrap.CurrSubModule == "default" {
  96. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  97. {Name: "List of posts"},
  98. })
  99. //
  100. } else if wrap.CurrSubModule == "categories" {
  101. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  102. {Name: "Categories", Link: "/cp/" + wrap.CurrModule + "/" + wrap.CurrSubModule + "/"},
  103. {Name: "List of categories"},
  104. })
  105. content += builder.DataTable(
  106. wrap,
  107. "blog_cats",
  108. "id",
  109. "ASC",
  110. &[]builder.DataTableRow{
  111. {
  112. DBField: "id",
  113. // NameInTable: "id",
  114. },
  115. {
  116. DBField: "user",
  117. // NameInTable: "user",
  118. },
  119. {
  120. DBField: "name",
  121. NameInTable: "Category",
  122. CallBack: func(values *[]string) string {
  123. sub := strings.Repeat("&mdash; ", utils.StrToInt((*values)[4]))
  124. name := `<a href="/cp/` + wrap.CurrModule + `/categories-modify/` + (*values)[0] + `/">` + sub + html.EscapeString((*values)[2]) + `</a>`
  125. // alias := html.EscapeString((*values)[3])
  126. // return `<div>` + name + `</div><div><small>` + alias + `</small></div>`
  127. return `<div>` + name + `</div>`
  128. },
  129. },
  130. {
  131. DBField: "alias",
  132. // NameInTable: "Alias",
  133. },
  134. {
  135. DBField: "depth",
  136. // NameInTable: "depth",
  137. },
  138. },
  139. func(values *[]string) string {
  140. return builder.DataTableAction(&[]builder.DataTableActionRow{
  141. {
  142. Icon: assets.SysSvgIconEdit,
  143. Href: "/cp/" + wrap.CurrModule + "/categories-modify/" + (*values)[0] + "/",
  144. Hint: "Edit",
  145. },
  146. {
  147. Icon: assets.SysSvgIconRemove,
  148. Href: "javascript:fave.ActionDataTableDelete(this,'blog-categories-delete','" +
  149. (*values)[0] + "','Are you sure want to delete category?');",
  150. Hint: "Delete",
  151. Classes: "delete",
  152. },
  153. })
  154. },
  155. "/cp/"+wrap.CurrModule+"/"+wrap.CurrSubModule+"/",
  156. func() (int, error) {
  157. var num int
  158. var err error
  159. err = wrap.DB.QueryRow("SELECT COUNT(*) FROM `blog_cats`;").Scan(&num)
  160. return num, err
  161. },
  162. func(limit_offset int, pear_page int) (*sql.Rows, error) {
  163. return wrap.DB.Query(
  164. `SELECT
  165. node.id,
  166. node.user,
  167. node.name,
  168. node.alias,
  169. (COUNT(parent.id) - 1) AS depth
  170. FROM
  171. blog_cats AS node,
  172. blog_cats AS parent
  173. WHERE
  174. node.lft BETWEEN parent.lft AND parent.rgt
  175. GROUP BY
  176. node.id
  177. ORDER BY
  178. node.lft ASC
  179. LIMIT ?, ?;`,
  180. limit_offset,
  181. pear_page,
  182. )
  183. },
  184. )
  185. } else if wrap.CurrSubModule == "add" || wrap.CurrSubModule == "modify" {
  186. if wrap.CurrSubModule == "add" {
  187. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  188. {Name: "Add new post"},
  189. })
  190. } else {
  191. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  192. {Name: "Modify post"},
  193. })
  194. }
  195. //
  196. } else if wrap.CurrSubModule == "categories-add" || wrap.CurrSubModule == "categories-modify" {
  197. if wrap.CurrSubModule == "categories-add" {
  198. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  199. {Name: "Categories", Link: "/cp/" + wrap.CurrModule + "/categories/"},
  200. {Name: "Add new category"},
  201. })
  202. } else {
  203. content += this.getBreadCrumbs(wrap, &[]consts.BreadCrumb{
  204. {Name: "Categories", Link: "/cp/" + wrap.CurrModule + "/categories/"},
  205. {Name: "Modify category"},
  206. })
  207. }
  208. data := utils.MySql_blog_category{
  209. A_id: 0,
  210. A_user: 0,
  211. A_name: "",
  212. A_alias: "",
  213. A_lft: 0,
  214. A_rgt: 0,
  215. }
  216. if wrap.CurrSubModule == "categories-modify" {
  217. if len(wrap.UrlArgs) != 3 {
  218. return "", "", ""
  219. }
  220. if !utils.IsNumeric(wrap.UrlArgs[2]) {
  221. return "", "", ""
  222. }
  223. err := wrap.DB.QueryRow(`
  224. SELECT
  225. id,
  226. user,
  227. name,
  228. alias,
  229. lft,
  230. rgt
  231. FROM
  232. blog_cats
  233. WHERE
  234. id = ?
  235. LIMIT 1;`,
  236. utils.StrToInt(wrap.UrlArgs[2]),
  237. ).Scan(
  238. &data.A_id,
  239. &data.A_user,
  240. &data.A_name,
  241. &data.A_alias,
  242. &data.A_lft,
  243. &data.A_rgt,
  244. )
  245. if err != nil {
  246. return "", "", ""
  247. }
  248. }
  249. // ---
  250. btn_caption := "Add"
  251. if wrap.CurrSubModule == "categories-modify" {
  252. btn_caption = "Save"
  253. }
  254. // ---
  255. // select_parent_options := this.blog_GetCategorySelectOptions(wrap, "")
  256. // ---
  257. parentId := 0
  258. if wrap.CurrSubModule == "categories-modify" {
  259. parentId = this.blog_GetCategoryParentId(wrap, data.A_id)
  260. }
  261. content += builder.DataForm(wrap, []builder.DataFormField{
  262. {
  263. Kind: builder.DFKHidden,
  264. Name: "action",
  265. Value: "blog-categories-modify",
  266. },
  267. {
  268. Kind: builder.DFKHidden,
  269. Name: "id",
  270. Value: utils.IntToStr(data.A_id),
  271. },
  272. {
  273. Kind: builder.DFKText,
  274. Caption: "Name",
  275. Name: "name",
  276. Value: data.A_name,
  277. },
  278. {
  279. Kind: builder.DFKText,
  280. Caption: "Alias",
  281. Name: "alias",
  282. Value: data.A_alias,
  283. Hint: "Example: popular-posts",
  284. },
  285. {
  286. Kind: builder.DFKText,
  287. Caption: "Parent",
  288. Name: "parent",
  289. Value: "0",
  290. CallBack: func(field *builder.DataFormField) string {
  291. return `<div class="form-group last">
  292. <div class="row">
  293. <div class="col-md-3">
  294. <label for="lbl_parent">Parent</label>
  295. </div>
  296. <div class="col-md-9">
  297. <div>
  298. <select class="form-control" id="lbl_parent" name="parent">
  299. <option value="0">&mdash;</option>
  300. ` + this.blog_GetCategorySelectOptions(wrap, parentId) + `
  301. </select>
  302. </div>
  303. </div>
  304. </div>
  305. </div>`
  306. },
  307. },
  308. {
  309. Kind: builder.DFKMessage,
  310. },
  311. {
  312. Kind: builder.DFKSubmit,
  313. Value: btn_caption,
  314. Target: "add-edit-button",
  315. },
  316. })
  317. if wrap.CurrSubModule == "categories-add" {
  318. sidebar += `<button class="btn btn-primary btn-sidebar" id="add-edit-button">Add</button>`
  319. } else {
  320. sidebar += `<button class="btn btn-primary btn-sidebar" id="add-edit-button">Save</button>`
  321. }
  322. // ---
  323. }
  324. return this.getSidebarModules(wrap), content, sidebar
  325. })
  326. }