جامد ویب سائٹ کی میزبانی کرنے کے کئی سستے طریقے ہیں جو جامد سائٹ جنریٹر جیسے جیکیل، ہیوگو، یا پیلیکن کے ساتھ بنائے گئے ہیں: یہ پورا بلاگ جامد طور پر جیکیل کا استعمال کرتے ہوئے تیار کیا گیا ہے۔ تاہم، میں مندرجہ بالا اختیارات میں سے کسی کو بھی استعمال کرنے سے قاصر ہوں، کیونکہ، اس بلاگ کی زندگی بھر میں، میں نے ڈومین کے نام تبدیل کیے ہیں، یو آر ایل اسکیموں کو تبدیل کیا ہے، اور پوسٹس کا نام تبدیل کیا ہے، اور میں چاہتا ہوں کہ تمام پرانے URLs کو زندہ رکھیں میں اس بلاگ کی میزبانی اپاچی اور، حال ہی میں، ایک ہی ورچوئل مشین پر nginx کا استعمال کر رہا ہوں، اور سافٹ ویئر کے کسی ایک حصے کی ری ڈائریکشن کی خصوصیات بالکل ٹھیک کام کرتی ہیں، لیکن میں اسے کسی نئی اور مختلف جگہ پر ہوسٹ کرنے کے لیے تیار تھا۔ پچھلی پوسٹ میں بتایا گیا ہے کہ میں گوگل ایپ انجن اور ازگر کا استعمال کرتے ہوئے یو آر ایل کو پرانے ڈومین سے نئے ڈومین پر کیسے ری ڈائریکٹ کرتا ہوں، لیکن اب مجھے جامد مواد پیش کرنے کے طریقے کی ضرورت ہے۔ **اور** اسی ڈومین سے یو آر ایل کو ری ڈائریکٹ کریں۔ اسی ڈومین ری ڈائریکشن کی ضرورت اس لیے ہے کہ میں صرف Google App EngineâÃÂÃàکی صرف جامد مواد کی خصوصیت (اوپر کی فہرست میں منسلک) استعمال نہیں کرسکتا۔ تاہم، میں ایک سادہ گولانگ ایپلیکیشن کے ساتھ مل کر گوگل ایپ انجن کا استعمال کر سکتا ہوں تاکہ جامد مواد **اور** ایک ہی ڈومین ری ڈائریکٹ دونوں کو پیش کیا جا سکے۔ ## گوگل ایپ انجن کیوں؟ اس سے پہلے کہ آپ باقی پوسٹ کو دیکھیں، شاید آپ سوچ رہے ہوں گے کہ گوگل ایپ انجن پر بلاگ کی میزبانی کیوں کی جائے؟ یہاں میری وجوہات ہیں کیوں: - اگر آپ کا ٹریفک ایپ انجن کے 28 مثالی گھنٹوں کے مفت درجے اور روزانہ 1 GB ایگریس ٹریفک کے اندر فٹ بیٹھتا ہے، تو بلاگ کی میزبانی عملی طور پر مفت ہے۔ - اپ ڈیٹس کو آگے بڑھانا ایک کمانڈ سے کیا جاتا ہے۔ - لاگنگ اور نگرانی Stackdriver کا استعمال کرتے ہوئے مربوط ہیں۔ - ٹریفک کے نمونوں کی بنیاد پر خودکار اوپر اور نیچے کی پیمائش - چند کلکس کے ساتھ، طویل مدتی اسٹوریج اور ایڈہاک تجزیہ کے لیے ویب لاگز کو BigQuery جیسی کسی چیز پر آسانی سے دھکیلا جا سکتا ہے۔ - LetâÃÂÃÂs کا استعمال کرتے ہوئے منظم کردہ SSL سرٹیفکیٹس ## شرائط یہ پوسٹ مندرجہ ذیل فرض کرتی ہے: - آپ گوگل کلاؤڈ پلیٹ فارم (GCP) سے واقف ہیں اور پہلے ہی ایک GCP پروجیکٹ بنا چکے ہیں۔ - آپ نے گوگل کلاؤڈ SDK انسٹال کیا ہے۔ - آپ نے تصدیق کی ہے۔ gcloudcommand آپ کے گوگل اکاؤنٹ کے خلاف ایک GCP پروجیکٹ بنائیں اگر آپ نے ابھی تک نہیں بنایا ہے a **جی سی پی پروجیکٹ ان مراحل پر عمل کریں: - ایک ویب براؤزر کھولیں، اور گوگل اکاؤنٹ بنائیں یا لاگ ان کریں۔ - GCP کنسول پر جائیں۔ - اگر یہ آپ کا پہلا GCP پروجیکٹ ہے، تو آپ کو ایک GCP پروجیکٹ بنانے کے لیے کہا جائے گا۔ ہر Google اکاؤنٹ کو GCP کے لیے 12 ماہ کے اندر استعمال کرنے کے لیے $300 کا کریڈٹ ملتا ہے۔ GCP پروجیکٹ بنانے کے لیے آپ کو کریڈٹ کارڈ داخل کرنا ہوگا، لیکن اس سے اس وقت تک چارج نہیں کیا جائے گا جب تک کہ $300 کا کریڈٹ استعمال نہ ہوجائے یا 12 ماہ کی میعاد ختم نہ ہوجائے۔ - اگر یہ ایک نیا GCP پروجیکٹ ہے، تو آپ کو GCP کنسول کے Compute Engine سیکشن میں جاکر Compute Engine API کو فعال کرنے کی ضرورت ہوگی اور شروع ہونے کے مکمل ہونے کا انتظار کرنا ہوگا۔ گوگل کلاؤڈ SDK انسٹال کریں۔ اگر آپ نے ابھی تک انسٹال نہیں کیا ہے۔ **Google Cloud SDK یہاں دی گئی ہدایات پر عمل کریں۔ gcloud کی تصدیق کریں۔ ایک بار جب آپ نے GCP پروجیکٹ بنا لیا اور گوگل کلاؤڈ SDK انسٹال کر لیا، تو آخری مرحلہ اس کی تصدیق کرنا ہے gcloud کمانڈ آپ کے گوگل اکاؤنٹ پر۔ اپنا ٹرمینل ایپلیکیشن کھولیں اور درج ذیل کمانڈ کو چلائیں: gcloud auth لاگ ان آپ کے ویب براؤزر میں ایک ویب صفحہ کھل جائے گا۔ اپنا Google اکاؤنٹ منتخب کریں اور اسے GCP تک رسائی کی اجازت دیں۔ ایک بار مکمل ہونے کے بعد، آپ کی توثیق ہو جائے گی اور آگے بڑھنے کے لیے تیار ہو جائیں گے۔ ## ایک ڈائرکٹری بنائیں اگلا، اپنے Google App Engine ایپلیکیشن کو ذخیرہ کرنے کے لیے اپنے ورک سٹیشن پر کہیں ایک ڈائریکٹری بنائیں: mkdir ~/Sites/example.com/app_engine اس ڈائریکٹری میں تبدیل کریں: cd ~/Sites/example.com/app_engine اس پوسٹ کا بقیہ حصہ فرض کرے گا کہ آپ اس ڈائریکٹری کے اندر کام کر رہے ہیں۔ مزید برآں، کے اندر ایک ڈائرکٹری بنائیں **app_engine** ڈائرکٹری جسے **سٹیٹک کہتے ہیں۔ mkdir ~/Sites/example.com/app_engine/static آپ اس ڈائریکٹری کو بعد میں دوبارہ دیکھیں گے۔ ## app.yaml بنائیں Google App Engine کو عام طور پر دو فائلوں کی ضرورت ہوتی ہے: **app.yaml** اور ایک **ایپلیکیشن فائل** جو Python، Golang، Java، یا PHP میں لکھی گئی ہے - اس صورت میں یہ Golang ہو گا۔ **app.yaml** آپ کی ایپلیکیشن چلانے کے لیے ضروری کنفیگریشن فراہم کرتا ہے۔ بہت سے مختلف پیرامیٹرز ہیں جو **app.yaml میں موجود ہو سکتے ہیں ان پیرامیٹرز میں استعمال ہونے والی پروگرامنگ زبان کی بنیاد پر فرق ہو سکتا ہے۔ اس پوسٹ کے لیے، گولانگ استعمال کیا جائے گا، اور آپ یہاں تمام دستیاب گولانگ پیرامیٹرز تلاش کر سکتے ہیں۔ فائل بنائیں **app.yaml** درج ذیل مواد کے ساتھ: رن ٹائم: go api_version: go1 handlers: - url:script: _go_app محفوظ: ہمیشہ ری ڈائریکٹ_http_response_code: 301 محسوس کرو اسے **محفوظ: ہمیشہ** سیٹ کر دیا گیا ہے۔ اس کا مطلب ہے کہ گولانگ ایپلیکیشن ہمیشہ HTTPS پر پیش کی جائے گی۔ اگر کوئی آخری صارف HTTP پر ویب ایپلیکیشن پر جاتا ہے، تو وہ بطور ڈیفالٹ 302 HTTPS ورژن پر بھیج دیا جائے گا۔ اسی لیے **redirect_http_response_code: 301** بھی سیٹ کیا گیا ہے۔ میں ہمیشہ یہ چاہتا ہوں کہ ویب ایپلیکیشن HTTPS پر پیش کی جائے، اور میں نہیں چاہتا کہ تلاش کے انجن HTTP سے HTTPS پر ری ڈائریکشن کو عارضی ری ڈائریکٹ کے طور پر بیان کریں۔ یہ ایک مستقل ری ڈائریکٹ ہے۔ اگر آپ کے پاس جامد اثاثے ہیں، اور آپ شاید کرتے ہیں، تو یہ بہتر ہے کہ آپ App Engine کو اس کے بارے میں مطلع کریں اور اسے ان اثاثوں کو آپ کی درخواست کے بجائے آبجیکٹ اسٹوریج سے پیش کرنے دیں۔ ایسا کرنا آسان ہے اور کے ذریعے بھی کیا جاتا ہے۔ **app.yaml** فائل مثال کے طور پر، اگر آپ کے پاس فیوی کون فائل، سی ایس ایس ڈائرکٹری، جاوا اسکرپٹ ڈائرکٹری، اور امیجز ڈائرکٹری ہے تو درج ذیل کا استعمال کریں **app.yaml** فائل: رن ٹائم: go api_version: go1 handlers: - url: /favicon.png$ static_files: static/favicon.png اپ لوڈ: static/favicon.png - url: /css static_dir: static/css - url: /js static_dir: static_js - url: /images static_dir: static/images - url:script: _go_app محفوظ: ہمیشہ ری ڈائریکٹ_http_response_code: 301 ## main.go بنائیں اگلا، آپ کو گولانگ ایپلیکیشن فائل کی ضرورت ہے۔ اپنی ضروریات کو پورا کرنے کے لیے درج ذیل کوڈ کے لیے، فائل بنائیں **main.go نیچے کوڈ کو کاپی اور پیسٹ کریں، اور درج ذیل ترمیم کریں: - میں ڈومین متغیر، اپنے ڈومین نام کو درست HTTP پروٹوکول کے ساتھ ملانے کے لیے قدر کو تبدیل کریں۔ - میں urlsmap، تمام کلیدی قدر کے جوڑوں کو تبدیل کریں تاکہ آپ کو مطلوبہ ری ڈائریکٹس سے مماثل کیا جا سکے۔ ہر کلید کو موجودہ ڈومین کے پرانے URL کے صرف پاتھ والے حصے (/example-post-1.html کی بجائے httpsexample.com/example-post-1.html) سے تبدیل کریں جس پر آپ چاہتے ہیں۔ زندہ رہو. پھر ہر ایک قدر کو موجودہ ڈومین کے نئے URL کے راستے والے حصے سے تبدیل کریں جس پر آپ ری ڈائریکٹ کرنا چاہتے ہیں۔ تمام ری ڈائریکٹس 301 ری ڈائریکٹ ہوں گے۔ اس میں تبدیلی کرکے ترمیم کی جاسکتی ہے۔ ذیل کے کوڈ میں **301** مختلف HTTP ری ڈائریکٹ اسٹیٹس کوڈ جیسے **302** پیکیج مین درآمد ("net/http""os""strings") func init() { http.HandleFunc handler) } func handler(w http.ResponseWriter, r *http.Request) {// True (OK) اگر درخواست اگر قدر ہو تو پاتھ یو آر ایل میپ میں ہے، ٹھیک ہے := urls[r.URL.Path]؛ ٹھیک ہے { ویلیو = ڈومین + ویلیو http.Redirect(w, r, value, 301) } else { path := "static/"+ r.URL.Path // اگر HTTP کی درخواست کسی ایسی ڈائرکٹری سے ہے جو موجود ہے اور کرتی ہے تو واپسی 403 index.html فائل پر مشتمل نہیں ہے اگر f، err := os.Stat(path)؛ err == nil&& f.IsDir() { index := strings.TrimSuffix(path,+ "/index.html"if _, err := os.Open(index); err != nil { w.WriteHeader (403) w.Writebytehtml> 403 حرام

403 Forbidden

return } } // Return custom 404 page if HTTP request is to a non-existent file if _, err := os.Stat(path); os.IsNotExist(err) { w.WriteHeader(404) http.ServeFile(w, r, "static/404.html") return // Withoutreturn, a "404 page not found" string will be displayed at the bottom of your custom 404 page } http.ServeFile(w, r, path) return } } var domain string = "httpsexample.com" var urls = map[string]string{ "/example-post-1.html": "/post/example-post-1.html", "/example-post-2.html": "/post/example-post-2.html", "/example-post-3.html": "/post/example-post-3.html", } ## Generate the Static Content With **app.yaml** and **main.go** saved, the last piece is to generate your static content and store it in the **static** directory you created earlier How you do this entirely depends on what static site generator you are using If you are using Jekyll, you can configure the **destination** parameter in Jekyll’s _ **config.yml** file to save your static content in any directory on your workstation. So, you could set the **destination** parameter to Sites/example.com/app_engine/static and, every time you run jekyll build, the static content will be saved in that directory ## Deploy to App Engine With **app.yaml **main.go and your static content generated, you are ready to deploy your Google App Engine application Assuming gcloud is already pointed at the Google Cloud Project you want to deploy to, verify with gcloud config list project, run the following command: gcloud app deploy The command will output the appspot URL your application will be deployed to and ask if you want to continue. Typically, the appspot URL is **httpsyour-project-id.appspot.com This is also a useful self-check to make sure you are not deploying your application to the wrong Google Cloud Project. If everything looks okay, type **Y** and **Enter** to deploy your application. Depending on how large your static content is, your application should be deployed within about one minute ## Setup DNS At this point, your application is deployed under URL **httpsyour-project-id.appspot.com Unless your website uses that as its domain name, you will probably want to setup a custom domain that uses your actual current domain name The App Engine section of the Google Cloud Console can be used to do this. Go here and follow the instructions to configure your custom domain Once that is complete and DNS has had time to propagate, you should be able to navigate in your web browser to one of your current domain’s old URLs, for example **httpsexample.com/example-post-1.html and have it redirect to your current domain’s new URLs, for example **httpsexample.com/post/example-post-1.html** ## Pushing Updates To push updates, make the necessary changes in your static site’s source directory, regenerate the static content, and redeploy to Google App Engine by changing into the Sites/example.com/app_engine** directory and running gcloud app deploy ## References - A Surprising Feature of Golang that Colored Me Impressed - How to check if a map contains a key in go? - Disable directory listing with http.FileServer - 3 Ways to Disable http.FileServer Directory Listings - Handling HTTP Request Errors in GO - HTTP and Error management in Go - please add ability to set custom 404 notFoundHandler for http.FileServer