Merge pull request #53 from sudo-Harshk/fix/stats-regex

fix(stats): implement regex for sentences, lists, and tables
This commit is contained in:
Gamosoft 2025-12-01 17:29:37 +01:00 committed by GitHub
commit d7c50eaac0
3 changed files with 54 additions and 1 deletions

View File

@ -2962,6 +2962,15 @@ function noteApp() {
// Paragraph count // Paragraph count
const paragraphs = content.split('\n\n').filter(p => p.trim()).length; const paragraphs = content.split('\n\n').filter(p => p.trim()).length;
// Sentences: punctuation [.!?]+ followed by space or end-of-string
const sentences = (content.match(/[.!?]+(?:\s|$)/g) || []).length;
// List items: lines starting with -, *, + or a number (e.g. 1., 10.), excluding tasks [-]
const listItems = (content.match(/^\s*(?:[-*+]|\d+\.)\s+(?!\[)/gm) || []).length;
// Tables: separator rows containing both '|' and '---'
const tables = (content.match(/^(?=.*\|)(?=.*---).*$/gm) || []).length;
// Link count // Link count
const linkMatches = content.match(/\[([^\]]+)\]\(([^\)]+)\)/g) || []; const linkMatches = content.match(/\[([^\]]+)\]\(([^\)]+)\)/g) || [];
const links = linkMatches.length; const links = linkMatches.length;
@ -2990,11 +2999,14 @@ function noteApp() {
this.noteStats = { this.noteStats = {
words, words,
sentences,
characters: chars, characters: chars,
total_characters: totalChars, total_characters: totalChars,
reading_time_minutes: readingTime, reading_time_minutes: readingTime,
lines, lines,
paragraphs, paragraphs,
list_items: listItems,
tables,
links, links,
internal_links: internalLinks, internal_links: internalLinks,
external_links: links - internalLinks, external_links: links - internalLinks,

View File

@ -1567,6 +1567,24 @@
<div class="font-semibold" style="color: var(--text-primary);" x-text="noteStats ? noteStats.lines.toLocaleString() : '0'"></div> <div class="font-semibold" style="color: var(--text-primary);" x-text="noteStats ? noteStats.lines.toLocaleString() : '0'"></div>
</div> </div>
<!-- Sentences -->
<div>
<div class="text-xs" style="color: var(--text-tertiary);">Sentences</div>
<div class="font-semibold" style="color: var(--text-primary);" x-text="noteStats ? noteStats.sentences.toLocaleString() : '0'"></div>
</div>
<!-- Lists -->
<div>
<div class="text-xs" style="color: var(--text-tertiary);">Lists</div>
<div class="font-semibold" style="color: var(--text-primary);" x-text="noteStats ? noteStats.list_items.toLocaleString() : '0'"></div>
</div>
<!-- Tables -->
<div>
<div class="text-xs" style="color: var(--text-tertiary);">Tables</div>
<div class="font-semibold" style="color: var(--text-primary);" x-text="noteStats ? noteStats.tables.toLocaleString() : '0'"></div>
</div>
<!-- Links --> <!-- Links -->
<template x-if="noteStats && noteStats.links > 0"> <template x-if="noteStats && noteStats.links > 0">
<div> <div>

View File

@ -41,6 +41,19 @@ class Plugin:
# Paragraph count (blocks separated by blank lines) # Paragraph count (blocks separated by blank lines)
paragraphs = len([p for p in content.split('\n\n') if p.strip()]) paragraphs = len([p for p in content.split('\n\n') if p.strip()])
# Sentence count: punctuation [.!?]+ followed by space or end-of-string
sentences = len(re.findall(r'[.!?]+(?:\s|$)', content))
# List items: lines starting with -, *, + or a number (e.g. 1., 10.), excluding tasks [-]
list_items = len(
re.findall(r'^\s*(?:[-*+]|\d+\.)\s+(?!\[)', content, re.MULTILINE)
)
# Tables: count separator rows containing both '|' and '---'
tables = len(
re.findall(r'^(?=.*\|)(?=.*---).*$', content, re.MULTILINE)
)
# Markdown link count # Markdown link count
links = len(re.findall(r'\[([^\]]+)\]\(([^\)]+)\)', content)) links = len(re.findall(r'\[([^\]]+)\]\(([^\)]+)\)', content))
@ -71,11 +84,14 @@ class Plugin:
return { return {
'words': words, 'words': words,
'sentences': sentences,
'characters': chars, 'characters': chars,
'total_characters': total_chars, 'total_characters': total_chars,
'reading_time_minutes': reading_time, 'reading_time_minutes': reading_time,
'lines': lines, 'lines': lines,
'paragraphs': paragraphs, 'paragraphs': paragraphs,
'list_items': list_items,
'tables': tables,
'links': links, 'links': links,
'internal_links': internal_links, 'internal_links': internal_links,
'external_links': links - internal_links, 'external_links': links - internal_links,
@ -129,7 +145,14 @@ class Plugin:
# Log key statistics # Log key statistics
print(f"📊 {note_path}:") print(f"📊 {note_path}:")
print(f" {stats['words']:,} words | {stats['reading_time_minutes']}m read | {stats['lines']:,} lines") print(
f" {stats['words']:,} words | "
f"{stats['sentences']:,} sentences | "
f"{stats['reading_time_minutes']}m read | "
f"{stats['lines']:,} lines | "
f"{stats['list_items']:,} lists | "
f"{stats['tables']:,} tables"
)
if stats['links'] > 0: if stats['links'] > 0:
print(f" {stats['links']} links ({stats['internal_links']} internal)") print(f" {stats['links']} links ({stats['internal_links']} internal)")