F-allahmoradi commited on
Commit
416d259
·
verified ·
1 Parent(s): f829092

Upload app.py

Browse files
Files changed (1) hide show
  1. app.py +135 -0
app.py ADDED
@@ -0,0 +1,135 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import os
2
+ import subprocess
3
+ import tempfile
4
+ import streamlit as st
5
+ import fitz # pymupdf
6
+
7
+ # === تنظیمات ===
8
+ LANG = "fas+eng"
9
+
10
+ # === سبک‌دهی راست‌چین ===
11
+ st.markdown("""
12
+ <style>
13
+ body, .stApp, .stMarkdown, .stText {
14
+ direction: rtl;
15
+ text-align: right;
16
+ font-family: 'Vazir', 'Tahoma', 'Arial', sans-serif;
17
+ }
18
+ .stButton>button {
19
+ width: 100%;
20
+ background-color: #4CAF50;
21
+ color: white;
22
+ border-radius: 8px;
23
+ }
24
+ .stDownloadButton>button {
25
+ background-color: #2196F3;
26
+ color: white;
27
+ border-radius: 6px;
28
+ }
29
+ </style>
30
+ """, unsafe_allow_html=True)
31
+
32
+ def get_pdf_page_count(pdf_path: str) -> int:
33
+ """بررسی تعداد صفحات PDF با استفاده از PyMuPDF"""
34
+ try:
35
+ with fitz.open(pdf_path) as doc:
36
+ return len(doc)
37
+ except Exception as e:
38
+ st.warning(f"⚠️ نتوانست تعداد صفحات {os.path.basename(pdf_path)} را بخواند: {e}")
39
+ return 1 # حدس اولیه
40
+
41
+ def run_ocr_with_progress(input_path: str, output_path: str, total_pages: int, status_placeholder):
42
+ """اجرای OCRmyPDF با نمایش پیشرفت صفحه به صفحه"""
43
+ command = [
44
+ "ocrmypdf",
45
+ "-l", LANG,
46
+ "--force-ocr",
47
+ "--verbose", "1",
48
+ input_path,
49
+ output_path,
50
+ ]
51
+
52
+ progress = 0
53
+ progress_bar = st.progress(0)
54
+ page_counter = st.empty()
55
+ page_counter.text(f"صفحهٔ پردازش‌شده: 0 از {total_pages}")
56
+
57
+ try:
58
+ process = subprocess.Popen(
59
+ command,
60
+ stdout=subprocess.PIPE,
61
+ stderr=subprocess.STDOUT,
62
+ text=True,
63
+ bufsize=1,
64
+ universal_newlines=True,
65
+ )
66
+
67
+ for line in iter(process.stdout.readline, ""):
68
+ if "page" in line.lower() and ("processing" in line.lower() or "rendering" in line.lower()):
69
+ progress += 1
70
+ if progress <= total_pages:
71
+ percent = int((progress / total_pages) * 100)
72
+ progress_bar.progress(min(percent, 100))
73
+ page_counter.text(f"صفحهٔ پردازش‌شده: {progress} از {total_pages}")
74
+
75
+ process.wait()
76
+ progress_bar.progress(100)
77
+ page_counter.text(f"✅ پردازش کامل شد: {total_pages} صفحه")
78
+ return process.returncode == 0, ""
79
+
80
+ except Exception as e:
81
+ return False, str(e)
82
+
83
+ # === رابط کاربری Streamlit ===
84
+ st.set_page_config(page_title="تبدیل PDF به PDF قابل جستجو", layout="wide")
85
+ st.title("🔍 تبدیل PDF تصویری به PDF قابل جستجو")
86
+ st.markdown("فایل‌های PDF خود را آپلود کنید — پیشرفت پردازش صفحه‌به‌صفحه نمایش داده می‌شود.")
87
+
88
+ with st.sidebar:
89
+ st.image("https://cdn-icons-png.flaticon.com/512/3050/3050307.png", width=80)
90
+ st.header("📤 آپلود فایل")
91
+ uploaded_files = st.file_uploader(
92
+ "فایل‌های PDF خود را انتخاب کنید",
93
+ type=["pdf"],
94
+ accept_multiple_files=True
95
+ )
96
+ st.markdown("---")
97
+ st.caption("✅ پشتیبانی از فارسی + انگلیسی\n\n📊 نمایش پیشرفت صفحه‌به‌صفحه")
98
+
99
+ if not uploaded_files:
100
+ st.info("👈 لطفاً فایل‌های PDF را از نوار کناری آپلود کنید.")
101
+ else:
102
+ results = []
103
+ for file in uploaded_files:
104
+ st.markdown(f"### پردازش: `{file.name}`")
105
+
106
+ with tempfile.TemporaryDirectory() as temp_dir:
107
+ input_path = os.path.join(temp_dir, file.name)
108
+ output_path = os.path.join(temp_dir, f"OCR_{file.name}")
109
+
110
+ with open(input_path, "wb") as f:
111
+ f.write(file.getbuffer())
112
+
113
+ total_pages = get_pdf_page_count(input_path)
114
+ st.caption(f"📄 تعداد صفحات: {total_pages}")
115
+
116
+ success, error = run_ocr_with_progress(input_path, output_path, total_pages, None)
117
+
118
+ if success and os.path.exists(output_path):
119
+ with open(output_path, "rb") as f:
120
+ results.append((file.name, f.read()))
121
+ st.success(f"✅ `{file.name}` با موفقیت پردازش شد!")
122
+ else:
123
+ st.error(f"❌ خطا در پردازش `{file.name}`:\n```\n{error}\n```")
124
+
125
+ if results:
126
+ st.markdown("---")
127
+ st.subheader("📥 دانلود فایل‌های OCR شده")
128
+ for orig_name, pdf_bytes in results:
129
+ st.download_button(
130
+ label=f"⬇️ دانلود OCR_{orig_name}",
131
+ data=pdf_bytes,
132
+ file_name=f"OCR_{orig_name}",
133
+ mime="application/pdf"
134
+ )
135
+ st.balloons()