apak commited on
Commit
40f29ea
·
verified ·
1 Parent(s): faaf135

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +69 -49
app.py CHANGED
@@ -4,9 +4,13 @@ from transformers import pipeline
4
  import gradio as gr
5
  import os
6
 
 
 
 
 
7
  # --- 1. İlk Tarama Modeli (Hızlı NER) ---
8
  # XLM-Roberta çok dillidir ve standart olarak PER, LOC, ORG, MISC etiketleri üretir.
9
- print("1. Standart NER Modeli yükleniyor...")
10
  # NER modelini yüklerken, cihazı açıkça belirterek Gradio'nun başlangıç aşamalarında oluşabilecek hataları azaltıyoruz.
11
  ner_pipe = pipeline(
12
  "ner",
@@ -16,7 +20,7 @@ ner_pipe = pipeline(
16
  )
17
 
18
  # --- 2. Akıl Yürütme Modeli (LLM - RAG Karar Verici) ---
19
- print("2. LLM (Karar Verici) yükleniyor...")
20
  model_id = "Qwen/Qwen2.5-1.5B-Instruct" # Türkçe yeteneği iyi ve hızlı
21
  llm_model_kwargs = {}
22
 
@@ -24,9 +28,9 @@ llm_model_kwargs = {}
24
  if torch.cuda.is_available():
25
  llm_model_kwargs["torch_dtype"] = torch.bfloat16
26
  llm_device_map = "auto"
27
- print("CUDA desteği bulundu, model GPU üzerinde bfloat16 ile yüklenecek.")
28
  else:
29
- print("CUDA desteği bulunamadı, model CPU üzerinde float32 ile yüklenecek.")
30
  llm_device_map = "cpu" # Açıkça CPU'ya ayarlandı
31
 
32
  try:
@@ -37,12 +41,12 @@ try:
37
  device_map=llm_device_map
38
  )
39
  except Exception as e:
40
- print(f"❌ LLM yüklenirken bir hata oluştu (Muhtemelen Bellek Yetersizliği/OOM): {e}")
41
  # Olası bir çökme durumunu önlemek için alternatif bir çözüm ekleyin
42
  gen_pipe = None
43
- print("LLM boru hattı devre dışı bırakıldı. Uygulama sadece temel NER yapacaktır.")
44
 
45
- print("✅ Modeller Hazır!")
46
 
47
  # --- Wikipedia Fonksiyonu ---
48
  wikipedia.set_lang("tr")
@@ -58,7 +62,7 @@ def get_wiki_summary(term):
58
  except wikipedia.exceptions.RedirectError:
59
  return None
60
  except Exception as e:
61
- print(f"Wikipedia hatası: {e}")
62
  return None
63
 
64
  # --- LLM ile Etiket Rafine Etme Fonksiyonu ---
@@ -74,28 +78,30 @@ def refine_label_with_llm(entity_text, wiki_context, custom_label_definitions):
74
 
75
  # LLM için örnekler (Few-shot learning)
76
  # Yeni etiketleri kapsayacak şekilde örnekler güncellendi.
 
77
  few_shot_examples = """ÖRNEK 1 (NORP İÇİN):
78
  VARLIK: Türk
79
  BAĞLAM: Türkler, Türkiye Cumhuriyeti'nde yaşayan ve Türkçe konuşan büyük bir etnik gruptur. (NORP tanımı ile eşleşir.)
80
  SONUÇ: NORP
81
 
82
- ÖRNEK 2 (MOVIE İÇİN):
83
- VARLIK: Yüzüklerin Efendisi
84
- BAĞLAM: Peter Jackson tarafından yönetilmiş, 2001-2003 yılları arasında yayınlanan üç fantastik macera filminden oluşan seridir. (MOVIE tanımı ile eşleşir.)
85
- SONUÇ: MOVIE
86
 
87
  ÖRNEK 3 (EVENT İÇİN):
88
- VARLIK: Kurtuluş Savaşı
89
- BAĞLAM: Türkiye Cumhuriyeti'nin kurulmasına yol açan, 1919-1922 yılları arasında Türk ulusal güçlerinin işgalci devletlere karşı verdiği mücadeledir. (EVENT tanımı ile eşleşir.)
90
  SONUÇ: EVENT
91
  """
92
 
93
  prompt = f"""Sen uzman bir veri sınıflandırma sistemisin.
94
- Görevin, aşağıdaki BAĞLAM'ı okumak ve ETİKET TANIMLARI'ndan hangisinin varlığa en uygun olduğunu belirlemektir.
95
  Aşağıdaki adımları izle:
96
  1. BAĞLAM'ı analiz et.
97
  2. ETİKET TANIMLARI ile karşılaştır.
98
  3. BULDUĞUN EŞLEŞMEYİ VE SEÇİMİ ÇIKTI FORMATINA UYGUN OLARAK VER.
 
99
 
100
  {few_shot_examples}
101
 
@@ -115,7 +121,7 @@ Cevap: [SEÇİLEN ETİKET]
115
  # LLM çağrısı
116
  outputs = gen_pipe(
117
  messages,
118
- max_new_tokens=50, # Yeterince kısa tutuldu
119
  do_sample=False,
120
  temperature=0.1
121
  )
@@ -134,9 +140,11 @@ Cevap: [SEÇİLEN ETİKET]
134
  if raw_label in valid_labels:
135
  final_label = raw_label
136
  else:
137
- print(f"❌ Uyarı: LLM geçersiz etiket döndürdü: {raw_label}. MISC olarak ayarlandı.")
 
138
  except IndexError:
139
- print(f"❌ Uyarı: LLM çıktı formatını bozdu. Ham çıktı: {full_output[:50]}...")
 
140
  final_label = "MISC"
141
 
142
  return final_label
@@ -147,7 +155,8 @@ def advanced_ner_pipeline(text, target_labels, progress=gr.Progress()):
147
  Standart NER modelini çalıştırır, MISC etiketli varlıklar için
148
  Wikipedia ve LLM kullanarak zenginleştirme (RAG) yapar.
149
  """
150
- log_messages = []
 
151
 
152
  try:
153
  initial_results = ner_pipe(text)
@@ -162,6 +171,7 @@ def advanced_ner_pipeline(text, target_labels, progress=gr.Progress()):
162
  log_messages.append(f"🕵️‍♀️ Toplam {total_entities} varlık inceleniyor...")
163
 
164
  # İlk yield (2 değer)
 
165
  yield log_messages, None
166
 
167
  for i, entity in enumerate(initial_results):
@@ -211,18 +221,34 @@ def advanced_ner_pipeline(text, target_labels, progress=gr.Progress()):
211
  # Sonuçlar hazır olduğunda final_results'ı gönder
212
  yield log_messages, final_results # Nihai loglar ve sonuçlar (2 değer)
213
 
214
- # --- Özel Etiket Tanımları (Güncellendi) ---
215
  custom_label_definitions = {
216
- "BOOK": "Yazılı veya basılı bir eser, yayınlanmış roman, ders kitabı, ansiklopedi.",
 
 
 
 
 
 
 
 
 
 
 
 
 
217
  "MOVIE": "Sinema filmi, dizi, belgesel gibi görsel-işitsel yapıt.",
218
  "SONG": "Müzik eseri, şarkı, beste veya albüm adı.",
219
- "AWARD": "Bir başarı, katkı veya üstünlük karşılığında verilen ödül, madalya veya nişan. (Örnek: Nobel, Oscar, Altın Küre, Film Festivali Ödülü)",
220
- "SOFTWARE": "Bilgisayar programları, mobil uygulamalar, yapay zeka sistemleri veya işletim sistemleri gibi dijital araçlar.",
221
- "PRODUCT": "Ticari olarak satılan somut bir eşya, model, cihaz veya marka serisi. (Örnek: Araba modeli, telefon serisi)",
222
- "NORP": "Milliyetler, dini veya politik gruplar. (Örnek: Türk, Hristiyan, Sosyalist Parti)",
223
- "EVENT": "Tarihi olaylar, savaşlar, festivaller, spor turnuvaları, doğal afetler veya kurumsal etkinlikler.",
224
- "LAW": "Resmi kanun, yönetmelik, anlaşma veya hukuki belge adı. (Örnek: TCK, AB Sözleşmesi)",
225
- "ORG_SUB": "Şirket birimleri, dernek şubeleri, üniversite fakülteleri gibi büyük bir kurumun alt birimleri."
 
 
 
226
  }
227
 
228
  # --- Gradio Arayüzü Fonksiyonu (Düzeltilmiş ve Birleştirilmiş) ---
@@ -234,11 +260,9 @@ def process_ner_request(text, progress=gr.Progress()):
234
  all_logs = []
235
  final_results = None
236
 
237
- # HATA GİDERİLDİ: advanced_ner_pipeline'dan sadece 2 değer (logs, results) bekleniyor.
238
  for logs_step, results_step in advanced_ner_pipeline(text, custom_label_definitions, progress=progress):
239
  all_logs = logs_step # Her adımda güncel logları al
240
 
241
- # Sonuçlar (liste) boş değilse final_results'a ata
242
  if results_step is not None:
243
  final_results = results_step
244
 
@@ -291,19 +315,17 @@ def process_ner_request(text, progress=gr.Progress()):
291
  current_results_html += " <th>KAYNAK</th>\n"
292
  current_results_html += " </tr>\n"
293
  for item in final_results:
294
- # Etiket renklendirmesi için basit bir mantık (Yeni etiketler eklendi)
295
  color_map = {
296
- "MISC": "background-color: #fef08a; padding: 4px; border-radius: 4px;", # Yellow (Çeşitli)
297
- "SOFTWARE": "background-color: #d1fae5; padding: 4px; border-radius: 4px;", # Green (Yazılım)
298
- "AWARD": "background-color: #fee2e2; padding: 4px; border-radius: 4px;", # Red (Ödül)
299
- "MOVIE": "background-color: #c7d2fe; padding: 4px; border-radius: 4px;", # Indigo (Film)
300
- "PRODUCT": "background-color: #fbcfe8; padding: 4px; border-radius: 4px;", # Pink (Ürün)
301
- "NORP": "background-color: #bfdbfe; padding: 4px; border-radius: 4px;", # Light Blue (Grup/Milliyet)
302
- "BOOK": "background-color: #ffedd5; padding: 4px; border-radius: 4px;", # Light Orange (Kitap)
303
- "SONG": "background-color: #e9d5ff; padding: 4px; border-radius: 4px;", # Light Purple (Şarkı)
304
- "EVENT": "background-color: #a7f3d0; padding: 4px; border-radius: 4px;", # Teal (Etkinlik)
305
- "LAW": "background-color: #d1d5db; padding: 4px; border-radius: 4px;", # Gray (Hukuk)
306
- "ORG_SUB": "background-color: #ccfbf1; padding: 4px; border-radius: 4px;", # Cyan (Kurum Alt Birimi)
307
  }
308
  final_label_style = color_map.get(item['final_label'], "")
309
 
@@ -324,16 +346,14 @@ iface = gr.Interface(
324
  inputs=gr.Textbox(lines=5, placeholder="Metin giriniz...", label="Giriş Metni"),
325
  # Çıktı olarak 2 ayrı HTML bileşeni döndürülmeli.
326
  outputs=[gr.HTML(label="İşlem Logları"), gr.HTML(label="Zenginleştirilmiş NER Sonuçları")],
327
- title="Gelişmiş İnce Taneli NER (RAG/LLM Destekli)",
328
- description="Metindeki MISC etiketli varlıkları tanır ve özel kategorilere dönüştürmek için Wikipedia (RAG) ve LLM (Qwen2.5-1.5B) kullanılmaktadır. Etiket seti 10 özel kategoriye genişletilmiştir.",
329
  examples=[
330
  # Yeni etiketleri test eden örnekler eklendi
331
- ["Milli Eğitim Bakanlığı'na bağlı Lise Birimleri, 2024 Türkiye Kupası etkinliğine katılacak."],
332
- ["Türkiye Cumhuriyeti Anayasası'nda yapılan bu değişiklikler, 'Son Mektup' şarkısının telif haklarını etkiledi."],
333
- ["Rus askerleri Yüzüklerin Efendisi filmini izlemiş ve NUTUK kitabını okumuş. Vedat Kara, Hababam Sınıfı, Altın Portakal ödülünü kazandı"],
334
- ["Microsoft tarafından geliştirilen Windows 11 işletim sistemi, Macbook Pro cihazlarında çalıştırılamaz."]
335
  ],
336
- # allow_flagging parametresi kaldırıldı.
337
  analytics_enabled=False
338
  )
339
 
 
4
  import gradio as gr
5
  import os
6
 
7
+ # --- Global Log Listesini Tanımla ---
8
+ # Başlangıçtaki model yükleme mesajlarını Gradio UI'a aktarmak için bu listeyi kullanıyoruz.
9
+ _initial_logs = []
10
+
11
  # --- 1. İlk Tarama Modeli (Hızlı NER) ---
12
  # XLM-Roberta çok dillidir ve standart olarak PER, LOC, ORG, MISC etiketleri üretir.
13
+ _initial_logs.append("1. Standart NER Modeli yükleniyor...")
14
  # NER modelini yüklerken, cihazı açıkça belirterek Gradio'nun başlangıç aşamalarında oluşabilecek hataları azaltıyoruz.
15
  ner_pipe = pipeline(
16
  "ner",
 
20
  )
21
 
22
  # --- 2. Akıl Yürütme Modeli (LLM - RAG Karar Verici) ---
23
+ _initial_logs.append("2. LLM (Karar Verici) yükleniyor...")
24
  model_id = "Qwen/Qwen2.5-1.5B-Instruct" # Türkçe yeteneği iyi ve hızlı
25
  llm_model_kwargs = {}
26
 
 
28
  if torch.cuda.is_available():
29
  llm_model_kwargs["torch_dtype"] = torch.bfloat16
30
  llm_device_map = "auto"
31
+ _initial_logs.append("CUDA desteği bulundu, model GPU üzerinde bfloat16 ile yüklenecek.")
32
  else:
33
+ _initial_logs.append("CUDA desteği bulunamadı, model CPU üzerinde float32 ile yüklenecek.")
34
  llm_device_map = "cpu" # Açıkça CPU'ya ayarlandı
35
 
36
  try:
 
41
  device_map=llm_device_map
42
  )
43
  except Exception as e:
44
+ _initial_logs.append(f"❌ LLM yüklenirken bir hata oluştu (Muhtemelen Bellek Yetersizliği/OOM): {e}")
45
  # Olası bir çökme durumunu önlemek için alternatif bir çözüm ekleyin
46
  gen_pipe = None
47
+ _initial_logs.append("LLM boru hattı devre dışı bırakıldı. Uygulama sadece temel NER yapacaktır.")
48
 
49
+ _initial_logs.append("✅ Modeller Hazır!")
50
 
51
  # --- Wikipedia Fonksiyonu ---
52
  wikipedia.set_lang("tr")
 
62
  except wikipedia.exceptions.RedirectError:
63
  return None
64
  except Exception as e:
65
+ # Bu loglar konsola düşer, ancak UI log akışına dahil edilmez.
66
  return None
67
 
68
  # --- LLM ile Etiket Rafine Etme Fonksiyonu ---
 
78
 
79
  # LLM için örnekler (Few-shot learning)
80
  # Yeni etiketleri kapsayacak şekilde örnekler güncellendi.
81
+ # LLM'in bu kadar çok etiket arasından doğru olanı bulması için iyi örnekler şart.
82
  few_shot_examples = """ÖRNEK 1 (NORP İÇİN):
83
  VARLIK: Türk
84
  BAĞLAM: Türkler, Türkiye Cumhuriyeti'nde yaşayan ve Türkçe konuşan büyük bir etnik gruptur. (NORP tanımı ile eşleşir.)
85
  SONUÇ: NORP
86
 
87
+ ÖRNEK 2 (TITLE İÇİN):
88
+ VARLIK: General
89
+ BAĞLAM: Birçok orduda yüksek rütbeli bir subay unvanıdır. Türkiye'de en yüksek rütbelerden biridir. (TITLE tanımı ile eşleşir.)
90
+ SONUÇ: TITLE
91
 
92
  ÖRNEK 3 (EVENT İÇİN):
93
+ VARLIK: İstanbul Film Festivali
94
+ BAĞLAM: Her yıl Nisan ayında İstanbul'da düzenlenen uluslararası film festivalidir. Türkiye'nin en eski ve prestijli film etkinliklerinden biridir. (EVENT tanımı ile eşleşir.)
95
  SONUÇ: EVENT
96
  """
97
 
98
  prompt = f"""Sen uzman bir veri sınıflandırma sistemisin.
99
+ Görevin, aşağıdaki BAĞLAM'ı okumak ve ETİKET TANIMLARI'ndan (MISC etiketini göz ardı et) hangisinin varlığa en uygun olduğunu belirlemektir.
100
  Aşağıdaki adımları izle:
101
  1. BAĞLAM'ı analiz et.
102
  2. ETİKET TANIMLARI ile karşılaştır.
103
  3. BULDUĞUN EŞLEŞMEYİ VE SEÇİMİ ÇIKTI FORMATINA UYGUN OLARAK VER.
104
+ Eğer tanımlardan hiçbiri uymuyorsa Cevap: MISC olarak döndür.
105
 
106
  {few_shot_examples}
107
 
 
121
  # LLM çağrısı
122
  outputs = gen_pipe(
123
  messages,
124
+ max_new_tokens=60, # Daha fazla etiket arasında ayrım için token sayısını artırdık.
125
  do_sample=False,
126
  temperature=0.1
127
  )
 
140
  if raw_label in valid_labels:
141
  final_label = raw_label
142
  else:
143
+ # LLM'in konsol loglarını kaldırdık
144
+ pass
145
  except IndexError:
146
+ # LLM'in konsol loglarını kaldırdık
147
+ pass
148
  final_label = "MISC"
149
 
150
  return final_label
 
155
  Standart NER modelini çalıştırır, MISC etiketli varlıklar için
156
  Wikipedia ve LLM kullanarak zenginleştirme (RAG) yapar.
157
  """
158
+ # İlk adımda, global başlangıç loglarını log_messages'a ekle.
159
+ log_messages = list(_initial_logs)
160
 
161
  try:
162
  initial_results = ner_pipe(text)
 
171
  log_messages.append(f"🕵️‍♀️ Toplam {total_entities} varlık inceleniyor...")
172
 
173
  # İlk yield (2 değer)
174
+ # Bu, model yükleme loglarını Gradio arayüzüne ilk kez gönderir.
175
  yield log_messages, None
176
 
177
  for i, entity in enumerate(initial_results):
 
221
  # Sonuçlar hazır olduğunda final_results'ı gönder
222
  yield log_messages, final_results # Nihai loglar ve sonuçlar (2 değer)
223
 
224
+ # --- Özel Etiket Tanımları (23 Etikete Genişletildi) ---
225
  custom_label_definitions = {
226
+ # Standart CoNLL-2003 etiketleri (LLM tarafından rafine edilmez, ancak sonuçta görünür)
227
+ "PER": "Kişi adları, takma adlar, ünlüler.",
228
+ "ORG": "Şirketler, kurumlar, hükümet kuruluşları.",
229
+ "LOC": "Coğrafi yerler, siyasi bölgeler, binalar.",
230
+ # MISC içinden rafine edilecek ince taneli etiketler (Toplam 19 adet)
231
+ "DATE": "Mutlak veya göreceli tarih ifadeleri (yıl, ay, gün).",
232
+ "TIME": "Günün saati, zaman aralığı.",
233
+ "MONEY": "Parasal değerler, para birimleri.",
234
+ "QUANTITY": "Ağırlık, uzunluk, hacim gibi ölçü birimleri ve sayısal değerler.",
235
+ "PERCENT": "Yüzdelik ifadeler.",
236
+ "NORP": "Milliyetler, etnik, dini veya politik gruplar.",
237
+ "LAW": "Resmi kanun, yasa, yönetmelik veya hukuki belge adı.",
238
+ "EVENT": "Savaşlar, festivaller, spor turnuvaları, doğal afetler veya kurumsal etkinlikler.",
239
+ "BOOK": "Yazılı veya basılı bir eser, yayınlanmış roman, ders kitabı.",
240
  "MOVIE": "Sinema filmi, dizi, belgesel gibi görsel-işitsel yapıt.",
241
  "SONG": "Müzik eseri, şarkı, beste veya albüm adı.",
242
+ "ART": "Resim, heykel, spesifik mimari eser adı (Örn: Mona Lisa).",
243
+ "AWARD": "Ödül, madalya veya nişan adı (Örn: Nobel, Oscar).",
244
+ "PRODUCT": "Ticari olarak satılan somut bir eşya, model, cihaz veya marka serisi (Örn: iPhone 15 Pro, Mercedes C200).",
245
+ "SOFTWARE": "Bilgisayar programları, mobil uygulamalar, yapay zeka sistemleri, işletim sistemleri.",
246
+ "ORG_SUB": "Şirket birimleri, üniversite fakülteleri, dernek şubeleri gibi büyük bir kurumun alt birimleri.",
247
+ "LANGUAGE": "Dillerin adı (Örn: İngilizce, Arapça).",
248
+ "TITLE": "Kişinin unvanı, rütbesi veya pozisyonu (Örn: Profesör, General, Başkan).",
249
+ "CYBER": "URL, E-posta adresi, IP adresi, hashtag veya kullanıcı adı.",
250
+ # MISC: Kalan her şey
251
+ "MISC": "Diğer adlandırılmış varlıklar (LLM tarafından rafine edilemeyen veya uymayanlar)."
252
  }
253
 
254
  # --- Gradio Arayüzü Fonksiyonu (Düzeltilmiş ve Birleştirilmiş) ---
 
260
  all_logs = []
261
  final_results = None
262
 
 
263
  for logs_step, results_step in advanced_ner_pipeline(text, custom_label_definitions, progress=progress):
264
  all_logs = logs_step # Her adımda güncel logları al
265
 
 
266
  if results_step is not None:
267
  final_results = results_step
268
 
 
315
  current_results_html += " <th>KAYNAK</th>\n"
316
  current_results_html += " </tr>\n"
317
  for item in final_results:
318
+ # Etiket renklendirmesi için basit bir mantık (23 etiket için rastgele renkler atandı)
319
  color_map = {
320
+ "PER": "background-color: #f8c291;", "LOC": "background-color: #a2c4c9;", "ORG": "background-color: #b3c99f;",
321
+ "MISC": "background-color: #fef08a;",
322
+ "DATE": "background-color: #e5ccff;", "TIME": "background-color: #d1d5db;", "MONEY": "background-color: #fcd34d;",
323
+ "QUANTITY": "background-color: #bfdbfe;", "PERCENT": "background-color: #99f6e4;", "NORP": "background-color: #fbcfe8;",
324
+ "LAW": "background-color: #f0abfc;", "EVENT": "background-color: #a7f3d0;", "BOOK": "background-color: #ffedd5;",
325
+ "MOVIE": "background-color: #c7d2fe;", "SONG": "background-color: #e9d5ff;", "ART": "background-color: #bae6fd;",
326
+ "AWARD": "background-color: #fee2e2;", "PRODUCT": "background-color: #ffc999;", "SOFTWARE": "background-color: #d1fae5;",
327
+ "ORG_SUB": "background-color: #ccfbf1;", "LANGUAGE": "background-color: #fef9c3;", "TITLE": "background-color: #fecaca;",
328
+ "CYBER": "background-color: #dbeafe;"
 
 
329
  }
330
  final_label_style = color_map.get(item['final_label'], "")
331
 
 
346
  inputs=gr.Textbox(lines=5, placeholder="Metin giriniz...", label="Giriş Metni"),
347
  # Çıktı olarak 2 ayrı HTML bileşeni döndürülmeli.
348
  outputs=[gr.HTML(label="İşlem Logları"), gr.HTML(label="Zenginleştirilmiş NER Sonuçları")],
349
+ title="Gelişmiş İnce Taneli NER (23 Etiket - RAG/LLM Destekli)",
350
+ description="Metindeki varlıkları tanır ve MISC etiketlileri, 23 ince taneli kategoriye dönüştürmek için Wikipedia (RAG) ve LLM (Qwen2.5-1.5B) kullanılmaktadır. Etiket seti, akademik çalışmalardan esinlenerek 23 özel kategoriye genişletilmiştir.",
351
  examples=[
352
  # Yeni etiketleri test eden örnekler eklendi
353
+ ["Milli Eğitim Bakanlığı'na bağlı Lise Birimleri, 2024 Türkiye Kupası etkinliğine katılacak ve %15 indirim uygulayacak."],
354
+ ["General Vural, Türkçe dilini kullanan Türk askerlerini, https://example.com üzerinden uyardı. 'Hürriyet Kasidesi' eserini okudu."],
355
+ ["Windows 11 işletim sistemi, 1000 TL karşılığında satışa sunulmuştur. 'Cumhurbaşkanı' unvanına sahip kişi, Kanun maddesini değiştirdi."],
 
356
  ],
 
357
  analytics_enabled=False
358
  )
359