לכבוש את העולם: תוכנה רב-לשונית

נניח שיש לכם מוצר בשם \"FlappyWare\", והוא מוצלח למדי. התחלתם למכור אותו בארה\"ב (דא!) והמכירות כבר זורמות מעצמן. עכשיו אתם רוצים להתרחב לשוק גדול אחר: אירופה. אולי לשוק קטן ומקומי: ישראל, ואולי למזרח הרחוק.

מה בעצם הבעיה לקחת את המערכת שנכתבה לשוק האמריקאי, ולהתאים אותה למדינות נוספות כגון: אנגליה, גרמניה, ספרד וישראל?

אנגליה: השפה היא כמו שפת המערכת הקיימת, אנגלית. גרמניה: יש לכם מתרגם שיתרגם בקלות לגרמנית ומישהו בחברה שיודע ספרדית היטב. תוך כמה ימים אתם יוצרים אקסל עם כל הודעות המערכת למשמש (\"user strings\") בכל 4 השפות.
סביבת הפיתוח מאפשרת ניהול מספר שפות ל User Strings (תהיה זו ג\'אווה עם Resource Bundle property files או iOS עם NSLocalizedString).
האם זה יותר מעניין של כמה ימים – בכדי לכבוש את העולם המערבי המפותח? (פרגון לישראל)

אני כותב את הפוסט בהמשך להאזנה לפרק של מובייל ובירה ששמעתי לאחרונה – פודקאסט עברי מוצלח על פיתוח מובייל שאני שמח להמליץ עליו בהזדמנות זאת. אני שומע קבוע והוא עוזר לי להישאר בעניינים בנושאי פיתוח למובייל.

אחד מחברי הפודקאסט סיפר שאפליקציית מובייל שהם כתבו הצליחה באופן מפתיע בשוק הרוסי והשוק הסיני – והם החליטו לתרגם את האפליקציה לשפות אלו. אני מכיר את נושאי רב-הלשוניות (Multi-lingual) מעולם ה Enterprise, אך נראה שהוא רלוונטי למדי גם לאפליקציות מובייל.

נושא ריבוי-הלשונות הוא נושא לא-מורכב, אך עשוי להיות מעט מפתיע. נראה לי שהוא גם לא כ\"כ מוכר. בבדיקה קצרה בגוגל לא מצאתי עליו חומר איכותי, לא ספרים ובטח לא חומר טוב בעברית.

אני אנסה לשנות זאת… 🙂

מושגים

בתחום זה יש 3 מושגים מבלבלים:

  • Internationalization (בקיצור: i18n)
  • Localization (בקיצור: l10n)
  • Globalization (בקיצור: g11n)
ראשית הסבר על מהות הקיצורים המשונים:
המינוח Internationalization הוא דיי ארוך. מכיוון שאנשים מזהים מילים בעיקר בעזרת האות הפותחת והמסיימת, אפשר לקצר ל \"i—n\" ולשמור על היכולת של לקשר את הקיצור למילה המקורית. כמה אותיות יש באמצע? 18. לכן: i18n. (לא מאמינים? תספרו).
מה הקשר בין שלושת המושגים? האם Globalization הוא ההיפך מ Localization? האם זה אותו הדבר?

אפשר לסכם את הקשר בעזרת הנוסחה הבאה: g11n = i18n + l10n.

Internationalization הוא התהליך של הכנת התוכנה לריבוי שפות ואזורים (regions).

Localization הוא התהליך של התאמה לאזור / שפה מסוימת. התאמה כוללת אלמנטים של שפה (עברית, אנגלית) כללים של האזור (מטבע, שיטה מטרית, צורה לכתוב תאריך וכו\') ורגולציות (למשל: חוקי פרטיות בגרמניה המחייבים למחוק פרטים היכולים לזהות אדם ספציפי מלוגים של מערכת).
עוד אלמנט שנוגע לאזור הוא עיצוב: צבעים, אייקונים וסמלים יכולים להתפרש במדינה אחת בצורה שונה מאשר במדינה אחרת.

Globalization הוא התהליך הכולל של Internationalization ו Localization, הכולל הכנה לריבוי-שפות ואז התאמה למספר שפות/אזורים ספציפיים.
שיטה אחרת (עמוד 2 במסמך) מתארת את הקשרים מעט אחרת ומדברת גם על Localizability, L12y). אם האנשים שעובדים אתכם נוהגים ע\"פ המודל השני, פשוט הפכו את שמות המושגים i18n ו g11n – כל השאר נשאר בערך אותו הדבר.
מונח נפוץ אחר, בעיקר ב API של שפות תכנות, הוא Locale (תרגום לעברית: מקום).

Locale הוא אובייקט המתאר קומבינציה של שפה (\"עברית\"), אזור (\"קנדה\") ולעתים גם codeset (שזה בעצם encoding, כמו UTF-8 – נושא שאפשר להקדיש לו פוסט משלו). בד\"כ יהיה לנו על ה session אובייקט locale שבעזרתו נדע כיצד לשרת את המשתמש הנוכחי.

נהוג לקדד את ה Locale בעזרת שפה ע\"פ תקן ISO 639-1 ואזור ע\"פ תקן ISO 3166-1.
למשל: en_US (אנגלית, ארה\"ב), en_GB (אנגלית, ארה\"ב) או zh_CN (סינית בסין) או אפשר גם he_CN (עברית בסין).

Locale, אפרופו, מבטאים כ\"לו-קאל\" (כמו \"לוראל\" – חברת קוסמטיקה) ולא \"לוקייל\", כפי שלעתים נהוג.

חזרה ל FlappyWare

הכנסתם למערכת את כל משפטי הטקסט ב-3 השפות החדשות (גרמנית, צרפתית ועברית). אבל הלקוחות מתלוננים:

  • הישראלים רוצים שכל התפריטים ועימודי הדף יהיו מימין לשמאל. העימוד הנוכחי פשוט לא מתאים!
    אולי למתכנת, עימוד משמאל לימין לא מפריע (או עדיף), אך פועל במפעל, או אמא שיש לה מספיק נושאי-עניין בחיים – פשוט רוצים שהממשק יהיה קל ונוח (\"למה לא עשו את זה בסדר? הם לא רואים שזה עקום?\").
  • הבריטים רוצים שהמערכת תשאל: \"?what is your favourite colour\" ולא \"?what is your favorite color\". הבדל בין אנגלית-אמריקאית לאנגלית-בריטית, שנתפס אצל הבריטים כמאוד-לא-קטנוני.
  • ישנם באגים לא צפויים במערכת בספרדית בתחום החיפוש. משום מה גם הטבלאות התחרבשו… מה זה קשור לתרגום?!
  • הגרמנים פשוט לא מרוצים ונמנעים משימוש באפליקציה. לא הצלחתם לייצר איתם קשר טוב מספיק להבין מה בכלל הבעיה (?!).

כאשר המשתמשים שלכם מגיעים מתרבות שונה ודוברים שפה שונה, גם הטיפול בכל case/bug נהייה קשה יותר. כשלקוח טוען ש\"בהונגרית זה צריך להיות ככה…\", ואתם לא מבינים על מה הוא מדבר / למה זה יצא אחרת – זה יכול להיות מאמץ לא קטן להבין ולתקן.

להבין את תהליך התרגום

לפני שנבחן \"מה יכול להשתבש?\" (זה החלק המשעשע), כדאי לדבר גם על תהליך התרגום, שגם הוא עשוי מעט להפתיע. בגדול, ניתן לחלק את מה שנרצה לתרגם ל 2 סוגים ב 2 קטגוריות.
הקטגוריות הן:

  1. תוכן מערכת – כל הודעות טקסט במסופקות כחלק מהאפליקציה: כותרות, תפריטים, הודעות שגיאה וכו\'. סוג זה הוא הנפוץ ביותר.
  2. תוכן לקוח – תוכן שהלקוח יצר בעצמו והוא רוצה לתרגם. סוג זה של תוכן רלוונטי כנראה רק לתוכנה עסקית, ורק לחלק קטן ממנה. לדוגמה: מערכת שיווק אונליין הנמכרת ללקוח (קמעונאי כלשהו) רוצה למכור סחורה במדינות שונות – לכן עליו לתרגם את קטלוג המוצרים, כתבי אחריות, מפרטים וכו\' – תוכן שהוא יצר.
שני סוגי התוכן הם:
  1. מחרוזות (Strings), קרי \"טקסט נטו\" – אותן קל למדי לתרגם.
  2. כל סוג אחר של מדיה: תמונות, מסמכים (למשל PDF), קישורים וכו\'.
    תמונות (כמו ה screenshot ב appstore או כפתורים באפליקציה) לעתים מכילות טקסט – ועל כן יש גם ליצור להן עותק מתורגם. ייתכנו תמונות שונות ללוקאלים שונים, למשל תמונה שונה לשוק החרדי ולשוק החילוני בארץ (כן… ניתן לראות את השוק החרדי כסוג של Locale שונה, למרות שהוא במדינת ישראל).
    לעתים אלו קישורים (URLs) לאתרים שונים, כאשר נקשר אתרים שונים לשפות / לוקאלים שונים.
את התרגום נוהגים לעשות מתוך ה Master Language. כלומר, בוחרים שפה \"מובילה\" (בארץ זו תהיה בד\"כ אנגלית, אך במדינות אירופיות זו עשויה בהחלט להיות השפה המקומית) בה ייכתבו הטקסטים המקוריים וממנה יתורגמו כל השפות – בכדי לצמצם טעויות.

אפילו אם המערכת שאותה נרצה לתרגם היא מערכת online (למשל ממשק וובי בענן), את התרגום נהוג לא לבצע בתוך המערכת אלא במערכות תרגום ייחודיות. למשל: במקרה של תרגום תוכן-לקוח, עשוי להראות סביר לספק את היכולת בתוך המערכת, הרי יש כבר ממשק ווב. מה יותר נוח מזה?!

לרוב זה לא יהיה נוח מ 2 סיבות:
א. למתרגם לא תמיד תהיה גישה למערכת ה Online.
ב. כלי התרגום מספקים יתרונות משמעותיים (למשל מילון-מונחים שכבר בשימוש במערכת, Thesaurus ועוד) – והמתרגמים עשויים דווקא לגבות מחיר גבוה יותר על שימוש במערכת אונליין.

בעיניים עצומות

פרט קטן לגבי התרגום לא ציינתי: המתרגמים לרוב עושים את עבודתם ללא שהם מכירים לעומק את האפליקציה שהם מתרגמים.
\"לעומק\"? תנו לי לתקן: הרבה פעמים הם מעולם לא ראו אותה או לא אפילו לא יודעים מהי.

רוצים להימנע מתרגום נוסח Google Translate או תרגומים מביכים כגון \"רפידת הטקסט\" (TextPad)? – אם כן, כדאי שתעזרו למתרגמים.

מקור: גיקטיים

מתרגמים קצת יותר רציניים יבקשו מסמך המתאר את האפליקציה, הסיטואציה והמשתמשים – או יקבעו פגישה כדי ללמוד ולכתוב כזה בעצמם למתרגמים האחרים. המתרגמים יכולים לעבוד בכל העולם ותרגום מחרוזות האפליקציה שלכם (אם היא לא גדולה) יכולה להיות אפליקציה אחת מתוך ארבעה שהם מתרגמים באותו היום. במיוחד כאשר מדובר בעדכוני-גרסה, ולא תוכנה שעוברת תרגום בפעם הראשונה.
עם מסמכים בפורמטים שונים (Pdf, תמונות, תמונות וקטוריות וכו\') – המתרגמים יכולים להסתבך, ולשלוח לקבלן משנה בעל הבנה פחותה יותר במה מדובר. איך תאמדו את איכות התוצאה?

מה שעושים בדרך כלל (כשרוצים תוצאות יותר טובות) הוא מפרקים את הטקסטים מתוך קבצי המדיה השונים ושולחים אותם כ Strings. משאירים את הטיפול בפורמטים השונים של קבצי המדיה in-house.
אם המערכת שלכם מספקת יכולת לתרגם תוכן-לקוח – זה אומר לאפשר להוסיף מחרוזות שלא נמצאות במערכת.

דבר שני וחשוב יותר הוא הוספת תיאור קצר שמספק את ההקשר לכל מחרוזת. לדוגמה על \"Hall of Fame\" ניתן לציין שזוהי כותרת מסך עם תוצאות המשחק הטובות ביותר או דף באתר האינטרנט המאתר את מורשת החברה. התרגום – יהיה שונה ע\"פ ההקשר שיסופק.

את ההערות מוסיפים פעמים רבות המתכנתים תוך כדי שהם כותבים את הקוד. כל מחרוזת שהיא טקסט לתרגום (לא כל המחרוזות בתוכנה הן כאלו, כמובן) – מתווספת עם הערה. יש סביבות בהן מוסיפים את ההערות בקוד (iOS?) וכאלו שבעזרת כלים נלווים ב IDE (למשל בג\'אווה).

אחרי שמסיימים פרויקט תרגום, נראה הגיוני מאוד לסמן את המחרוזות למשתמש (\"User Strings\") בפרויקט הבא מהיום הראשון, כך שלא יהיה צריך לעבור מחרוזת-מחרוזת בקוד ולאתר את כל הטקסטים למשתמש. כך גם הומלץ בפרק של \"מובייל ובירה\" שעסק בנושא.
מניסיוני, אפשר לעשות זאת אם כלי הפיתוח באמת נוחים. Localization הוא קצת מעבר ל User Strings ולא כדאי להתחיל להשקיע לפני שברור שזו המטרה.

את המחרוזות לתרגום, נוהגים לנהל באחד מ-2 פורמטים נפוצים:
PO/POT – שמקובל בעולם ה Unix. מערכת WordPress, למשל משתמשת בו.
XLIFF – מקובל יותר בעולם הג\'אווה / אנטרפרייז. אפשר להמיר בקלות קבצי properties שמייצר Eclipse ל XLIFF.

עוד בסיס מידע חשוב הוא ה Translation Memory, מין \"בסיס נתונים\" (קובץ TMX או TBX) של המונחים בהם השתמשו במערכת. כאשר מתרגם יקבל מכם עוד עבודה אחרי חצי שנה שלא נגע במערכת (כאילו שהוא זוכר אותה) – ה Translation Memory יזכירו לו באלו מונחים הוא השתמש בעבר והוא יוכל לשמור על קונסיסטנטיות.

כדי שהמתרגמים יוכלו להיות עקביים, גם עליכם להיות עקביים במונחים בהם אתם משתמשים בשפת ה Master Language, כמובן.

כיצד נראה התרגום בקוד

זה כמובן תלוי בשפת וסביבת הפיתוח. אני אצמד לדוגמאות ב Java – השפה בה אני מכיר את הנושא בצורה הטובה ביותר.
בג\'אווה יש מנגנון בשם Resource Bundles שעוזר לנהל user strings בשפות שונות.
את ה Resource Bundle ניתן לייצר בעזרת Wizard ב Eclipse:

באותו הרגע נוצרים הקבצים הבאים:

  • קובץ plugin.properties שכולל את טקסטי ברירת-המחדל / ה Master Language.
  • לכל שפה, אזור או צימוד של השניים שהגדרנו – ייווצר קובץ נוסף, לדוגמה plugin_en.properties או plugin_en_GB.properties.

לאחר מכן ניתן לערוך את קבצי ה properties, כאשר כל key מייצג מחרוזת בכל שפה.

הערה: אצלנו בחברה היה Editor אחר, אולי פרי פיתוח פנימי. אנא סלחו אם אני מפספס פה איזה פרט.

בזמן ריצה של הקוד ישלוף את המחרוזת המתורגמת המתאימה:

ResourceBundle bundle = ResourceBundle.getBundle(\"properties.namespace\", someLocale);

String translatedString = bundle.getString(\"someKey\");

שימו לב שלג\'אווה יש מנגנון fallback אם הוא לא מוצא את הלוקאל המדויק:
אם למשל הלוקאל הוא \"en_US\" אך אין קובץ כזה, הוא ינסה להשתמש ב \"en\". אם אין גם קובץ כזה – הוא ילך לקובץ ברירת המחדל (למשל: plugin.properties).

מה יכול להשתבש ב Localization?  – מיון

אם האפליקציה שלכם מקבלת קלט בשפה שאיננה אנגלית ומנסה למיין אותו – היא עלולה להיכשל.
נתחיל בכך שמתודת ()compareTo של המחלקה String בג\'אווה עלולה כבר לגרום לטעות, אפילו בשפה האנגלית.
מדוע? בגלל הקידוד (להלן כמה יסודות שחשובים בכדי להבין).

בגדול, כל מחרוזת טקסט היא חסרת משמעות – אלא אם ידוע הקידוד שלה. הקידוד הוא כמו מפתח שמסביר כיצד לקרוא את המחרוזת. אם השתמשתם בקידוד שגוי, אתם עשויים לראות במקום טקסט – רצף של קשקושים או ריבועים חלולים (שמשמעם ב\"חלונות\": אות שהייתה תקלה בפענוח שלה ולא יודעים כיצד לפענח).

הקידוד הבסיסי ביותר הוא קידוד בשם ASCII:
ASCII הוא קידוד 7-ביט. כלומר: כל אות יכולה להיות אחת מתוך 128 סימנים או אותיות.
32 התווים הראשונים הם control characters: טאב, רווח, מחיקה ועוד סימנים שרובם חסרי משמעות גרפית (למשל: סוף שורה). שאר התווים הם מספרים, אותיות וכמה סימני-שפה.
ישנן הרחבות לASCII של 8-ביט המוסיפות עוד כ 128 תווים המותאמים לשפות נוספות (כל הרחבה – לשפה אחרת). כלומר כל סימן/אות (character) הוא בית אחד / 8-ביט.

משפחת הסימנים הנראים של ASCII 8bit, בהתאמה לעברית (סימנים במסגרת הירוקה), מוצגים בתוכנת Character Map של \"חלונות\".

מיון בסיסי בשפת ג\'אווה (וברוב השפות האחרות) מתבסס על הערך המספרי של האותיות במחרוזת.
כפי שניתן לראות, הערך המספרי של האות \"Z\" (גדולה) הוא 90, בעוד שהערך של \"a\" (קטנה) הוא גבוה יותר (97) – ולכן מיון יסדר מחרוזות בסדר הבא:

  1. Ant
  2. Zoo
  3. ambulance
…למרות שהיינו מצפים שהמילה ambulance תהיה במקום הראשון (סדר לקסיקוגרפי – כמו מילון).
פתרון נפוץ לאנגלית: לעשות מיון ע\"פ צורת ה upperCase של המחרוזות.

אך זה לא עובד בשפות רבות אחרות….
  • בשוודית, ישנה אות הנכתבת כ ae (או סימן æ) – מקומה בסדר הלקסיקוגרפי הוא אחרי האות \"z\".
  • בגרמנית, כאשר האות s מופיעה ברצף פעמיים – מקצרים את הצמד לכתיבת ß (כמו ביטא). סידור ע\"פ ערכי ASCII ימיין את המילה groß (שקול ל gross = \"גדול\") לאחר המילה grost – מכיוון שערך ה ASCII של ß גדול יותר. זו כמובן טעות צורמת לדובר גרמנית.
  • ע\"פ חוקי הדקדוק של שפות אירופאיות שונות, אותיות מוטעמות (\"accent\") צריכות לבוא אחרי אותיות דומות לא מוטעמות. צרפתית גרועה אפילו יותר: אות מוטעמת מאוחרת היא חזקה יותר, כלומר: יש לבדוק את האותיות המוטעמות מימין לשמאל.
הצרפתים, כידוע, רגישים לשפה שלהם. לא תרכשו ידידות עם לקוח צרפתי בניסיון להסביר לו שמיון ע\"פ הטעמה בחוקים הצרפתיים זו דקות מוזרה או קטנה – ושיסתדר.
אז מה עושים?
אפשר להתייאש. להגיד ללקוחות שככה זה אצלכם ושיעברו לאנגלית, אם זה מפריע להם.
אפשר לנסות ללמוד את כל הבעיות בכל השפות השונות – ולממש אלגוריתם מיון, אך לא כדאי.
אפשר להשתמש בכלי קיים להתמודד עם בעיות ה internationalization – וזה מה שאמליץ לעשות.

ג\'אווה, כבר מגרסאות מוקדמות, כללה סט כלים עשיר ל i18n, רובם תחת החבילה java.text.
במשך השנים, התחזוקה והעדכון של ספריות אלו מעט הוזנח וכיום הן נחשבות עדיין טובות – אך לא \"state of the art\".
אם נושא ה i18n חשוב לכם באמת – הייתי ממליץ להשתמש בספריית ICU של IBM – ספריית open source בג\'אווה (יש גם גרסת ++C) ל g11n המתוחזקת ברמה טובה.
יש גם רשימה של ספריות ג\'אווהסקריפט לתמיכה ב i18n – אולם אין לי ניסיון עמן ואני לא יודע להמליץ.

בג`אווה, הביטוי הבא יבצע השוואה נכונה, ע\"פ השפה הנתונה:

Collator.getInstance(Locale.FRENCH).compare(stringA, stringB)



ל ICU יש גרסה משלה ל Collator – מדויקת יותר.

אם אתם מתכוונים לעשות הרבה השוואות על אותה קבוצת מחרוזות (למשל: מיון תכוף), collator איננו מאוד יעיל ועדיך להשתמש ב CollatorKeys.

סיכום

טוב, כיסינו רק את נושא המיון – אך יש עוד מספר מקרים שכדאי להתייחס אליהם (חיפוש, עיבוד מחרוזות, html וכו\') אותם אני מקווה לכסות בפוסט המשך.

התאמה של אפליקציה לשפות אחרות (\"ריבוי-לשונות\") היא לא רק \"כאב ראש\" ו\"סיבוך נוסף\" – זוהי הזדמנות להגיע לפלח שוק גדול בהרבה, מבלי להוסיף למערכת הרבה פיצ\'רים. בעוד אנשי מקצוע מסוימים (למשל: מתכנתים) \"מחויבים\" לשלוט בשפה האנגלית, עובדים במגזרים שונים ואנשים פרטיים – לא זקוקים לכך. מעבר לכך: הם יכולים לשלוט באנגלית, אך עדיין לרצות תוכנה בשפה שלהם.
ריבוי-לשונות עשוי להיות פיצ\'ר מכניס מאוד למערכת שכבר הוכיחה את עצמה.

כמובן שיש לתהליך globalization מלא יש עלות, במיוחד אם מתחילים לעשות שינויים בקוד (עבור חיפוש, מיון וכו\'). כדאי להכיר את הנושאים ולהשתמש בפוסט(ים) כ reference לאלו בעיות יכולות לצוץ, ולבחור ע\"פ מצב השוק – כמה רחוק ללכת.

שיהיה בהצלחה!

—-

לינקים רלוונטיים:

סקירה מקיפה על פורמטים וכלים על תרגום (אם המערכת שלכם תנהל תרגום): http://edutechwiki.unige.ch/en/Software_localization
התרגומיה, בלוג עברי על תרגום :http://yaeltranslation.com

הו-נתונים! – (AtomPub) חלק 2

זהו פוסט המשך לפוסט ההקדמה על ODATA.

במידה ואתם תוהים כיצד אמור להראות מימוש REST – אז AtomPub הוא דוגמא טובה. הוא תקן ותיק (יחסית, אתם יודעים) שהוכיח את עצמו ורץ בהרבה מערכות, גם של סטארט-אפים קטנים וגם מערכות Enterprise גדולות. יתרה מזו, הוא זכה לכמה הרחבות שהחשובות בהן הן GDATA ו ODATA. ללמוד ולהבין את AtomPub הוא תרגיל טוב על מנת להבין את ODATA – ולשם אנחנו חותרים. GDATA דומה בהרבה ל\"מקור\", אם כי כמה דברים מעניינים לדבר עליהם.

AtomPub – תקן פיצוץ

מבוא לפאב האטום (AtomPub)
בתחילה היה פורמט RSS – פורמט מבוסס XML לתיאור בלוגים. RSS זכה (וזוכה) לפופולאריות רבה בקרב אתרי חדשות ובלוגים.
אולם, ל RSS יש כמה בעיות: התקן לא מפורט עד הסוף ומשאיר כמה שאלות פתוחות – דבר שיכול ליצור בעיות תאימות. למשל: התקן מציין שהתוכן של רשומה יכול להיות HTML או טקסט – אך לא מגדיר דרך לומר במה השתמשו בפועל. על הצרכן לעבור על הטקסט, לחפש תגי HTML ומהם להסיק מהו הפורמט. חובבני משהו.
יתרה מכך, מפתח הפורמט מסר את הזכויות עליו (גרסה 2.0) לאוניבסיטת הארוורד וזו לא הואילה לפתוח את התקן או לשפר אותו בצורה מורגשת. מאז התקן \"נעול\".

סיבות אלו הספיקו ליצור צורך הולך וגובר בתקן חלופי ובעקבותיו הוגדר פורמט ה Atom: פורמט מוגדר היטב, בעל תקינה סטנדרטית של IETF (עוד גוף תקינה שעוסק באינטרנט). התקן זכה לאימוץ מתוקשר ע\"י גולגל וכחלק מ AtomPub הוא אומץ ע\"י מערכות תוכנה רבות.

המודל הבסיסי של אטום הוא פשוט למדי, פיד המכיל מספר רשומות:

יש כאלו שמציינים את היחס בין האובייקטים כרבים לרבים – אך למיטב ידיעתי זו טעות: בפורמט אטום הפיד מייצג את העולם. אם יש אותה רשומה בשני פידים – אז זה \"מקרה\" – זוהי רשומה שונה.

הנה דוגמא אמיתית של קובץ Atom מינימלי (הכולל רשומה אחת):


<feed xmlns=\"http://www.w3.org/2005/Atom\">

Example Feed

2003-12-13T18:30:02Z

John Doe

urn:uuid:60a76c80-d399-11d9-b93C-0003939e0af6

<entry>
Atom-Powered Robots Run Amok

urn:uuid:1225c695-cfb8-4ebb-aaaa-80da344efa6a
2003-12-13T18:30:02Z
Some text.
</entry>

</feed>
אטום מחייב במינימום את השדות שיש בדוגמא זו (Author וכו). זוהי החלטה דיי הגיונית לפורמט של פיד חדשות/בלוג.
הערה קטנה: בדוגמא למעלה הרשומה כוללת שדה Summary. אטום מחייב או Summary או Content (התוכן המלא).

כאשר קובץ הפיד (סיומת .xml. או atom.) יושב על שרת ווב – כל שיש לעשות על מנת לקרוא את תוכנו (עבור Feed Reader כדוגמת Outlook או Google Reader) הוא לבצע קריאת Http get פשוטה לכתובת הפיד, לקבל את הקובץ שלמעלה ולהציג אותו בצורה יפה.

Atompub

AtomPub מוסיף מימד של עריכה לפיד, ע\"פ עקרונות ה REST ומאפשר לבצע פעולות CRUD שונות:

אם ארצה להוסיף רשומה לפיד, פשוט אשלח Http Post לכתובת הפיד, המכילה XML עם הרשומה להוספה וכל השדות המתאימים.
תזכורת: פעולת POST ב REST משמעה: \"שלח מידע למשאב קיים\". הפיד קיים ואנחנו שולחים לו עוד Entry והוא מוסיף אותו לפיד.

להלן הפעולות המוגדרות בתקן (ניתן להרחיב):
על פיד (ליתר דיוק Collection – עוד מעט אסביר) ניתן לבצע:
       GET כדי לקרוא אותו
       PUT על מנת להוסיף רשומה.
על רשומה (ליתר דיוק Member – פריט) ניתן לבצע:
      GET (קריאת רשומה בודדת)
      PUT (עדכון רשומה)
      DELETE (מחיקת רשומה).
על Service Document ניתן לבצע:
      GET.

מדוע אנחנו מדברים על Collection ו Member ולא על פיד ורשומה? מהו ה Service Document??

ובכן… AtomPub תוכנן על מנת להיות פרוטוקול כללי יותר מהשימושים להם נוצר אטום. אי אפשר להתווכח שמונחים כמו \"פיד\" הם דיי ספציפיים לדומיין המסוים של בלוגים/חדשות. על מנת להתנתק מהדומיין הספציפי, AtomPub הגדיר מודל כללי יותר. צעד ראשון להתנתקות הוא הגדרת שמות יותר נכונים. פרוטוקול AtomPub מתייחס ומדבר על אוספים של פריטים. במקרה, הם תמיד נשלחים בפורמט של Atom – ששם הם נקראים פיד ורשומה. זהו הבדל בין המודל האבסטרקטי והמימוש – לצורך העניין.

לא כ\"כ משנה התמרון האקדמי הזה, האלמנט החשוב לדעתי הוא ש AtomPub תוכנן לצרכים רחבים יותר ממה שתוכנן אליהם Atom. הוא בחר להשתמש הפורמט הקיים והמוכר על מנת לא \"להמציא את הגלגל\". האם תמרון כזה מסתיים בהצלחה? כארכיטקט, אני נוטה לענות שלא – על \"תמרונים\" משלמים. אנו עוד נראה שגרורה זו היא אחת המגבלות של AtomPub ונדון האם היא הייתה נכונה.

Service, או בעצם ה Service Document, הוא מסמך המתאר מספר אוספים (Collection) הקשורים לעולם זהה (Service). המסמך מחלק אותם לקבוצות הנקראות Workspaces – אין להם משמעות רבה.

הנה המודל של AtomPub בצורה ויזואלית:

עקרון של REST שאני רוצה להזכיר הוא Hypermedia Transformations. מה שעומד מאחורי השם המפחיד הזה הוא הרעיון לפיו בכל רשומה, (כלומר: בכל פריט. אדבר AtomPub) יש קישורים לפעולות האחרות האפשריות כגון האפשרות לעריכת פריט. הנה דוגמא:

  Some Report
 
  <link href="http://host/products/some_report.atom“ rel=\"edit\"/>
  …

Rel הוא קיצור ל relationship שאומר שהלינק בשורה זו הוא לא לינק לתיאור הפריט אלא בעל משמעות אחרת (במקרה זה – הלינק לעריכת הפריט).
אליה וקוץ בה: המקרה הנפוץ הוא אפליקציה שצורכת את הפידים ומכילה בתוכה את הידע על הפעולות האפשריות. אם יש פעולות חדשות – אין קוד שישתמש ויפעיל אותן והתוצאה היא תוספת מחיר משמעותית בגודל הנתונים מכיוון שיש כמה קישורים לכל רשומה.

אם אתם רוגזים בלבכם עד כמה שזה בזבזני – יש לי שני דברים לומר לכם:
א. אתם כנראה צודקים.
ב. נוסיף קצת פרספקטיבה: תקני *-WS הם בזבזניים משמעותית יותר. כלומר – אנחנו משתפרים.

מעבר לצרכים הבסיסיים (פעולות CRUD)
AtomPub מכיל יכולות נוספות, אגע בעיקריות:
Paging

ברור שאוסף פריטים יכול להיות דיי ארוך ואנו לא תמיד נרצה לקבל (או לשלוח – בצד השרת) את כל הרשימה – לפני שברור שזקוקים לכולה. אולי היא ארוכה מאוד וכוללת אלפי פריטים? ב AtomPub יש מנגנון Paging (השם הרשמי הוא Partial Lists) שנשלט ע\"י צד השרת – הוא מחליט כמה פריטים להעביר בכל Chunk. מסמך האטום שיחזור יכיל קישור עם rel של next האומר \"אם אתה רוצה עוד – גש ללינק הבא\":

למפתחי UI של מערכות סגורות הבחירה לתת לצד השרת להכתיב את גודל ה paging יכולה להראות קצת תמוהה – הרי ה UI יודע הכי טוב מה הוא רוצה. אולם, חשבו REST ועל החשיבות של דפים אחידים על מנת להשתמש ב caches (של HTTP) – יש פה פוטנציאל ממשי.
השרת יכול גם להחליט אם הוא מותיר גם ללכת אחורה (קישור Pervious) או לקפוץ להתחלת או סוף האוסף. אם דיברנו על ההבדלים בין אוסף (collection) לפיד (של פורמט Atom) אז אוסף הוא הסט השלם והפיד הוא view או page שקיבלנו בכל פעם.

Categories
ב Atom (אופס, דילגנו על זה כבר) וגם ב AtomPub יש עניין של קטגוריות. אלו בעצם תגיות (tags) על הרשומות או הפריטים באוסף. יש גם \"מסמך קטגוריות\" שמגדיר את כל הקטגוריות (או תגיות) הקיימות במערכת. דיי בנאלי ולא כ\"כ שווה להתעכב על זה לדעתי.

באספקט התכנוני נראה שהקטגוריות מתאימות מאוד לבלוגים / חדשות, אך יוצרי AtomPub הכניסו פה אלמנט ששייך לדומיין הספציפי. ייתכן וזה היה צעד חשוב לאימוץ ראשוני של הפרוטוקול – אך כיום הוא נראה קצת כפשרה.

Drafts
זוהי יכולת שמתאימה לניהול רשומות שהן עוד בכתיבה, כך שיוצגו רק לעורך/ים ולא לקוראי האתר. הפתרון מבוסס על הפרדה בין פיד לקוראים ופיד לכתובים הכולל גם את הרשומות שבכתיבה. כמו נושא ה categories זוהי יכולת המאימה מאוד לדומיין הספיציפי, אם כי ניתן להכליל אותה למקרה קצת יותר כללי (כמו פריטים שעוד בשלב היצירה).

עוד נקודה מעניינת היא שיכולת זו מעודדת לייצר פידים שונים המתארים אותם פריטים – עם שוני קטן שהוא הפריטים שבעריכה. מימושים רבים המבוססים על AtomPub נוטים להגדיר מספר מצומצם של שאילותות קבועות (פידים) עם URI קבועים אותם ניתן לתשאל. זו גישה שמתאימה ל REST ולניצולת טובה של ה caches אך היא קצת מגבילה את הלקוח ולעיתים דורשת ממנו \"לבחור את פיד-הבסיס\" ועליו לעשות עוד מעבר של \"פילטור ידני\". זו לא גישה רעה – יש פה  tradeoff. בהמשך נראה ש ODATA דוגל בגישה אחרת.

מדיה (Media Library Entries (MLE
כפי שציינו Atom הוא פורמט מבוסס XML. מה קורה אם אני מעוניין לנהל מידע שלא יכול להיות מתואר בצורת XML? כגון תמונות, מסמכים (נאמר PDF) וכו\'? כמובן שאפשר לעטוף את המידע הבינרי ב XML בעזרת בלוקים של CDATA – אך אז פעולת Http Get של פיד תגרום לקריאת כל התוכן הבינרי של כל הרשומות – כמות גדולה של נתונים.
הפתרון של AtomPub הוא לייצר אוספים של רשומות מדיה (מידע בינרי) רשומות אלו נקראות Media Members.

הפיד של רשומת המדיה יכלול רשומות XML המתארות את הפריט וכוללות URI שלו. מעין metadata. אם אתם זוכרים, פורמט atom מחייב מספר שדות חובה כגון \"Author\". האם מעניין אותי לנהל את היוצר של התמונה? אם לא – האם נספק מסמך Atom לא תקני?

ההחלטה של AtomPub היא להחזיר את שדות אלו למיטב יכולתו של השרת, כנראה על בסיס המידע שיש לו על הפיד, וסביר שקצת יפוברקו. רשומות ה Media Library Entries הן בעצם מצביע לקובץ המדיה. הרשומות יכללו לינק אחת לעריכת ה MLE – כלומר ה metadata (בצורת \"rel=\"edit) ו URI נפרד לעריכת קובץ ה מדיה עצמו (בצורת \"rel=\"media-edit)

הערה: פוסט זה התארך מעל לתכנון – יש לי עוד מה לומר ואיני רוצה לקצץ. לאחר כמה ימים רצופים שנאבקתי לסיים את הפוסט הארוך ללא הצלחה החלטתי לחלק את נושא ה AtomPub לשני חלקים ולפרסם כבר עכשיו את החלק הראשון.
אני מוצא את עצמי משקיע לא מעט מאמץ בכניסה לתפקיד החדש (ישן) – כך שנותרים בי פחות כוחות בערבים. אני אשתדל לאזן ולשמר את הכוחות. לילה טוב 🙂

ארכיטקטורה מונחית-שירותים (SOA): על מה המהומה?

הרכינו ראשיכם והחרישו צעדיכם!
בפוסט זה אדבר על נושאי דת.

לא מדובר ביהדות או בנצרות, אם כי בדת לא פחות אדוקה – ושמה: Service Oriented Architecture – SOA.

האמת שאנסה גישה קופטשואית משהו: לדבר אל החילוניים של הדת, בנימה קלילה ובהומור. קרוב לוודאי שכמה מאמיני SOA אדוקים עלולים להפגע. אם אתם במגזר, כדאי לנטוש מייד את הפוסט ולעבור לכאן.

(אם אתם עדיין כאן, אתם יכולים לחזור שנייה ללינק ולהתבונן על התמונה \"דוגמא לארכיטקטורת SOA\". לשם בדיוק אני רוצה לא להגיע)

ישנן גישות שונות ל SOA, רובן כוללות אלמנטים בירוקרטיים של ארגון גדול:

  • יש כאלו שחושבים שסט תקני ה WS-* הם הבסיס לכל פתרון, גם לאינטגרציה בין ארגונים וגם פנימית בתוך הארגון. כיום, זהו קומץ קטן וסהרורי, דיברתי על האלטרנטיבות כאן.
  • יש כאלו שמאמינים ש SOA היא לא רק טכנולוגיה, אלא כמעט דרך-חיים. SOA חוצה את הצד הטכנולוגי וממפה את תהליכי העבודה הקיימים באירגון. כשרוצים להוסיף תהליך עסקי / אירגוני חדש יש ללכת ולמדל אותו ב SOA. סוג של איחוד שמיימי בין אדם ומכונה – שהגבולות הולכים ומטשטשים. כדי לתאר כמעט-כל תהליך בארגון יש לנהל אלפי שירותים. מי ששולט בשירותים שולט בארגון ויש לשים Governance מרכזי על השירותים והשימוש בהם. אלו הם האורתודוקסים של SOA. הם לוקחים את התורה רחוק, רחוק. לפעמים נדמה שעבורם SOA היא כמעט-מטרה ולא \"עוד כלי\". האמונה שלהם ב SOA – גדולה.
  • יש כאלו שמנסים להעמיק בלמידת  הצדדים הטכנולוגיים של SOA. הם מתמודדים עם בעיות שונות ומשונות בעזרת כל מיני משחקים (Patterns) ברמת השירותים והרשת. הם משתמשים ב REST, אך גם ב WS-*. מנסים למצוא איזון בין השניים ולחתור במאמץ לא קטן ל\"ארכיטקטורת SOA נכונה\". הם מאמינים. אלו הם ה\"כיפות הסרוגות\" של SOA, הם הכי קרובים בתפיסה לחילונים, להם אין כל רגשות ל SOA, אבל לעיתים נדמה שאנשי ה\"כיפות הסרוגות\" מתאמצים קצת יותר מדי בכדי לפתור בעיות דווקא בעזרת SOA.
בפוסט זה אנסה להציג כמה רעיונות מוצלחים מהדת שגם לחילוניים כדאי לאמץ גם ממקומם הנוכחי. מן סוג של \"כבד את אביך ואת אמך\" – עצות חברתיות שימושיות.

בראשית

אם תכנות מונחה-עצמים הוא כלי לארגון מערכת-תוכנה ברמת המיקרו, ארכיטקטורה מונחית-שירותים היא דרך אחת לתכנן את המערכת ברמת המאקרו.

לפני עשור (וקצת) דובר הרבה על Component-Based Development. הרעיון היה להחיל את עקרונות ה OO על \"קוביות גדולות יותר\". \"אם תכנון מונחה אובייקטים הוא טוב, למה לא לעשות אותו גם ב High Level?\" שאלו.

למרות ההגיון שברעיון וכמה נסיונות כנים – הרעיון נכשל. ביצוע upscaling לתכנות מונחה-אובייקטים לרמת המאקרו פשוט לא צלח. הגישה הפשוטה והאינטואטיבית של חלוקה למודולים עם תחומי אחריות ברורים והגדרת ממשקים נכונים הצליחה יותר.

…ואז באה SOA. מאיפה היא באה? השגחה עליונה? בתולה קדושה? זינוק אבלוציוני בתובנה של האנושות? – אף אחד לא יודע.
מדי פעם נאמרים דברי כפירה כגון \"הא – חזרנו לתכנון פרוצדורלי של שנות ה 60\" או \"זוהי פשוט התפחות צפויה נוסח \'הברירה הטבעית\' של עקרונות ארכיטקטונים בסיסיים, למשל הגדרת ממשקים מוגדרים-היטב\". כדאי לשקול דיבורים שכאלו בשיחה עם אנשים מאמינים!

אמנם החשיבה של שירותים סותרת לכאורה את סגנון התכנון ה Object Oriented הנפוץ כיום, אך יש לה שני יתרונות:

היא פשוטה והיא עובדת. אין מניעה, ואולי אפילו מומלץ, שכל שירות יהיה בנוי בעצמו בצורה Object Oriented.
\"כל מה שעשינו עד היום – רע, ומהיום הכל יהיה טוב\" רומזת כרזה שיווקית של SUN, אחת המשקיעות הגדולות ב SOA.
נדמה לי שאני זוכר את השקף השמאלי מככב בצד ימין לפני עשור כשדובר על ארכיטקטורת N-Tier 🙂  מקור sun.com

שמות
ואלו שמות ומושגים בעולם ה SOA:
WS-*, ESB, EAI, SOAP, MOM, WSDL, UDDI, REST, SLA, DDS, JBI, CEA, E-SOA, Event-Driven SOA, Middleware, Business Process, BPM, BPMN, BPEL, SOMA ועוד ועוד…

סתם, לספוג קצת אווירה.

ויקרא
כפי שציינתי – אני אנסה להתמקד בעקרונות העקריים של SOA בסיסי. במקום בו SOA היא עוד כלי טכנולוגי ולא תוכנית זדונית למפות ולשלוט, מתוך התוכנה, על בני-האדם. 🙂

לא כל מערכת עם כמה שירותים נפרדים היא SOA. הנה מספר עקרונות מרכזיים ההופכים את הארכיטקטורה שלכם ל SOA:

הכמסה של שירותים
על השירות לכמוס (= לא לשתף) את פרטי המימוש שלו. האם הוא בנוי Object Oriented או Data Oriented? האם הוא משתמש בבסיס נתונים או בזיכרון? האם הוא משתמש ב Cache או לא? – כל אלה פרטים שכדאי למנוע ממשתמשי השירות כך שלא ייקשרו אליהם ויפגעו משינויים במימוש.

Service Contract
לכל שירות יש חוזה פעולה ברור. החוזה של השירות הוא לרוב ה API.
עד כמה ששפות התכנות מפותחות – הן עדיין מוגבלות ביכולת הביטוי. חשוב להבין שה API הוא רק חלק מהחוזה הכולל. כלומר, בעזרת Interface בשפת #C או Java אני יכול לומר מהן המתודות והמשתנים שהשירות מצפה לקבל, אך אני לא יכול לבטא דברים כמו:

  • האם קריאה לשירות היא יקרה או זולה (Performance)
  • לאיזה התנהגויות הוא תוכנן ולאיזה לא (הנחות יסוד). באיזה מקרים הוא לא תומך או לא נכון להשתמש בו.
  • התנהגות במקרי קיצון
  • וכו\'
כל אלה מרכיבים את החוזה של השירות. כדאי מאוד שהחוזה יהיה מפורש וברור: גם למי שמפתח את השירות (נשמע ברור, אך לא תמיד זה כך) וגם למי שצורך אותו.
הכלים לתיאור החוזה הם:
  • אכיפה ברמת השפה  (למשל טיפוסים) / פרוטוקול (למשל MIME TYPE).
  • שמות נכונים של השירות, המתודות והמשתנים.
  • מטאפורה, חלוקה לשירותי משנה בצורה שמכוונת את המשתמש נכונה.
  • תיעוד, תיעוד תיעוד.
באופן תאורטי היה נחמד אם היה אפשר להחליף את שירות אחד בשירות עם מימוש אחר שעונה לאותו contract, מבלי שאף אחד מהלקוחות שלו ישים לב.
עצה טובה היא להתחיל שירות בתכנון החוזה ורק אח\"כ לעבור למימוש, בדומה מאוד לתכנון ממשק משתמש. מה שחשוב הוא שהחוזה היה נקי, יציב ומלוטש. על המימוש אפשר להמשיך לעבוד אח\"כ.
Service Policy

ברגע שהמערכת היא מבוזרת (מערכות גדולות לרוב מבוזרות בצורה כזו או אחרת), עלינו לפתור עוד מספר עניינים:
איך מוצאים את כתובת השירות? אבטחה (Authentication, Audit) של השירות? התנהגות השירות בעת עומס / תקלות ועוד.
במקום לפתור את הבעיה כל פעם מחדש – אני יכול לפתור אותה פעם אחת בצורה מרוכזת ע\"י הגדרת מדיניות לכל השירותים במערכת / ארגון. מצד שני לשירותים שונים יש צרכים שונים. חלקם מכילים מיידע חסוי – חלקם לא. חלקם קריטיים לפעילות עסקית, ונרצה שתמיד יהיו למעלה גם במחיר גבוה, – וחלקם לא.

הרבה פעמים מקובל להגדיר כמה סוגי מדיניות שונים של שירותים. הדבר דומה לרשיונות קוד-חופשי נוסח Apache או GPL – במקום שספק הספרייה יתעמק בנושאים משפטיים על מנת להגדיר רשיון הוא בוחר בנוסח סטנדרטי שמתאים לו ביותר, מסט רשיונות קיימים. גם הצרכן של הספריה יכול מהר מאוד ללמוד: MIT = אומר משהו כזה, LGPL = אומר משהו כזה.

אין הגדרה חד משמעית מה אמור להכיל ה Policy – יש גישות שונות. יש כאלו שיכילו אלמנטים של אבטחה וגישה – יש כאלו שיכללו בהם SLA או צורת ההתקשרות (messaging, request-response). העניין המעניין הוא שזהו חלק בחוזה שמשותף להרבה שירותים ואין טעם להגדירו כל פעם מחדש, יהיה החלק מה שיהיה.

ומחשבה קצרה בצד: אם נחשוב בצורה יותר מופשטת, אין קשר חזק בין איך עובד השירות לאיך מוצאים אותו, מבצעים Authentication אליו, היכן השירות ממוקם גיאורפית וכו\'. יש decoupling אמיתי בין מה שהשירות מספק לאופן הצריכה של השירות. על בסיס זה ניתן לעשות הרבה משחקים ווריאציות. זו יכולה להיות הזדמנות לכמה פתרונות ארכיטקטוניים מעניינים ולא מעט דיונים ופילפולים הנגמרים בהסתבכויות בלתי-רצויות. ל SOA יש על כך גם \"גמרה\" וגם \"משנה\" – יש היסטוריה של אנשים שהלכו רחוק מדי עם SOA אל חזון שנשמע מתוחכם אך לא היה מעשי – כדאי להזהר.

תכננו לעצמאות מירבית
כפי שציינו, השירותים לרוב יהיו חלק ממערכת מבוזרת. במערכת מבוזרת יש לעיתים Latency (אם היא מבוזרת על פני Data Centers) אבל גם ייתכנו כשלים: שירות לא זמין, נתק ברשת וכו\'.
כשאתם מתכננים שירות עליכם לדאוג שהוא ימשיך לעבוד טוב ככל האפשר כאשר שירותים אחרים שהוא מסתמך עליהם אינם זמינים. טעות דבילית למדי (סליחה, היסטוריה אישית) היא לבצע קריאה סינכרונית שנכנסת לBlocking לשירות אחר. אם השירות האחר חי אבל תקוע – גם השירות שלכם ייתקע במהרה.
כאשר שירות אחר שאתם תלויים בו כושל – תרצו להחזיר תשובות פחות-טובות או להחזיר הודעות שגיאה. לא תרצו לא-להגיב או להתקע (ואולי לתקוע שירותים אחרים שאינם זהירים).

במדבר
חשבתם ש SOA הוא גן של שושנים? חשבו שוב. על מנת להצליח עם SOA יש לחצות מדבר של סכנות. השוק הוא תחרותי – אז מומלץ שתעשו זאת בפחות מ-40 שנה.

סכנה ראשונה היא לקחת ספר של SOA ואשכרה לעבוד לפיו. סיכוי טוב שתעשו over-over-engineering. עצה טובה ב SOA היא להתחיל בקטן ולגדול בזהירות רבה ובהדרגה. דיי בטוח של-SOA יש הרבה יותר מה להציע ממה שהמערכת שלכם צריכה.

סכנה שנייה היא יצירה של המון שירותים. שמעתי כבר את המשפט \"מעולם לא הצטערנו על שירות שחילקנו ל 2\" מפי אנשים שאני מעריך, אבל בעיה נפוצה היא להפוך כל 3 פונקציות בסיסיות לשירות – ה overhead הפוטנציאלי הוא אדיר. שירות צריך להיות coarse-grained ולתאר פונקציה גדולה ומשמעותית מספיק.

סכנה שלישית היא, במערכת מבוזרת, לחלק שירות – לשרת פיסי. כתבתי על זה בהרחבה כאן. טעות נפוצה וקשה.

סכנה אחרונה שאציין היא התעסקות עם תקני WS-*. אלו תקנים סבירים לחיבור בין מערכות שונות מאוד (שפה שונה, אירגון שונה, מערכות Legacy) – אבל דיי overkill לרוב השימושים האחרים. התחילו בקטן עם שירותים מבוססי HTTP Messages או REST.

דברים
כמה דברי סיכום:

SOA קושרה בצדק או לא (תלוי את מי שואלים) ל Web Services ו WS-* עם הבעיות הרבות שלהם. SOA יכולה להיות מוצלחת למדי – אם מצליחים לעשות אותה במידה ובמקומות המתאימים.

ל SOA יש כמה ייתרונות ברורים:

  • צורה פשוטה יחסית לבניית מערכת מבוזרת – מערכות שקל מאוד להסתבך איתן.
  • פוטנציאל טוב לשימוש חוזר בקוד (רעיון נשגב, שפעמים רחוקות יוצא אל הפועל). שירות הוא רמה מצויינת לשימוש חוזר: בעל משמעות, אך לא נקודתי מדי.
  • פרדיגמה פשוטה שקל להבין.
  • בניה של שירותים עצמאיים עם תלות נמוכה תקל על ה Upgrade ותפחית את ה down-time של המערכת: ניתן לעשות upgrade לשירות אחד בלבד – ושאר השירותים יתמודדו עם ה down time בצורה טובה. יכולת זו תקל על יישום של Continuous Delivery.
  • הגדרה של שירותים הפועלים ע\"פ חוזים תקל על מתכנני המערכת לבקר את נכונות הארכיטקטורה של המערכת: ניתן להתמקד בחוזה של השירותים והתלויות בין השירותים – ללא הצורך להכיר כל פינה במערכת.

שמים לב לקשר בין הנקודות?
מערכות מבוזרות…? שימוש-חוזר בקוד…? Continuous Delivery ו Availability…?

SOA והענן. מקור: http://webtechnologiesarticle.blogspot.com/

צודקים לגמרי! SOA פורחת מחדש בעולם הענן. היא מתאימה למדי ואכן היא זוכה לשימוש נפוץ. ציינתי אותה כתכונה עשירית ב 10 המאפיינים של שירותי ענן.

בהצלחה והמשיכו בזהירות. נתראה בחגים!

עננים ציבוריים ועננים פרטיים (Cloud Computing)

זהו פוסט המשך לפוסט שדיבר על PaaS, SaaS ו IaaS, ולפוסט 10 תכונות של שירותי ענן.

ארגונים רבים הביטו בשנים האחרונות על הענן בקנאה: הענן, מלבד היותו באזז מגניב, מספק יתרונות ממשיים בעלויות ובגמישות לארגונים שהצליחו לאמץ אותו בהצלחה. ישנם גם קשיים: אפליקציות בענן שוברות לא-מעט מוסכמות והרגלים קיימים, מציבות אתגרים חדשים בבקרה ואבטחה.

דמיינו שאתם משתמשים באפליקציית-ענן לניהול לקוחות ופרטיהם הרצה על הענן של אמזון. מידע רגיש וקריטי לארגון שלכם יושב באתר המנוהל ע\"י ארגון אחר. אין לכם שום ידיעה מי נכנס ומתחבר פיסית למחשבים שהוקצו לכם – ויכול לגשת ולהעתיק / לשנות את הנתונים.

נאמר שההגנה הפיסית טובה מספיק, אך אתר כלשהו שרץ על אמאזון הוציא לשון הרע של ארגון אחר ופגע בו. בהוראת בית משפט יכול ה FBI להכנס לחדרי השרתים של אמזון ולהחרים את החומרה. על אותו node או בלוק של Storage – גם אתם ישבתם, ביש מזל. המידע שלכם מוחזק ונבחן עכשיו בידי עובדים של ה FBI.

גם מבחינת חומרה, אם אפליקציה או מידע מסוים חשוב לכם יותר אתם יכולים לרכוש חומרה ייחודית, מנהל ה IT יוכל להורות על תחזוקה תכופה יותר. אם וירוסים משתוללים הוא יכול להורות על סריקת כל המחשבים ב Data Center. שליטה זאת בדרך כלל לא-אפשרית בענן. אמנם יש ספקי ענן, כמו Racksapce, שיתנו לכם להתקין חומרה ע\"פ דרישה, אך זה רק צעד אחד והם לא ימלאו חוסרים אחרים – שאותם כן הייתם יכולים למלא אם ה\"ענן\" היה יושב ומנוהל אצלכם בארגון.

כשאמזון הציגו את פתרון הענן שלהם הם עשו תצוגת תכלית של אבטחה: קירות בטון, מצלמות אבטחה, שומרים מגודלים וכלבים רעים. משהו נוסח חומת ברלין בזמן המלחמה הקרה[1]. \"בוודאי יותר אבטחה ממה שיש לכם היום\" הם הצהירו. מה קרה מאז? עד כמה מנגנון האבטחה החזיק מעמד? אף עובד שכפוף אליכם לא יכול \"לקפוץ לביקור פתע\". מנהלים מכירים היטב את הפער ברמת המחויבות של עובדים שכפופים אליהם וכאלו שלא.
במידה רבה אלו הם שיקולים פסיכולוגיים, קרוב לוודאי שגם אמאזון דואגים לאבטחה – יש להם הרבה מה להפסיד. בכל זאת אלו דאגות מוחשיות המקשות על ארגונים לעבור לענן ציבורי.

אינטרנט פרטי?
באופן דומה להפליא, ארגונים רבים התקנאו בעבר באינטרנט וכל היכולות שהוא הציע. בתחילת שנות התשעים רוב הארגונים עוד עבדו עם רשתות של נובל או מייקרוסופט שתוכננו במקור לקנה מידה קטו בהרבה: עשרות עד מאות מחשבים. טכנולוגיות כמו Token Ring ו NetBIOS (או גרסה יותר מתקדמת שנקראה NBF) איפשרו יכולות די בסיסיות והיוו את הסטנדרט הארגוני. \"רשת\" לא הייתה יכולת מובנית במערכת ההפעלה. על המשתמש היה להתקין מערכת הפעלה, \"חומרה יעודית לרשתות\" (כרטיס רשת) ותוכנה (נובל או מייקורוספט) להרצת הרשת. לנובל, אם אני זוכר נכון, היה נדרש שרת ש\"ינהל את הרשת\". חשבו באיזה קלות אתם מתחברים היום עם ה iPad לרשת הביתית.
האינטרנט נחשב לאיטי (הגישה לרוב הייתה דרך קווי טלפון), חסר תמיכה בצרכים ארגוניים (לדוגמא הדפסה) ובלתי-ניתן לשליטה. בכלל – הוא תוכנן כאילו יש בעולם רק אינטרנט אחד(!). למרות זאת, טכנולוגיות האינטרנט היו יעילות בהרבה וככל שלארגונים נוספו עוד ועוד מחשבים, \"הרשתות הארגוניות\" התקשו לעמוד במשימה.

בתחילת שנות ה-90 אוניברסיטאות, וכמה שנים אח\"כ גם ארגונים עסקיים, התחילו להטמיע \"טכנולוגיות אינטרנט\" ברשת הארגונית. על מגבלת המחסור ברשתות התמודדו עם subnet masking ואת שירותי ההדפסה העבירו על גבי TCP. בהדרגה, פחת החלק של הטכנולוגיות של מייקרוסופט ונובל והוחלף ע\"י טכנולוגיות אינטרנט סטנדרטיות: HTTP, אתרי אינטרנט (\"פורטל ארגוני\"), Firewalls, דואר אלקטרוני ועוד.
הסיפור אינו אמור להפליא, הוא מתרחש שוב ושוב במהלך ההיסטוריה: טכנולוגיה עם ייתרון מובנה (scale במקרה שלנו) מתחילה בעמדת נחיתות, המתחרים מזלזלים וצוחקים עליה אך הבעיות בה נפתרות אחת אחת עד שהיא הופכת להיות מתמודדת ראויה. בשלב זה הייתרון המובנה של הטכנולוגיה החדשה אינו ניתן לחיקוי ע\"י המתחרים המסורתיים – והמערכה מוכרעת לטובתה. כך היה עם הטלפון שבגרסאות הראשונות היה מוגבל לטווח של 10 ק\"מ ודרש חיווט ידני. מנהלי המוצר של חברות הטלגרף, חברות בעלות אמצעים אדירים, צחקו על הטלפון והסבירו ש\"בשביל 10 ק\'\'מ תלך ותפגש עם האדם פנים-מול-פנים. כל הבלאגן כדי לדבר איתו בטלפון הוא פשוט use-case מגוחך\". בל ניסה למכור ל Western Union את הפטנט ב 100,000 דולר – אך הם ויתרו. התוצאה כיום ידועה. הרכבים הראשונים היו ללא בלמים, על הנהג היה ללחוץ על הקלאץ\' כל הדרך לעצירה. חברות הרכבת, תאגידים עצומי-מימדים, גיחכו והתעלמו. התוצאה ידועה. כך גם עם המחשב הפרטי (PC) ועוד ועוד… [3]

ע\"פ סקר עכשיווי (מקור, עמ\' 5) שתי הדאגות העקריות של ארגונים מאפליקציות ענן הן אבטחה וביצועים (זמני תגובה, איכות הרשת וזמינות). את שתי הבעיות הללו ניתן לפתור ע\"י הטמעת \"טכנולוגיות ענן\" בתשתית הארגונית: להתקין כמה עשרות שרתים עם טכנולוגיות Virtualization, אלסטיות וניהול אוטומטי – ולהריץ ענן קטן.

שלושה סוגים של עננים \"פרטיים\"
בשונה מ\"עננים ציבוריים\" המתאורים בפוסט 10 תכונות של שירותי ענן, יש כמה סוגים של \"עננים פרטיים\" אשר שונים בכמה תכונות עקריות. נחלק אותם ל:

  • ענן פרטי (Private Cloud)
  • ענן מנוהל (Hosted Cloud)
  • ענן משותף (Community Cloud)

ענן פרטי
מגמה שתופסת תאוצה היא ארגונים שרוצים להריץ את אפליקציות הענן – In House. \"שלחו לנו את ה Appliances\" הם מבקשים מאיש המכירות של אפליקציית ה SaaS – \"ה IT שלנו יתקין ויתחזק אותם, מקסימום עם קצת תמיכה מכם\". ספקי הענן לרוב מופתעים בהתחלה – אך יש כסף בצד השני והמעבר הוא לא כ\"כ קשה:

  • אפליקצית הענן לרוב נכתבה עבור חומרה לא ידועה. ניתן לבחון שרתים סטנדרטיים של חברות כמו IBM או HP ולמכור אותם כ \"Appliance\".
  • נוהלים וכלי אוטומציה לניהול הענן – כבר יש. לבנות גוף תמיכה על בסיס ידע קיים – לא כ\"כ קשה.
  • \"טכנולוגיות הענן\" אינן נחלתן הבלעדית של אמזון או מייקרוסופט, ישנן ספריות קוד-פתוח כגון OpenStack או vCloud שמספקות יכולות דומות.

סוג אחר של ענן פרטי הוא ארגון שמפתח אפליקציות בעצמו (או עם קבלנים) ורוצה להריץ אותן עם כל היתרונות של הענן. במקרה זה הארגון יקים DataCenter של עשרות או מאות שרתים, יקים צוות Operations מתאים – והענן הפרטי מוכן לפעולה.

שאלה לגיטימית היא למה פתרון שכזה הוא \"ענן פרטי\" ולא \"Data Center מנוהל מרכזית\"?
השוני הוא, במידה רבה, בשימוש בוירטואליציה. וירטואליזציה שמאפשרת לאפליקציות לרוץ על מספר שונה של שרתים – ע\"פ הצורך. אמנם הארגון צריך להחזיק מספיק מכונות לתמוך ברגעי שיא של צריכה, אך הוא יכול לווסת בין האפליקציות השונות שרצות על אותה חומרה. הסבירות ל Peak בשימוש בכל האפליקציות בו-זמנית הוא קטן[4]. עוד יכולת מעניינת היא היכולת של ה IT לחייב את היחידות הארגוניות השונות ע\"פ שימוש בשירותי המחשוב בפועל.
לרוב הענן הפרטי יהיה קצת יותר יקר מענן ציבורי – יש פחות ייתרון לגודל והנצילות של החומרה נמוכה יותר, אך יתרונות האבטחה והרשת המהירה מצדיקים את מחיר הפרמיום עבור ארגונים רבים.

ארגונים שהקימו ענן פרטי בהצלחה והגיעו למצויינות תפעולית / אפליקציות מעניינות – יכולים להתחיל ולהציע את שירותי הענן שלהם לארגונים אחרים, כעסק משני. כך למשל התחילה אמזון.

עוד מודל מעניין הוא חברות שיש להן הרבה מאוד חומרה לגיבוי שאינה בשימוש רוב הזמן, אך בעזרת טכנולוגיות ענן הן יכולות להציע שימוש בחומרה עבור אפליקציות שיסכימו \"לרדת ברגע\" במקרה של תקלה בציוד הראשי של הארגון. דוגמא טובה לכך הם Carriers שמחזיקים חומרה רבה לגיבוי, הפריסה שלהם רחבה ומגוונת והם לא היסטריים לאבטחה (כמו בנקים או חברות ביטוח, למשל).

ענן מנוהל
זהו שלב-ביניים בין ענן פרטי לציבורי: ארגון הרוצה אבטחה גבוהה ורשת יציבה ממה שמספקים ספקי ענן ציבוריים, אך לא רוצה לנהל את הענן בעצמו. חברות כמו HP, GoGrid ו IBM ישמחו לעשות זאת עבורו עבור תשלום (לא-)צנוע. חברות אלה מספקות שירותים של Hosting ל Data Centers של ארגונים כבר במשך שנים והן צברו מיומנות לא מבוטלת. אמנם ספק ה Hosting יושב באתר מרוחק (עם כל המגבלות שבכך), אך עבור התשלום המתאים הוא ישמח לפתוח VPN על גבי קו אינטרנט מהיר שישפר בהרבה את ביצועי הרשת והאבטחה שלכם.

ענן משותף
סוג ענן זה הוא עדיין בחיתוליו – אך נראה שיש לו הרבה פוטנציאל. חשבו על הענן הפרטי שמקימה רשת בתי חולים גדולה, למשל (Hospital Corporation of America (HCA – רשת אמריקאית של 150 בתי חולים ב 270 אתרים. HCA הוא ארגון-העל המשרת בתי-חולים רבים. כאשר ארגון מנהל מידע רפואי של חולים, יש עליו דרישות מחמירות בתחום אבטחת הפרטיות של של חולה. רופא שיחשוף פרטים חסויים של מטופל – עלול להשלל רשיונו. מה יקרה לאיש-IT רשלן? לצורך כך הגדירו בארה\"ב תקן מחמיר בשם HIPPA המחייב ארגונים המחזיקים במידע רפואי של חולים לנהוג ע\"פ סדרה מסוימת של נוהלים. אני לא מקנא בקבוצת הפיתוח שתאלץ להתמודד עם התקן בפיתוח תוכנה בענן,  אך לאחר שתאימות ה-HIPPA הושגה, תוכל HCA להציע את השירות לכל בתי-החולים ברשת.
ומה עם שותפי-מחקר? אוניברסיטאות, חברות תרופות ועוד? גם הם מחזיקים במידע רגיש הנכלל בתקן ה HIPPA. מלבד הייתרון של \"לא להמציא את הגלגל מחדש\", יש עוד ייתרון לאותו שותף עסקי שיצטרף לענן של HCA: הוא יוכל להציע את השירותים שלו לבתי-החולים השונים עם Latency נמוך (הרי השירותים יושבים באותו Data Center) ואבטחה גבוהה (התקשורת לא עוברת באינטרנט הפתוח)!

אם אתם זוכרים את הפוסטים הקודמים, ציינו שאחת המגמות הפחות מפורשות של שימוש בענן הוא אימוץ SOA ובניית המערכת בעזרת שירותים אחרים בענן. מצד אחד – זהו שיפור משמעותי ביכולת לפתח אפליקציה בקלות. מצד שני – לא ברור היכן השירותים הללו יושבים. אולי הם מפוזרים אצל ספקי IaaS/PaaS ברחבי העולים? ה Latency לפעולה הדורשת קריאה למספר שירותים, הקוראים לשירותים אחרים יכולה להצטבר לזמן משמעותי.
עוד אלמנט מורגש, למי שפיתח מערכת התלויה בשירותים שונים בפיזור גאוגרפי, היא בעיית הזמינות. ככל שהמערכת שלי תלויה ביותר שירותים חיצוניים כך גדל הסבירות שאחד מהם לא זמין ברגע מסוים. האם זו בעייה של ספק השירות, ספק הענן הציבורי או בעיית תקשורת – זה לא משנה בכלל. השירות לא זמין והפונקציונליות (או יותר גרוע – הזמינות) של האפליקציה שלי – נפגעת.

עבודה בתוך ענן משותף מאפשרת לשירותים מתחום דומה להשען על תשתית קרובה ואמינה בהרבה ולהגביר את הזמינות אחד של השני.

סיכום
כמובן שהחלוקה שלי כאן היא אחת וניתן לחלק את סוגי העננים בצורות שונות. בכל זאת, רציתי לתאר כמה היבטים פחות מוכרים של טכנולוגיות הענן. רבים בתעשיית התוכנה מאמינים שענן הוא המהפכה המשמעותית הבאה, ומכיוון שכולם (כמעט) עשו MBA ומכירים את ה-Case-Studies שתוארו לעיל (או דומים), הם לא ממתינים בחיבוק ידיים. הענן הוא לא רק אמזון, למרות ההצלחה המרשימה. יש מקום לעוד הרבה שחקנים, יצירתיות ואתגרים טכנולוגיים ועסקיים.

בהצלחה.

הערות שוליים

[1]  מערך ההגנה של חומת ברלין הוא סיפור מעניין בפני עצמו:

  • 302 מגדלי שמירה עם שומרים חמושים.
  • קיר בטון חלק בגובה 4 מטר עם גדרות תייל בראשו
  • שדה של ברזנטים מחודדים (שנקרא \"העשב של סטאלין\") שמקשה מאוד על ריצה והופך נפילה למסוכנת.
  • 20 בונקרים עם שומרים בקו ההיקף של השדה
  • מאות שומרים חמושים מלווים בכלבים תוקפניים
  • שביל גישוש ברוחב 6 עד 15 מ\' עם פטרול לגילוי חדירות למרחב
  • תעלה למניעת מעבר של רכבים
  • גדר חשמלית וגלאי תנועה
  • מרחב גדול שהושטח על מנת להסיר מקומות מחבוא אפשריים (שנקרא \"רצועת המוות\")
בודדים הצליחו לברוח דרך קו הגנה זה, רובם שומרים. רוב הבורחים מגרמניה המזרחית פשוט ברחו ממקום אחר (מה שמזכיר את הסינים שבנו במערב המדינה חומה אדירה באורך 5000 ק\"מ בכדי למנוע מג\'ינגיס חאן לפלוש, אך הוא פשוט עשה מעקף ופלש מצפון).

[2] מנכל אינטל, אנדי גרוב, ניסה ללמוד את הלקח וגרס \"רק הפרנואידים שורדים\". עד היום אינטל הפליאה להיות קשובה לשינויים: קו מעבדי הסלרון, מעבדים חסכניים באנרגיה ועכשיו מעבדים למחשבי tablet ואבטחה בחומרה. כל אלו תגובות של אינטל למגמות שלא הומצאו אצלה אך היא נותרה קשובה. האם מודעות מספיקה? האם ארגון רגיש-לשוק יצליח להיות מספיק גמיש כדי לשרוד את שינויי המגמה בעולם? האם התרבות הארגונית וההשקעות הקיימות לא יכבלו אותו, מתישהו, להשאר בפינה \"נוחה\"? שאלה טובה – אין לי תשובה.

[3] המעבר מ Appliances לענן הוא לרוב קשה בהרבה!

[4] אמזון וספקי IaaS אחרים אוהבים ליצור את הרושם שיש להם Data Centers אינסופיים – אך גם הם מוגבלים.

על Domain Driven Design

האם נתקלתם אי-פעם בתוכנה שקשה לתחזקה?
האם אי פעם קיבלתם דרישה קטנה שהייתה קשה במיוחד ליישום, כאילו המערכת שלכם פשוט לא מוכנה לקבל אותה?
בפוסט זה אחשוף טכניקה מתקדמת בה משתמשים המקצוענים על מנת להמנע-מ להקל על מקרים כאלו.

הקדמה
הקשר בין גודל התוכנה לסיבוכיות שבה הוא קשר ברור וידוע.

עוד עובדה ידועה היא חוסר הבהירות הכמעט-קבועה לגבי הדרישות בזמן הפיתוח (אלא אם אתם חסידי Waterfall שמאמינים ש\"אצלי זה לא קורה\").

בסופו של דבר (בשאיפה), התוכנה פוגשת לקוח, הלקוח מרים גבה, הדרישות משתנות, והשינויים במערכת גדולה ומורכבת – הם קשים.

כיצד ניתן לשנות זאת?

  • קבלת דרישות איכותיות יותר
  • בניית מערכת פשוטה יותר
  • העברת הפיתוח להודו = לא רלוונטי, גם ההודים סובלים משינויים קשים.

עד כאן, לא חידשנו כלום.
כיצד מקבלים דרישות איכותיות יותר? \"מתמקדים בלקוח\"? \"שמים את הלקוח במרכז\"? \"חושבים טוב-טוב\"?
ואיך בכלל יוצרים מערכת פשוטה יותר? \"חושבים פשוט\"? \"עושים KISS\"? \"עובדים לאט ובזהירות\"?

הרבה יודעים לתת הנחיות וטיפים, אך מלבד בודדים (כמו תנועת האג\'ייל שהציגה שיטות ישימות), הרוב סתם מדברים. פעם עבדתי בחברה בה הביאו מרצה אורח שדיבר על פשטות ובסופה חילקו לכל העובדים ספר משעמם עד גרוע על פשטות. המרצה סיפר בהתלהבות כמה פשטות היא טובה בכל תחומי החיים, אך מלבד העצה \"לחשוב פשוט על פשטות\" – הוא לא עזר בכלל להגיע לשם 🙁

ובכן, היכונו! אוונס וה DDD (כלומר [Domain Driven Design [1) הולכים ללמד אתכם כיצד לקבל דרישות איכותיות יותר וכיצד לבנות מערכת שתהיה גמישה יותר לקבלת דרישות עתידיות. הדרך להתמקצעות היא לא פשוטה, אך כל מי שיש לו גישה לדרישות של לקוחות וקצת חשיבה מופשטת יכול די מהר להגיע לתוצאות ראשונות.

מעט היסטוריה
את המונח DDD טבע אריק אוונס בשנת 2003 בספר בשם זהה, שעורר לא מעט הדים וזכה להערכה רבה. מאז יצאו כמה ספרים ואתרים המוקדשים לזרם החדש שיצר.

אוונס לא ניסה ליצור זרם חדש בעולם התוכנה, כל מה שהוא רצה הוא להציע דרך איך לפתח מערכות תוכנה גדולות ומורכבות כך שלא יצאו כ\"כ מסובכות. הרעיונות שהציג היו שילובים של רעיונות קיימים מעולם ה Object-Oriented ומכמה עולמות אחרים, אך הוא הצליח לחדד כמה עקרונות שקודם לכן לא הוצגו בצורה כ\"כ ברורה ושימושית.

על התהליך הנפוץ לתכנון תוכנה
לא משנה אם אתם עובדים Waterfall או Agile, קרוב לוודאי שהמתכנתים לא אוספים את הדרישות מהלקוח בעצמם. יתרה מכך, גם שמדברים עם הלקוח לא תמיד יהיה זה המומחה העסקי. ייתכן ואתם מדברים עם מנהל התפעול בבנק (\"לקוח\") שרוצה מערכת לניהול משכנתאות, אבל אתם לא מדברים עם מי שמתעסק עם זה בפועל (Domain Expert). על מנת לפשט לכם את הנושא, מנהל התפעול משתמש במושגים שיותר קלים להבנה. ה PM לוקח צעד אחד הלאה ומשתמש במושגים יותר מקובלים מהעולם-הלא-מקצועי כי \"מפתחים יאבדו כיוון אם נציף אותם בכל המידע הזה\". זהו הרי תפקידו.
הארכיטקט או המומחה הטכנולוגי מפשט את הדברים קצת יותר להתאים לתשתית הקיימת , זה תפקידו, והופ – המפתחים מבינים בקלות על מה מדובר וניגשים מייד לעבודה.

הנה דוגמא ויזואלית של הסיפור עבור מערכת מעקב חיובים. אמנם פיתחתי כזו לפני 10 שנים ויותר, ובוודאי שכחתי את הרוב. סליחה על אי-דיוקים או חוסר שלמות במודל. הדוגמא למטה אינה מבוססת על מספיק ידע בכדי לפתח מערכת חיובים ע\"פ ה DDD, אבל אני מקווה שהיא מספיקה לצורך הדגמת התהליך (יש לקרוא משמאל לימין):

מקור: softwarearchiblog

כפי שסיפרנו ה Domain Expert (אשתמש ב DE מעכשיו) משתמש בטרמינולוגיה משלו וכל שאר הגורמים בדרך מתרגמים, שלב אחר שלב, כך שלמפתחים יהיה ברור מה \"עליהם לעשות\". הכל טוב, לזמן מה – עד אשר מגיע שינוי לא-צפוי בדרישות:

מקור: softwarearchiblog

אולי לא בשינוי הראשון ואולי לא בשני, אך מתישהו, ובד\"כ לא מאוד באיחור, מגיע דרישה שקשה לתרגם. אמנם בעולם של ה DE היא הגיונית ופשוטה למדי, אך שרשרת התרגומים יצרה עולם מושגים ששונה מאוד מעולם המושגים של ה DE. המערכת מסתבכת. עוד כמה הפתעות כאלו וכל המערכת היפה שיצרנו תהפוך לתל-בלאגן.

בואו נעצור לרגע: אנו מדברים במושגים (\"חשבונית\") ובתסריטים (Use-Cases) אך מאחורי כל אלה יש לנו מודל תפיסתי (Conceptual Model) שמתאר איך הדברים מתרחשים. בני-אדם, כמונו, נוטים להרגיש אי-נוחות בעת שהם עוסקים בנושא לא מוכר. כתרופה, מנגנוני החשיבה שלנו גורמים לנו להשלים, באופן כמעט מיידי, את סט העובדות שניתנו לנו למודל תפיסתי הגיוני (מבחינתנו). איכות העובדות שהועברה לנו, כשרון ומזל יכתיבו עד כמה נכון המודל שבנינו. לא מעט ריבים / חוסרי-הבנה נוצרים בגלל הפער שבין המודל של אדם א\' לאדם ב\', שניהם ניזונו מאותן עובדות.

הפתרון \"הרשמי\"
אז מה עושים? אחד העקרונות המרכזיים של DDD הוא שפה-רוחבית (ubiquitous language). על מישהו, ה business analyst, לחפור ללמוד ולהגדיר עם ה DEs שפה אחידה ומוסכמת על פיה כולם יעבדו, שפה שבעצם תגזר מתוך Conceptual Model ברור ומלוטש (במידת האפשר).

מקור: softwarearchiblog

הנה הנקודה החשובה: כאשר אנו אוספים דרישות מלקוח אנו נוטים הרבה פעמים \"להתמקד בחלקים שרלוונטיים לתוכנה\", להתמקד בדרישות בטווח הקרוב ולהתמקד ב UI – כלי שעוזר מאוד להמחשה של רעיונות.

כמו שאנו לומדים את הלקוח, הלקוח לומד אותנו ונחשף למציאות חדשה שתוכנה תסייע לו בהתליך עסקי. גם המידע אצלו בראש לא תמיד ברור ומאורגן.

בפועל, הדרישות ותיאורי ה use-cases שאספנו – ישתנו, גם ב-UI שנראה נהדר על הנייר – יתגלו חוסרים. הכל נתון לשינוי.
אפשר לצעוק ולהאשים \"אנחנו עושים את הדרישות האלו – הנה יש לנו חוזה כתוב\", אך בפועל – האם לא נרצה לצמצם את הטעות הצפוייה?

אז מה יותר יציב מרשימת use-cases ומסכי UI? היכן אנו יכולים להשקיע בלמידה של המקור ממנו באות הדרישות? ידע יציב שאינו נוטה להשתנות בקלות?
ובכן – זהו ה Domain, תחום העיסוק, הביזנס, הידע שמי שעוסק בתחום חייב לדעת על מנת לעסוק בו. הביזנס אינו משתנה במהירות.

כשתגיע דרישה חדשה היא תגיע מהדומיין (ביזנס, תחום), בשפה של הדומיין וקרוב לוודאי שלא תשנה את הדומיין אלא תשתלב בו.
אם נצליח לבנות תוכנה שתשקף בצורה טובה את הדומיין – היא תהיה גמישה הרבה יותר לקבל בטבעיות דרישות עתידיות במרחב בדומיין.

ע\"פ DDD, יש להשקיע זמן לא דווקא בשמיעת עוד דרישות וציור עוד מסכים – דבר שאנו מתפתים לעשות, אלא בלמידה לעומק של הדומיין. הדומיין יתואר במודל (להלן Conceptual Model) שהשימוש בו יהיה חוצה גבולות: לקוחות, מחלקת מוצר/שיווק ומחלקות הפיתוח השונות. כל דרישה עתידית תעבור דרך אותו מודל ותעדכן אותו ע\"פ הצורך, אך סביר שהשינויים יהיו קטנים והגיוניים.
אם הקוד יהיה שיקוף של המודל – גם השינויים בו יהיו קלים יותר.

המודל לא צריך להיות מושלם או מפורט במיוחד – הוא צריך להיות נכון לשם המטרה ומועיל.
דרך מקובלת ונוחה לתאר מודל היא תרשימי Class Diagram של UML. כמובן שזו רק דרך אחת, אפשר בכל תרשים חופשי, טקסט וכו\'.

מודל קונספטואלי המתאר פעולה בנקאית. האם המפתחים, מנהלי המוצר והלקוחות שותפים לאותה תמונה (או הבנה)? מקור: martinfowler.com

חזרה למציאות
סביר להניח שאין לכם בחברה תפקיד של Business Analyst, ושרוב הלקוחות שלכם לא מוכנים שה DEs שלהם ישבו שעות וימים בכדי לצייר UML, או בכלל ילמדו UML. ארגון שרוצה להגיע ל DDD מלא כיעד אסטרטגי כנראה יכול לעשות זאת, אך לא נתקלתי בחברה בישראל שעובדת כך בצורה שיטתית.

אילוסטרציה: domain experts.
כמעט ושמתי תמונה אומנותית של מנהל חשבונות זקן משנות ה-50, אך כנראה שבישראל בשנות ה-10, תתקלו יותר ב domain experts שדומים לאלו, שני מנהלים ב-888.
מקור: כתבה ב\"אנשים ומחשבים\".

בכל זאת יש כמה צעדים שאתם יכולים לעשות מתוך הפיתוח על מנת לשפר את המצב.

צרו, ועבדו עם מודל קונספטואלי
צרו לעצמכם מודל קונספטואלי. אני מוצא את התרגיל הזה מועיל: מצד אחד עושה סדר בראש מצד שני מעורר שאלות. אני מצייר את המודל ב UML אך ברגע שאני צריך לתקשר אותו לפיתוח או להתייעץ עם לקוח אני מפשט מאוד את התרשימים ומשתמש הרבה בטקסט. גילוי פערים בהבנה שלי את המודל היא תוצאה שכיחה יחסית, וכפי שאנו זוכרים: תיקון \"באג\" בשלב הדרישות הוא זול לאין ערוך מתיקון באג בשטח.

אם נשקיע זמן בשיפור ובאימות המודל, נמצא אי-דיוק קטן אחד פה ועוד אי-דיוק קטן שם, אך ככל כשנמשיך, מדי פעם, נגיע ל\"פריצת דרך\" של הבנה חשובה, טעות קריטית בהבנת עולם הבעיה שפיספסו. זהו ה Money Time של DDD – הרגעים בהם ההשקעה מחזירה את עצמה ובגדול.

הקשיבו לשפה
כלל #1: אם בשיחה עם הלקוח (DE), הלקוח משתמש הרבה במושג (למשל, \"חשבונית\") ואין לכם אובייקט מרכזי בשם \"חשבונית\" – זהו סימן לפער במודל. תקנו את המודל שייתן משקל מתאים למושגים החשובים בהם משתמש הלקוח בשיחה היום-יומית.

כלל #2: אם אינכם יכולים לבטא רעיון מרכזי או דרישה (למשל: \"יש בסוף כל שנה להוציא דו\"ח של החשבוניות שלא זוכו ממס\") מבלי להתבסס על המושגים הבסיסיים במודל – עליכם לחזור ולהבין למה. לרוב זה יהיה אי-דיוק, בהירות או שלמות של המודל.

זכרו: \"(You can run, but you cannot hide (a bad conceptual model\". אם \"תשקרו\" את המערכת ותעבדו עם מודל לא מדוייק, זה יחזור אליכם בדמות תחזוקה קשה ודרישות עתידיות הקשות ליישום.
לדוגמא: תיאור של מחשב עם 2 כתובות IP כשני מחשבים עם אותו השם, כל אחד עם כתובת IP אחת – אולי יקצר את הפיתוח בשלב הראשון, אך יחזור אליכם כמוברנג כחלק מדרישות עתידיות. ניסיתם \"לשקר\" במודל.

סיכום
למי שהתנסה בהצלחה במידול בכלל או DDD בפרט, מידול נראה חלק הכרחי בבנייה של כל מערכת. תורת המידול אינה נפוצה ואינה קלה – אך היא מביאה תוצאות ממשיות. המקור הטוב ביותר שאני נתקלתי בו עד היום הוא הספר Analysis Patterns של Martin Fowler, ספר קצת לא-מסודר אך בעל תובנות עמוקות.

ה-DDD בא להתמודד עם סיבוכיות של מערכות ענקיות. חלק גדול בהתורה מדבר על ניהול של כמה מודלים שונים לאותו מערכת ואיך לתחזק מבנה שכזה. אני מניח שבבעיות אלו תתקלו רק בפרוייקטים של עשרות אנשים ויותר – ולכן אני לא מוצא טעם להמשיך ולפרט. אנסה בפוסטי המשך להראות כמה בעיות מידול וכיצד הן מובילות, מהר מאוד, לקוד טוב ויציב יותר.

העקרונות הבסיסיים שהבאתי כאן יעילים וישימים לפרוייקטים קטנים מאוד. מניסיון. בניית מודל היא משימה שמתאימה יותר לאנשים בעלי חשיבה מופשטת שמגלים עניין אישי בצד העסקי של עולם התוכנה.
Martin Fowler מספר שהממדל הטוב ביותר שפגש אי פעם היה פיסיקאי – לקוח שעבד עמו. הוא מעולם לא תכנת או התעסק בתוכנה, אך הוא למד את הרעיון במהירות עצומה והפליא במודלים רבי-ערך.

[1] בעברית: תכנון מונחה-תחום, תרגום לא כל-כך מוצלח לדעתי – אך לא מצאתי טוב יותר.