rss email digests over ssh because you're a cool kid herald.dunkirk.sh
go rss rss-reader ssh charm
at main 183 lines 5.1 kB view raw
1package email 2 3import ( 4 "strings" 5 "testing" 6 "time" 7) 8 9func TestRenderDigest_HTMLNotEscaped(t *testing.T) { 10 // Create test data with HTML content 11 data := &DigestData{ 12 ConfigName: "Test Config", 13 TotalItems: 1, 14 FeedGroups: []FeedGroup{ 15 { 16 FeedName: "Test Feed", 17 FeedURL: "https://example.com/feed", 18 Items: []FeedItem{ 19 { 20 Title: "Test Article", 21 Link: "https://example.com/article", 22 Content: "<p>This is a <strong>test</strong> article with <a href='https://example.com'>a link</a>.</p>", 23 Published: time.Now(), 24 }, 25 }, 26 }, 27 }, 28 } 29 30 // Render with inline mode enabled 31 htmlOutput, _, err := RenderDigest(data, true, 30, false, false) 32 if err != nil { 33 t.Fatalf("RenderDigest failed: %v", err) 34 } 35 36 // Debug: print actual output 37 t.Logf("HTML Output:\n%s", htmlOutput) 38 39 // Verify HTML is NOT escaped (should contain actual tags, not &lt; entities) 40 if strings.Contains(htmlOutput, "&lt;p&gt;") { 41 t.Error("HTML is being escaped - found &lt;p&gt; instead of <p>") 42 } 43 if strings.Contains(htmlOutput, "&lt;strong&gt;") { 44 t.Error("HTML is being escaped - found &lt;strong&gt; instead of <strong>") 45 } 46 47 // Verify HTML tags are present (not escaped) 48 if !strings.Contains(htmlOutput, "<p>This is a <strong>test</strong>") { 49 t.Error("HTML tags are not being rendered - content appears to be escaped") 50 } 51} 52 53func TestRenderDigest_UnsafeHTMLStripped(t *testing.T) { 54 // Create test data with unsafe HTML content 55 data := &DigestData{ 56 ConfigName: "Test Config", 57 TotalItems: 1, 58 FeedGroups: []FeedGroup{ 59 { 60 FeedName: "Test Feed", 61 FeedURL: "https://example.com/feed", 62 Items: []FeedItem{ 63 { 64 Title: "Test Article", 65 Link: "https://example.com/article", 66 Content: "<p>Safe content</p><script>alert('xss')</script><p style='color:red'>No styles</p>", 67 Published: time.Now(), 68 }, 69 }, 70 }, 71 }, 72 } 73 74 // Render with inline mode enabled 75 htmlOutput, _, err := RenderDigest(data, true, 30, false, false) 76 if err != nil { 77 t.Fatalf("RenderDigest failed: %v", err) 78 } 79 80 // Debug: print actual output 81 t.Logf("HTML Output:\n%s", htmlOutput) 82 83 // Verify script tags are removed 84 if strings.Contains(htmlOutput, "<script>") { 85 t.Error("Unsafe <script> tags were not stripped") 86 } 87 if strings.Contains(htmlOutput, "alert('xss')") { 88 t.Error("Script content was not removed") 89 } 90 91 // Verify safe content remains 92 if !strings.Contains(htmlOutput, "<p>Safe content</p>") { 93 t.Error("Safe HTML content was incorrectly removed") 94 } 95} 96 97func TestRenderDigest_TextOutputNoHTMLTags(t *testing.T) { 98 // Create test data with HTML content 99 data := &DigestData{ 100 ConfigName: "Test Config", 101 TotalItems: 1, 102 FeedGroups: []FeedGroup{ 103 { 104 FeedName: "Test Feed", 105 FeedURL: "https://example.com/feed", 106 Items: []FeedItem{ 107 { 108 Title: "Test Article", 109 Link: "https://example.com/article", 110 Content: "<article><p>This is a <strong>test</strong> article with <a href='https://example.com'>a link</a>.</p></article>", 111 Published: time.Now(), 112 }, 113 }, 114 }, 115 }, 116 } 117 118 // Render with inline mode enabled 119 _, textOutput, err := RenderDigest(data, true, 30, false, false) 120 if err != nil { 121 t.Fatalf("RenderDigest failed: %v", err) 122 } 123 124 // Verify text output does NOT contain HTML tags 125 htmlTags := []string{"<article>", "<p>", "<strong>", "<a href", "</article>", "</p>", "</strong>", "</a>"} 126 for _, tag := range htmlTags { 127 if strings.Contains(textOutput, tag) { 128 t.Errorf("Text output contains HTML tag %q - should be stripped", tag) 129 } 130 } 131 132 // Verify the actual text content is present 133 if !strings.Contains(textOutput, "This is a test article with a link") { 134 t.Error("Text content was not preserved after HTML stripping") 135 } 136} 137 138func TestRenderDigest_CodeBlockFormatting(t *testing.T) { 139 data := &DigestData{ 140 ConfigName: "Test Config", 141 TotalItems: 1, 142 FeedGroups: []FeedGroup{ 143 { 144 FeedName: "Test Feed", 145 FeedURL: "https://example.com/feed", 146 Items: []FeedItem{ 147 { 148 Title: "Test Article", 149 Link: "https://example.com/article", 150 Content: `<p>Code example:</p><pre><span class="c1"># comment</span> 151echo hello</pre><p>Done.</p>`, 152 Published: time.Now(), 153 }, 154 }, 155 }, 156 }, 157 } 158 159 htmlOutput, textOutput, err := RenderDigest(data, true, 30, false, false) 160 if err != nil { 161 t.Fatalf("RenderDigest failed: %v", err) 162 } 163 164 // HTML: verify code block has styling 165 if !strings.Contains(htmlOutput, `<pre style="background-color:#f5f5f5`) { 166 t.Error("HTML code block missing styling") 167 } 168 169 // HTML: verify syntax highlighting spans are stripped 170 if strings.Contains(htmlOutput, `class="c1"`) { 171 t.Error("Syntax highlighting classes should be stripped") 172 } 173 174 // Text: verify code is indented 175 if !strings.Contains(textOutput, " # comment") { 176 t.Error("Text code block should be indented with 4 spaces") 177 } 178 179 // Text: verify no HTML tags in code block 180 if strings.Contains(textOutput, "<span") || strings.Contains(textOutput, "<pre") { 181 t.Error("Text output should not contain HTML tags") 182 } 183}