tablib_tabular.go 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172
  1. package tablib
  2. import (
  3. "github.com/bndr/gotabulate"
  4. "regexp"
  5. "strings"
  6. "unicode/utf8"
  7. )
  8. var (
  9. // TabularGrid is the value to be passed to gotabulate to render the table
  10. // as ASCII table with grid format
  11. TabularGrid = "grid"
  12. // TabularSimple is the value to be passed to gotabulate to render the table
  13. // as ASCII table with simple format
  14. TabularSimple = "simple"
  15. // TabularCondensed is the value to be passed to gotabulate to render the table
  16. // as ASCII table with condensed format
  17. TabularCondensed = "condensed"
  18. // TabularMarkdown is the value to be passed to gotabulate to render the table
  19. // as ASCII table with Markdown format
  20. TabularMarkdown = "markdown"
  21. )
  22. // Markdown returns a Markdown table Exportable representation of the Dataset.
  23. func (d *Dataset) Markdown() *Exportable {
  24. return d.Tabular(TabularMarkdown)
  25. }
  26. // Tabular returns a tabular Exportable representation of the Dataset.
  27. // format is either grid, simple, condensed or markdown.
  28. func (d *Dataset) Tabular(format string) *Exportable {
  29. back := d.Records()
  30. t := gotabulate.Create(back)
  31. if format == TabularCondensed || format == TabularMarkdown {
  32. rendered := regexp.MustCompile("\n\n\\s").ReplaceAllString(t.Render("simple"), "\n ")
  33. if format == TabularMarkdown {
  34. firstLine := regexp.MustCompile("-\\s+-").ReplaceAllString(strings.Split(rendered, "\n")[0], "- | -")
  35. // now just locate the position of pipe characterds, and set them
  36. positions := make([]int, 0, d.cols-1)
  37. x := 0
  38. for _, c := range firstLine {
  39. if c == '|' {
  40. positions = append(positions, x)
  41. }
  42. x += utf8.RuneLen(c)
  43. }
  44. b := newBuffer()
  45. lines := strings.Split(rendered, "\n")
  46. for _, line := range lines[1 : len(lines)-2] {
  47. ipos := 0
  48. b.WriteString("| ")
  49. for _, pos := range positions {
  50. if ipos < len(line) && pos < len(line) {
  51. b.WriteString(line[ipos:pos])
  52. b.WriteString(" | ")
  53. ipos = pos + 1
  54. }
  55. }
  56. if ipos < len(line) {
  57. b.WriteString(line[ipos:])
  58. }
  59. b.WriteString(" | \n")
  60. }
  61. return newExportable(b)
  62. }
  63. return newExportableFromString(rendered)
  64. }
  65. return newExportableFromString(t.Render(format))
  66. }