תקשורת שרת-לקוח נכונה בבחירה מעץ נתונים
-
כהמשך לאשכול הקודם שלי בנושא, אני עוסק בבניית מערכת בה הלקוח מתבקש לבחור נתון מתוך עץ נתונים.
כפי שהציע לי @צדיק-תמים באשכול הנ"ל, אני משתמש בפרמטר ApiCallId שמתקבל ממערכת ימות המשיח כדי לקבוע את הID של הסשן.
בבקשה הראשונה של הלקוח אני מאחזר את כל הנתונים ללא הורה (כלומר - הנתונים ראשיים), וקובע את האינדקס שלהם לפי הסדר בה הם אוחזרו. את התוצאה הזו אני שומר במערך מיוחד בתוך הסשן של הלקוח, ובמקביל שולח ללקוח הודעה בתוך בקשת read לבחירת אחד מהנתונים הללו באמצעות הקשה (לתוצאה הראשונה הקש 1, שנייה הקש 2 וכו').
כאשר הלקוח חוזר עם הבחירה-אינדקס שלו אני בודק במערך בסשן שלו לאיזה מהנתונים הוא מתכוון, ומאחזר מהDB את כל הילדים של אותו נתון, וכן הלאה, עד לבחירת נתון ללא ילדים.א - אני מניח שבחירה מתוך עץ נתונים היא פעולה נפוצה אצל המפתחים כאן, האם הצורה בה בניתי אותה היא הצורה הפשוטה והנכונה?
ב - בעיה משמעותית בצורת תקשורת זו היא שכידוע 'ימות-המשיח' מצרפים בכל שליחה את כל מה שנשלח מתחילת ההתקשרות. בצורה הנ"ל אותו פרמטר נשלח באופן כפול ומשולש. (למעשה, בפועל אני יכול להמשיך לעבוד כך כי במקרה של פרמטרים כפולים PHP נוהג להתייחס בבקשות GET לבקשה האחרונה מהם, אך לא ברור מהתיעוד של 'ימות-המשיח' שהם מחוייבים לשמור על סדר שליחת הפרמטרים, ואני חושש מבאגים משמעותיים).הערה I : 'מיספור' של בקשות הלקוח כדי לדעת היכן הלקוח 'אוחז' אינה אפקטיבית במקרה זה, כיון שאורך עץ הנתונים אינו סימטרי. ישנם נתונים עם אב אחד בלבד, וישנם נתונים עם סבא וסבא רבא וכו'.
הערה II : אני עובד עם PHP על גבי שרת שיתופי (מדובר בשרת של מזמין העבודה ולא נתון לבחירתי).מקווה שהייתי מספיק ברור,
אשמח לקבל תובנות מקהילת המומחים כאן. -
@איש-סוד
בכמה פרוייקטים שלי אני גם נותן בחירה מתוך עץ נתונים בכמה וריאציות
פחות או יותר אני משתמש ממש עם הרעיון שכתבת, יצרתי לזה מחלקות מסודרות ב PHP והיום אני רק צריך לקרוא למחלקה תוך שליחת הפרמטרים הרלוונטים
ביחס לצורת הקבלה של הנתון אני אישית שומר את כל ההקשות במערך של הסשן ולא קורא ישירות מה GET, ובכל טעינה של הדף אני לוקח באמת את הפרמטר האחרון, במידה וימות המשיח ישנו את השיטה, זו אכן תהיה בעיה (באחד הפיתוחים החדשים של שליחת API במהלך שמיעת קבצים הפרמטרים המיוחדים נשלחים באמת בתחילת המחרוזת)
לחילופין, אם אתה לא רוצה לקחת סיכון ושוה לך בשביל זה לסרבל את הפיתוח, תוכל לממש פיתרון שאני משתמש במקרה שבו אני רוצה לאפס את כל ההקשות (כשנדרש הקשה חוזרת וכו') והוא שאני שומר את ההקשות בתוך מערך הסשן (ואני מגדיר את ה key שאני רוצה) ואני פשוט מפנה אותו מחדש לשלוחה באמצעותgo_to_folder
מה שמאפס את הסטרינג שנשלח -
@amp-Software-0 תודה רבה!
(אני חסר מינימום מוניטין להצביע לתגובתך).@amp-Software-0 כתב בתקשורת שרת-לקוח נכונה בבחירה מעץ נתונים:
אני אישית שומר את כל ההקשות במערך של הסשן ולא קורא ישירות מה GET
כלומר?
אתה שומר מערך של הקשות ובכל פעם מבצע את כל השאילתות מהDB בסדר הזה?@amp-Software-0 כתב בתקשורת שרת-לקוח נכונה בבחירה מעץ נתונים:
אני פשוט מפנה אותו מחדש לשלוחה באמצעות go_to_folder מה שמאפס את הסטרינג שנשלח
ראיתי את העצה הזו בכמה מקומות בפורום, אך לא הבנתי כיצד להשתמש בה. כאשר אני 'מוציא' את הלקוח מהשלוחה ומחזיר אותו אליה, הוא ישמע שוב את הודעת הפתיחה בכניסה לשלוחה.
-
@איש-סוד
אני אסביר יותר,
הגישה המקובלת היא לקבל את הפרמטרים ישירות מאובייקט$_GET
החסרון בגישה הזו היא שאין אפשרות לשלוט או להסיר הקשות שהתקבלו, בנוסף אין לי אפשרות 'להוריש' הקשות משלוחה אחת לשלוחה אחרת מכיון שאובייקט ה$_GET
מתאפס בכל כניסה מחדש לשלוחה
השיטה שאני משתמש היא שבעצם בכל כניסה לכל דף שהוא זה עובר בהתחלה במחלקה שמלקטת את הפרמטר האחרון שנשלח ומאחסנת אותו במערך של הסשן (שיטה דומה לזה מיושמת במחלקה שכתב @צדיק-תמים ב nodeJs), הנתון נשמר שם גם אם הוא יצא מהשלוחה, כמו"כ יש אפשרות לשלוט על ההקשות \ להסיר הקשות במידה ויש צורך לקבל אותם שובזה בדיוק הפתרון גם למקרה שרוצים להכניס מחדש לשלוחה ושלא ישמיע את הודעת הפתיחה, פשוט מאחסנים באובייקט הסשן שההודעה הושמעה, וזה לא מתאפס גם כשיוצאים מהשלוחה
דוגמא:if (!isset($_SESSION['play_message'])){ echo 'id_list_message=f-message&'; $_SESSION['play_message'] = true; } .....
אותו דבר ביחס לנתונים או הקשות, בהם אפשר כמובן להשתמש ישירות בשם של הפרמטר
-
@amp-Software-0 כתב בתקשורת שרת-לקוח נכונה בבחירה מעץ נתונים:
(שיטה דומה לזה מיושמת במחלקה שכתב @צדיק-תמים ב nodeJs)
לא נכון, בנוד עם הספריה הפונקציה רצה מתחילה עד סוף לפי הסדר, ואפשר להתייחס לread כאילו זה קריאה לאיזה API פשוט עם await, ואתה מקבל בחזרה את התשובה של המשתמש
זה לא רץ מאפס כל פעם ורק מאכלס מחדש את המשתנים -
@צדיק-תמים
כמובן שהמימוש ב node שונה מהמימוש ב php מחמת היותה אסינכורנית.
אני התכוונתי בעיקר לנקודה שציינת שהפונקציה 'נפתרת' בקבלת הנתון החדש, וזה, לכאורה הנתון האחרון שהתקבל ב GET, כך שלכאורה במידה וימות יחליפו את מיקום הפרמטרים זה יהווה בעיה.
יתכן שלא הבנתי נכון, אבל כך זה נשמע ממה שכתבת כאן -
@amp-Software-0 כברירת מחדל לא מגדירים בכלל את השם של הפרמטר בURL, הוא נקבע אוטומטית על ידי הספריה
const name = await call.read([{ type: 'text', data: 'הקלד את שמך' }]);
בפועל הערך שנשלח הוא val_1, אבל זה לא מעניין אותי כמתכנת
ואני לא רואה סיבה לעשות אחרת חוץ מקצת יותר נוחות בדיבוג כשחושדים בבאג בצד של ימות, שלא שווה את הטרחה (למרות שיש אופציה להגדיר val_name משלך, אני לא רואה סיבה להשתמש בה) -
@צדיק-תמים
אני מבין, באמת בשיטה הפעולה הזו (גם במימוש שלה ב PHP) אין שום משמעות לשם הפרמטר.
האזכור של הספריה שלך נגעה רק ביחס לנקודה הזו שגם היא חשופה ותלויה בכך שהערך החדש שהמשתמש הקיש יופיע תמיד בסוף המחרוזת, האם אני צודק? -
@amp-Software-0 כתב בתקשורת שרת-לקוח נכונה בבחירה מעץ נתונים:
האזכור של הספריה שלך נגעה רק ביחס לנקודה הזו שגם היא חשופה ותלויה בכך שהערך החדש שהמשתמש הקיש יופיע תמיד בסוף המחרוזת, האם אני צודק?
אם מגדירים val_name ידנית ולא אוטומטית
ומבקשים יותר מפעם אחת את אותו פרמטר
אז כן, הספריה מניחה שהפעם החדשה תהיה בסוף הכתובתfunction shiftDuplicatedValues (values) { for (const key of Object.keys(values)) { const value = values[key]; if (Array.isArray(value)) { values[key] = value[value.length - 1]; } } return values; }