1. package chroma
    
  2. 
    
  3. import (
    
  4. 	"bytes"
    
  5. 	"compress/gzip"
    
  6. 	"encoding/xml"
    
  7. 	"fmt"
    
  8. 	"regexp"
    
  9. 	"testing"
    
  10. 
    
  11. 	assert "github.com/alecthomas/assert/v2"
    
  12. )
    
  13. 
    
  14. func TestEmitterSerialisationRoundTrip(t *testing.T) {
    
  15. 	tests := []struct {
    
  16. 		name    string
    
  17. 		emitter Emitter
    
  18. 	}{
    
  19. 		{"ByGroups", ByGroups(Name, Using("Go"))},
    
  20. 		{"UsingSelf", UsingSelf("root")},
    
  21. 		{"Using", Using("Go")},
    
  22. 		{"UsingByGroup", UsingByGroup(1, 2, Name)},
    
  23. 		{"TokenType", Name},
    
  24. 	}
    
  25. 	for _, test := range tests {
    
  26. 		// nolint: scopelint
    
  27. 		t.Run(test.name, func(t *testing.T) {
    
  28. 			data, err := xml.Marshal(test.emitter)
    
  29. 			assert.NoError(t, err)
    
  30. 			t.Logf("%s", data)
    
  31. 			value, target := newFromTemplate(test.emitter)
    
  32. 			err = xml.Unmarshal(data, target)
    
  33. 			assert.NoError(t, err)
    
  34. 			assert.Equal(t, test.emitter, value().(Emitter))
    
  35. 		})
    
  36. 	}
    
  37. }
    
  38. 
    
  39. func TestMutatorSerialisationRoundTrip(t *testing.T) {
    
  40. 	tests := []struct {
    
  41. 		name    string
    
  42. 		mutator Mutator
    
  43. 	}{
    
  44. 		{"Include", Include("string").Mutator},
    
  45. 		{"Combined", Combined("a", "b", "c")},
    
  46. 		{"Multi", Mutators(Include("string").Mutator, Push("quote"))},
    
  47. 		{"Push", Push("include")},
    
  48. 		{"Pop", Pop(1)},
    
  49. 	}
    
  50. 	for _, test := range tests {
    
  51. 		// nolint: scopelint
    
  52. 		t.Run(test.name, func(t *testing.T) {
    
  53. 			data, err := xml.Marshal(test.mutator)
    
  54. 			assert.NoError(t, err)
    
  55. 			t.Logf("%s", data)
    
  56. 			value, target := newFromTemplate(test.mutator)
    
  57. 			err = xml.Unmarshal(data, target)
    
  58. 			assert.NoError(t, err)
    
  59. 			assert.Equal(t, test.mutator, value().(Mutator))
    
  60. 		})
    
  61. 	}
    
  62. }
    
  63. 
    
  64. func TestMarshal(t *testing.T) {
    
  65. 	actual := MustNewLexer(&Config{
    
  66. 		Name:      "PkgConfig",
    
  67. 		Aliases:   []string{"pkgconfig"},
    
  68. 		Filenames: []string{"*.pc"},
    
  69. 	}, func() Rules {
    
  70. 		return Rules{
    
  71. 			"root": {
    
  72. 				{`#.*$`, CommentSingle, nil},
    
  73. 				{`^(\w+)(=)`, ByGroups(NameAttribute, Operator), nil},
    
  74. 				{`^([\w.]+)(:)`, ByGroups(NameTag, Punctuation), Push("spvalue")},
    
  75. 				Include("interp"),
    
  76. 				{`[^${}#=:\n.]+`, Text, nil},
    
  77. 				{`.`, Text, nil},
    
  78. 			},
    
  79. 			"interp": {
    
  80. 				{`\$\$`, Text, nil},
    
  81. 				{`\$\{`, LiteralStringInterpol, Push("curly")},
    
  82. 			},
    
  83. 			"curly": {
    
  84. 				{`\}`, LiteralStringInterpol, Pop(1)},
    
  85. 				{`\w+`, NameAttribute, nil},
    
  86. 			},
    
  87. 			"spvalue": {
    
  88. 				Include("interp"),
    
  89. 				{`#.*$`, CommentSingle, Pop(1)},
    
  90. 				{`\n`, Text, Pop(1)},
    
  91. 				{`[^${}#\n]+`, Text, nil},
    
  92. 				{`.`, Text, nil},
    
  93. 			},
    
  94. 		}
    
  95. 	})
    
  96. 	data, err := Marshal(actual)
    
  97. 	assert.NoError(t, err)
    
  98. 	expected, err := Unmarshal(data)
    
  99. 	assert.NoError(t, err)
    
  100. 	assert.Equal(t, expected.Config(), actual.Config())
    
  101. 	assert.Equal(t, mustRules(t, expected), mustRules(t, actual))
    
  102. }
    
  103. 
    
  104. func mustRules(t testing.TB, r *RegexLexer) Rules {
    
  105. 	t.Helper()
    
  106. 	rules, err := r.Rules()
    
  107. 	assert.NoError(t, err)
    
  108. 	return rules
    
  109. }
    
  110. 
    
  111. func TestRuleSerialisation(t *testing.T) {
    
  112. 	tests := []Rule{
    
  113. 		Include("String"),
    
  114. 		{`\d+`, Text, nil},
    
  115. 		{`"`, String, Push("String")},
    
  116. 	}
    
  117. 	for _, test := range tests {
    
  118. 		data, err := xml.Marshal(test)
    
  119. 		assert.NoError(t, err)
    
  120. 		t.Log(string(data))
    
  121. 		actual := Rule{}
    
  122. 		err = xml.Unmarshal(data, &actual)
    
  123. 		assert.NoError(t, err)
    
  124. 		assert.Equal(t, test, actual)
    
  125. 	}
    
  126. }
    
  127. 
    
  128. func TestRulesSerialisation(t *testing.T) {
    
  129. 	expected := Rules{
    
  130. 		"root": {
    
  131. 			{`#.*$`, CommentSingle, nil},
    
  132. 			{`^(\w+)(=)`, ByGroups(NameAttribute, Operator), nil},
    
  133. 			{`^([\w.]+)(:)`, ByGroups(NameTag, Punctuation), Push("spvalue")},
    
  134. 			Include("interp"),
    
  135. 			{`[^${}#=:\n.]+`, Text, nil},
    
  136. 			{`.`, Text, nil},
    
  137. 		},
    
  138. 		"interp": {
    
  139. 			{`\$\$`, Text, nil},
    
  140. 			{`\$\{`, LiteralStringInterpol, Push("curly")},
    
  141. 		},
    
  142. 		"curly": {
    
  143. 			{`\}`, LiteralStringInterpol, Pop(1)},
    
  144. 			{`\w+`, NameAttribute, nil},
    
  145. 		},
    
  146. 		"spvalue": {
    
  147. 			Include("interp"),
    
  148. 			{`#.*$`, CommentSingle, Pop(1)},
    
  149. 			{`\n`, Text, Pop(1)},
    
  150. 			{`[^${}#\n]+`, Text, nil},
    
  151. 			{`.`, Text, nil},
    
  152. 		},
    
  153. 	}
    
  154. 	data, err := xml.MarshalIndent(expected, "  ", "  ")
    
  155. 	assert.NoError(t, err)
    
  156. 	re := regexp.MustCompile(`></[a-zA-Z]+>`)
    
  157. 	data = re.ReplaceAll(data, []byte(`/>`))
    
  158. 	b := &bytes.Buffer{}
    
  159. 	w := gzip.NewWriter(b)
    
  160. 	fmt.Fprintln(w, string(data))
    
  161. 	w.Close()
    
  162. 	actual := Rules{}
    
  163. 	err = xml.Unmarshal(data, &actual)
    
  164. 	assert.NoError(t, err)
    
  165. 	assert.Equal(t, expected, actual)
    
  166. }