(html: string)
| 175 | } |
| 176 | |
| 177 | function extractHtml(html: string): { |
| 178 | title?: string |
| 179 | description?: string |
| 180 | text: string |
| 181 | } { |
| 182 | const title = extractFirstMatch(html, /<title\b[^>]*>([\s\S]*?)<\/title>/i) |
| 183 | const description = |
| 184 | extractMetaContent(html, 'description') ?? |
| 185 | extractMetaContent(html, 'og:description') |
| 186 | |
| 187 | let readable = html |
| 188 | .replace(/<!--[\s\S]*?-->/g, '\n') |
| 189 | .replace(/<!doctype[^>]*>/gi, '\n') |
| 190 | |
| 191 | for (const tagName of [ |
| 192 | 'script', |
| 193 | 'style', |
| 194 | 'svg', |
| 195 | 'canvas', |
| 196 | 'iframe', |
| 197 | 'noscript', |
| 198 | 'nav', |
| 199 | 'header', |
| 200 | 'footer', |
| 201 | 'form', |
| 202 | 'button', |
| 203 | 'select', |
| 204 | ]) { |
| 205 | readable = removeElement(readable, tagName) |
| 206 | } |
| 207 | |
| 208 | readable = selectReadableHtml(readable) |
| 209 | |
| 210 | readable = readable |
| 211 | .replace(/<br\s*\/?>/gi, '\n') |
| 212 | .replace( |
| 213 | /<\/(p|div|section|article|main|aside|li|tr|td|th|h[1-6]|blockquote|pre)>/gi, |
| 214 | '\n', |
| 215 | ) |
| 216 | .replace(/<(li|tr|h[1-6])\b[^>]*>/gi, '\n') |
| 217 | .replace(/<[^>]*>/g, '') |
| 218 | |
| 219 | const text = normalizeText(decodeHtmlEntities(readable)) |
| 220 | return { title, description, text } |
| 221 | } |
| 222 | |
| 223 | function extractMarkdownFrontmatter(body: string): { |
| 224 | title?: string |
no test coverage detected