ויקיפדיה:לואה
ההרחבה Scribunto, שמאפשרת כתיבת מודולים בשפת Lua ושימוש בהם בתבניות, הופעלה בוויקיפדיה העברית.
תיעוד
עריכהתיעוד באנגלית ניתן לקרוא כאן.
איך זה פועל
עריכהלהבדיל מתבניות, שהן בעצם דפים "רגילים" שיכולים להימצא במרחב שם כלשהו, מודולים חייבים להמצא במרחב שם חדש שנקרא "יחידה" (באנגלית module). כל יחידה צריכה להחזיר טבלה שהשדות השונים שלה הם פונקציות שתבניות ויחידות אחרות יכולות להשתמש בהן.
כך נראית יחידה שנקראת, נניח, "קופים וחתולים" (כלומר, נמצאת בדף יחידה:קופים וחתולים) ומייצאת שתי פונקציות: "קוף מטפס על עץ" ו"חתולה על גג פח":
-- each module returns a table, whose keys are the invocation names, which can be any string, including spaces, numbers, hebrew letters etc.
-- the values are functions to be invoked using those names.
-- there are several ways to achieve this. the "best practice" in hewiki described below.
-- modules imported from other wikis often use different way to create and return this table.
-- best practice:
-- all variables and functions are local.
-- at the bottom of the module, we return a literal table, constructed by assigning functions to invocation names:
local function f1(frame) -- documentation linked above explains how to extract parameters from frame
return 'בכל הרצינות!'
end
local function f2(frame)
return 'עבדתי עליך'
end
-- here we return the invocations:
return {
['קוף מטפס על עץ'] = f1,
['חתולה על גג פח'] = f2,
}
כדי להשתמש במודול, יש "מילת קסם" חדשה בשם invoke. למילה הזו יש לתת שני פרמטרים: שם המודול ושם הפונקציה. בנוסף, אפשר להוסיף פרמטרים נוספים ככל שנדרש. פרמטרים נוספים אלו יועברו לפונקציה. להלן דוגמה להפעלת הפונקציה בלי פרמטרים: {{#invoke:קופים וחתולים|קוף מטפס על עץ}}
העברת פרמטרים לפונקציה ב-Lua
עריכההפונקציה שנקראת מ-invoke מקבלת תמיד פרמטר יחיד שנהוג (אם כי לא חובה) לקרוא לו frame. פרמטר זה אורז בתוכו מידע שהפונקציה ב-lua יכולה למצות ולהשתמש בו. לדוגמה, מידע על התבנית שמכילה את הקריאה ל-invoke ארוז ב-frame:getParent(). בדומה, הפרמטרים שמועברים מהתבנית ארוזים ב-frame.args. בדומה לפרמטרים לתבניות, פרמטרים לפונקציה יכולים להיות מבוססי סדר או שמיים. נניח שאנחנו רוצים להעביר לפונקציה king_wives שלושה פרמטרים: פרמטר שמי בשם "מלך", ושני פרמטרים מבוססי סדר:
{{#invoke:m|king_wives|מלך=שלמה|40|25}}
הפונקציה ניגשת לפרמטרים בעזרת args:
function m.king_wives(frame)
local king = frame.args["מלך"]
local param1 = frame.args[1]
local param2 = frame.args[2]
-- do something with the parameters, e.g.:
return string.format("ל%s המלך היו %d נשים", king, param1 * param2)
end
אם נקרא לפונקציה כמו בדוגמה למעלה, נקבל בדף "לשלמה המלך היו 1000 נשים".
לעומת זאת, הקריאה:
{{#invoke:m|king_wives|מלך=דוד|3|6}}
תניב "לדוד המלך היו 18 נשים".
הערך המוחזר מהפונקציה
עריכההפונקציות הפנימיות במודול יכולות להחזיר ערך מסוג כלשהו - שום דבר, מספר, מחרוזת, טבלה, ערך בוליאני, או אפילו פונקציה. פונקציה "ראשית", כלומר כזו שנקראת מקוד ויקי, צריכה להחזיר מחרוזת. אחרי הקריאה לפונקציה, המחרוזת שהוחזרה מועברת לפורס (parser) להמשך העיבוד. המשמעות היא שאם הפונקציה רוצה, למשל, לצייר תמונה, היא לא אמורה להחזיר מחרוזת html עם תג img, אלא מחרוזת בקוד ויקי, כמו שהייתם שמים בדף - [[קובץ:שם הקובץ]].
פיתוח ו"ארגז חול"
עריכהפיתוח בוויקיפדיה
עריכהבמהלך הפיתוח, מופיעה בעורך קוד המקור, מתחת כפתור השמירה, השורה "תצוגה מקדימה של הדף עם התבנית הזאת". מזינים שם דף שמשתמש ביחידה, ולוחצים "הצגה". הדף המוצג ישתמש בקוד הלואה שנמצא בעורך. בפיתוח יחידה חדשה, צרו דף במרחב המשתמש שלכם שמשתמש ביחידה, והציגו אותו. כאשר משנים פונקציה ביחידה קיימת, שנמצאת בשימוש במרחב הערכים, מצאו ערך שמשתמש בפונקציה הזו, כדי לבדוק את השינוי שלכם משיג את התוצאה הרצויה.
כדי לסייע לפיתוח, ניתן לשלוח מהקוד "הודעות", בעזרת mw.log()
, ו-mw.logObject()
. ההודעות נרשמות ב"יומני לואה". תיעוד הפונקציות הללו בmw:Extension:Scribunto/Lua reference manual
יומני לואה מופיעים בתצוגה המקדימה בתחתית הדף. יש להרחיב את "ביצועי המפענח", ובתחתיתו נמצאים היומנים, בצורה מקופלת.
פיתוח במחשב
עריכהניתן לבדוק קוד לואה מחוץ לוויקיפדיה, בעזרת הרצתו במחשב. שימו לב שגרסת לואה בוויקיפדיה היא גרסה 5.1, וחשוב להשתמש בגרסה זו כאשר מפתחים, משום שגרסאות חדשות יותר של לואה לא תואמות לאחור באופן מושלם, וכוללות שינויים בכמה אופרטורים. פיתוח במחשב מאפשר שימוש במערכת הפיתוח המועדפת עליכם, ויכולות debugging שלא קיימות בפיתוח בוויקיפדיה עצמה.
ארגז החול
עריכהההרחבה ארגז חול לתבניות תומכת גם בסקריבונטו. במלים אחרות, ניתן לפתח ולבדוק מודולים במרחב המשתמש, לפני העברתם למרחב יחידה.
בדרך כלל אין צורך להשתמש בארגז חול, משום שהדרך שתוארה למעלה, בעזרת "תצוגה מקדימה של דף", מספיקה, וה"ביורוקרטיה" שכרוכה בשימוש בארגז אינה מוצדקת.
כאשר רוצים לבצע שינוי מקיף, שדורש שינויים במקביל במספר יחידות, או ביחידה ובמספר תבניות, "ארגז החול" מאפשר לבנות במרחב המשתמש "מרחב וירטואלי", אליו מעתיקים את היחידות והתבניות אותן רוצים לשנות. ארגז החול "מפענח" דפים תוך שהוא מחליף תבניות ויחידות שהועתקו לארגז, באלו שנמצאות בארגז עצמו.
ה"מרחב הוירטואלי" הזה הוא דף במרחב המשתמש, כאשר היחידות והתבניות שמועתקות הן דפי משנה של הדף הזה, ששמותיהם מתחילים ביחידה:
או תבנית:
.
הסבר ודוגמה
עריכההמשתמשת משתמשת:אלמונית רוצה לפתח מודול חדש בשם "אתגר", או לבדוק שינויים שהיא רוצה לעשות במודול קיים בשם זה. לשם כך היא מייצרת דף חדש בשם "משתמשת:אלמונית/ארגז חול/יחידה:אתגר". שימו לב לשתי נקודות עדינות:
- הנקודתיים בשם הדף, ש"מתחזות" לנקודתיים הרגילות שמפרידות בין מרחב שם ושם דף, אבל במקרה הזה לא מדובר בדף במרחב יחידה, אלא בדף במרחב המשתמש, ששמו מכיל נקודתיים.
- כשמשתמשים בשם מודול באותיות לטיניות, השם חייב להתחיל באות גדולה, ובאופן כללי השם הוא תלוי רישיות. בקריאה למודול (כלומר כשמפעילים את מילת הקסם invoke#), המערכת תחליף את האות הראשונה בשם המודול שמועבר לקריאה באותו התו מותמר לאות גדולה. במודול רגיל, אותה התמרה מתבצעת בשם הדף עצמו. בשימוש ב"ארגז חול לתבניות", האות הראשונה ב"שם המודול" היא בעצם אות שנמצאת באמצע השם (כלומר, במקום שם דף "אתגר" במרחב "יחידה", שם הדף הוא בעצם יחידה:אתגר, במרחב המשתמש) ולכן המערכת לא מתמירה אותה אוטומטית לאות גדולה. מפני שההתמרה בקריאה למודול עדיין מתבצעת, באחריות המשתמשת לייצר את הדף בשם שנפתח באות גדולה. אם שם המודול הוא בעברית, בעיה זו לא קיימת.
כשהמשתמשת מבקשת להציג דף כלשהו בוויקיפדיה או קוד ויקי שמוזן בקופסה המתאימה ב"ארגז חול לתבניות", הדף המוצג לא נלקח מזיכרון המטמון של השרת, אלא מחושב מחדש, כשעבור כל תבנית ומודול שנמצאים בשימוש, המערכת בודקת האם דף בשם המתאים נמצא תחת "תחילית לארגז חול". אם תבנית או מודול כאלו קיימים, המערכת תשתמש בהם. אם לא, היא תשתמש בתבנית או המודול שקיים במרחב התבניות או המודולים בשם זה. בדוגמה שלנו, "תחילית לארגז חול" היא "משתמשת:אלמונית/ארגז חול", ולכן כשהמערכת תיתקל ב {{#invoke:אתגר|....}}, המערכת תריץ את הקוד שנמצא בדף "משתמשת:אלמונית/ארגז חול/יחידה:אתגר".