leilaghomashchi commited on
Commit
a6733f0
·
verified ·
1 Parent(s): fcb9fb5

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +60 -11
app.py CHANGED
@@ -19,6 +19,21 @@ class UniversalAnonymizer:
19
  'percent': 0
20
  }
21
  self.api_key = os.getenv("OPENAI_API_KEY", "")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
22
 
23
  def anonymize_text(self, original_text, lang='fa'):
24
  """ناشناس‌سازی جامع با تشخیص خودکار الگوها"""
@@ -97,13 +112,22 @@ class UniversalAnonymizer:
97
 
98
  # الگوهای جامع مبالغ مالی
99
  amount_patterns = [
 
 
 
 
 
 
 
100
  # مبالغ با کاما و نقطه
101
  r'\d+,\d{3},\d{3} میلیون ریال',
102
  r'\d+\.\d{3}\.\d{3} میلیون ریال',
103
  r'\d+,\d{3} میلیارد ریال',
104
  r'\d+\.\d{3} میلیارد ریال',
105
 
106
- # مبالغ با واحد همت
 
 
107
  r'\d+\.?\d* همت',
108
  r'بیش از \d+\.?\d* همت',
109
  r'نزدیک به \d+\.?\d* همت',
@@ -215,6 +239,9 @@ class UniversalAnonymizer:
215
 
216
  # الگوهای جامع نام‌های اشخاص
217
  person_patterns = [
 
 
 
218
  # نام‌های کامل با عناوین
219
  r'دکتر\s+[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+',
220
  r'مهندس\s+[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+',
@@ -228,12 +255,9 @@ class UniversalAnonymizer:
228
  r'سیدمحمد\s+[آ-ی]+',
229
  r'سیدحسن\s+[آ-ی]+',
230
 
231
- # نام و نام خانوادگی ساده
232
- r'[آ-ی]{3,}\s+[آ-ی]{3,}(?:\s+[آ-ی]{3,})?',
233
-
234
  # نام‌هایی که با مدیرعامل همراه هستند
235
- r'[آ-ی]+\s+[آ-ی]+\s*،?\s*مدیرعامل',
236
  r'[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+\s*،?\s*مدیرعامل',
 
237
 
238
  # نام‌هایی که با سمت همراه هستند
239
  r'[آ-ی]+\s+[آ-ی]+\s*،?\s*رئیس',
@@ -245,6 +269,9 @@ class UniversalAnonymizer:
245
  r'علیرضا\s+[آ-ی]+',
246
  r'محمدعلی\s+[آ-ی]+',
247
  r'حسینعلی\s+[آ-ی]+',
 
 
 
248
  ]
249
 
250
  return self._apply_patterns(text, person_patterns, 'person')
@@ -254,6 +281,12 @@ class UniversalAnonymizer:
254
 
255
  # الگوهای جامع نام‌های شرکت‌ها
256
  company_patterns = [
 
 
 
 
 
 
257
  # شرکت‌های کامل با پرانتز
258
  r'شرکت\s+[آ-ی\s]+\([آ-ی\s]+\)',
259
  r'بانک\s+[آ-ی\s]+\([آ-ی\s]+\)',
@@ -264,6 +297,7 @@ class UniversalAnonymizer:
264
  r'شرکت\s+[آ-ی\s]{5,}',
265
  r'شرکت\s+گروه\s+[آ-ی\s]+',
266
  r'شرکت\s+سرمایه‌گذاری\s+[آ-ی\s]+',
 
267
  r'شرکت\s+بیمه\s+[آ-ی\s]+',
268
  r'شرکت\s+پتروشیمی\s+[آ-ی\s]+',
269
  r'شرکت\s+فولاد\s+[آ-ی\s]+',
@@ -296,7 +330,8 @@ class UniversalAnonymizer:
296
 
297
  # نام‌های کوتاه شرکت‌ها (باید در آخر باشند)
298
  r'همراه\s+اول',
299
- r'ایران\s*[-‌]*\s*خودرو',
 
300
  r'فولاد\s+مبارکه',
301
 
302
  # مجله‌ها و نشریات
@@ -319,6 +354,10 @@ class UniversalAnonymizer:
319
  for match in matches:
320
  matched_text = match.group(0)
321
 
 
 
 
 
322
  # اگر قبلاً جایگزین نشده باشد
323
  if matched_text not in self.mapping_table and matched_text in text:
324
  # بررسی که کلمه کامل باشد (نه بخشی از کلمه بزرگ‌تر)
@@ -331,6 +370,13 @@ class UniversalAnonymizer:
331
 
332
  return text
333
 
 
 
 
 
 
 
 
334
  def _is_complete_word(self, text, match):
335
  """بررسی اینکه آیا کلمه کامل است یا بخشی از کلمه بزرگ‌تر"""
336
  start, end = match.span()
@@ -532,7 +578,7 @@ def update_interface(language):
532
 
533
  return [
534
  gr.update(value=f"<h1 style='text-align: center; color: #FFD700; font-size: 3.5em; font-weight: bold; text-shadow: 3px 3px 6px rgba(0,0,0,0.5); margin: 20px 0; background: linear-gradient(45deg, #FFD700, #FFA500); -webkit-background-clip: text; -webkit-text-fill-color: transparent; background-clip: text;'>📊 {ui_text['title']}</h1>"),
535
- gr.update(value=f"<h2 style='direction: {ui_text['direction']};'>🔍 {ui_text['step1']}</h2>"),
536
  gr.update(placeholder=ui_text['input_placeholder'], rtl=not is_english),
537
  gr.update(value=f"🚀 {ui_text['process_btn']}"),
538
  gr.update(value=f"🗑️ {ui_text['clear_btn']}"),
@@ -647,7 +693,7 @@ with gr.Blocks(title="📊 Universal Anonymization System", theme=gr.themes.Soft
647
 
648
  with gr.Row(elem_classes="workflow rtl") as workflow_row:
649
  with gr.Column():
650
- step1_title = gr.HTML('<h2 style="direction: rtl;">🔍 متن ورودی و تنظیمات</h2>')
651
 
652
  input_text = gr.Textbox(
653
  lines=15,
@@ -745,8 +791,11 @@ with gr.Blocks(title="📊 Universal Anonymization System", theme=gr.themes.Soft
745
  )
746
 
747
  if __name__ == "__main__":
748
- # تست سیستم با نمونه از داده‌های شما
749
- test_text = """مهدی اخوان بهابادی، مدیرعامل همراه اول، در مجمع عمومی عادی سالیانه اعلام کرد درآمد عملیاتی شرکت اصلی با رشد قابل توجه 37 درصدی نسبت به سال 1402، به 70 هزار و 677 میلیارد تومان رسیده است. شرکت گروه توسعه مالی مهر آیندگان (ومهان) در گزارش عملکرد مردادماه 1404 بار دیگر توانست با رشد 14 درصدی سرمایه‌گذاری‌ها جایگاه خود را تثبیت کند."""
 
 
 
750
 
751
  anonymizer_test = UniversalAnonymizer()
752
  result = anonymizer_test.anonymize_text(test_text)
@@ -756,4 +805,4 @@ if __name__ == "__main__":
756
  for original, code in anonymizer_test.mapping_table.items():
757
  print(f"{original} -> {code}")
758
 
759
- app.launch()
 
19
  'percent': 0
20
  }
21
  self.api_key = os.getenv("OPENAI_API_KEY", "")
22
+
23
+ # لیست عبارات عمومی که نباید ناشناس‌سازی شوند
24
+ self.common_phrases = [
25
+ 'مجمع عمومی عادی سالیانه',
26
+ 'مجمع عمومی فوق‌العاده',
27
+ 'هیئت مدیره',
28
+ 'سهامداران محترم',
29
+ 'صورت‌های مالی',
30
+ 'شرکت اصلی',
31
+ 'درآمد عملیاتی',
32
+ 'سود عملیاتی',
33
+ 'زیان انباشته',
34
+ 'محصولات گرم',
35
+ 'محصولات سرد',
36
+ ]
37
 
38
  def anonymize_text(self, original_text, lang='fa'):
39
  """ناشناس‌سازی جامع با تشخیص خودکار الگوها"""
 
112
 
113
  # الگوهای جامع مبالغ مالی
114
  amount_patterns = [
115
+ # مبالغ با پسوند "ی" - مهم: باید قبل از الگوهای بدون "ی" باشد
116
+ r'\d+ میلیارد تومانی',
117
+ r'\d+ میلیون تومانی',
118
+ r'\d+ هزار تومانی',
119
+ r'\d+\.?\d* میلیارد تومانی',
120
+ r'\d+\.?\d* میلیون تومانی',
121
+
122
  # مبالغ با کاما و نقطه
123
  r'\d+,\d{3},\d{3} میلیون ریال',
124
  r'\d+\.\d{3}\.\d{3} میلیون ریال',
125
  r'\d+,\d{3} میلیارد ریال',
126
  r'\d+\.\d{3} میلیارد ریال',
127
 
128
+ # مبالغ با واحد همت - با و بدون اعشار
129
+ r'\d+ همت',
130
+ r'\d+\.\d+ همت',
131
  r'\d+\.?\d* همت',
132
  r'بیش از \d+\.?\d* همت',
133
  r'نزدیک به \d+\.?\d* همت',
 
239
 
240
  # الگوهای جامع نام‌های اشخاص
241
  person_patterns = [
242
+ # نام‌های خاص که در متن ذکر شده
243
+ r'مهدی اخوان بهابادی',
244
+
245
  # نام‌های کامل با عناوین
246
  r'دکتر\s+[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+',
247
  r'مهندس\s+[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+',
 
255
  r'سیدمحمد\s+[آ-ی]+',
256
  r'سیدحسن\s+[آ-ی]+',
257
 
 
 
 
258
  # نام‌هایی که با مدیرعامل همراه هستند
 
259
  r'[آ-ی]+\s+[آ-ی]+\s+[آ-ی]+\s*،?\s*مدیرعامل',
260
+ r'[آ-ی]+\s+[آ-ی]+\s*،?\s*مدیرعامل',
261
 
262
  # نام‌هایی که با سمت همراه هستند
263
  r'[آ-ی]+\s+[آ-ی]+\s*،?\s*رئیس',
 
269
  r'علیرضا\s+[آ-ی]+',
270
  r'محمدعلی\s+[آ-ی]+',
271
  r'حسینعلی\s+[آ-ی]+',
272
+
273
+ # نام و نام خانوادگی ساده - حداقل 3 حرف برای هر کلمه
274
+ r'[آ-ی]{3,}\s+[آ-ی]{3,}(?:\s+[آ-ی]{3,})?',
275
  ]
276
 
277
  return self._apply_patterns(text, person_patterns, 'person')
 
281
 
282
  # الگوهای جامع نام‌های شرکت‌ها
283
  company_patterns = [
284
+ # نام‌های خاص که در متن ذکر شده
285
+ r'شرکت سرمایه گذاری پارسیان',
286
+ r'شرکت سرمایه‌گذاری پارسیان',
287
+ r'بانک پارسیان',
288
+ r'گروه مالی پارسیان',
289
+
290
  # شرکت‌های کامل با پرانتز
291
  r'شرکت\s+[آ-ی\s]+\([آ-ی\s]+\)',
292
  r'بانک\s+[آ-ی\s]+\([آ-ی\s]+\)',
 
297
  r'شرکت\s+[آ-ی\s]{5,}',
298
  r'شرکت\s+گروه\s+[آ-ی\s]+',
299
  r'شرکت\s+سرمایه‌گذاری\s+[آ-ی\s]+',
300
+ r'شرکت\s+سرمایه گذاری\s+[آ-ی\s]+',
301
  r'شرکت\s+بیمه\s+[آ-ی\s]+',
302
  r'شرکت\s+پتروشیمی\s+[آ-ی\s]+',
303
  r'شرکت\s+فولاد\s+[آ-ی\s]+',
 
330
 
331
  # نام‌های کوتاه شرکت‌ها (باید در آخر باشند)
332
  r'همراه\s+اول',
333
+ r'ایران‌خودرو',
334
+ r'ایران خودرو',
335
  r'فولاد\s+مبارکه',
336
 
337
  # مجله‌ها و نشریات
 
354
  for match in matches:
355
  matched_text = match.group(0)
356
 
357
+ # بررسی اینکه آیا عبارت جزو عبارات عمومی است
358
+ if self._is_common_phrase(matched_text):
359
+ continue
360
+
361
  # اگر قبلاً جایگزین نشده باشد
362
  if matched_text not in self.mapping_table and matched_text in text:
363
  # بررسی که کلمه کامل باشد (نه بخشی از کلمه بزرگ‌تر)
 
370
 
371
  return text
372
 
373
+ def _is_common_phrase(self, text):
374
+ """بررسی اینکه آیا عبارت جزو عبارات عمومی است"""
375
+ for phrase in self.common_phrases:
376
+ if phrase.lower() in text.lower():
377
+ return True
378
+ return False
379
+
380
  def _is_complete_word(self, text, match):
381
  """بررسی اینکه آیا کلمه کامل است یا بخشی از کلمه بزرگ‌تر"""
382
  start, end = match.span()
 
578
 
579
  return [
580
  gr.update(value=f"<h1 style='text-align: center; color: #FFD700; font-size: 3.5em; font-weight: bold; text-shadow: 3px 3px 6px rgba(0,0,0,0.5); margin: 20px 0; background: linear-gradient(45deg, #FFD700, #FFA500); -webkit-background-clip: text; -webkit-text-fill-color: transparent; background-clip: text;'>📊 {ui_text['title']}</h1>"),
581
+ gr.update(value=f"<h2 style='direction: {ui_text['direction']};'>📝 {ui_text['step1']}</h2>"),
582
  gr.update(placeholder=ui_text['input_placeholder'], rtl=not is_english),
583
  gr.update(value=f"🚀 {ui_text['process_btn']}"),
584
  gr.update(value=f"🗑️ {ui_text['clear_btn']}"),
 
693
 
694
  with gr.Row(elem_classes="workflow rtl") as workflow_row:
695
  with gr.Column():
696
+ step1_title = gr.HTML('<h2 style="direction: rtl;">📝 متن ورودی و تنظیمات</h2>')
697
 
698
  input_text = gr.Textbox(
699
  lines=15,
 
791
  )
792
 
793
  if __name__ == "__main__":
794
+ # تست سیستم با نمونه‌های ذکر شده
795
+ test_text = """مهدی اخوان بهابادی در مجمع عمومی عادی سالیانه اعلام کرد درآمد عملیاتی شرکت اصلی به 178 میلیارد تومانی رسیده است.
796
+ در خودروسازان حالا از مرز 305 همت عبور کرده و در سال گذشته سود عملیاتی داشته اما زیان انباشته این شرکت 7.6 همت زیاد شده است.
797
+ تولید محصولات گرم این شرکت به 1000 هزار تن و محصولات سرد به 1378 هزار تن رسید.
798
+ شرکت سرمایه گذاری پارسیان سود خوبی را نشان داد. بانک پارسیان و گروه مالی پارسیان هم عملکرد مثبتی داشتند."""
799
 
800
  anonymizer_test = UniversalAnonymizer()
801
  result = anonymizer_test.anonymize_text(test_text)
 
805
  for original, code in anonymizer_test.mapping_table.items():
806
  print(f"{original} -> {code}")
807
 
808
+ app.launch()