-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathconvert.py
More file actions
133 lines (116 loc) · 5.59 KB
/
Copy pathconvert.py
File metadata and controls
133 lines (116 loc) · 5.59 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
import os
import re
import glob
import shutil
def clean_text(text):
if not text: return ""
text = re.sub(r'<.*?>', '', text)
text = re.sub(r'[\t\r\n]', ' ', text)
text = "".join(char for char in text if char.isprintable())
return text.strip()
def convert_post(html_path, dest_path):
with open(html_path, 'r', encoding='utf-8') as f:
html = f.read()
# Title Extraction
title = ""
patterns = [
r'<h1 class="entry-title">.*?>(.*?)</a></h1>',
r'<h1 class="entry-title">(.*?)</h1>',
r'<h1 class="single-post-title">.*?<h1>(.*?)</h1>',
r'<div class="single-post-title">.*?<h1>(.*?)</h1>',
r'<title>(.*?) – SouJava</title>'
]
for p in patterns:
m = re.search(p, html, re.DOTALL)
if m:
title = clean_text(m.group(1))
break
if not title: title = os.path.basename(os.path.dirname(html_path)).replace("-", " ").capitalize()
title = title.replace('"', '\\"')
# Date Extraction
date_match = re.search(r'datetime="(.*?)"', html)
date = date_match.group(1) if date_match else "2024-01-01T00:00:00+00:00"
# Content Extraction
c_match = re.search(r'<div class="single-entry-content">(.*?)</div>\s*<!-- .single-entry-content -->', html, re.DOTALL)
if not c_match: c_match = re.search(r'<div class="entry-content">(.*?)</div>\s*<!-- .entry-content -->', html, re.DOTALL)
content = c_match.group(1).strip() if c_match else ""
content = re.sub(r'<p>(.*?)</p>', r'\1\n\n', content, flags=re.DOTALL)
# Featured Image Extraction - HIGH PRECISION
featured_img = ""
# 1. Search for background-image style (most accurate for this theme)
img_m = re.search(r'background-image: url\([\'"]?(.*?)[\'"]?\)', html)
if not img_m:
# 2. Search for the single-featured-image img tag
img_m = re.search(r'<div class="single-featured-image">.*?src="(.*?)"', html, re.DOTALL)
if img_m:
featured_img = img_m.group(1)
# Clean relative bits like 'url(\'/wp-content...)'
featured_img = featured_img.strip("'").strip('"')
# Comments Parsing
comments_md = ""
if '<ol class="comment-list">' in html:
list_match = re.search(r'<ol class="comment-list">(.*?)</ol>', html, re.DOTALL)
if list_match:
items = re.findall(r'<li id="comment-\d+".*?>(.*?)</li>', list_match.group(1), re.DOTALL)
if items:
comments_md = "\n\n---\n### Comentários Antigos (WordPress)\n\n"
for item in items:
author_m = re.search(r'<b class="fn">(.*?)</b>', item, re.DOTALL)
if not author_m: author_m = re.search(r'Pingback: (.*?) <', item, re.DOTALL)
author = clean_text(author_m.group(1)) if author_m else "Anônimo"
date_m = re.search(r'<time.*?>(.*?)</time>', item, re.DOTALL)
c_date = clean_text(date_m.group(1)) if date_m else ""
text_m = re.search(r'<div class="comment-content">(.*?)</div>', item, re.DOTALL)
text = clean_text(text_m.group(1)) if text_m else clean_text(item)
if text:
comments_md += f"> **{author}** ({c_date})\n>\n> {text}\n\n"
# URL Cleanup
full_body = content + comments_md
for domain in [".us.stackstaging.com/wp-content/uploads/", "https://soujava.org.br/wp-content/uploads/", "http://soujava.org.br/wp-content/uploads/"]:
full_body = full_body.replace(domain, "/wp-content/uploads/")
featured_img = featured_img.replace(domain, "/wp-content/uploads/")
# Author/Meta
author_name = ""
a_match = re.search(r'<span class="author vcard"><a .*?>(.*?)</a></span>', html)
if a_match: author_name = clean_text(a_match.group(1))
cat_match = re.search(r'<span class="cat-links">(.*?)</span>', html, re.DOTALL)
categories = [clean_text(c) for c in re.findall(r'<a .*?>(.*?)</a>', cat_match.group(1))] if cat_match else []
tag_block_match = re.search(r'<div class="tags-links">(.*?)</div>', html, re.DOTALL)
tags = [clean_text(t) for t in re.findall(r'<a .*?>(.*?)</a>', tag_block_match.group(1))] if tag_block_match else []
# Build MD
authors_list = f'["{author_name}"]' if author_name else "[]"
fm = f"""---
title: "{title}"
date: {date}
authors: {authors_list}
categories: {categories}
tags: {tags}
featured_image: "{featured_img}"
---
{full_body}
"""
os.makedirs(os.path.dirname(dest_path), exist_ok=True)
with open(dest_path, 'w', encoding='utf-8') as f:
f.write(fm)
print(f"OK: {dest_path}")
if __name__ == "__main__":
import sys
if len(sys.argv) != 3:
print("Uso: python convert.py <diretorio_html> <diretorio_output>")
print("Exemplo: python convert.py ./html-export ./content")
sys.exit(1)
base = sys.argv[1]
out = sys.argv[2]
if not os.path.exists(base):
print(f"Erro: diretório {base} não encontrado")
sys.exit(1)
if os.path.exists(out): shutil.rmtree(out)
for root, dirs, files in os.walk(base):
dirs[:] = [d for d in dirs if d not in ['wp-content', 'wp-includes', 'author', 'category', 'tag', 'page']]
if "index.html" in files:
rel = os.path.relpath(root, base)
if rel == ".": continue
if re.match(r'^\d{4}', rel): dest = os.path.join(out, "posts", f"{os.path.basename(root)}.md")
elif any(os.path.isdir(os.path.join(root, d)) for d in os.listdir(root)): dest = os.path.join(out, rel, "_index.md")
else: dest = os.path.join(out, f"{rel}.md")
convert_post(os.path.join(root, "index.html"), dest)