@אדם אתה מבין שאתה לא יכול לתת אמון במערכת שפתאום מתחילים לקרות כל מיני קריסות מוזרות ואין לך יכולת לגבות את המערכת
ומי יודע מה יהיה עוד חודש?
הפוסטים הטובים ביותר שנוצרו על ידי BEN ZION
-
RE: פילטר הפניה עם API
@אביי-ורבא אתה משתמש כשלוחה? או כהטמעה בכל מודול?
לפי התיעוד GOTO זה רק כמודול בפני עצמו,
כהטמעה ניתן להחזיר רקOK = ממשיך מיד לשלוחה בצורה רגילה
NO = יוצא מהשלוחה עם הודעה M1102 אין לכם הרשאת גישה לתיקיה זו
Out = יוצא מהשלוחה ללא הודעה
-
RE: האם זה "מוזר" לכתוב כל כך טוב?
@מוזר אני אוהב את הסגנון שאתה כותב לי אין סבלנות לעשות את זה אבל באמת אם כל אחד היה חושב לפני שהוא כותב, הרבה שאלות לא היו כי היה יותר קל למצוא תשובות מפוסטים שכבר נכתבו
תודה על ההשקעה ועל ההערכה מערכים מאד

-
קוד לספר טלפונים אם זיהוי דיבור
קרדיט ל @איל-משולש חלק מהקוד ממנו והרעיון כולו שלו
מצרף קוד לאלפון אם זיהוי דיבור הקוד מבוסס על תרגום גוגל קלוד הוא לוקח את השמות מרשימת תפוצה
הקוד לשרת<?php ob_start(); require __DIR__ . '/vendor/autoload.php'; use Google\Cloud\Speech\V1\SpeechClient; use Google\Cloud\Speech\V1\RecognitionConfig; use Google\Cloud\Speech\V1\RecognitionConfig\AudioEncoding; use Google\Cloud\Speech\V1\RecognitionAudio; /* ---------------- 1. פונקציות עזר ---------------- */ function normalizeText($text) { $text = mb_strtolower($text, 'UTF-8'); $text = preg_replace('/[^\p{Hebrew}\p{Latin}\s]/u', '', $text); return trim(preg_replace('/\s+/', ' ', $text)); } function smartNameMatchScore($transcript, $nameTemplate) { $wordsTranscript = explode(' ', normalizeText($transcript)); $wordsTemplate = explode(' ', normalizeText($nameTemplate)); $scoreFamily = 0; // משקל 55 $bestNameMatch = 0; // השם הכי חזק יקבל 35 $secondBestName = 0; // השם הבא בתור יקבל 10 $familyWord = $wordsTemplate[0] ?? ''; $givenNamesTemplate = []; if (isset($wordsTemplate[1])) $givenNamesTemplate[] = $wordsTemplate[1]; if (isset($wordsTemplate[2])) $givenNamesTemplate[] = $wordsTemplate[2]; foreach ($wordsTranscript as $wordUser) { // בדיקת שם משפחה similar_text($wordUser, $familyWord, $pFamily); if ($pFamily > $scoreFamily) $scoreFamily = $pFamily; // בדיקה דינמית מול השמות הפרטיים foreach ($givenNamesTemplate as $templateName) { similar_text($wordUser, $templateName, $pName); if ($pName > $bestNameMatch) { $secondBestName = $bestNameMatch; $bestNameMatch = $pName; } elseif ($pName > $secondBestName) { $secondBestName = $pName; } } } $finalScore = ($scoreFamily * 0.55) + ($bestNameMatch * 0.35) + ($secondBestName * 0.10); // חסימה אם לא נאמר שם פרטי ברור (מונע זיהוי שגוי של משפחה בלבד) if ($bestNameMatch < 70) { $finalScore = min($finalScore, 68); } return $finalScore; } /* ---------------- 2. ניהול תיקיות ---------------- */ $callId = $_GET['ApiCallId'] ?? 'unknown'; $cacheDir = __DIR__ . '/people_cache'; $logDir = __DIR__ . '/logs'; if (!is_dir($cacheDir)) @mkdir($cacheDir, 0775, true); if (!is_dir($logDir)) @mkdir($logDir, 0775, true); $sessionFile = $cacheDir . '/session_' . $callId . '.json'; $token = $_GET['token'] ?? ''; $call = $_GET['call'] ?? ''; $exit = $_GET['exit'] ?? ''; /* ---------------- 3. טיפול בהקשות (MySelection) ---------------- */ if (isset($_GET['MySelection'])) { $choice = trim($_GET['MySelection']); $sessionData = file_exists($sessionFile) ? json_decode(file_get_contents($sessionFile), true) : []; ob_end_clean(); header('Content-Type: text/plain; charset=utf-8'); if ($choice == '1') { $txt = $sessionData['full_text'] ?? "אין נתונים לשמיעה חוזרת"; die("read=t-$txt=MySelection,no,1,1,7,no,no,no,,1.2.3.4,,,,,no"); } elseif ($choice == '2') { $phone = $sessionData['phone'] ?? ''; if ($phone && $token) { $updateUrl = "https://www.call2all.co.il/ym/api/UpdateExtension?token=" . urlencode($token) . "&path=ivr2:/15/NIT&type=nitoviya&nitoviya_dial_to=" . urlencode($phone); @file_get_contents($updateUrl); } @unlink($sessionFile); die("go_to_folder=NIT"); } elseif ($choice == '3') { @unlink($sessionFile); die($_GET['call'] ?? ''); } elseif ($choice == '4') { @unlink($sessionFile); die($_GET['exit'] ?? ''); } exit; } /* ---------------- 4. תמלול וחיפוש ---------------- */ $rapi = $_GET['rapi'] ?? ''; $templateId = $_GET['templateId'] ?? ''; if (!$token || !$rapi) exit; $downloadUrl = "https://www.call2all.co.il/ym/api/DownloadFile?token=" . urlencode($token) . "&path=ivr2:" . urlencode($rapi); $audioData = @file_get_contents($downloadUrl); $transcriptText = ''; if ($audioData) { try { $client = new SpeechClient(['credentials' => __DIR__ . '/key.json']); $audio = (new RecognitionAudio())->setContent($audioData); $config = (new RecognitionConfig())->setEncoding(AudioEncoding::LINEAR16)->setLanguageCode('he-IL'); $response = $client->recognize($config, $audio); foreach ($response->getResults() as $result) { $alt = $result->getAlternatives(); if (!empty($alt[0])) $transcriptText .= $alt[0]->getTranscript() . " "; } } catch (Exception $e) { ob_end_clean(); die('go_to_folder=/95'); } finally { if (isset($client)) $client->close(); } } $normalized = normalizeText($transcriptText); if (!$normalized) { ob_end_clean(); die('go_to_folder=/95'); } /* בדיקה ב-Cache */ $transcriptKey = md5($normalized); $fastCacheFile = $cacheDir . '/fast_text_' . $transcriptKey . '.json'; $matchedEntry = null; $bestScore = 0; $source = "Cache"; if (file_exists($fastCacheFile)) { $matchedEntry = json_decode(file_get_contents($fastCacheFile), true); $bestScore = 100; } else { $source = "New Search"; $templateUrl = "https://www.call2all.co.il/ym/api/GetTemplateEntries?token=" . urlencode($token) . "&templateId=" . urlencode($templateId); $templateData = json_decode(@file_get_contents($templateUrl), true); if (isset($templateData['entries'])) { foreach ($templateData['entries'] as $entry) { $score = smartNameMatchScore($normalized, $entry['name'] ?? ''); if ($score > $bestScore) { $bestScore = $score; $matchedEntry = $entry; } } } if ($matchedEntry && $bestScore >= 75) { file_put_contents($fastCacheFile, json_encode($matchedEntry + ['transcript' => $transcriptText], JSON_UNESCAPED_UNICODE)); } } /* ---------------- 5. שמירת לוג לבקרה מורחבת ---------------- */ $logContent = "--- [" . date('Y-m-d H:i:s') . "] ---\n"; $logContent .= "Call ID: $callId\n"; $logContent .= "Audio Path (rapi): $rapi\n"; $logContent .= "Transcript: $transcriptText\n"; $logContent .= "Source: $source\n"; if ($matchedEntry) { $logContent .= "Matched Name: " . ($matchedEntry['name'] ?? 'N/A') . " (" . round($bestScore, 2) . "%)\n"; $logContent .= "Result: SUCCESS\n"; } else { $logContent .= "Best Score Found: " . round($bestScore, 2) . "%\n"; $logContent .= "Result: FAILED\n"; } $logContent .= "---------------------------\n\n"; file_put_contents($logDir . '/audit_log_' . date('Y-m') . '.txt', $logContent, FILE_APPEND); /* ---------------- 6. פלט סופי ---------------- */ ob_end_clean(); header('Content-Type: text/plain; charset=utf-8'); if ($matchedEntry && $bestScore >= 75) { $name = $matchedEntry['name'] ?? ''; $phone = $matchedEntry['phone'] ?? ''; $info = $matchedEntry['moreinfo'] ?? 'אין מידע נוסף'; $cleanInfo = str_replace([',', '=', '.', '"', "'"], ' ', $info); $fullSayText = "נמצאו פרטים עבור $name טלפון $phone כתובת $cleanInfo לשמיעה חוזרת הקישו 1, לחיוג הקישו 2, לחיפוש חדש הקישו 3, לביטול וחזרה הקש 4"; file_put_contents($sessionFile, json_encode(['full_text' => $fullSayText, 'phone' => $phone], JSON_UNESCAPED_UNICODE)); echo "read=t-$fullSayText=MySelection,no,1,1,7,no,no,no,,1.2.3.4,,,,,no"; } else { echo 'go_to_folder=/95'; } exit;הקוד עבר עדכון החיפוש יותר חכם
אצלי מוגדר בשגיאה מעבר לשלוחה 95 שזה ניתוק
ההגדרות בשלוחהtype=api title=אלפון קהילה api_link=קישור לשרת api_add_0=token=טוקן אני השתמשתי בחדש api_add_1=templateId=מזהה רשימת תפוצה api_add_2=call=go_to_folder=/נתיב השלוחה לחיפוש חוזר api_add_3=exit=go_to_folder=/נתיב השלוחה לביטול וחזרה אצלי זה בתוך מערכת וואצפון זה מחזיר למערכת api_000=rapi,,record,/15/api,,no api_hangup_send=no api_phone_send=no api_did_send=no api_enter_id_send=no api_enter_id_name_send=no api_time_send=no api_call_id_send=yesהקוד שומר כל זיהוי טקסט שנמצא אם הטלפון והמידע הנוסף ככה בפעמים הבאות הוא לא צריך לחפש ברשימה אלא שולף מהזיכרון יש 4 אופציות שמיעה חוזרת, חיוג, חיפוש חדש, ביטול וחזרה
אשמח לקבל הערות והארותאם מישהו יוכל להגדיר תמלול בגימיני ושישלחו מפתח גימני אני אולי אפרסם קישור פתוח לתועלת הציבור
-
RE: מהפך במנוע הצינתוקים
@יהודה-צ.-כ. בדקתי עכשיו זה יפה שהם מייעלים את המערכת אבל זה יוצר מלא בעיות אני לא מבין למה אפילו לא חשבו לעדכן דבר כזה אני נותן לאנשים מס' משנה למערכת בידיעה שהם מוגבלים לשלוחה שזה מכניס אותם ופתאום אם הם עונים לצינתוק הם יכולים לשוטט במרחבי הקו להנאתם ולהגיע לתכנים שהם לא אמורים להגיע
אני לא יודע מי אחראי על הפיתוח @ימות-המשיח @שמואל חשוב מאוד לעשות דרך שצינתוק שנשלח מזיהוי משני במענה זה יהיה כאילו חייגו אליו ויפעל לפי ההגדרות של הניתוב שלו ולא יגיע לשלוחה ראשית
פוסטים אחרונים שנוצרו על ידי BEN ZION
-
RE: ביטול אפשרות שמקליטים ישמעו הקלטות קודמות של אחרים
@תיכון-מ.ר. מוגדר שבסיום ההקלטה עובר לתיקייה בה נשמרים ההקלטות לכן ניתן לשמוע ניתן להעביר בסיום ההקלטה לשלוחה אחרת
ההגדרה הראשונה אם הנתיב זה לאן להעביר את המשתמש בסיום הקלטה
ההגדרה השניה היא באיזה תיקיה לשמור את ההודעות -
RE: צפייה ברשימות צינתוקים בהקלדת list_tzintuk=
@uytrn אני חושב ששימושי לפעמים אתה טועה תוך כדי הקלדה במקום זה מופיע לך רשימה חזק וברוך על התוסף מה עושים אם הקובץ שהעלת?
-
RE: עזרה בקו משפחתי
@בית-המדרש בשלוחה 1 הגדרת אותה כתפריט ויצרת בתוכה שתי שלוחות פנימיות שלוחה 1 צריכה להיות השמעת קבצים
-
RE: צפייה ברשימות צינתוקים בהקלדת list_tzintuk=
הקוד עודכן עכשיו גם בפילטר לפי רשימת צינתוקים נפתח הרשימה ואם רוצים פילטר לכמה רשימות אחרי ה , שוב יופיע הרשימות לבחירה
-
RE: שלוחה 10 11
@יוסי-מהמרכז לא קרה להודעות כלום הרגע ששינתי ל 01 ולא הגדרת תפריט שתי ספרות זה פשוט לא מוצא את השלוחה
תוסיף את ההגדרה הזו לתפריט ראשי
digits=2 -
RE: שמות למספרי משנה
הקוד למעלה עודכן, כרגע הוא מציג את כל המספרים גם בלי שמות, מה שכתוב שם מציג את השם.
וגם בכל מקום במערכת שיש לבחור זיהוי יוצא מופיע השמות, בתפריט שיגור הודעות או הפעלת צינתוקים דרך המערכת וכו'
אם יש הגדרות של זיהוי יוצא שלא הוספתי ניתן לכתוב פה ואני יעדכן, כמו כן מי שיש לו רעיון לשדרוג ניתן לכתוב פה ואני ישתדל לעדכן