Lesson 21 of 22
Refactoring- Introduce Instance Delegator
In this lesson
Roy Osherove sets out to test the static Send method of a class named Manager in the ping namespace, which sends a trackback or ping for the links in a post or comment, and suggests finding its dependencies by calling it and seeing where it fails. The calls that send a trackback or ping are the end results (external link, opens in new tab), and the tests should prove the loop and each if. Because the class is static, he introduces instance delegator: remove static from the class, move the logic into an instance method that the static method calls on a new manager, then extract and override (external link, opens in new tab) settings such as the trackback check in a testable subclass (external link, opens in new tab).
Transcript
[00:04] (external link, opens in new tab) אה לא צילם את המקונסגרו שם את הדלת בסדר רגע סגרו אתכן >> סגירו את הדלת תפעילו את המזגן >> תביא את המסג' >> נראה לי שווה שכולם יעמדו להוריד את הגירה >> אוקיי למי עברו כל הטestטים דרך אגב >> למי עברו למי למי נכשל רק טestט אחד למי נכשלו יותר מטestט אחד אוקיי אוקי מה למדנו עלגרש testing היום ילדים זה שונה את המחשב >> אם זה לא עובר זה בסדר >> אם זה לא עובר אתה רואה כל הזמן אני אומר לך מה היה קורה אם יש יוניטסטים שם מסובחים אז רובו הסיכויים שלא הייתם שמים לב אליהם וזאת אחת הסיבות שצריך להפריד את הדברים האלה אוקיי אנחנו נניח לצורך המשך התרגול של היום כשכל הטestטים עוברים אצלכם על המחשב
[00:52] (external link, opens in new tab) דרך אגב הרבה מזה קשור לאם רסing כאדמין או לא וחלק מזה קשור גם לגרסאות שלד דוקים שמכונות לכם על המחשב אבל זאת המטרה האמיתית שלנו להמשך היום יש לנו קלאס שנקרא מנג'ר נכון שאנחנו לא שמעתם קלאס עם שם כזה למנגר יש פונקציה publicקס static ש קוראים להסנ זאת הפונקציה שאנחנו הולכים לנסות לכתוב להestטים היום אנחנו בהתחלה נתחיל לכתוב טestטים
[01:24] (external link, opens in new tab) גם באותו פקטורים לבריאות בלי טיפ והמטרה היא שאתם תראו שיש דרכים כמעט כל חתיכת קוד להפוך אותה לטבabית ולבדוק אותה וזה גם פרפקטורים שחשוב ללמוד קצת אני אסביר מה המטרה של המנג'ר הזה המנג'ר נמצא בתוך נמספס שנקרא פינג והרעיון הוא מישהו יודע מה זה פינג או טרקבק בבלוגים מי יכול להסביר את זה דרך
[01:55] (external link, opens in new tab) של זה דרך של מחבר פוסט להודיע למחבר פוסט אחר שהוא קישר עליו בוא הסתב לבלוגר אחר בלוגר אוקיי זה קצת כמו מה שכתר אחרי זה נהיה שאתה כותב על מישהו ואטומטית הוא יודע שהזכרת את השם שלו אז בבלוגים אה אתה עושה לינק לבלוג של מישהו אחר ואייכשהו אוטומטית מופיע לו איזה לינק מתחת לבלוג שלו עצמו שאתה כתבת עליו וזה נעשה באמצעות סדרה של שרטים בעולם שנקראים ping server וb servers והמטרה שלהם היא בדיוק לעגור את המידע הזה על בלוגים שמקשרים אחד לשני ותרך זה לעשות שיחה קצת יותר מעניינת בין בלוגרים
[02:38] (external link, opens in new tab) אז הפונקציה הזאת היא בעצם פונקציה שמקבלת publishable שזה יכול להיות פוסט או comment כל דבר שיכולים להיות בו לינקים למשהו ובהתאם אם יש טרקבק URL או URLים לבלוגים אחרים היא שולחת אוטקבק אופינ בהתאם לכל מיני תנאים מסוימים. אבל אנחנו הולכים לנסות לבדוק את הפונקציה הזאת בהתאם לדף שכבר יש לכם פתוח אצלכם בבראוזר. אבל הבעיה האמיתית היא שיש פה המון צרות שלותסטביליות.
[03:09] (external link, opens in new tab) F12 לדוגמה יש לנו block settings. Trackb שזה קשור לקונפיגורציה אז זה סוג של dependency שמאוד קל לזהות. אבל הרבה פעמים יש depend בקוד מג שאין לנו מושג מה הdependencies שלו ואז עושים דבר שאני קורא לו wishfulation וזה סתם מילה יפה ללנסות להריץ ולראות מה יקרה אז בטestטים שלנו אנחנו יכולים לנסות להפעיל את הפונקציה ולראות מה קורה אם מקבלים איזשהו אפtion מסתכלים על הסט ורואים איפה דברים מתחילים להיכשל ושם כנראה הדepפendנסי נמצא ואז מנסים לחשוב באיזה רמה כדאי לנו לעשות פייק (external link, opens in new tab) למשהו הזה או לעשות לעשות סטאר או לעשות או שצריך מוקט פה כדי
[03:58] (external link, opens in new tab) לבדוק את הקומפוננטה שלנו. אז אחד הדברים שאני ממליץ לכם כשאתם מתחילים לכתוב לבדוק את הפונקציה הזאת זה פשוט לנסות לקרוא לה ולראות מה קורה רגע אבל תר לי מה שאתה אומר כי את עצ אומר אני לא אני לא יודע בכלל מה אני בודק לא אני לא יודע מה הדפנסי של מה שאני זה אותו דבר אבל >> לא בכב זה אותו דבר הרבה פעמים הקוד לגסי שלך מסתמך על קוד שלא אתה כתבת מסתמך על אינפסטקטור שלא אתה כתבת >> אוקי >> ולכן אתה לא יודע מה הדפנenנies שלו למה אני מסתכל על הקוד ואני אובל את הדברים כי אני לא רוצה לבדוק אותם לא אתה לא צריך לבדוק אותם המטרה שלך היא למצוא את הUNIT World ולבודד אותו שקט שליטה עליו זה כל המטרה זאת אומרת אתה רוצה לבדוק עד כמה אתה יכול להריץ את הדבר הזה בזיכרון בלי לפנות אתדabסיט בלי לפנות פיילסיסטם שזה ירוץ בלי רדינ אז בהתחלה אתה לא יודע איפה הגבול הזה עובר בתוך הכל אז אתה צריך לראות מה קורה אבל >> עכשיו בלגסי קוד זה לא tvd חשוב להבין שהכללים של TVD לא חלים פה בכלל לגס קוד וגדול
[04:59] (external link, opens in new tab) זה לקחת בדבוק וודק כטוב כל אדם לעצמו ופשוט לצאת לשדות ולראות מה קורה עם סוס פשוט לקחת גם רובה טוב כי אתם תראו שם כל מיני דברים ואתם ומה שקורה שם זה נשאר ביניכם לבין לבין הקומפיילר כמובן שאחרי זה מישהו יצטח לקרוא את הטestטים שלכם אז תרשו אותם קריאים כמה שיותר אבל טestטים של לגסיקות יכולים להיות הרבה יותר מסובכים יכולים להיות להם הרבה יותר depפendנenes ובעולם האמיתי בקוד שלא נכתב עם testing אז הוא גם קוד שלא נועד לטestטים בדרך כלל זאת אומרת צריך למצוא המון דרכים יצירתיות לבדוק את הקוד הזה.
[05:34] (external link, opens in new tab) ובקוד שאתה לא מכיר, כמובן להסתכל בקוד ולהבין את כל החתיכות שלו זה בהחלט חשוב, אבל צריך באיזשהו שלב גם להיות פרודוקטיבי ופשוט לנסות להפעיל אותו. עכשיו, אני יכול לקחת רק את המתודה הזאת ולהפריד אותה מכל הדפנדנenנס ברמת הקס, אבל זה לא בהכרח רעיון טוב. אני הרבה יותר מעדיף שאני משתמשת במשהו להבריאות, שאפשר להריץ גם בזיכרון, אז אני אריץ בא את הדבר הזה. אני מעדיף שזה שלא יהיה אכפת לי מהאימפלמנטיש כמה שיותר. בסדר? ולכן אני רוצה לבדוק עד כמה impפלמנטש אני יכול להשתמש בו בלי לקבל אספtion בלי להפעיל דטבס כדי שהעומק שלי שאני מפעיל את הIT one הוא יורד מבחינתי אפילו שלוש חבות אבל אם זה הכל בזיכרון זה לא כזה מפריע מבחינתי הend resultלט הוא מה שחשוב ואז השאלה את השאלה מה הend resultלט איפה הend resultלטs פה
[06:21] (external link, opens in new tab) אז יש פה שני סוגים של אד resultלט היא קרה קריאה לtrackbנ וקריה לפי בקסנט אלה שני הנרזלצ היחידים שיכולים להיות פ אוקיי עכשיו מבחינתנו פינbקס וצקבק נסנ הם יכולים להיות thדפ party נבדוק שמישהו קרא לטרקבק נקס כי אם באמת נבדוק שהם קרו זה כבר יהיה אטגרש test לכל דבר בסדר עכשיו זה לא אומר שלא צריך test זה אומר שמבחינתנו האינטגרש test הם יהיו מטבח משלים לדבר הזה אני רוצה לבדוק ביניטest שקראתי לדבר הזה ולבדוק ביניטest שקראתי לדבר הזה אם אני לא קראתי לדבר הזה על זה בעצם הדברים הגדולים שאני אכוון אליהם.
[07:04] (external link, opens in new tab) עכשיו, במסמך שיש אצלכם במחשב כתוב מה תרצו לבדוק. לדוגמה, אם אני שולח שני UR בקונטנט של IUBL, אם אני שולח שני URLים אז אני באמת עובר על כל אחד. אני רוצה להוכיח שיש סיבה שהלולאה הזאת נמצאת שם. לולאה זה כשיש לך יותר מאחד אז אין לי צורך לבדוק עם שלושה. אני יכול לבדוק עם שניים שהובר בלולה ושולח את כל אחד מהם לטראקב. אני רוצה להוכיח שיש סיבה לאיף הזה ולאיף הזה. אז אני אבדוק כל אחד מהם אני רוצה להוכיח שאם בטק back הוא דווקא מחזירפס אז הוא לא שולח לט
[07:39] (external link, opens in new tab) אוקיי עכשיו הסיבה היא יכול להיות שגיליתי בג ולפעמים זה כן קורה לפעמים זה לא קורה אז אני רוצה לבדוק אותו בכל התנאים האלה עכשיו כל מבחינת הדיזיין יש פה דברים מבחינתity שעוד לא עברנו עליהם לדוגמה כל הפונקציה הזאתי סטטית והיא בקלאס שהוא סטטיק זאת אומרת לדוגמה פה יש לי trackb send בעולם יותר פשוט הייתי אומר וואלה תביא לי איזה אינטרפי של i trck i trackb ותבלוג שckb נקרא ואתם באמת יכולים לעשות את הדבר הזה
[08:15] (external link, opens in new tab) הבעיה היא לאן אתם מים את האינטרפס אין פה שום אינס של קס שמקבל אינטרפס כל הקלאס הזה הוא סטטי וכל המתודות פה הם סטט אופליקסטיק אוטסטיק בסדר אני מניח שאצלכם זה לא ככה אל תניבתי ואם אני מנסה לבדוק את הדבר הזה ואני רוצה להשתלט על הbקס send אני לא יכול לשלוח אינטרפס אני גם לא יכול לעשות פה אstract and over בגלל שאני לא יכול לעשות over לקסט אני לא יכול לרשת ממנו כי אין לי אינסטנס של משהו אז אני עוד פעם בבעיה אז שום שום דרך מהרפאקטורים שלמדנו עד עכשיו לא יכול לעזור לנו אז מה שנלמד עכשיו זה דרך ריפאקטורינג שיכולה להביא אותנו לרפ פקטורים שאנחנו יכולים לעשות.
[09:00] (external link, opens in new tab) זאת אומרת אם אין לנו instance אנחנו נעשה פה שיתן לנו instance והרפקטורing שאני ללמד פה נקרא introduce instance delegator זה אומר שאנחנו נעשה נהפוך את הקריאות של פונקציה סטטית לקריאה לפונקציה שהיא איסטנס בגדול מה שזה אומר זה ככה אם הקלאס הזה שלי הוא סטטי אוקיי כל הקלאס הזה הוא סטטי אני רוצה שתהיה לי את היכולת להפוך את הקלאס הזה לקס אסטי חלק מהרפקטורing אני הולך להוריד את המילה סטטיק מהקלאס מי יודע מה המילה סטטיק בעצם נותנת לנו ברמת הקסה
[09:37] (external link, opens in new tab) שכל המת >> שכל הס מה מה זה מונע מאיתנו לעשות >> זה מונע לעשות ניו וזה מונע מאיתנו לכתוב מתודות של אינס כל המתודות בקס חייבות להיות סטט מבחינת השימוש של כל הקלאסים האחרים בקס הזה זה לא משנה שום דבר ריפה גדול זה בסך הכל מוריד חלק מהקונסטרינטים של הקפיילר עלינו אוקיי זה שם מוריד את הקלאס סטטי לא משנה התנהגות בסך הכל עושה את הקלאס יותר מגיש לאינסטנסים ברגע שהורדתי את הטat instance אני יכול לעשות
[10:10] (external link, opens in new tab) את הדבר הבא אם אני רוצה שתהיה לי גישה אם אני רוצה שתהיה לי דרך לעשות אסטרct וadדוס interfס אני צריך שתהיה לי דרך אני צריך שהמתוד send תהיה על אינסנט של משהו אבל המתוד הסנ היא כרגע סטית אז מה שאני אעשה זה בעצם להכפיל את המתודה הזאת. אוקיי?
[10:40] (external link, opens in new tab) ובעצם מה שאני הולך לעשות זה ככה. אני הופך להפוך את המתודה הסתית של למתודה שלא עושה שום דבר מלבד לעשות new instance של manager וקורת לסנ על הance. אוקיי? זאת אומרת לקחתי את כל הפונקציה שלס sנ אני לוקח את הפונקציה הישנה של שהייתה סטטיק ואני מוריד את הסטטיק ממנה ומשנה לה את השם כי אחרת הקפיילר צל אני קורא לזה sendal אוקיי היא לא השתנתה מבחינת הפלמנטש בשום דבר עדיין רק עכשיו המתודה הסטטית אני לא רוצה לשנות את ה את העובדה שהיא שם מכיוון שיש לי את כל הפרודקש קוד שעדיין משתמש במתודה הסטטית המטרה שלי היא לא לשנות את ההתנהגות של כל מי שקורא לי אלא לשאר את התנגות פנימית ולכן מה שאני עושה פה זה
[11:26] (external link, opens in new tab) Maner sendal עם הפרמטרים שלי אוקיי אז מה שהיא עושה עכשיו היא בסך הכל עושה דלגציה לאיance ולכן זה נקרא instance delegator אז הפונקציה שהייתה פעם סטטית לא עושה שום דבר מאשר new manager נקודה sendal internal היא עכשיו מטה שנמצאת על instance של clס ואם יש לה אינסט שלס אנחנו צים לעשות את כל הרפקטורים שעשינו קודם זאת אומרת אני יכול עכשיו להגיד וואלה block settings instant enable trend
[11:58] (external link, opens in new tab) זה dependency אז אני יכול לקחת את כל הדבר הזה לעשות extract method ולהגיד get enable trackb send להפוך אותו ללאסטatטי לעשות אותו וירטואלי ואחרי זה לעשות לו overיט בעצם לרשת מהמנגר לעשות testable manגס משלי לעשות שם להחזיר שם מה שאני רוצה עכשיו יש לי את היכולת לעשות את הרפקטורים הזה כי זה באינסטנס אז אם קודם היה לי רק סטטי לקחתי את הסטטי ואמרתי
[12:28] (external link, opens in new tab) אתה אתה כביכול עושה מה שעשית קודם ההבדל היחיד הוא שאתה עושה את זה על אינסטנ של קס עכשיו פה אני עושה ניו אבל מ בעולם האמיתי מה שבדרך כלל הייתי עושה הייתי לוקח את הניו מנגר ו עושה לזה אקסטר זה מתודה שהיא כנראה get man שלא בהכרח תמיד עושה ני אבל זה כבר זה כבר לא בעיה זה כבר משהו שעושים בלי קשר מה שחשוב זה לדעת לעשות את הדליגציה הזאת בגלל שבמקרים כאלה לא תהיה לכם הרבה ברירה כדי שתוכלו לבדוק משהו שהטestטים יהיו קריאים הרבה פעמים זה שיטה מאוד מאוד פשוטה ונוחה
[13:03] (external link, opens in new tab) שלא משנה את ההתנהגות היא אך ורק משנה את הטסטביליות של הקלאס שאלות לגבי מה שראיתם עד עכשיו כן מי רוצה שאני אחזור על מה שעשיתי >> לא יהיה יותר קל כאילו לא יהיה יותר קל פשוט בפ לתפוס את הקריאה סטא >> בטח שזה יותר קל אבל אני רוצה שתלמדו את שתי השיטות בגלל שלא תמיד יהיה לכם כלים ולא תמיד זה רעיון טוב להשתמש בכלי בשביל לתפוס את זה לפעמים כן ולפעמים לא >> באיזה מקרים לא היית אומרים >> במקרים שבהם הטestט יהיה בלתי קרי בעליל בגלל כמות הדpנenנies
[13:41] (external link, opens in new tab) וגם בגלל ש' חשוב לכם ללמוד את הטכניקה של הרפקטורי חלק מהקורס אתם תגלו שלפעמים זה הרבה יותר פשוט מאשר לכתוב טest ולגלות את כל האינטרספtionס אבל לפעמים זה באמת יותר קל להשתמש בטל מה שחשוב זה שתהיה לכם אופציה שלא תהיו תגידו אני חייב לעשות את זה ככה אלא אני בוחר לעשות את זה ככה זה הכוח האמיתי בסדר >> ואז הוד הקוד עכשיו נהיה קצת לא קריכ >> הקוד נהיה לא קרי >> של הפרודקש כי עכשיו אתה קורא לפונקציה >> כן אני יכול לעשות את זה >> בעיקרון יש לך עכשיו >> כן >> אה אפשר לעשות את זה
[14:19] (external link, opens in new tab) אוקיי בסדר בסדר? דרך אגב, לא בטוח שהייתי עושה את זה אנטרנל, הייתי עושה את זה פאבליק בגלל שמה שהייתי רוצה זה שקוד חדש כבר ישתמש באינסטנס ולא ישתמש בסטטיק. המטרה שלי להיפטר מהסטטיק הזה בסוף. לאט לאט אני אני אפטר מכל הטיפנסי שמשתמשים בסטאטיק עד שיום אחד אני לא אשח את הסטטיק בכלל. >> אבל עם האינטרנט אתה יכול לקרוא לזה אינטרנל? אני יכול לקרוא לזה מתוך האסמלי. אני יכול לעשות את זה אבל פאבליק ולא אינטרנל. >> אבל אתה רוצה לקרוא בטest? אתה רוצה לקרוא לפונקציה? >> בטסטים שלי אני יכול לעשות internal שהטestטים שלי יוכלו לראות את זה עם האטריבט.
[14:50] (external link, opens in new tab) אבל בדרך כלל מה שהייתי עושה הייתי משאיר זהפליק בגלל שמבחינתי זה פחות משנה הייתי יכול אם זה באמת מפריע לי הייתי עושה את זה publicקל ואז עושה internal וזה בלטו בטestים שלי אני לא מפעיל את הטat method אני עושה new manager או testable manager וקורה לס internal אוקיי דרך sendal זה סתם שם שאני בחרתי תם תקו לזה send instance או תמצאו לזה שם אחר שאתם יותר אוהבים השם פחות משנה כל זמן שזה שם שונה מסנ >> אולי עדיף אה עוד אופציה זה במקום לעשות את הריפאקטור הזה פשוט להפוך משהו שהסתטי
[15:25] (external link, opens in new tab) קלאס לסינגלטון ואז פשוט אין לך את הדפליק שלי סינגלטון זה משהו שמחייב אינסטנס כן >> ולכן זה זה בהחלט אבולוציה שיכולה להביל אותך לסינגלטון >> גם כאן אתה זה יהיה מי >> כן אז יהיה לך אתה יכול להגיד ככה instance כן >> הבעיה עם סינגלטון זה שאתה עוד פעם צריך להחליף אותו איכשהו בטestטים שלך נכון אה אה אבל אתה עדיין יכול לעשות את את אותו תדליק בעצם יכול לעשות בטestים שלך ניו מנג'ר אבל בדרך כלל בסינגלטון הם מחביעים את הקונסטרקטור כדי שאף אחד לא יוכל לעשות את זה הסינגלטון בדרך כלל הוא גם משהו שהוא לא testable יותר מדי אבל אתה יכול כמו שעשינו בטיים אתה יכול להגיד
[16:04] (external link, opens in new tab) Instance נקס set לטesting אבל אתה עדיין צריך את הצד הזה כדי שיהיה לך אינסטנס מלכתחילה תחשבו על זה כאזשהו צד איזשהו מתאטפ כדי שבכלל תוכלו לעשות משהו על זה סינגלטון הוא גם אופציה אתה יכול גם בסינגלט שהקונסטרקטור יהיהד ואז מי שיורש ממך יעלה לו את רמת הביity לפליק >> נכון נכון אבל עוד פעם זה כבר תלוי באיך אתם רוצים שהדיזיין שלכם יראה זה לא קלאס על דיזיין זה פשוט להראות לכם איזה אופציות יש מפה ההחלטה איך הדיזיין יראה הוא כבר שלכם בסדר אני לא רוצה להיכנס לזה כי זה יכול דיון של יום בפני עצמו מה כדאי וגם יש לכם פה כל מיני איזשהו סטנדרטים שאולי אתם רוצים לשמור עליהם זה חשוב
[16:43] (external link, opens in new tab) גם הרבה פעמים זה מפחיד אנשים לחסוף משהו V שאנשים יכולים לרשת ממנו בלי שהם יתכוונו רק בשביל הטest. אבל זה הכל עניין של דיון שהוא לא רלוונטי לנו כרגע כי אנחנו לומדים טכניקה. הדיון המוסרי של מתי להשתמש בטכניקה זה באמת דיון לקורס אחר. אוקיי? שאלות? מישהו רוצה שאני אראה עוד פעם את הטכניקה של איסון אליגטור? אוקיי, אז מה שאני מבקש,
[17:14] (external link, opens in new tab) נלך להמשיך את הצעדים. אתם לא צריכים עכשיו להוסיף לעשות את התרגיל הראשון של להוסיף test. מבחינתי תתחילו מהתרגיל השני, מיד אחרי התרגיל של הטestי. מה שכתוב אטר launch מבחינתנו, אחרי האדום הזה אנחנו ממשיכים משם והמטרה היא לסיים את כל הדטה ה בסדר? בהצלחה. Ja.