جیکیل بلاگ تھیم کو ازگر پر کیسے پورٹ کیا جائے: اسے کرنے سے سیکھے گئے اسباق

میں کئی سالوں سے tufte-jekyll سٹائل کے بلاگ کی پیروی کر رہا ہوں اور اس کی وجہ سے مجھے ایڈورڈ ٹفٹے کی کتاب کی ترتیب دریافت ہوئی۔

ایڈورڈ ٹفٹے ڈیٹا ویژولائزیشن اور انفارمیشن ڈیزائن میں اپنے کام کے لیے جانا جاتا ہے، اور وہ ڈیٹا کی اعلی کثافت اور "چارٹ جنک” کے خاتمے کے لیے ایک مضبوط وکیل ہے۔

یہ وہی ہے جو tufte-css (اور اس میں شامل بہت سی بندرگاہیں) ویب پر لاتا ہے: فراخ سفید جگہ، سیرف پڑھنے کے قابل کالم، اور قیمتی نوٹ اضافی معلومات (مداخلت کرنے والے ماڈلز کے بجائے)

مجھے تقریباً ہر چیز پسند تھی۔ ٹوپے جیکیل بلاگ، مائنس دی غیر تحریری متعلقہ حصے: یہ روبی کا جیکیل پر مبنی ورژن ہے جو میں صرف اس پروجیکٹ کے لیے آیا ہوں۔

تو میں نے پوری تھیم کو ازگر میں دوبارہ لکھا۔ ایسا نہیں ہے کیونکہ جیکیل برا ہے۔ یہ سچ نہیں ہے۔ لیکن چونکہ میں ایک ٹول چین چاہتا تھا جس سے میں آرام سے تھا۔ میں یہ بھی سوچ رہا تھا کہ کیا میں واقعتا سمجھ سکتا ہوں اور اس کو مل سکتا ہوں کہ ایک جامد سائٹ جنریٹر کیسے کام کرتا ہے۔

tufte-python وہ بندرگاہ ہے، اور یہ مضمون ایک رہنما کے طور پر کام کرتا ہے: جب آپ مائع پر مبنی Jekyll تھیم کو Python تھیم پر منتقل کرتے ہیں تو اصل میں کیا ہونے کی ضرورت ہے، اور مخصوص جگہ میں نے اسے صحیح ہونے سے پہلے ہی غلط سمجھا۔

اس میں سے کوئی بھی جیکل مخصوص مشورہ نہیں ہے۔ وہی پیٹرن لاگو ہوتا ہے چاہے ہدف ہیوگو (گو لانگ)، گیارہ (جاوا اسکرپٹ) وغیرہ ہو۔

یہاں آپ کو پتہ چل جائے گا کہ مسائل کا تجزیہ کیسے کیا جائے جبکہ ایک بہت ہی تکنیکی توجہ کا احاطہ کیا جائے۔ اگر آپ ایک مختلف تھیم پورٹ کر رہے ہیں، یا بالکل مختلف زبان میں پورٹ کر رہے ہیں، تو درج ذیل کو یاد رکھیں: اگرچہ نحو بدل جاتا ہے: شکل چیلنج کا مواد ایک جیسا ہے۔

انڈیکس

لیکن ٹھہرو، جامد بلاگ کیوں؟

متحرک ویب سائٹس کے مقابلے میں، جامد سائٹس میں اشاعتی کام کا بہاؤ آسان ہوتا ہے۔ اس صورت میں یہ مندرجہ ذیل 5 مراحل پر مشتمل ہے:

  1. مارک ڈاؤن فائل بنائیں۔

  2. جنریٹر چلائیں۔

  3. پیش نظارہ کریں اور نتائج کا جائزہ لیں۔

  4. سورس فائل کا ارتکاب کریں۔

  5. GitHub ایکشنز کو اپنی سائٹ شائع کرنے دیں۔

یہ ورک فلو میری ضروریات کے لیے کافی آسان ہے۔ میں اپنے ذاتی ڈویلپر بلاگ پر کبھی کبھار پوسٹ کرتا ہوں۔ ٹیکسٹ ایڈیٹر آپ کے مواد کو پڑھنے کے قابل رکھتا ہے اور کسی بھی تبدیلی کا جائزہ لینا آسان بناتا ہے۔

پچھلے کوڈ کی طرح، اصل کوڈ بیس مواد کے لیے Jinja2 ٹیمپلیٹس، مارک ڈاؤن، اور YAML عنوانات کو برقرار رکھتا ہے۔ GitHub ایکشن ورک فلو آپ کی سائٹ بناتا ہے اور تیار کردہ مواد کو تعینات کرتا ہے۔ _site/ اپنے GitHub صفحہ پر ایک ڈائریکٹری شامل کریں۔

کسی تھیم کو اس طرح استعمال کرنے کے بجائے پورٹ کیوں کریں؟

ایسا کرنے کی کئی وجوہات ہیں۔

سب سے پہلے، آپ ایک ٹول چین استعمال کرنا چاہتے ہیں جسے آپ کہیں اور استعمال نہیں کرتے ہیں۔ میں نے اپنے کمپیوٹر پر روبی کو صرف اس مقصد کے لیے انسٹال کیا ہے۔ یہ اتنا ہی نرم تھا۔ میرے بلاگ کو اپ ڈیٹ کریں۔ کبھی کبھی بدلنا میرے روبی ماحول میں ترمیم کریں۔ پہلے

یا ہوسکتا ہے کہ آپ پہلے سے ہی ہر روز اپنی ٹارگٹ زبان میں لکھ رہے ہوں اور پلگ ان فائلوں کو موافقت کرنے کے لیے ایک اور ماحولیاتی نظام سیکھنے کے بجائے ان جنریٹرز کو پڑھ کر بڑھا دیں گے جن میں آپ اچھے ہیں۔

یا ہوسکتا ہے کہ آپ صرف جامد سائٹ جنریٹر کو سمجھنا چاہتے ہوں نہ کہ یہ کیسے کام کرتا ہے۔ جب آپ پورٹ کرتے ہیں، تو آپ کو ہر ٹیمپلیٹ، ہر حسب ضرورت ٹیگ، اور ہر تعمیراتی قدم کو اتنی باریک بینی سے پڑھنے کی ضرورت ہوتی ہے کہ ان کو دوبارہ لاگو کرنے کے قابل ہو۔ ہم معلومات کو مختلف طریقے سے سیکھتے اور برقرار رکھتے ہیں۔ سمجھنے کی سطح بہت مختلف ہے۔ اوہ! یہ کام کرتا ہے، اور یہ مہارت حاصل کرنے کے بہترین طریقوں میں سے ایک ہے۔

آپ کو کیا ضرورت ہے

  • بنیادی ازگر: ورچوئل ماحول، دوسرے لوگوں کا کوڈ پڑھنا۔

  • گٹ اور گٹ ہب اکاؤنٹس (چونکہ دونوں ورژن کا ہدف گٹ ہب پیجز ہے)

  • مارک ڈاؤن اور گٹ کا علم (گیمز کے ذریعے بھی سیکھا جا سکتا ہے)

  • جیکل پروجیکٹ لے آؤٹ کا بنیادی علم: _config.yml, _layouts/, _includes/اور مائع ٹیمپلیٹ نحو۔

  • جنجا 2 کے پہلے تجربے کی ضرورت نہیں ہے۔ یہ تصوراتی طور پر مائع سے کافی مماثلت رکھتا ہے کہ آپ جاتے وقت اسے اٹھا سکتے ہیں۔

پہلے منزل کی جانچ کریں: مکمل شدہ پورٹ کو چلائیں۔

اس سے پہلے کہ ہم یہ دیکھیں کہ بندرگاہ کو درحقیقت کیسے ایک ساتھ رکھا جاتا ہے (بشمول ٹوٹے ہوئے حصوں)، یہ جاننا ضروری ہے کہ بندرگاہ کیسے ختم ہوتی ہے۔ میں جس تھیم کو بیان کر رہا ہوں وہ پہلے سے ہی ایک ریڈی ٹو ریلیز پروجیکٹ کے طور پر موجود ہے۔ tufte-python اپنے ٹیوٹوریل کے ساتھ آتا ہے اور اسے منٹوں میں مقامی طور پر چلایا جا سکتا ہے۔

اس سے آپ کو موازنہ کرنے کے لیے کچھ ٹھوس ملے گا جیسا کہ آپ بقیہ پڑھتے ہیں، اور اگر آپ کسی موجودہ بندرگاہ کو شروع سے بنانے کے بجائے اسے موافقت کرنا چاہتے ہیں تو اس سے کانٹے کے لیے کچھ ملے گا۔

ترتیب

سب سے پہلے، اسے کلون کریں اور اسے اپنے ذخیرے کی طرف اشارہ کریں (یا اسے فورک کریں)۔

GitHub پر ایک نیا، خالی ذخیرہ بنا کر شروع کریں۔ اسے اس طرح کا نام دیں: my-blog:

git clone https://github.com/hyperphantasia/tufte-python.git my-blog
cd my-blog

اگلا، اپنے ذخیرے کی طرف اشارہ کرنے کے لیے اوریجن ریموٹ کو تبدیل کریں۔

git remote set-url origin 

پھر اپنے پروجیکٹ کو آگے بڑھائیں۔

git push -u origin main

اگلا، انحصار کو اپنے ورچوئل ماحول میں انسٹال کریں۔

python -m venv .venv
# Uncomment to match your OS
# source .venv/bin/activate      # macOS/Linux
# .venvScriptsActivate.ps1     # Windows PowerShell
pip install -r requirements.txt

اب ہم اپنی پہلی تعمیر سے پہلے ڈیفالٹ کنفیگریشن ویلیوز سیٹ کرنا چاہتے ہیں۔

کھلا config.yml منصوبے کی جڑ میں:

title: "A Quiet Corner of the Web"
author: "Your Name"
email: "you@example.com"

url: "https://yourusername.github.io"
baseurl: "/my-blog"              # "" instead, if this is a user/org page
permalink: "/articles/{year}/{slug}/"

theme: "solAArized"
options:
  mathjax: true

اگر آپ پوسٹ کرتے ہیں: https://yourusername.github.io/my-blog/, baseurl ریپوزٹری کا نام بالکل مماثل ہونا چاہیے، لیڈنگ سلیشز کے ساتھ اور کوئی ٹریلنگ سلیش نہیں ہے۔ اگر یہ غلط ہو جاتا ہے تو، تعینات کردہ سائٹ پر تمام اندرونی لنکس اور اسٹائل شیٹ کے حوالے 404 ہوں گے اور مقامی طور پر ٹھیک کام کریں گے (نیچے کیوں کے بارے میں مزید)۔

آخر میں، تعمیر اور پیش نظارہ.

python build.py --serve --watch

تعینات ٹفٹی ازگر مثال کا ٹرمینل لوکل ہوسٹ کو دکھا رہا ہے۔

وہ پتہ کھولیں جو ٹرمینل پرنٹ کرتا ہے۔ http://localhost:8000 آپ ڈیمو مواد دیکھیں گے جو (عام طور پر) پہلے سے موجود ہے۔ content/. چھوڑ دو --watch پوسٹس کو چلانا اور ان میں ترمیم کرنا: آپ کو کچھ دوبارہ کیے بغیر صفحہ دوبارہ بنایا جائے گا۔

بعد میں آپ کو الجھا دینے والی سہ پہر سے پہلے ایک چیز جاننا ضروری ہے: مقامی --serve پیش نظارہ کو نظر انداز کریں۔ baseurl ہم جان بوجھ کر روابط اور اثاثوں کو جڑ سے حل کرنے پر مجبور کرتے ہیں۔ ڈویلپر سرور ذیلی ڈائریکٹریوں کے بجائے۔

اگر آپ یہ دیکھنا چاہتے ہیں کہ تعیناتی کے بعد سائٹ کیسی نظر آئے گی، بشمول اصل سائٹ۔ baseurl: دوڑنا python build.py --serve --production-urls اس کے بجائے۔ یہ پروڈکشن یو آر ایل کی ساخت کا استعمال کرتے ہوئے آپ کی سائٹ کا پیش نظارہ کرنے کے لیے ہے۔

اسی لیے تفریق کی گئی ہے۔ مقامی طور پر کام کریں، پیداوار بند کریں۔ ذیلی ڈائریکٹریوں میں جامد سائٹس کے لیے کیڑے موجود ہیں، اس لیے اصل میں تعینات کرنے سے پہلے کم از کم ایک بار جان بوجھ کر دونوں طریقوں کی جانچ کرنا ضروری ہے۔

اپنی پہلی پوسٹ لکھیں۔

آپ ڈیمو کے مواد کے بجائے آپ کے اپنے مواد میں پیش کردہ تھیم کی خصوصیات دیکھیں گے۔ بنانا content/posts/2024-06-07-hello.md:

---
title: "Hello, Margins"
date: 2024-06-07 14:30:00
categories: notes
tags: [smile, writing]
---

{% newthought 'A new thought' %} can open a section without another heading.

Here's a sidenote{% sidenote 'note-1' 'This appears in the right margin on wide screens, and behind a tap target on narrow ones.' %} to try the feature that made me want this theme in the first place.



Everything past the `` marker stays off the homepage excerpt but shows up on the full post.

بہت سی دوسری بصری خصوصیات بھی دستیاب ہیں۔ اس پر عمل درآمد کے دوران ذیل میں مزید تفصیل سے تبادلہ خیال کیا جائے گا۔

دوبارہ تعمیر کریں (یا --watch (اختیاری)، پھر آپ کو چھوٹے بڑے حروف میں ایک ابتدائی بیان اور پیراگراف کے آگے مارجن میں ایک نمبر والا نوٹ دیکھنا چاہیے جو اس کا حوالہ دیتا ہے۔ ایک بار جب دونوں کو پیش کیا جاتا ہے، تھیم کے بنیادی میکانکس آپ کے کمپیوٹر پر پوری طرح کام کر رہے ہیں۔ بہت اچھا یہ وہ طریقہ کار ہے جس کا اس ٹیوٹوریل کے بقیہ حصے میں احاطہ کیا گیا ہے۔

GitHub صفحہ سیکشن کا اسکرین شاٹ GitHub ایکشن سورس کو صحیح طریقے سے تعینات کرنے کے لیے دکھا رہا ہے۔

آپ کے ذخیرے میں ترتیبات → صفحاتماخذ کو اس پر سیٹ کریں: گٹ ہب آپریشنز اگر پہلے ہی نہیں۔ آپ کے پروجیکٹ کے ساتھ بنڈل بنائے گئے ورک فلو ہر ایک پش کے ساتھ خود بخود بنائے جاتے ہیں اور تعینات ہوتے ہیں۔ main. GitHub صفحات کے بعد، ہم دیکھیں گے کہ وہ ورک فلو دراصل مرحلہ 6 میں کیا کرتا ہے۔ نہیں جانتے ازگر کی تعمیر اسکرپٹ کے ساتھ کیا کرنا ہے؟

اگر آپ مطمئن ہیں تو اسے مقامی طور پر پہنچا دیں۔

git add config.yml content/
git commit -m "Configure site and add first post"
git push

ایک بار جب آپ اسے چلاتے ہیں، تو آپ کے پاس ایک ورکنگ ریفرنس پوائنٹ آن لائن ہوگا۔ اب آئیے ایک نظر ڈالتے ہیں کہ یہ کیسے بنایا گیا ہے۔

tufte-jekyll سے tufte-python تک، قدم بہ قدم

جیکیل تھیم کو پائتھون بلڈ سسٹم میں منتقل کرنے کے لیے، اپنے موجودہ سیٹ اپ کو ڈی کنسٹریکٹ کرنے کے لیے ساختی اقدامات پر عمل کرنا ضروری ہے۔

میں نے یہاں اعلیٰ سطح کے چھ مراحل طے کیے ہیں، لیکن یہ آپ کے کام کے لحاظ سے مختلف ہو سکتے ہیں۔ سب سے پہلے اپنے دماغ میں نتائج کو "خود” بنانا بہت ضروری ہے۔ یہ نقطہ نظر آپ کو کنفیگریشنز کو مستحکم کرنے اور اس عمل کے دوران کم سے کم رکاوٹ کے ساتھ ٹولز کو جدید بنانے کی اجازت دیتا ہے۔

مرحلہ 1: اپنے ماخذ تھیم کے متحرک حصوں کی فہرست بنائیں

پہلے جیسا کہ میں Python میں لکھتا ہوں، میں نے Jekyll مشین کے ان تمام حصوں کو درج کیا ہے جن پر تھیم دراصل منحصر ہے۔ اس مائع مرکوز تھیم کے لیے، اسے چار زمروں میں تقسیم کیا گیا ہے:

جیکل پیس فنکشن متوقع ازگر کے برابر
_config.yml + _data/*.yml سٹرکچرڈ ڈیٹا جیسے سائٹ میٹا ڈیٹا، بیس یو آر ایل، پرمالنک پیٹرن، فیچر ٹوگلز، اور سوشل لنکس۔ ایک config.yml
_layouts/ + _includes/ صفحہ ٹیمپلیٹس اور حصے کوئی راستہ نہیں templates/ Jinja2 ٹیمپلیٹ ڈائرکٹری
_plugins/*.rb ایک روبی کلاس جو آپ کے تھیم کے حسب ضرورت مائع ٹیگز کو رجسٹر کرتی ہے۔ ایک چھوٹا Python ماڈیول جو ایک ہی ٹیگ نحو کو بڑھاتا ہے۔
_sass/*.scss تعمیر کے وقت ایک اسٹائل شیٹ میں سس کا حصہ مرتب کیا گیا۔ سادہ سی ایس ایس فائل، کوئی تالیف کا مرحلہ نہیں۔

میں پہلے مرحلے میں پانچویں کیٹیگری سے محروم رہا۔ اصل تھیم دو الگ الگ ریک آپریشنز فراہم کرتا ہے: ایک نئی پوسٹس اور پیجز کو سہاروں کے لیے، اور دوسرا بالکل مختلف کام ہے۔ UploadToGithub.Rakefile تعمیر شدہ سائٹ gh-pages ہاتھ سے جانا۔

یہ ضروری ہے کیونکہ تھیم کے پلگ ان جیکیل کے صفحہ حفاظتی وائٹ لسٹ میں نہیں ہیں۔ میں مرکزی مواد پڑھوں گا۔ Rakefile اور یہ فرض کرتے ہوئے کہ میں تعیناتی کی پوری کہانی کو جانتا ہوں، میں نے تھوڑی دیر کے لیے سوچا کہ اصل مصنف نے سائٹ کو کیسے لائیو کیا۔

مشورہ: مکمل ذخیرہ کی جڑ پڑھیںاس کے ساتھ ساتھ فائلوں کو ڈھانچے میں شامل کرنے سے پہلے واضح ناموں کے ساتھ۔

مرحلہ 2: بکھری ہوئی ترتیب کو ایک فائل میں کم کریں۔

جیکیل کا یہ ورژن ترتیبات کو متعدد جگہوں پر پھیلاتا ہے۔ _config.yml (سائٹ کا عنوان، URL، بنیادی URL، permalink پیٹرن) اور ذیل میں ایک یا زیادہ فائلیں۔ _data/: ایک فائل میں میتھ جیکس اور فونٹ لوڈنگ کے لیے ٹوگلز ہیں، دوسری میں سماجی روابط کی فہرست ہے۔ یہ تقسیم جیکیل کے اپنے ڈیٹا فائل کنونشنز کی پیروی کرتی ہے، لیکن اپنا (کم سے کم) لوڈر لکھتے وقت پیچیدہ ہونے کی ضرورت نہیں ہے۔

واضح سیکشن کے ناموں کے ساتھ ہر چیز کو ایک فائل میں یکجا کر کے، جو بھی تھیم کو بعد میں بڑھاتا ہے وہ تین کے بجائے ایک جگہ پر تمام ترتیبات تلاش کر سکتا ہے۔ آپ کو کچھ ملتا ہے جیسے:

# config.yml
# --- site metadata ---
title: "A Quiet Corner of the Web"
author: "Your Name"
email: "you@example.com"

# --- URL settings ---
url: "https://yourusername.github.io"
baseurl: "/my-blog"
permalink: "/articles/{year}/{slug}/"

# --- feature toggles (previously in _data/options.yml) ---
mathjax: true
justify_text: false

# --- social links (previously in _data/social.yml) ---
social:
  - link: "github.com/yourusername"
    icon: icon-github

مرحلہ 3: اپنے حسب ضرورت مائع ٹیگ کو ٹیکسٹ شارٹ کوڈ میں دوبارہ ترتیب دیں۔

یہ وہ حصہ ہے جس کو ٹھیک کرنے میں سب سے زیادہ وقت لگا۔ یہ وہ جگہ ہے جہاں تھیم کی زیادہ تر اصل فطرت ہے۔ یہ وہ جگہ ہے جہاں آپ واقعی بصری خصوصیات (سائیڈ نوٹ، مارجن تصویریں، ایپی گراف) بناتے ہیں۔

جیکل کیا کرتا ہے؟

اپنی مرضی کے مطابق مائع ٹیگز _plugins/روبی کلاس جیکیل مائع پارسر کے ساتھ رجسٹرڈ ہے۔ جیکیل اس کو مائع رینڈر پاس کے دوران بڑھاتا ہے۔ پہلے نتائج کو مارک ڈاون انجن میں منتقل کریں۔

ٹیگز جیسے {% sidenote "note-1" "Some aside." %} یہ مارک ڈاؤن کنورٹر تک نہیں پہنچتا جیسا کہ ہے۔ جب آپ صفحہ دیکھتے ہیں تو مارک ڈاؤن کو پہلے ہی ایچ ٹی ایم ایل سے بدل دیا گیا ہے۔

میں اس 1:1 کو جنجا 2 پر کیوں نہیں پورٹ کر سکتا ہوں؟

Jinja2 کا اپنا ٹیگنگ سسٹم ہے، لیکن یہ منطق کی ٹیمپلیٹنگ کے لیے بنایا گیا ہے (بشمول لوپس، کنڈیشنلز وغیرہ)، مارک ڈاؤن فائلوں کے اندر نثر سے صوابدیدی نقل شدہ دلائل کو پارس کرنے کے لیے نہیں۔ اور یہاں تک کہ اگر آپ نے اس کے لیے جنجا 2 ایکسٹینشن بنایا ہے تو، تمام موجودہ پوسٹس پرانی ایکسٹینشن استعمال کریں گی۔ {% sidenote ... %} آپ کو اپنے نحو کو دوبارہ لکھنے کی ضرورت ہے۔ یہ کیچ ڈراپ ان پورٹ کے پورے پوائنٹ کو نیچے گرا دیتا ہے۔

اصل میں کیا کام کرتا ہے

ٹیگ نحو کو سادہ متن کے طور پر پروسیس کیا جاتا ہے، اسے خام مارک ڈاؤن پر پری پروسیسنگ کے ذریعے پھیلایا جاتا ہے، اور پھر مارک ڈاؤن رینڈرر کو منتقل کیا جاتا ہے۔ حکمت عملی یہ ہے کہ جیکیل کے منفرد پوسٹ ٹیگ مارک ڈاؤن آرڈرنگ کو درست طریقے سے ظاہر کیا جائے۔ اس پاس کا ایک آسان ورژن یہ ہے:

import re, shlex

TAG_RE = re.compile(r"{%s*(w+)s*(.*?)s*%}")

def split_args(raw: str) -> list[str]:
    lexer = shlex.shlex(raw, posix=True)
    lexer.whitespace_split = True
    return list(lexer)

def render_sidenote(args, resolve_img, render_md):
    note_id, text = args[0], args[1]
    text = render_md(text)
    return (f"{text}")

HANDLERS = {"sidenote": render_sidenote}  # All visual features are registered here

def expand_shortcodes(text: str, resolve_img, render_md) -> str:
    def dispatch(match: re.Match) -> str:
        name, raw_args = match.group(1), match.group(2)
        handler = HANDLERS.get(name)
        if handler is None:
            return match.group(0)  # leave unknown tags untouched
        return handler(split_args(raw_args), resolve_img, render_md)
    return TAG_RE.sub(dispatch, text)

مندرجہ بالا کوڈ کا ٹکڑا ایک حسب ضرورت "تلاش اور تبدیل کریں” انجن کے طور پر کام کرتا ہے جو حتمی صفحہ پیش کرنے سے پہلے شارٹ ہینڈ ٹیگز کو HTML میں بدل دیتا ہے۔ درج ذیل نمونوں کے لیے متن تلاش کرنے کے لیے ریگولر ایکسپریشنز کا استعمال کریں: {% tag arguments %}.

باقاعدہ اظہار (TAG_RE) "اسکینر” ہے۔

متن کے بڑے بلاکس میں ٹیگ تلاش کرنے کے لیے ریگولر ایکسپریشنز ذمہ دار ہیں۔ تمام میچوں کو دو مخصوص گروپوں میں تقسیم کریں۔

  • گروپ 1 (نام): {% کے فوراً بعد کا لفظ (مثلاً "سائیڈ نوٹ”)۔

  • گروپ 2 (خام دلائل): بند ہونے تک باقی سب کچھ %} (جیسے "نوٹ-1” "کچھ ایک طرف۔”)۔

expand_shortcodes "کوآرڈینیٹر” ہے:

یہ فنکشن مجموعی عمل کا انتظام کرتا ہے۔ یہ استعمال کرتا ہے re.sub متن کو دہرائیں۔ جب بھی ریگولر ایکسپریشن کو کوئی مماثلت ملتی ہے۔ expand_shortcodes یہ ایک ڈسپیچ فنکشن کو متحرک کرتا ہے جو دو چیزیں کرتا ہے:

split_args "پارسر” ہے:

split_args سٹرنگ کو "سمارٹ اسپلٹ” کرنے کے لیے shlex لائبریری کا استعمال کرتا ہے۔ یہ اقتباسات کو پہچانتا ہے، لہذا اقتباسات کے اندر موجود ہر چیز ایک دلیل کے طور پر ایک ساتھ رہتی ہے۔ یہ ایک صاف فہرست تیار کرتا ہے جہاں خالی جگہوں پر مشتمل دلائل، جیسے اقتباسات کے اندر جملے، کو متعدد انفرادی الفاظ کے بجائے ڈیٹا کے ایک ٹکڑے کے طور پر سمجھا جاتا ہے، جیسے [‘note-1’, ‘Some aside.’])۔ حتمی ہینڈلر فنکشن اسے آسانی سے سنبھال سکتا ہے۔

کھڑا کرنا:

آخری مرحلہ اصل رینڈرنگ ہے۔ ہر ٹیگ کا نام ہے۔ HANDLERS ڈکشنریوں کو Python کے مخصوص فنکشنز سے جوڑا جاتا ہے جو جانتے ہیں کہ متعلقہ HTML مارک اپ کو کیسے واپس کرنا ہے، جیسے render_sidenote() صرف حوالہ کے لیے)۔

آپ دیکھ سکتے ہیں .sidenote اور .margin-toggle CSS کلاسز اس خیال کو بصری طور پر حاصل کرتی ہیں کہ چیزیں کیسے کام کرتی ہیں۔

دو کیڑے نے مجھے دکھایا کہ اوپر کی تفصیلات کیوں اہم ہیں۔ دونوں کو ڈیمو مواد کی بجائے نئی عمارتوں پر اصلی پرانی پوسٹس پوسٹ کرکے دریافت کیا گیا۔

  • کوٹیشن یہ پہلے ٹوٹ گیا۔ میری پہلی دلیل تقسیم کرنے والا ہے۔ raw.split() خالی جگہ میں۔ یہ اس وقت تک ٹھیک کام کر رہا تھا جب تک میں نے سائیڈ نوٹ میں apostrophe کے ساتھ ایک پوسٹ ٹائپ نہیں کی تھی۔

    مثال: "قارئین کا” مسئلہ ہے۔ یہ دو دلائل میں تقسیم ہوتا ہے اور اس کے بعد تمام دلائل کو ایک کے ذریعے منتقل کرتا ہے۔ مائع کی اپنی ٹیگ دستاویزات دراصل اس کی وضاحت کرتی ہیں۔ سنگل یا ڈبل ​​اقتباسات اور بیک سلیش کو متن کے اندر اقتباسات سے بچنے کی اجازت دیتا ہے۔ shlex پوسکس موڈ میں، یہ تقریباً دو لائنوں میں بالکل ایسا ہی کرتا ہے، جو کہ اس کے حقدار سے چھوٹا حل ہے۔

  • کوڈ باڑ دوسری بار ٹوٹ گیا۔ میں نے شارٹ کوڈ نحو کی وضاحت کرنے والی ایک پوسٹ لکھی تھی، جس کی مثالیں باڑ والے کوڈ بلاکس میں بند ہیں۔ یہ سیاق و سباق کے اندھے پن کا معاملہ ہے۔ باقاعدہ اظہار کو پیٹرن تلاش کرنے کے لیے ڈیزائن کیا گیا ہے۔ {% ... %} یہ دستاویز میں ہر جگہ ظاہر ہوتا ہے، لیکن یہ "حقیقی” کوڈ کے درمیان فرق نہیں بتاتا ہے جس پر عمل کرنے کی ضرورت ہے اور "مثال” کوڈ جو قاری کے سامنے پیش کیا جاتا ہے۔ The expand_shortcodes فنکشن ہے {% and %} کوڈ بلاک کے اندر آپ کہتے ہیں، "آہ! یہ ایک بصری خصوصیت ہے!” اگر آپ مثال کے متن کو سائیڈ نوٹ سے اصل HTML سے بدل دیتے ہیں، تو آپ کو کوڈ بلاک کے اندر موجود فنکشنل فنکشنلٹی کے ساتھ ٹوٹے ہوئے لے آؤٹ کے ساتھ ختم کر دیں گے۔

    ایک حل یہ ہے کہ الگ کیے گئے ان لائن کوڈ کو پلیس ہولڈر کے پیچھے چھپانا، جیسے ##CODEBLOCK_1##) regex ٹیگ پر عمل کرنے سے پہلے، پھر اسے بعد میں بحال کریں۔

پیش کردہ خصوصیات

مارجن نہیں۔ سجاوٹ ٹفٹے سے متاثر لے آؤٹ کم درج شدہ ٹائپوگرافی اور معاون مواد کے لیے کافی سفید جگہ کی بدولت پڑھنے کی اہلیت کو برقرار رکھتا ہے۔

معاون معلومات کو مضمون کے باڈی میں لمبا وقفہ ہونے کے بجائے حاشیے پر منتقل کیا جاتا ہے۔ دیگر بصری عناصر، جیسے نوٹس، حوالہ جات اور تصویروں کو بنیادی دلیل سے ہٹے بغیر ان کی اپنی جگہ دیں۔

باقی ٹیگز کو وہاں سے پورٹ کرنا مکرر اور مکینیکل تھا۔ ایک ہی پیٹرن، مختلف ہینڈلر اور ہر بار دلائل کی تعداد، پورا کوڈ اس فائل میں دستیاب ہے اور یہاں یہ ہے کہ اسے کیسے پیش کیا گیا ہے:

نئے خیالات:

ٹفتے ازگر: نیو تھوٹ مثال اسکرین شاٹ۔

  • مائع ٹیگز: {% newthought 'text' %}

حوالہ:

ٹفتے ازگر: سائڈنوٹ مثال اسکرین شاٹ۔

مارجن نوٹ:

ٹفتے ازگر: مثال کے مارجن نوٹ کا اسکرین شاٹ۔

مارجن کے اعداد و شمار:

ٹفتے ازگر: مثال کے مارجن کے اعداد و شمار کا اسکرین شاٹ۔

  • مائع ٹیگز: {% marginfigure 'id' 'path' 'caption' %}

    معاون تصاویر مارجن کالم تک محدود ہیں۔ امیج پروسیسنگ کوئی بہت بڑا چیلنج نہیں ہے جیسا کہ ایچ ٹی ایم ایل اسے فراہم کرتا ہے۔ img ٹیگ ویو پورٹ کے اندر پوزیشننگ حاصل کرنا قدرے مشکل ہے، لیکن اصل SCSS میں پہلے ہی اچھی طرح سے ہینڈل کیا گیا تھا۔

اہم کالم تصویر:

ٹفتے ازگر: مرکزی کالم فگر مثال کا اسکرین شاٹ۔

مکمل چوڑائی تصویر:

ٹفتے ازگر: مکمل چوڑائی والی تصویر کا اسکرین شاٹ۔

اخراج:

Tufte-Python: شلالیھ مثال کا اسکرین شاٹ۔

ریاضی:

ٹفتے ازگر: میتھ جیکس مثال اسکرین شاٹ۔

  • مائع ٹیگز: {% math %} ... {% endmath %}

    یہ خالص بلاک LaTeX ہے جسے MathJax کے ذریعے پیش کیا گیا ہے۔

آپ معیاری مارک ڈاؤن خصوصیات جیسے کوڈ کے ٹکڑوں کو بھی استعمال کر سکتے ہیں۔

Tufte-Python: مثال کے کوڈ کے ٹکڑوں کا اسکرین شاٹ۔

یا میز:

Tufte-Python: ٹیبل مثال اسکرین شاٹ۔

ان آخری دو عناصر کو لاگو کرنا آسان تھا۔ چونکہ اسے خالص مارک ڈاؤن کے طور پر پیش کیا گیا ہے، آپ اسے براہ راست اپنی CSS اسٹائل شیٹ میں ہینڈل کر سکتے ہیں (جیسے tufte.css فائل کے ٹیبل اسٹائل سیکشن میں)۔

مرحلہ 4: کمپائلڈ سس کو بدلنے کے قابل سادہ سی ایس ایس سے تبدیل کریں۔

جیکیل میں ساس پائپ لائن مرتب کرنا _sass/ تعمیر کے وقت، ہم آؤٹ پٹ پر ایک فکسڈ کلر پیلیٹ لگاتے ہیں، جسے ایک اسٹائل شیٹ میں حصوں میں تقسیم کیا جاتا ہے۔

میں نے سی ایس ایس پر رنگوں کو مرتب کرنا صرف اس لیے روک دیا کہ میں تھیم کو پورٹ کرنے کے لیے ساس کمپائلیشن انحصار نہیں چاہتا تھا۔

ایک باقاعدہ سی ایس ایس اسٹائل شیٹ دو پرتوں پر مشتمل ہوتی ہے: ساختی سی ایس ایس۔ رنگوں کی کوئی ہارڈ کوڈنگ نہیں۔یہ صرف حسب ضرورت خصوصیات کا حوالہ دیتا ہے: color: var(--color-text)اور ہم فی پیلیٹ صرف ایک چھوٹی تھیم فائل کی وضاحت کرتے ہیں۔ --color-* وصف تعمیر صرف فائلوں کو منتخب کردہ تھیم سے آؤٹ پٹ میں کاپی کرتی ہے۔ theme: کی اسٹروک config.yml.

دستیاب تھیمز سے Tufte Python SSG اینیمیشنز کے اسکرین شاٹس۔

اپنی مرضی کے موضوعات بڑی بہتری میں اسے نافذ کرنا چاہتا تھا۔ اصل میں نمبروں کو دیکھنے کے بعد، یہ صرف ایک حل سے زیادہ میں بدل گیا. پہلے مجھے سولرائزڈ پسند آیا، اس لیے میں نے اسے ڈیفالٹ بنا دیا، لیکن پھر مجھے احساس ہوا کہ یہ قابل رسائی کے لیے موزوں نہیں ہے۔ یہ ایک معروف اور دستاویزی جائیداد ہے۔ آنکھوں کے دباؤ کو کم کرنے کے لیے کچھ برعکس تجارت کریں۔

براہ کرم مندرجہ ذیل طور پر بھیجیں: بنیادی میں نے محسوس کیا کہ اگر میں نے اسے جھنڈا نہیں لگایا تو میں کچھ غلط کر رہا ہوں جسے دوسرے لوگ پڑھنے کے لیے استعمال کر سکتے ہیں۔

چونکہ تھیم سسٹم ایک قابل بدلنے والی CSS فائل ہے، اس لیے ترمیم میں ایک اور WCAG 2.0 AA قابل رسائی ویرینٹ فائل کو شامل کرنا تھا جس میں اصل کے ہی پیلیٹ کے ساتھ 4.5:1 کنٹراسٹ کو صاف کرنے کے لیے ایڈجسٹ کیا گیا تھا۔ یہ وہ اختیار ہے جس کا اس ٹیوٹوریل کی ترتیب کی مثالیں حوالہ دیتی ہیں: solAArized۔

اپنی مرضی کے مطابق پراپرٹی اپروچ ادا کیا ایک لمحے میں ایک بار پھر: چونکہ رنگ براؤزر کے ذریعے رن ٹائم پر حل کیے جاتے ہیں بجائے اس کے کہ براؤزر کی طرف سے تعمیر کے وقت بیک ان کیا جائے، اس لیے ہم ایک ہلکا/گہرا ٹوگل شامل کریں گے جس کے ذریعے چلایا جائے گا: prefers-color-scheme یہ پیکج کے لیے ایک چھوٹی JS فائل تھی۔ یہ وہ چیز ہے جو Sass کے ساتھ مرتب کردہ ایک پیلیٹ دو بار دوبارہ مرتب کیے بغیر نہیں کر سکتی۔

مرحلہ 5: واضح بلڈ کیشے کے لیے فائل سسٹم واچ کو تبدیل کرنا

jekyll serve -w بنڈل فائل کا مشاہدہ اور اضافی تخلیق نو۔ اضافی میں اصل حالت کا سراغ لگانا شامل ہے۔

میرے پہلے کیشے نے ہر پوسٹ کے ترمیمی وقت کو ٹریک کیا۔ فائل میں کوئی تبدیلی نہیں کی گئی ہے اور دوبارہ رینڈرنگ کو چھوڑ دیا گیا ہے۔ جب تک آپ مشترکہ ٹیمپلیٹ میں ترمیم نہیں کرتے یہ درست ہے۔ میں نے اپنی پوسٹ لے آؤٹ کو تبدیل کیا اور دوبارہ لکھا اور میری صرف دو پوسٹس میں تبدیلیاں آئیں۔ اس دن میں نے جس پوسٹ کو چھوا تھا اس کے لیے بھی یہی بات تھی۔ دوسرے صرف اس تعریف کے مطابق "بغیر تبدیل شدہ” ہیں جو کیشے کو معلوم ہے، لہذا وہ پرانے پہلے سے ترمیم شدہ HTML ہیں۔ _site/.

ترمیم ایک دوسرا، علیحدہ ٹائم اسٹیمپ ہے جو کسی ایک دستاویز سے منسلک نہیں ہے۔ پوری دستاویز میں ترمیم کے تازہ ترین وقت کو ٹریک کرتا ہے۔ عالمی تعمیر ان پٹ: ٹیمپلیٹ؛ config.ymlجنریٹر کا اپنا ذریعہ۔ اگر ان میں سے کوئی بھی کیشے سے نیا ہے، تو مکمل دوبارہ تعمیر پر مجبور کریں، قطع نظر اس کے کہ انفرادی پوسٹس پر ٹائم اسٹیمپ کیا کہتے ہیں۔

import json
from pathlib import Path

CACHE_FILE = Path(".build_cache.json")

def load_cache() -> dict:
    if not CACHE_FILE.exists():
        return {"global_mtime": 0.0, "docs": {}}
    return json.loads(CACHE_FILE.read_text())

def needs_rebuild(src: Path, out: Path, cache: dict, global_stale: bool) -> bool:
    if global_stale or not out.exists():
        return True
    cached_mtime = cache["docs"].get(str(src))
    return cached_mtime is None or src.stat().st_mtime > cached_mtime

def save_cache(cache: dict, docs: dict) -> None:
    cache["docs"] = docs
    CACHE_FILE.write_text(json.dumps(cache))

کہ load_cache() فنکشن ایک ذخیرہ شدہ JSON فائل کو پڑھتا ہے جو یاد رکھتا ہے کہ ہر دستاویز میں آخری بار کب ترمیم کی گئی تھی، یا اگر فائل پہلے سے موجود نہیں ہے تو ایک نیا، خالی کیش بناتا ہے۔

کہ needs_rebuild() فنکشن اس بات کا تعین کرتا ہے کہ آیا ماخذ فائل کو اصل میں ترمیم کے موجودہ وقت کا کیشے میں محفوظ کردہ ٹائم اسٹیمپ سے موازنہ کرکے دوبارہ لکھنے کی ضرورت ہے۔ اگر فائل کیشڈ سے نئی ہے یا آؤٹ پٹ فائل موجود نہیں ہے تو، واپس آتی ہے: True (مطلب "دوبارہ تعمیر کی ضرورت ہے”)

آخر کار save_cache() یہ نئی تعمیراتی معلومات کے ساتھ کیشے کو اپ ڈیٹ کرتا ہے اور اسے JSON فائل میں واپس محفوظ کرتا ہے، تاکہ آپ کسی بھی ایسی فائل کو چھوڑ سکتے ہیں جو اگلی بار آپ کے بلڈ چلانے پر تبدیل نہیں ہوئی ہیں۔

سستے میں تلاش کرنے کا کوئی طریقہ نہیں ہے۔ کوئی بھی میں نے اس بارے میں ہوشیار بننے کی کوشش کرنا چھوڑ دی ہے کیونکہ مشترکہ ٹیمپلیٹس ہر چیز کو دوبارہ پارس کیے بغیر ہی صفحہ کو نشانہ بنا سکتے ہیں۔ اس کے نتیجے میں ٹیمپلیٹ کی ترامیم کے بعد تعمیرات سست ہوں گی، لیکن یہ ان صفحات کو خود بخود آگے نہ بھیجنے کے لیے تجارت بند ہے جو بظاہر کامیابی کے ساتھ بنائے گئے ہیں لیکن حقیقت میں کوئی تبدیلی لاگو نہیں کی گئی ہے۔

مرحلہ 6: Jekyll کے پہلے سے طے شدہ GitHub صفحات کو اپنے CI سے تبدیل کریں۔

GitHub صفحات مقامی طور پر جانتے ہیں کہ جیکیل کو کیسے بنانا ہے۔ مجھے کوئی اندازہ نہیں ہے کہ وہ کیا ہے۔ python build.py اس کا مطلب ہے کہ پورٹ کو سائٹ بنانے اور آؤٹ پٹ کو صفحات پر منتقل کرنے کے لیے اپنے CI قدم کی ضرورت ہے۔

# .github/workflows/deploy.yml
name: Build and deploy site
on:
  push:
    branches: [main]

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-python@v5
        with:
          python-version: "3.12"
      - run: pip install -r requirements.txt
      - run: python build.py
      - uses: actions/upload-pages-artifact@v3
        with:
          path: _site

  deploy:
    needs: build
    runs-on: ubuntu-latest
    permissions:
      pages: write
      id-token: write
    steps:
      - uses: actions/deploy-pages@v4

کیا ہوتا ہے؟ جب آپ دبائیں گے تو GitHub سرور خود بخود بلڈ جاب چلاتے ہیں۔ یہ ٹاسک آپ کے کوڈ کی تصدیق کرتا ہے، ازگر 3.12 انسٹال کرتا ہے، اور پروجیکٹ کے انحصار کو ڈاؤن لوڈ کرتا ہے ( requirements.txt)، پھانسی build.py ایک ویب سائٹ بنائیں اور پھر بنائی گئی ویب سائٹ اپ لوڈ کریں۔ _site ایک فولڈر کو بطور نمونہ استعمال کریں۔

اگر کامیاب ہوجاتا ہے، تو تعیناتی کا کام خود بخود چلتا ہے، متعلقہ نمونے کھینچتا ہے، اور انہیں حقیقی وقت میں آپ کے GitHub صفحہ پر شائع کرتا ہے۔ براہ کرم اس کا حوالہ دیں۔ needs: build لائن ہم اس بات کو یقینی بناتے ہیں کہ تعمیر کے کامیابی سے مکمل ہونے کے بعد ہی تعیناتی کا مرحلہ ہوتا ہے، لہذا آپ غلطی سے ٹوٹی ہوئی عمارت کو تعینات نہیں کر سکتے۔

یہ اس آرٹیکل میں پہلے استعمال کیے گئے کوئک اسٹارٹ کا ورک فلو ہے۔ یاد رکھیں کہ ترتیبات → صفحاتماخذ کو اس پر سیٹ کیا جانا چاہیے: گٹ ہب آپریشنز برانچ نہیں (یہ مکمل طور پر جیکیل کے بلٹ ان بلڈ سٹیپ کی جگہ لے لیتا ہے) میں نے اپنے آپ کو یہ باور کرانے میں چند منٹ گزارے کہ میں نے پہلی بار اس سیٹ اپ کو کھو دیا اور ورک فلو خاموشی سے ناکام ہو گیا۔ لیکن حقیقت میں یہ کامیاب رہا اور تعیناتی کے لیے کہیں بھی کوئی ترتیب نہیں تھی۔

مرحلہ 7: خصوصیت کی برابری کی تصدیق کریں، نہ صرف "تعمیر”

ایک بندرگاہ جو صاف طور پر مرتب کرتی ہے ضروری نہیں کہ صحیح بندرگاہ ہو۔ اوپر بیان کردہ تمام کیڑے پہلے صاف ستھری تعمیر سے گزرے۔ میں نے اسے مکمل کرنے سے پہلے درج ذیل کا تجربہ کیا:

  • اصل تھیم سے اصلی، غیر ترمیم شدہ پوسٹیہ صرف ڈیمو مواد نہیں ہے۔ یہ وہی ہے جس نے اصل میں کوٹنگ بگ اور کوڈ فینس بگ کو پکڑا، جن میں سے کوئی بھی اس وقت تک ظاہر نہیں ہوا جب تک کہ میں نے لکھنے میں آسانی پیدا کرنے کے لیے خاص طور پر لکھے گئے مواد کی جانچ کرنا بند نہیں کیا۔

  • انتہائی مقدمات کا حوالہ دیتے ہوئے ڈیزائن کے لحاظ سے: نوٹس کے اندر apostrophes، نوٹ کے اندر مارک ڈاون فارمیٹنگ، ڈبل کوٹس سے بچ گئے۔

  • رد عمل کا رویہسائیڈ نوٹ اور مارجن نوٹ ظاہر کرنے کے لیے تھپتھپائیں۔ تنگ اسکرینوں پر، ڈیسک ٹاپ پر ہی چلنا آسان ہے اور موبائل ورژن پر خاموشی سے لٹکا رہتا ہے۔

ایک ٹفتے ازگر پر مبنی بلاگ جو رد عمل کی حیثیت کو ظاہر کرتا ہے۔

ریسپانسیو ڈیزائن کو کبھی کبھی نظرانداز کر دیا جاتا ہے اور آج جب ڈیوائس کے تنوع کی بات آتی ہے تو یہ یقینی طور پر کوئی آپشن نہیں ہے۔ اسے ہمیشہ ایک مکمل اور الگ صارف کے تجربے کے طور پر سوچیں۔

جو میں پہلے اپنے آپ کو بتانا چاہتا ہوں۔

اس پورٹ میں تمام اصل کیڑے ایک ہی بنیادی وجہ سے پیدا ہوتے ہیں۔ یہ پہلے سے موجود مواد کی بجائے آسانی سے لکھے گئے مواد کا امتحان ہے۔

پرانے ٹیگ کو کیسے کام کرنا چاہئے اس پر میری کوئی رائے نہیں ہے۔ تصحیح ہر بار ایک جیسی تھی۔ یہ اندازہ لگانے کے بجائے کہ آپ کو "شاید” کس چیز کی حمایت کرنے کی ضرورت ہے، پرانے ذخیروں کے دستاویزات اور کوڈ میں اصلی کنارے کے معاملات تلاش کریں۔

اقدامات خود اس ایک عنوان سے آگے بڑھتے ہیں۔ سورس جنریٹر کے متحرک حصوں کو کیٹلاگ کریں، ان کی کنفیگریشن کو مضبوط کریں، نئے ٹیمپلیٹ انجن کے نحو سے لڑنے کے بجائے ٹیکسٹ پری پروسیسنگ پاسز کے ساتھ حسب ضرورت ٹیگز کو دوبارہ لاگو کریں، مرتب شدہ اسٹائلز کو ان سے تبدیل کریں جو کہ نیا اسٹیک بغیر کسی اضافی ٹولز کے پیدا کر سکتا ہے، عالمی سطح پر تبدیلیوں کے لیے واضح تبدیلیوں کے لیے اپنا اضافی کیش بنائیں۔ آپ کے اپنے CI کے ساتھ پیچھے رہ گئے، اور کلین بلڈز کے بجائے اصل مواد کے خلاف چیک کریں۔ یہ سچ ہے چاہے آپ جیکیل سے ازگر، ازگر سے گو، یا کہیں اور جا رہے ہوں۔

پڑھنے کے لیے شکریہ! براہ کرم tufte-python میں تعاون کرنے کے لئے آزاد محسوس کریں! میں بہت متجسس ہوں کہ اس لائبریری کو بہتر بنانے کے لیے کیا کیا جا سکتا ہے۔ آپ میرے GitHub اور Kaggle پر میرے مزید ذاتی پروجیکٹس دیکھ سکتے ہیں۔ آپ مجھ سے براہ راست LinkedIn پر بھی رابطہ کر سکتے ہیں۔

اوپر تک سکرول کریں۔