दो पार्सर आपके दस्तावेज़ पर असहमत क्यों होते हैं
Markdown 2004 में एक Perl स्क्रिप्ट और एक पेज के विवरण के रूप में प्रकाशित हुआ था, किसी औपचारिक व्याकरण के बिना। यही अनौपचारिकता उसके फैलने का कारण बनी, और यही कारण है कि वही दस्तावेज़ अलग-अलग टूल में अलग तरह रेंडर होता है। मूल कार्यान्वयन ने दर्जनों स्थितियाँ अपरिभाषित छोड़ दीं: तीन स्पेस इंडेंट किए गए लिस्ट मार्कर का क्या होता है, किसी शब्द के भीतर ज़ोर कैसे नेस्ट होता है, हेडिंग से पहले खाली पंक्ति चाहिए या नहीं। हर कार्यान्वयनकर्ता ने इन खालीपनों को अनुमान से भरा, और सबके अनुमान अलग रहे।
CommonMark इसी खाई को भरने के लिए है। यह एक सटीक स्पेसिफ़िकेशन है जिसमें कई सौ अनुरूपता परीक्षण हैं, जो ठीक उन्हीं अस्पष्ट स्थितियों को कवर करते हैं जिन्हें मूल संस्करण ने खुला छोड़ा था। यह कनवर्टर markdown-it उपयोग करता है, जो पूरा CommonMark सूट पास करता है, इसलिए आउटपुट वही होता है जो GitHub, Reddit, Discourse और बहुत से आधुनिक टूल बनाते हैं। यदि कोई दस्तावेज़ यहाँ रेंडर होता है, तो वहाँ भी उसी तरह रेंडर होगा।
GitHub Flavored Markdown इसके ऊपर जोड़ा गया एक सुपरसेट है: टेबल, स्ट्राइकथ्रू, टास्क लिस्ट और ऑटोलिंक किए गए URL। इस टूल में टेबल और टास्क लिस्ट काम करते हैं, इसीलिए नमूना दस्तावेज़ में दोनों शामिल हैं। यह अंतर तब मायने रखता है जब आप किसी ऐसे लक्ष्य के लिए लिख रहे हों जिस पर आपका नियंत्रण न हो, क्योंकि टेबल असल CommonMark का हिस्सा नहीं है और कोई सख़्त पार्सर उसे सादे टेक्स्ट की तरह आगे बढ़ा देगा।
चार टॉगल वास्तव में क्या बदलते हैं
ऑटोलिंकिंग किसी सादे URL को एंकर बना देती है। यह चेंजलॉग और नोट्स के लिए सुविधाजनक है, लेकिन CommonMark से विचलन है, जो सादे लिंक के चारों ओर एंगल ब्रैकेट माँगता है। यदि आउटपुट किसी सख़्त पार्सर तक पोर्टेबल होना चाहिए तो इसे बंद कर दें।
स्मार्ट टाइपोग्राफ़ी सीधे कोट्स को घुमावदार कोट्स में बदल देती है और -- को en डैश में। यह गद्य के लिए सही है और कोड ब्लॉक के बाहर कोड अंश वाली किसी भी चीज़ के लिए ग़लत, क्योंकि यह कमांड-लाइन फ़्लैग को खुशी-खुशी बिगाड़ देगी। कोड स्पैन और फ़ेंस्ड ब्लॉक हमेशा अछूते रहते हैं।
हार्ड लाइन ब्रेक बदल देते हैं कि एक न्यूलाइन का क्या अर्थ है। डिफ़ॉल्ट रूप से Markdown लगातार पंक्तियों को एक पैराग्राफ में जोड़ देता है, और अधिकांश दस्तावेज़ यही मानते हैं। चैट जैसे इनपुट में, जहाँ लोग नई पंक्ति के लिए Enter दबाते हैं, इसे चालू रखना ज़रूरी है, वरना उनकी फ़ॉर्मैटिंग ढह जाती है।
कच्चे HTML का पासथ्रू वही विकल्प है जिसके सुरक्षा परिणाम होते हैं। इसे बंद रखने पर स्रोत में मौजूद <img onerror=...> एस्केप होकर टेक्स्ट की तरह दिखता है। चालू रखने पर वह जीवित मार्कअप के रूप में निकलता है। उपयोगकर्ता द्वारा भेजी गई किसी भी सामग्री के लिए इसे बंद रखें।
सैनिटाइज़ करना एक अलग काम है
किसी भी Markdown पाइपलाइन के साथ सबसे आम भूल यह मान लेना है कि कनवर्टर आपकी रक्षा करता है। वह नहीं करता, और उसे करना भी नहीं चाहिए। कच्चा HTML बंद होने पर भी लिंक का लक्ष्य हमलावर के नियंत्रण में रहता है, इसलिए [click](javascript:alert(1)) एक ऐसा एंकर बनाता है जिसे ब्राउज़र मान सकता है। काम करने वाला हमला बनाने के लिए अकेला Markdown सिंटैक्स ही पर्याप्त है।
सही तरीका है: पहले बदलें, फिर सैनिटाइज़ करें, फिर डालें। HTML को DOMPurify जैसे समर्पित सैनिटाइज़र से टैग और एट्रिब्यूट की अनुमति-सूची के साथ गुज़ारें, और तभी उसे पेज में रखें। यदि कंटेंट उसके लेखक के अलावा किसी और को दिखेगा तो यह काम सर्वर पर करें, क्योंकि क्लाइंट-साइड सैनिटाइज़िंग को कोई भी बायपास कर सकता है जो सीधे आपके API से बात कर सके। यह टूल अपना प्रीव्यू आपके ही ब्राउज़र में, आपके ही इनपुट के साथ रेंडर करता है, जो किसी और के Markdown को प्रकाशित करने से अलग थ्रेट मॉडल है।