מקודד ומפענח URL

Acrafto Team מפתחים
עודכן
קידוד בתור

לערך אחד בשאילתה או לקטע אחד בנתיב. מקודד הכול חוץ מאותיות, ספרות ו- - _ . ! ~ * ' ( ), בדיוק כמו encodeURIComponent.

תוצאה

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

קידוד ופענוח URL אונליין תוך כדי הקלדה: הכלי הופך רווחים, אותיות עם סימנים ותווים כמו & או ? לרצפים בקידוד אחוזים כמו %20, וגם מחזיר אותם לטקסט קריא. הלשונית השנייה היא מנתח URL. היא מפצלת כל כתובת לפרוטוקול, מארח, נתיב ופרמטרים של שאילתה, שאפשר לערוך, לכבות או לנקות מתגי מעקב, וכותבת בחזרה את הכתובת בקידוד הנכון. הכול קורה בדפדפן שלכם.

איך עושים קידוד ופענוח URL לטקסט

  1. הקלידו או הדביקו בשדה שבלשונית קידוד ופענוח. התוצאה מתעדכנת עם כל הקשה.
  2. בחרו כיוון. קידוד הופך טקסט לבטוח לשימוש בכתובת, פענוח הופך caf%C3%A9%20au%20lait בחזרה ל-café au lait. אם תדביקו בשדה ריק טקסט עם רצפים כמו %20, הכלי יעבור לפענוח מעצמו (לקודד אותו במקום מחזיר). טקסט רגיל שצריך קידוד, שהודבק במצב פענוח, מעביר אותו לקידוד באותו אופן, עם לפענח אותו במקום.
  3. בקידוד בחרו תחת קידוד בתור מהו הטקסט (ראו בפרק הבא). ברירת המחדל, ערך פרמטר, מתאימה לערך בודד בשאילתה.
  4. העתקה מעתיק את התוצאה ללוח. החלפה מעביר את התוצאה לקלט והופך את הכיוון. זו בדיקה מהירה של הלוך וחזור: פענוח של מה שקודד זה עתה חייב להחזיר את הטקסט המקורי.

כל תו שהכלי שינה מודגש בתוצאה. העבירו עליו את העכבר כדי לראות את התו, את נקודת הקוד שלו ביוניקוד ואת הבייטים שלו, למשל é U+00E9 %C3%A9. מתחת לשדות מוצגים מספר התווים, הבייטים ב-UTF-8 והתווים מקודדים (או תווים מפוענחים). נסו דוגמה טוען את המשפט מחיר: 50% הנחה, קפה & עוגה? כן!, שיש בו 31 תווים אבל 48 בייטים ב-UTF-8, כי כל אות עברית תופסת שני בייטים.

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

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

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

  • ערך פרמטר פועל כמו encodeURIComponent של JavaScript ומתאים לערך אחד בשאילתה או לקטע אחד בנתיב. הוא מקודד הכול חוץ מאותיות, ספרות ו-- _ . ! ~ * ' ( ), כך ש-&, =, / או ? בתוך הערך לא יכולים לשבור את הכתובת. קידוד של café & crème נותן caf%C3%A9%20%26%20cr%C3%A8me, מוכן להצבה אחרי q=.
  • כתובת שלמה מיועד לכתובת שלמה שצריך רק לנקות. הוא מקודד רווחים, תווים שאינם ASCII, תווי בקרה, את הגרש ההפוך ואת " < > \ ^ { | }, ושומר על כל מה שנותן לכתובת את המבנה שלה: : / ? # [ ] @ ! $ & ' ( ) * + , ; =. כך https://example.com/search?q=café au lait&lang=fr הופך ל-https://example.com/search?q=caf%C3%A9%20au%20lait&lang=fr. רצפים שכבר מקודדים נשארים כמו שהם, ו-% בודד הופך ל-%25. זה ההבדל מ-encodeURI של JavaScript, שהופך %20 קיים ל-%2520 ומקודד את הסוגריים המרובעים של כתובת IPv6 כמו http://[2001:db8::1]:8080/.
  • נתוני טופס פועל לפי הפורמט application/x-www-form-urlencoded (באנגלית) שמפיקים טפסי HTML ו-URLSearchParams. רווח הופך ל-+, ורק אותיות, ספרות ו-* - . _ נשארים בלי קידוד, ולכן גם ! ' ( ) ~ מקודדים.
  • RFC 3986 מחמיר משאיר בלי קידוד רק את התווים הלא שמורים של RFC 3986 (באנגלית): אותיות, ספרות ו-- . _ ~. OAuth 1.0 (RFC 5849) וחתימות AWS גרסה 4 דורשים בדיוק את הצורה הזו, כי חתימה מתאימה רק כשני הצדדים מקודדים ! או * באותו אופן.

אותם תווים בכל מצב:

תוערך פרמטרכתובת שלמהנתוני טופסRFC 3986 מחמיר
רווח%20%20+%20
&%26&%26%26
/%2F/%2F%2F
+%2B+%2B%2B
~~~%7E~
!!!%21%21
****%2A
é%C3%A9%C3%A9%C3%A9%C3%A9

הטקסט תמיד מקודד כ-UTF-8 וספרות ההקסדצימליות תמיד באותיות גדולות. אם הקלט כבר מכיל רצפים כמו %20, הערה מציינת זאת ומציעה לפענח אותו במקום, כדי שלא תקודדו את הטקסט פעמיים בטעות.

כדי להעביר JSON בפרמטר של שאילתה, כווצו אותו במעצב JSON וקודדו אותו כערך פרמטר: {"id":7,"tags":["a","b"]} הופך ל-%7B%22id%22%3A7%2C%22tags%22%3A%5B%22a%22%2C%22b%22%5D%7D. זה עובד גם בכיוון ההפוך: פענחו כאן את הפרמטר, ואז עצבו אותו שם.

בעיות בפענוח URL: סימני פלוס, %2520 ורצפים שבורים

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

  • סימן פלוס מייצג רווח בנתוני טופס ברוב מחרוזות השאילתה. פענוח + כרווח פעיל כברירת מחדל, ולכן caf%C3%A9+au+lait מתפענח ל-café au lait. בכתובת שלמה רק סימני פלוס שאחרי ה-? נחשבים רווחים, כי בנתיב פלוס הוא תו רגיל. כבו את האפשרות כשהפלוס נועד להיות פלוס ממש. פלוס שקודד כ-%2B תמיד נשאר פלוס.
  • קידוד כפול קורה כששתי שכבות קוד מקודדות את אותו ערך, וזה דבר ש-RFC 3986 מזהיר ממנו במפורש. כל % הופך ל-%25, ולכן רווח עובר מ-%20 ל-%2520. אם התוצאה המפוענחת עדיין מכילה רצפים כמו %20, הכלי אומר שהטקסט כנראה קודד פעמיים ומציע לפענח שוב.
  • רצף לא תקין, % שלא אחריו שתי ספרות הקסדצימליות כמו ב-100% או %G1, גורם ל-decodeURIComponent של JavaScript לזרוק URIError. כאן רצפים כאלה נשארים כמו שהם, מסומנים באדום ונספרים, ושאר הטקסט מתפענח.
  • קישורי Latin-1 ישנים מגיעים מהתקופה שלפני UTF-8, כשחלק מהאתרים קידדו את é כבייט בודד %E9. caf%E9 אינו UTF-8 תקין, ולכן decodeURIComponent נכשל ו-unquote של Python מחזיר caf ואחריו תו ההחלפה U+FFFD. הכלי קורא בייטים כאלה כ-Windows-1252, מפענח את caf%E9 ל-café ומוסיף הערה על כך.

תווי בקרה בטקסט מפוענח, כמו טאב או בייט ריק, מוצגים כסמלים גלויים כמו ␉ ו-␀, אבל העתקה מעתיק את הטקסט האמיתי.

מנתח URL: פיצול כתובת ועריכת פרמטרים של שאילתה

הדביקו כתובת בשדה URL בלשונית ניתוח ועריכת URL והיא תפוצל לפרוטוקול, מארח, פורט, נתיב ומקטע (#), וכן לשם משתמש ולסיסמה כשהכתובת מכילה אותם. הערכים מוצגים מפוענחים, ולכן הלשונית היא גם הדרך המהירה ביותר לפענח פרמטרים של URL: קוראים נעלי ריצה במקום %D7%A0%D7%A2%D7%9C%D7%99+%D7%A8%D7%99%D7%A6%D7%94. העריכה עובדת בשני הכיוונים, כמו שורת הכתובת וטבלת הפרמטרים ב-Postman. משנים שדה והכתובת נכתבת מחדש מיד, בקידוד נכון. משנים את הכתובת וכל החלקים נקראים מחדש. חלקים שלא נגעתם בהם נשארים בדיוק כפי שהיו, תו אחר תו.

הטבלה פרמטרים של שאילתה מפרטת כל פרמטר עם השם והערך שלו. בטלו את הסימון בלכלול בכתובת כדי להשאיר פרמטר מחוץ לכתובת בלי למחוק אותו, וזה עוזר כשמחפשים את הפרמטר היחיד ששובר בקשה. הוספת פרמטר, הסרת פרמטר ומיון א עד ת עושים את מה שכתוב עליהם. שמות שחוזרים כמו tag=a&tag=b ושמות בלי ערך כמו ?debug נשמרים. רווחים בפרמטרים קובע אם רווחים נכתבים כ-%20 או כ-+, וכברירת מחדל הוא הולך לפי הכתובת שהדבקתם.

קישורי התחברות ותשלום נושאים לא פעם כתובת שנייה בתוך פרמטר, מקודדת כך שה-? וה-& שלה לא יתערבבו באלה של הכתובת החיצונית:

https://auth.example.com/authorize?client_id=abc&redirect_uri=https%3A%2F%2Fapp.example.com%2Fcallback%3Ftab%3D2

לערך שהוא עצמו כתובת, בדרך כלל ב-redirect_uri, return, url או next, מופיע כפתור עריכת הכתובת שבפנים. הכתובת הפנימית https://app.example.com/callback?tab=2 נפתחת כרמה נפרדת עם חלקים ופרמטרים משלה, פירורי לחם (הכתובת הראשית › redirect_uri) מחזירים אחורה, וכל שינוי מקודד בחזרה אל הכתובת החיצונית. העתקת הכתובת הראשית מעתיק את התוצאה. זה עובד גם כמה רמות לעומק.

כשהחלק שאחרי # נראה כמו פרמטרים, כמו #access_token=...&state=... בזרימה המשתמעת של OAuth או #/search?q=shoes בנתיבים של אפליקציות עמוד יחיד, טבלה שנייה, פרמטרים במקטע, מפרטת גם אותם.

המנתח גם מצביע על בעיות: כתובת בלי פרוטוקול, שדפדפנים מתייחסים אליה כקישור יחסי, פורט מחוץ לטווח 0 עד 65535, ותווים שחובה לקודד, כמו רווחים, אותיות עם סימנים, " או <, שלקודד אותם מתקן בצעד אחד. טקסט בלי כתובת, כמו a=1&b=2, נקרא כמחרוזת שאילתה. עבור שם דומיין בינלאומי (באנגלית) הכלי מציג את צורת ה-Punycode שבה משתמשים DNS ודפדפנים, כך ש-münchen.de הופך ל-xn--mnchen-3ya.de, ודומיין שמתחיל ב-xn-- מקבל את הצורה הקריאה שלו.

העתקת URL מעתיק את הכתובת המוגמרת, פתיחה פותח אותה בלשונית חדשה (קישורי http ו-https בלבד), והעתקה כ-JSON נותן את הפרמטרים כאובייקט JSON, כשהשמות החוזרים נאספים למערך.

הסרת UTM ופרמטרי מעקב אחרים מכתובת URL

קישורים מניוזלטרים, ממודעות וממדיה חברתית נושאים פרמטרים שרק מספרים לאתר מאיפה הגיע המבקר. פרמטרי UTM (באנגלית) utm_source, utm_medium, utm_campaign, utm_term ו-utm_content מגיעים מ-Urchin, קודמתה של Google Analytics. מזהי קליקים כמו fbclid (פייסבוק), gclid (Google Ads) ו-msclkid (Microsoft Advertising) מתווספים על ידי הפלטפורמות עצמן.

המנתח מסמן אותם בתג מעקב, והסרת מעקב (n) מוחק את כולם בבת אחת. מלבד כל פרמטר utm_* הוא מזהה יותר מ-20 אחרים, כמו ttclid (TikTok), mc_cid (Mailchimp) ו-_hsenc (HubSpot). פרמטרים שהדף צריך נשארים במקומם: בקישור החנות מנסו דוגמה, הסרת מעקב (4) מסיר את utm_source, utm_medium, utm_campaign ו-fbclid ומשאיר את q, size, return ואת המקטע #reviews.

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

מהו קידוד אחוזים ואיך תווים הופכים ל-%XX

קידוד URL (Percent-encoding), הנקרא גם קידוד אחוזים, כותב תו כ-% ואחריו שתי ספרות הקסדצימליות. כתובת URL יכולה להכיל רק קבוצה מוגבלת של תווי ASCII, ולחלקם יש תפקיד: ? פותח את השאילתה, & מפריד בין פרמטרים, # פותח את המקטע. RFC 3986 קורא לאלה תווים שמורים (: / ? # [ ] @ ו-! $ & ' ( ) * + , ; =). אותיות, ספרות ו-- . _ ~ אינם שמורים ולעולם לא צריכים קידוד. כל השאר, וכל תו שמור שמשמש כמידע רגיל, מקודד.

תווים מחוץ ל-ASCII הופכים תחילה לבייטים של UTF-8, וכל בייט מקבל %XX משלו:

  • é הוא U+00E9, ש-UTF-8 שומר כשני הבייטים C3 A9, ולכן הוא הופך ל-%C3%A9.
  • € הוא U+20AC, שלושה בייטים: %E2%82%AC.
  • אימוג’י כמו U+1F600 (פרצוף מחייך) תופס ארבעה בייטים: %F0%9F%98%80.

%c3%a9 ו-%C3%A9 זהים במשמעותם, אבל RFC 3986 ממליץ על אותיות גדולות, וזה מה שהכלי כותב. טבלת קידוד אחוזים של התווים שפוגשים הכי הרבה:

תומקודדתומקודד
רווח%20+%2B
!%21,%2C
"%22/%2F
#%23:%3A
$%24;%3B
%%25=%3D
&%26?%3F
'%27@%40
(%28[%5B
)%29]%5D
*%2Aמעבר שורה%0A

קידוד URL ב-JavaScript, ב-Python וב-PHP

לכל שפה יש פונקציות לכך, והן נבדלות בעיקר ביחס לרווחים, ללוכסנים ול-! ' ( ) * ~.

ב-JavaScript יש encodeURIComponent (באנגלית) לערך, encodeURI לכתובת שלמה ו-URLSearchParams לקידוד טפסים:

encodeURIComponent("café & crème")                     // "caf%C3%A9%20%26%20cr%C3%A8me"
encodeURI("https://example.com/a b?q=café")            // "https://example.com/a%20b?q=caf%C3%A9"
new URLSearchParams({ q: "café & crème" }).toString()  // "q=caf%C3%A9+%26+cr%C3%A8me"
decodeURIComponent("caf%C3%A9")                        // "café"

decodeURIComponent לא הופך + לרווח, והוא זורק URIError על רצף לא תקין כמו 100%.

ב-Python הפונקציות נמצאות ב-urllib.parse. quote שומר על / כברירת מחדל (safe='/') ומקודד כל השאר חוץ מהתווים הלא שמורים של RFC 3986. quote_plus כותב רווחים כ-+ ומקודד גם את /:

from urllib.parse import quote, quote_plus, urlencode, unquote_plus

quote("café & crème/brûlée")       # 'caf%C3%A9%20%26%20cr%C3%A8me/br%C3%BBl%C3%A9e'
quote("a b/c", safe="")            # 'a%20b%2Fc'
quote_plus("café & crème/brûlée")  # 'caf%C3%A9+%26+cr%C3%A8me%2Fbr%C3%BBl%C3%A9e'
urlencode({"q": "café & crème", "page": 2})  # 'q=caf%C3%A9+%26+cr%C3%A8me&page=2'
unquote_plus("caf%C3%A9+au+lait")  # 'café au lait'

ב-PHP, urlencode מקודד כמו טופס HTML וכותב רווח כ-+, ואילו rawurlencode הולך לפי RFC 3986 וכותב %20:

urlencode("café & crème");     // "caf%C3%A9+%26+cr%C3%A8me"
rawurlencode("café & crème");  // "caf%C3%A9%20%26%20cr%C3%A8me"

rawurlencode נותן אותה תוצאה כמו RFC 3986 מחמיר. urlencode תואם לנתוני טופס חוץ מ-*, שהוא מקודד כ-%2A.

שאלות נפוצות

האם לקודד רווח כ-%20 או כ-+?

%20 עובד בכל מקום בכתובת. + מייצג רווח רק במחרוזת השאילתה ובנתוני טופס, הפורמט ששולחים טפסי HTML. בנתיב + הוא סימן פלוס רגיל, ולכן /a+b נשאר /a+b. כשערך בשאילתה צריך פלוס אמיתי, כתבו אותו כ-%2B. בכלי, נתוני טופס כותב רווחים כ-+ ושלושת המצבים האחרים כ-%20.

מה המשמעות של %20, %2F ו-%3D בכתובת URL?

אלה תווים מקודדים: %20 הוא רווח, %2F לוכסן ו-%3D סימן שוויון. אחרים שרואים הרבה הם %26 (&), %3F (?), %3A (:), %2C (פסיק) ו-%27 (גרש). שתי הספרות הן קוד התו בבסיס הקסדצימלי. אותיות עם סימנים ותווים אחרים שאינם ASCII תופסים שניים עד ארבעה זוגות כאלה, כמו %C3%A9 ל-é. הדביקו את כל המחרוזת במפענח כדי לקרוא אותה.

מה ההבדל בין encodeURI ל-encodeURIComponent?

encodeURI מיועד לכתובת שלמה ומשאיר בשקט את התווים שמבנים אותה, כמו : / ? # & =. encodeURIComponent מיועד לחלק אחד, ערך של פרמטר או קטע בנתיב, ומקודד גם את התווים האלה, ולכן https://example.com/?a=1&b=2 הופך ל-https%3A%2F%2Fexample.com%2F%3Fa%3D1%26b%3D2. בכלי, ערך פרמטר תואם ל-encodeURIComponent, וכתובת שלמה דומה ל-encodeURI אבל שומר על רצפים קיימים כמו %20 במקום להפוך אותם ל-%2520.

איך מסירים פרמטרי UTM מכתובת URL?

הדביקו את הקישור בלשונית ניתוח ועריכת URL ולחצו על הסרת מעקב (n). הכלי מוחק בבת אחת כל תג utm_* ומזהי קליקים כמו fbclid ו-gclid. אחר כך לחצו על העתקת URL. כדי להסיר רק חלק מהם, השתמשו ב-הסרת פרמטר בשורות שאינכם רוצים.

האם קידוד URL זהה להצפנה או ל-Base64?

לא. קידוד URL לא מסתיר דבר: כל אחד יכול לפענח caf%C3%A9 בחזרה ל-café, ולכן הוא אף פעם לא מגן על סיסמה או על אסימון. הוא רק הופך תווים לבטוחים לשימוש בכתובת. Base64 הוא קידוד אחר, שהופך כל מידע, כולל קבצים בינאריים, למחרוזת של 64 תווים. מחרוזת Base64 בכתובת עדיין צריכה קידוד של +, / ו-=, אלא אם משתמשים בגרסה הבטוחה לכתובות, שאפשר להפיק במקודד ומפענח Base64.

האם כתובות ה-URL שאני מדביק מועלות או נשמרות?

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

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

אשמח אם תוכלו לשתף את הדפים האלה עם חברים, לשמור אותם במועדפים או לקשר אליהם. תודה! 🙏