जेफिरनेट लोगो

Node.js के साथ एक जावास्क्रिप्ट कमांड लाइन इंटरफेस (CLI) बनाएँ

दिनांक:

Node.js के रूप में महान "पारंपरिक" वेब अनुप्रयोगों के लिए है, इसके संभावित उपयोग कहीं अधिक व्यापक हैं। माइक्रोसॉफ़्ट, रीस्ट एपीआई, टूलिंग, इंटरनेट ऑफ थिंग्स और यहां तक ​​कि डेस्कटॉप एप्लिकेशन के साथ काम करना: यह आपकी पीठ मिल गया है।

एक अन्य क्षेत्र जहां Node.js वास्तव में उपयोगी है कमांड-लाइन अनुप्रयोगों के निर्माण के लिए - और यही हम इस लेख में करने जा रहे हैं। हम कमांड लाइन के साथ काम करने में मदद करने के लिए डिज़ाइन किए गए कई तृतीय-पक्ष पैकेजों को देखकर शुरू करने जा रहे हैं, फिर स्क्रैच से वास्तविक दुनिया उदाहरण का निर्माण करें।

हम जो निर्माण करने जा रहे हैं वह एक गिट रिपॉजिटरी को शुरू करने के लिए एक उपकरण है। यकीन है, यह चलेगा git init हुड के नीचे, लेकिन यह सिर्फ उससे अधिक करेगा। यह कमांड लाइन से सही GitHub पर एक रिमोट रिपॉजिटरी भी बनाएगा, जो उपयोगकर्ता को अंतःक्रियात्मक रूप से बनाने की अनुमति देगा .gitignore फ़ाइल, और अंत में एक प्रारंभिक प्रतिबद्ध और धक्का प्रदर्शन।

हमेशा की तरह, इस ट्यूटोरियल के साथ कोड हमारे पर पाया जा सकता है गीथहब रेपो.

एक नोड सीएलआई बनाएँ

इस लेख को 2020 में अद्यतन किया गया था। अधिक गहराई से जावास्क्रिप्ट ज्ञान के लिए, हमारी पुस्तक पढ़ें, जावास्क्रिप्ट: नोवाइस टू निंजा, दूसरा संस्करण.

इससे पहले कि हम अंदर जाएं और निर्माण शुरू करें, यह देखने लायक है कि हम कमांड लाइन एप्लिकेशन बनाने के लिए Node.js क्यों चुन सकते हैं।

सबसे स्पष्ट लाभ यह है कि, यदि आप इसे पढ़ रहे हैं, तो आप शायद पहले से ही इससे परिचित हैं - और, वास्तव में, जावास्क्रिप्ट के साथ।

एक और महत्वपूर्ण लाभ, जैसा कि हम देखते हैं कि हम साथ-साथ चलते हैं, यह है कि मजबूत Node.js पारिस्थितिकी तंत्र का मतलब है कि सभी प्रकार के प्रयोजनों के लिए उपलब्ध सैकड़ों-हजारों पैकेजों में से, एक संख्या है जो विशेष रूप से शक्तिशाली बनाने में मदद करने के लिए डिज़ाइन की गई हैं कमांड लाइन उपकरण।

अंत में, हम उपयोग कर सकते हैं npm किसी भी निर्भरता का प्रबंधन करने के बजाय, एप्टीट्यूड, यम या होमब्रे जैसे ओएस-विशिष्ट पैकेज प्रबंधकों के बारे में चिंता करने की आवश्यकता है।

युक्ति: यह आवश्यक नहीं है कि सही हो, इसमें आपके कमांड-लाइन टूल में अन्य बाहरी निर्भरताएँ हो सकती हैं।

हम क्या बनाने जा रहे हैं: ginit

कार्रवाई में हमारा नोड सीएलआई गिनीट

इस ट्यूटोरियल के लिए, हम एक कमांड-लाइन यूटिलिटी बनाने जा रहे हैं, जिसे मैं कॉल कर रहा हूँ परिहास। आईटी इस git init, लेकिन स्टेरॉयड पर।

आप शायद सोच रहे हैं कि पृथ्वी पर इसका क्या मतलब है।

जैसा कि आप पहले से ही जानते हैं, git init वर्तमान फ़ोल्डर में Git रिपॉजिटरी को इनिशियलाइज़ करता है। हालांकि, यह आमतौर पर एक नए या मौजूदा प्रोजेक्ट को गिट करने के लिए शामिल करने की प्रक्रिया में शामिल कई दोहरावदार चरणों में से एक है। उदाहरण के लिए, एक सामान्य वर्कफ़्लो के हिस्से के रूप में, आप अच्छी तरह से हो सकते हैं:

  1. स्थानीय रिपॉजिटरी को चालू करके आरंभ करें git init
  2. GitHub या Bitbucket पर उदाहरण के लिए एक दूरस्थ रिपॉजिटरी बनाएं - आमतौर पर कमांड लाइन को छोड़कर और वेब ब्राउज़र को फायर करके
  3. रिमोट जोड़ें
  4. बनाओ .gitignore पट्टिका
  5. अपनी परियोजना फ़ाइलें जोड़ें
  6. फ़ाइलों का प्रारंभिक सेट करें
  7. दूरस्थ रिपॉजिटरी तक पहुंचाएं।

इसमें अक्सर अधिक चरण शामिल होते हैं, लेकिन हम अपने ऐप के उद्देश्यों के लिए उनसे चिपके रहेंगे। फिर भी, ये कदम बहुत दोहराव वाले हैं। यह बेहतर नहीं होगा अगर हम कमांड लाइन से यह सब कर सकते हैं, जिसमें जीआईटी यूआरएल और इस तरह की कोई कॉपी-पेस्टिंग नहीं है?

तो क्या ginit करेगा वर्तमान फ़ोल्डर में Git रिपॉजिटरी बनाएं, रिमोट रिपॉजिटरी बनाएं - हम इसके लिए GitHub का उपयोग करेंगे - और फिर इसे रिमोट के रूप में जोड़ें। तब यह एक सरल इंटरैक्टिव "विज़ार्ड" प्रदान करने के लिए प्रदान करेगा .gitignore फ़ाइल, फ़ोल्डर की सामग्री जोड़ें और इसे दूरस्थ रिपॉजिटरी तक बढ़ाएं। यह आपको घंटों नहीं बचा सकता है, लेकिन यह एक नई परियोजना शुरू करते समय कुछ प्रारंभिक घर्षण को हटा देगा।

इसे ध्यान में रखते हुए, आइए शुरू करें।

अनुप्रयोग निर्भरताएँ

एक बात निश्चित है: उपस्थिति के संदर्भ में, कंसोल में ग्राफिकल यूजर इंटरफेस का परिष्कार कभी नहीं होगा। फिर भी, इसका मतलब यह नहीं है कि यह सादा, बदसूरत, मोनोक्रोम पाठ होना चाहिए। आप इसे देखकर आश्चर्यचकित हो सकते हैं कि आप इसे दृष्टिगत रखते हुए कितना कुछ कर सकते हैं। हम प्रदर्शन को बढ़ाने के लिए पुस्तकालयों के एक जोड़े को देख रहे हैं: चाक आउटपुट को रंगीन करने के लिए और क्लुई कुछ अतिरिक्त दृश्य घटकों को जोड़ने के लिए। बस मनोरंजन के लिए, हम उपयोग करेंगे अंजीर एक फैंसी ASCII आधारित बैनर बनाने के लिए, और हम भी उपयोग करेंगे स्पष्ट कंसोल को खाली करने के लिए।

इनपुट और आउटपुट के संदर्भ में, निम्न-स्तर ReadLine Node.js मॉड्यूल का उपयोग उपयोगकर्ता को संकेत देने और इनपुट का अनुरोध करने के लिए किया जा सकता है, और सरल मामलों में पर्याप्त से अधिक है। लेकिन हम तृतीय-पक्ष पैकेज का लाभ उठाने जा रहे हैं जो परिष्कार की एक बड़ी डिग्री जोड़ता है - इन्क्वायरर। प्रश्न पूछने के लिए एक तंत्र प्रदान करने के साथ, यह सरल इनपुट नियंत्रणों को भी लागू करता है: रेडियो बटन और चेकबॉक्स, लेकिन कंसोल में सोचें।

हम भी उपयोग करेंगे न्यूनतम कमांड-लाइन तर्कों को पार्स करने के लिए।

यहां उन पैकेजों की एक पूरी सूची दी गई है जिन्हें हम विशेष रूप से कमांड लाइन पर विकसित करने के लिए उपयोग करेंगे:

  • चाक - आउटपुट को रंगीन करता है
  • स्पष्ट - टर्मिनल स्क्रीन को साफ करता है
  • क्लुई - कमांड-लाइन टेबल, गेज और स्पिनर खींचता है
  • अंजीर - पाठ से ASCII कला बनाता है
  • इन्क्वायरर - इंटरैक्टिव कमांड लाइन उपयोगकर्ता इंटरफ़ेस बनाता है
  • न्यूनतम - पार्स तर्क विकल्प
  • विन्यास - आसानी से लोड और बचाता है आप के बारे में सोचने के बिना कहाँ और कैसे।

इसके अतिरिक्त, हम निम्नलिखित का उपयोग भी करेंगे:

Getting Started

हालाँकि हम एप्लिकेशन को स्क्रैच से बनाने जा रहे हैं, लेकिन यह मत भूलिए कि आप कोड की एक प्रति भी ले सकते हैं रिपॉजिटरी जो इस लेख के साथ है.

प्रोजेक्ट के लिए एक नई निर्देशिका बनाएँ। आपको इसे कॉल करने की आवश्यकता नहीं है ginit, बेशक:

mkdir ginit
cd ginit

कोई नया बनाएं package.json फ़ाइल:

npm init -y

और ऐसा दिखने के लिए इसे संपादित करें:

{ "name": "ginit", "version": "1.0.0", "description": "'git init' on steroids", "main": "index.js", "scripts": { "test": "echo "Error: no test specified" && exit 1" }, "keywords": [ "Git", "CLI" ], "author": "<YOUR NAME>", "license": "ISC"
}

अब निर्भरता स्थापित करें:

npm install chalk clear clui figlet inquirer minimist configstore @octokit/rest @octokit/auth-basic lodash simple-git touch

अब एक बनाएँ index.js एक ही फ़ोल्डर में फ़ाइल और require निम्नलिखित निर्भरताएँ:

const chalk = require('chalk');
const clear = require('clear');
const figlet = require('figlet');

कुछ हेल्पर तरीकों को जोड़ना

हम एक बनाने जा रहे हैं lib फ़ोल्डर जहां हम अपने सहायक कोड को मॉड्यूल में विभाजित करेंगे:

  • फ़ाइलें.जेएस - मूल फ़ाइल प्रबंधन
  • पूछताछकर्ता.जेएस - कमांड लाइन उपयोगकर्ता बातचीत
  • जीथब.जेएस - पहुंच प्रबंधन
  • रेपो.जेएस - गिट भंडार प्रबंधन।

चलो साथ - साथ शुरू करते हैं lib/files.js। यहां, हमें निम्न करने की आवश्यकता है:

  • वर्तमान निर्देशिका प्राप्त करें (डिफ़ॉल्ट रेपो नाम पाने के लिए)
  • जाँचें कि क्या कोई निर्देशिका मौजूद है (यह निर्धारित करने के लिए कि वर्तमान फ़ोल्डर पहले से ही नाम वाले फ़ोल्डर की तलाश में Git रिपॉजिटरी है या नहीं .git).

यह सीधा लगता है, लेकिन ध्यान में रखने के लिए कुछ जोड़े हैं।

सबसे पहले, आप का उपयोग करने के लिए परीक्षा हो सकती है fs मॉड्यूल के रीयलपथसिंक वर्तमान निर्देशिका प्राप्त करने की विधि:

path.basename(path.dirname(fs.realpathSync(__filename)));

यह तब काम करेगा जब हम उसी निर्देशिका से एप्लिकेशन को कॉल कर रहे हैं (उदाहरण के लिए, उपयोग कर रहे हैं node index.js), लेकिन ध्यान रखें कि हम अपने कंसोल एप्लिकेशन को विश्व स्तर पर उपलब्ध कराने जा रहे हैं। इसका मतलब है कि हम उस निर्देशिका का नाम चाहते हैं जिसमें हम काम कर रहे हैं, न कि उस निर्देशिका में जहां आवेदन रहता है। इस उद्देश्य के लिए, इसका उपयोग करना बेहतर है प्रक्रिया:

path.basename(process.cwd());

दूसरे, एक फ़ाइल या निर्देशिका मौजूद है या नहीं यह जाँचने का पसंदीदा तरीका बदलता रहता है। वर्तमान तरीका उपयोग करना है existsSync। यह लौटता है true यदि पथ मौजूद है, false अन्यथा।

अंत में, यह ध्यान देने योग्य है कि जब आप कमांड-लाइन एप्लिकेशन लिख रहे हों, तो इन प्रकार के तुल्यकालिक संस्करण का उपयोग करना ठीक है।

उस सभी को एक साथ रखते हुए, चलो एक उपयोगिता पैकेज बनाते हैं lib/files.js:

const fs = require('fs');
const path = require('path'); module.exports = { getCurrentDirectoryBase: () => { return path.basename(process.cwd()); }, directoryExists: (filePath) => { return fs.existsSync(filePath); }
};

करने के लिए वापस जाओ index.js और आप सुनिश्चित करें require नई फ़ाइल:

const files = require('./lib/files');

इसके स्थान पर, हम एप्लिकेशन को विकसित करना शुरू कर सकते हैं।

नोड सीएलआई की शुरुआत

अब हमारे कंसोल एप्लिकेशन के स्टार्ट-अप चरण को लागू करते हैं।

कंसोल आउटपुट को बढ़ाने के लिए हमने कुछ पैकेजों को प्रदर्शित करने के लिए, स्क्रीन को साफ़ करें और फिर एक बैनर प्रदर्शित करें:

// index.js clear(); console.log( chalk.yellow( figlet.textSync('Ginit', { horizontalLayout: 'full' }) )
);

आप एप्लिकेशन का उपयोग करके चला सकते हैं node index.js। इस से आउटपुट नीचे दिखाया गया है।

हमारे नोड सीएलआई पर स्वागत बैनर, चाक और फिगलेट का उपयोग करके बनाया गया

अगला, चलिए यह सुनिश्चित करने के लिए एक साधारण चेक चलाते हैं कि वर्तमान फ़ोल्डर पहले से ही Git रिपॉजिटरी नहीं है। यह आसान है: हम सिर्फ एक के अस्तित्व के लिए जाँच करते हैं .git हमारे द्वारा बनाई गई उपयोगिता विधि का उपयोग करके फ़ोल्डर:

//index.js if (files.directoryExists('.git')) { console.log(chalk.red('Already a Git repository!')); process.exit();
}

युक्ति: ध्यान दें कि हम इसका उपयोग कर रहे हैं चाक मॉड्यूल लाल रंग का संदेश दिखाने के लिए।

इनपुट के लिए उपयोगकर्ता को प्रेरित करना

अगली चीज़ जो हमें करने की ज़रूरत है वह एक फ़ंक्शन है जो उपयोगकर्ता को उनके GitHub क्रेडेंशियल के लिए संकेत देगा।

हम प्रयोग कर सकते हैं इन्क्वायरर इसके लिए। मॉड्यूल में विभिन्न प्रकार के संकेतों के लिए कई विधियां शामिल हैं, जो HTML फॉर्म नियंत्रणों के लगभग अनुरूप हैं। उपयोगकर्ता के GitHub उपयोगकर्ता नाम और पासवर्ड को इकट्ठा करने के लिए, हम इसका उपयोग करने जा रहे हैं input और password क्रमशः प्रकार।

सबसे पहले, बनाएँ lib/inquirer.js और यह कोड डालें:

const inquirer = require('inquirer'); module.exports = { askGithubCredentials: () => { const questions = [ { name: 'username', type: 'input', message: 'Enter your GitHub username or e-mail address:', validate: function( value ) { if (value.length) { return true; } else { return 'Please enter your username or e-mail address.'; } } }, { name: 'password', type: 'password', message: 'Enter your password:', validate: function(value) { if (value.length) { return true; } else { return 'Please enter your password.'; } } } ]; return inquirer.prompt(questions); },
};

जैसा कि आप देख सकते हैं, inquirer.prompt() उपयोगकर्ता को पहले तर्क के रूप में एक सरणी के रूप में प्रदान किए गए प्रश्नों की एक श्रृंखला पूछता है। प्रत्येक प्रश्न एक वस्तु से बना होता है जो परिभाषित करता है name क्षेत्र के, type (हम सिर्फ उपयोग कर रहे हैं input और password यहाँ क्रमशः, लेकिन बाद में हम एक और अधिक उन्नत उदाहरण देखेंगे), और प्रॉम्प्ट (message) प्रदर्शित करने के लिए।

उपयोगकर्ता द्वारा प्रदान किए जाने वाले इनपुट को कॉलिंग फ़ंक्शन के रूप में पास किया जाएगा Promise। सफल होने पर, हम दो गुणों के साथ एक साधारण वस्तु के साथ समाप्त करेंगे - username और password.

आप निम्न में से सभी को जोड़कर इसका परीक्षण कर सकते हैं index.js:

const inquirer = require('./lib/inquirer'); const run = async () => { const credentials = await inquirer.askGithubCredentials(); console.log(credentials);
}; run();

फिर स्क्रिप्ट का उपयोग करके चलाएं node index.js.

इन्क्वायरर के साथ उपयोगकर्ता इनपुट प्राप्त करना

युक्ति: जब आप परीक्षण कर रहे हों, तो लाइन निकालना न भूलें const inquirer = require('./lib/inquirer'); से index.js, क्योंकि हमें वास्तव में इस फाइल में इसकी आवश्यकता नहीं होगी।

GitHub प्रमाणीकरण के साथ काम करना

अगला कदम GitHub API के लिए OAuth टोकन प्राप्त करने के लिए एक फ़ंक्शन बनाना है। अनिवार्य रूप से, हम एक टोकन के लिए उपयोगकर्ता नाम और पासवर्ड "एक्सचेंज" करने जा रहे हैं।

बेशक, हम नहीं चाहते हैं कि उपयोगकर्ता हर बार उपकरण का उपयोग करने के बाद अपनी साख दर्ज करें। इसके बजाय, हम OAuth टोकन को बाद के अनुरोधों के लिए संग्रहीत करेंगे। यह वह जगह है जहाँ विन्यास पैकेज आता है

स्टोरिंग कॉन्फ़िगरेशन

भंडारण विन्यास बाहरी रूप से काफी सीधा है: आप किसी JSON फ़ाइल से तृतीय-पक्ष पैकेज की आवश्यकता के बिना बस पढ़ / लिख सकते हैं / कर सकते हैं। हालाँकि, कॉन्फ़िगरस्टोर पैकेज कुछ प्रमुख लाभ प्रदान करता है:

  1. यह आपके लिए फ़ाइल के लिए सबसे उपयुक्त स्थान निर्धारित करता है, आपके ऑपरेटिंग सिस्टम और वर्तमान उपयोगकर्ता को ध्यान में रखता है।
  2. फ़ाइल को स्पष्ट रूप से पढ़ने या लिखने की कोई आवश्यकता नहीं है। आप बस एक कॉन्फ़िगरस्टोर ऑब्जेक्ट को संशोधित करते हैं और पृष्ठभूमि में आपके लिए इसका ध्यान रखा जाता है।

इसका उपयोग करने के लिए, बस एक उदाहरण बनाएं, इसे एक एप्लिकेशन आइडेंटिफ़ायर पास करें। उदाहरण के लिए:

const Configstore = require('configstore');
const conf = new Configstore('ginit');

अगर configstore फ़ाइल मौजूद नहीं है, यह एक खाली ऑब्जेक्ट लौटाएगा और फ़ाइल को पृष्ठभूमि में बनाएगा। यदि पहले से ए configstore फ़ाइल, सामग्री आपके आवेदन के लिए उपलब्ध कराई जाएगी। अब आप उपयोग कर सकते हैं conf एक साधारण वस्तु के रूप में, आवश्यकता के अनुसार गुण प्राप्त करना या स्थापित करना। जैसा कि ऊपर उल्लेख किया गया है, आपको बाद में इसे बचाने के बारे में चिंता करने की आवश्यकता नहीं है। जो आपकी देखभाल करता है।

युक्ति: macOS पर, आपको फ़ाइल मिल जाएगी /Users/[YOUR-USERNME]/.config/configstore/ginit.json। लिनक्स पर, यह अंदर है /home/[YOUR-USERNME]/.config/configstore/ginit.json.

GitHub एपीआई के साथ संचार

GitHub टोकन को संभालने के लिए एक लाइब्रेरी बनाएं। फ़ाइल बनाएँ lib/github.js और इसके अंदर निम्नलिखित कोड रखें:

const CLI = require('clui');
const Configstore = require('configstore');
const Octokit = require('@octokit/rest');
const Spinner = CLI.Spinner;
const { createBasicAuth } = require("@octokit/auth-basic"); const inquirer = require('./inquirer');
const pkg = require('../package.json'); const conf = new Configstore(pkg.name);

अब चलिए उस फंक्शन को जोड़ते हैं जो चेक करता है कि हमें पहले से ही एक्सेस टोकन मिल चुका है। हम एक ऐसा फंक्शन भी जोड़ेंगे, जो अन्य लिबास तक पहुंचने की अनुमति देता है octokit(गिटहब) कार्य:

let octokit; module.exports = { getInstance: () => { return octokit; }, getStoredGithubToken: () => { return conf.get('github.token'); },
};

एक तो conf वस्तु मौजूद है और उसके पास है github.token संपत्ति, इसका मतलब है कि भंडारण में पहले से ही एक टोकन है। इस स्थिति में, हम टोकन मान को वापस लौटाते हैं। हम बाद में उस पर पहुँचेंगे।

यदि कोई टोकन नहीं मिला है, तो हमें एक लाने की जरूरत है। बेशक, OAuth टोकन प्राप्त करने में एक नेटवर्क अनुरोध शामिल है, जिसका अर्थ है उपयोगकर्ता के लिए एक छोटा इंतजार। यह हमें देखने का अवसर देता है क्लुई पैकेज जो कंसोल-आधारित अनुप्रयोगों के लिए कुछ संवर्द्धन प्रदान करता है, उनमें से एक एनिमेटेड स्पिनर है।

स्पिनर बनाना आसान है:

const status = new Spinner('Authenticating you, please wait...');
status.start();

एक बार पूरा कर लेने के बाद, बस इसे रोक दें और यह स्क्रीन से गायब हो जाएगा:

status.stop();

युक्ति: आप कैप्शन को गतिशील रूप से उपयोग करके भी सेट कर सकते हैं update तरीका। यह उपयोगी हो सकता है यदि आपके पास प्रगति के कुछ संकेत हैं - उदाहरण के लिए, प्रतिशत को पूर्ण प्रदर्शित करना।

यहाँ GitHub के साथ प्रमाणित करने के लिए कोड है:

module.exports = { getInstance: () => { ... }, getStoredGithubToken: () => { ... }, getPersonalAccesToken: async () => { const credentials = await inquirer.askGithubCredentials(); const status = new Spinner('Authenticating you, please wait...'); status.start(); const auth = createBasicAuth({ username: credentials.username, password: credentials.password, async on2Fa() { // TBD }, token: { scopes: ['user', 'public_repo', 'repo', 'repo:status'], note: 'ginit, the command-line tool for initalizing Git repos' } }); try { const res = await auth(); if(res.token) { conf.set('github.token', res.token); return res.token; } else { throw new Error("GitHub token was not found in the response"); } } finally { status.stop(); } },
};

आइए इसके माध्यम से कदम बढ़ाएं:

  1. हम उपयोगकर्ता का उपयोग करके उनकी साख के लिए संकेत देते हैं askGithubCredentials विधि जिसे हमने पहले परिभाषित किया था।
  2. हम उपयोग क्रिएटबेसिकऑथ बनाने की विधि a auth फ़ंक्शन, जिसे हम अगले चरण में कॉल करेंगे। हम उपयोगकर्ता के उपयोगकर्ता नाम और पासवर्ड को इस विधि और साथ ही दो गुणों के साथ एक टोकन ऑब्जेक्ट पास करते हैं:
  3. हम तो await कॉल करने का परिणाम है auth एक के अंदर कार्य try ब्लॉक।
  4. यदि प्रमाणीकरण सफल है और प्रतिक्रिया में एक टोकन मौजूद है, तो हम इसे सेट करते हैं configstore अगली बार और टोकन वापस करने के लिए।
  5. यदि टोकन गायब है, या प्रमाणीकरण किसी भी कारण से सफल नहीं होता है, तो त्रुटि स्टैक पर बबल जाएगी ताकि हम इसे पकड़ सकें index.js। हम इस कार्यक्षमता को बाद में लागू करेंगे।

आप जो भी एक्सेस टोकन बनाते हैं, चाहे मैन्युअल रूप से या एपीआई के माध्यम से, जैसा कि हम यहां कर रहे हैं, आप कर पाएंगे उन्हें यहाँ देखें। विकास के दौरान, आप पा सकते हैं कि आपको जिनिट के पहुँच टोकन को हटाने की आवश्यकता है - द्वारा पहचाने जाने योग्य note ऊपर दिया गया पैरामीटर - ताकि आप इसे फिर से उत्पन्न कर सकें।

यदि आप साथ चल रहे हैं और हम अभी तक क्या करना चाहते हैं, तो आप अपडेट कर सकते हैं index.js के रूप में इस प्रकार है:

const github = require('./lib/github'); ... const run = async () => { let token = github.getStoredGithubToken(); if(!token) { token = await github.getPersonalAccesToken(); } console.log(token);
};

पहली बार जब आप इसे चलाते हैं, तो आपको अपने उपयोगकर्ता नाम और GitHub पासवर्ड के लिए संकेत दिया जाना चाहिए। तब एप्लिकेशन को GitHub पर एक व्यक्तिगत एक्सेस टोकन बनाना चाहिए और टोकन को सहेजना चाहिए configstore, सांत्वना में प्रवेश करने से पहले। हर बार जब आप उसके बाद ऐप चलाते हैं, तो ऐप टोकन को सीधे खींच देगा configstore और स्क्रीन पर लॉग इन करें।

दो-कारक प्रमाणीकरण के साथ काम करना

उम्मीद है आपने गौर किया होगा on2Fa ऊपर दिए गए कोड में विधि। यह तब कहा जाएगा जब किसी उपयोगकर्ता के पास उनके GitHub खाते पर दो-कारक प्रमाणीकरण सक्षम हो। चलो अब इसे भरें:

// inquirer.js const inquirer = require('inquirer'); module.exports = { askGithubCredentials: () => { ... }, getTwoFactorAuthenticationCode: () => { return inquirer.prompt({ name: 'twoFactorAuthenticationCode', type: 'input', message: 'Enter your two-factor authentication code:', validate: function(value) { if (value.length) { return true; } else { return 'Please enter your two-factor authentication code.'; } } }); },
};

हम कॉल कर सकते हैं getTwoFactorAuthenticationCode के भीतर से विधि on2Fa विधि, जैसे:

// github.js async on2Fa() { status.stop(); const res = await inquirer.getTwoFactorAuthenticationCode(); status.start(); return res.twoFactorAuthenticationCode;
},

और अब हमारा ऐप GitHub खातों को दो-कारक प्रमाणीकरण सक्षम कर सकता है।

रिपोजिटरी बनाना

एक बार जब हमें OAuth टोकन मिल जाता है, तो हम इसका उपयोग GitHub के साथ रिमोट रिपॉजिटरी बनाने के लिए कर सकते हैं।

फिर, हम प्रश्नों की एक श्रृंखला पूछने के लिए इन्क्वायरर का उपयोग कर सकते हैं। हमें रेपो के लिए एक नाम की आवश्यकता है, हम एक वैकल्पिक विवरण मांगेंगे, और हमें यह भी जानना होगा कि क्या यह सार्वजनिक या निजी होना चाहिए।

हम उपयोग करेंगे न्यूनतम वैकल्पिक कमांड-लाइन तर्कों से नाम और विवरण के लिए चूक को पकड़ना। उदाहरण के लिए:

ginit my-repo "just a test repository"

यह डिफ़ॉल्ट नाम को सेट करेगा my-repo और का वर्णन just a test repository.

निम्न पंक्ति एक अंडरस्कोर द्वारा अनुक्रमित सरणी में तर्कों को रखेगी:

const argv = require('minimist')(process.argv.slice(2));
// { _: [ 'my-repo', 'just a test repository' ] }

युक्ति: यह केवल न्यूनतम पैकेज की सतह को खरोंचता है। आप इसका उपयोग झंडे, स्विच और नाम / मूल्य जोड़े की व्याख्या करने के लिए भी कर सकते हैं। अधिक जानकारी के लिए दस्तावेज़ीकरण देखें।

हम कमांड-लाइन तर्कों को पार्स करने और प्रश्नों की एक श्रृंखला पूछने के लिए कोड लिखेंगे। सबसे पहले, अद्यतन lib/inquirer.js के रूप में इस प्रकार है:

const inquirer = require('inquirer');
const files = require('./files'); module.exports = { askGithubCredentials: () => { ... }, getTwoFactorAuthenticationCode: () => { ... }, askRepoDetails: () => { const argv = require('minimist')(process.argv.slice(2)); const questions = [ { type: 'input', name: 'name', message: 'Enter a name for the repository:', default: argv._[0] || files.getCurrentDirectoryBase(), validate: function( value ) { if (value.length) { return true; } else { return 'Please enter a name for the repository.'; } } }, { type: 'input', name: 'description', default: argv._[1] || null, message: 'Optionally enter a description of the repository:' }, { type: 'list', name: 'visibility', message: 'Public or private:', choices: [ 'public', 'private' ], default: 'public' } ]; return inquirer.prompt(questions); },
};

इसके बाद फाइल बनाएं lib/repo.js और इस कोड को जोड़ें:

const CLI = require('clui');
const fs = require('fs');
const git = require('simple-git/promise')();
const Spinner = CLI.Spinner;
const touch = require("touch");
const _ = require('lodash'); const inquirer = require('./inquirer');
const gh = require('./github'); module.exports = { createRemoteRepo: async () => { const github = gh.getInstance(); const answers = await inquirer.askRepoDetails(); const data = { name: answers.name, description: answers.description, private: (answers.visibility === 'private') }; const status = new Spinner('Creating remote repository...'); status.start(); try { const response = await github.repos.createForAuthenticatedUser(data); return response.data.ssh_url; } finally { status.stop(); } },
};

एक बार जब हमारे पास वह जानकारी हो जाती है, तो हम बस GitHub पैकेज का उपयोग कर सकते हैं रेपो बनाएं, जो हमें नए बनाए गए भंडार के लिए एक URL देगा। उसके बाद हम अपने स्थानीय Git रिपॉजिटरी में रिमोट के रूप में सेट कर सकते हैं। हालांकि, पहले, चलो अंतःक्रियात्मक रूप से एक बनाते हैं .gitignore फ़ाइल.

.Gitignore फ़ाइल बनाना

अगले चरण के लिए, हम जनरेट करने के लिए एक साधारण कमांड-लाइन "विज़ार्ड" बनाएंगे .gitignore फ़ाइल। यदि उपयोगकर्ता किसी मौजूदा प्रोजेक्ट डायरेक्टरी में हमारे एप्लिकेशन को चला रहा है, तो आइए उन्हें पहले से ही काम कर रहे डायरेक्टरी में मौजूद फाइलों और डायरेक्टरी की एक सूची दिखाएं, और उन्हें चुनें कि किन लोगों को अनदेखा करना है।

इन्क्वायरर पैकेज एक प्रदान करता है checkbox इनपुट प्रकार के लिए बस।

कार्रवाई में पूछताछकर्ता के चेक बॉक्स

पहली चीज़ जो हमें करने की ज़रूरत है वह वर्तमान निर्देशिका को अनदेखा करना है .git फ़ोल्डर और किसी भी मौजूदा .gitignore फ़ाइल (हम यह दर्ज करने का उपयोग करके करते हैं बिना तरीका):

const filelist = _.without(fs.readdirSync('.'), '.git', '.gitignore');

अगर जोड़ने के लिए कुछ भी नहीं है, तो जारी रखने का कोई मतलब नहीं है, तो चलो बस touch वर्तमान .gitignore फ़ाइल और समारोह से बाहर जमानत:

if (filelist.length) { ...
} else { touch('.gitignore');
}

अंत में, फाइल को सूचीबद्ध करने के लिए इंक्वायरर के चेकबॉक्स "विजेट" का उपयोग करें। निम्न कोड डालें lib/inquirer.js:

askIgnoreFiles: (filelist) => { const questions = [ { type: 'checkbox', name: 'ignore', message: 'Select the files and/or folders you wish to ignore:', choices: filelist, default: ['node_modules', 'bower_components'] } ]; return inquirer.prompt(questions);
},

ध्यान दें कि हम चूक की सूची भी प्रदान कर सकते हैं। इस मामले में, हम पूर्व-चयन कर रहे हैं node_modules और bower_components, वे मौजूद होना चाहिए।

जगह में Inquirer कोड के साथ, अब हम निर्माण कर सकते हैं createGitignore() समारोह। इस कोड को डालें lib/repo.js:

createGitignore: async () => { const filelist = _.without(fs.readdirSync('.'), '.git', '.gitignore'); if (filelist.length) { const answers = await inquirer.askIgnoreFiles(filelist); if (answers.ignore.length) { fs.writeFileSync( '.gitignore', answers.ignore.join( 'n' ) ); } else { touch( '.gitignore' ); } } else { touch('.gitignore'); }
},

एक बार “सबमिट” करने के बाद, हम फिर जनरेट करते हैं .gitignore फ़ाइलों की चयनित सूची में शामिल होकर, एक नई रेखा के साथ अलग हो गया। हमारा कार्य अब बहुत गारंटी देता है कि हमें ए .gitignore फ़ाइल, इसलिए हम एक गिट रिपॉजिटरी को शुरू करने के साथ आगे बढ़ सकते हैं।

एप्लिकेशन के भीतर से गिट के साथ बातचीत

गिट के साथ बातचीत करने के कई तरीके हैं, लेकिन शायद सबसे सरल उपयोग करना है सरल-Git पैकेज। यह चेनेबल तरीकों का एक सेट प्रदान करता है, जो पर्दे के पीछे, Git निष्पादन योग्य चलाते हैं।

ये दोहराए जाने वाले कार्य हैं जिनका उपयोग हम इसे स्वचालित करने के लिए करेंगे:

  1. रन git init
  2. जोड़ें .gitignore पट्टिका
  3. कार्यशील निर्देशिका की शेष सामग्री जोड़ें
  4. एक प्रारंभिक कमिटमेंट करें
  5. नए बनाए गए दूरस्थ रिपॉजिटरी को जोड़ें
  6. कार्यशील निर्देशिका को दूरस्थ तक धकेलें।

निम्न कोड डालें lib/repo.js:

setupRepo: async (url) => { const status = new Spinner('Initializing local repository and pushing to remote...'); status.start(); try { git.init() .then(git.add('.gitignore')) .then(git.add('./*')) .then(git.commit('Initial commit')) .then(git.addRemote('origin', url)) .then(git.push('origin', 'master')); } finally { status.stop(); }
},

यह सभी एक साथ लाना

सबसे पहले, एक सहायक फ़ंक्शन सेट करते हैं lib/github.js स्थापित करने के लिए oauth प्रमाणीकरण:

githubAuth: (token) => { octokit = new Octokit({ auth: token });
},

इसके बाद, हम एक फंक्शन बनाते हैं index.js टोकन प्राप्त करने के तर्क को संभालने के लिए। से पहले इस कोड को रखें run() समारोह:

const getGithubToken = async () => { // Fetch token from config store let token = github.getStoredGithubToken(); if(token) { return token; } // No token found, use credentials to access GitHub account token = await github.getPersonalAccesToken(); return token;
};

अंत में, हम अपडेट करते हैं run() कोड लिखकर कार्य करें जो ऐप के मुख्य तर्क को संभाल लेगा:

const repo = require('./lib/repo'); ... const run = async () => { try { // Retrieve & Set Authentication Token const token = await getGithubToken(); github.githubAuth(token); // Create remote repository const url = await repo.createRemoteRepo(); // Create .gitignore file await repo.createGitignore(); // Set up local repository and push to remote await repo.setupRepo(url); console.log(chalk.green('All done!')); } catch(err) { if (err) { switch (err.status) { case 401: console.log(chalk.red('Couldn't log you in. Please provide correct credentials/token.')); break; case 422: console.log(chalk.red('There is already a remote repository or token with the same name')); break; default: console.log(chalk.red(err)); } } }
};

जैसा कि आप देख सकते हैं, हम सुनिश्चित करते हैं कि उपयोगकर्ता हमारे सभी अन्य कार्यों को कॉल करने से पहले प्रमाणित हो (createRemoteRepo(), createGitignore(), setupRepo()) क्रमिक रूप से। कोड किसी भी त्रुटि को भी संभालता है और उपयोगकर्ता को उचित प्रतिक्रिया प्रदान करता है।

आप पूर्ण की जाँच कर सकते हैं index.js हमारे GitHub रेपो पर फ़ाइल।

इस बिंदु पर आपके पास एक काम करने वाला ऐप होना चाहिए। इसे आज़माएं और खुद को संतुष्ट करें कि यह उम्मीद के मुताबिक काम करता है।

विश्व स्तर पर गिनेट कमांड उपलब्ध कराना

एक शेष बात हमारे आदेश को विश्व स्तर पर उपलब्ध कराना है। ऐसा करने के लिए, हमें एक जोड़ने की आवश्यकता होगी कुटिया के शीर्ष पर लाइन index.js:

#!/usr/bin/env node

अगला, हमें एक जोड़ने की आवश्यकता है bin हमारे लिए संपत्ति package.json फ़ाइल। यह कमांड नाम को मैप करता है (ginit) निष्पादित करने के लिए फ़ाइल के नाम पर (के सापेक्ष) package.json):

"bin": { "ginit": "./index.js"
}

उसके बाद, मॉड्यूल को विश्व स्तर पर स्थापित करें और आपके पास एक कार्यशील शेल कमांड होगी:

npm install -g

टिप: यह विंडोज पर भी काम करेगा, जैसा कि npm आपकी स्क्रिप्ट के साथ-साथ एक cmd आवरण स्थापित करने में मदद करेगा.

यदि आप इंस्टॉल किए गए काम की पुष्टि करना चाहते हैं, तो आप इसका उपयोग करके अपने विश्व स्तर पर स्थापित नोड मॉड्यूल को सूचीबद्ध कर सकते हैं:

npm ls -g --depth=0

इसे और आगे ले जाना

Git रिपॉजिटरी को इनिशियलाइज़ करने के लिए हमे काफी निफ्टी, साधारण कमांड लाइन ऐप मिला है। लेकिन आगे इसे बढ़ाने के लिए आप बहुत कुछ कर सकते हैं।

यदि आप एक Bitbucket उपयोगकर्ता हैं, तो आप एक रिपॉजिटरी बनाने के लिए Bitbucket API का उपयोग करने के लिए प्रोग्राम को अनुकूलित कर सकते हैं। वहां एक Node.js एपीआई रैपर उपलब्ध है आरंभ करने में आपकी सहायता करने के लिए। आप एक अतिरिक्त कमांड-लाइन विकल्प जोड़ना चाहते हैं या उपयोगकर्ता से पूछ सकते हैं कि क्या वे GitHub या Bitbucket का उपयोग करना चाहते हैं (Inquirer सिर्फ उसी के लिए एकदम सही होगा) या GitHub-विशिष्ट कोड को Bitbucket विकल्प के साथ बदलें।

आप अपने लिए डिफॉल्ट का अपना सेट निर्दिष्ट करने की सुविधा भी प्रदान कर सकते हैं .gitgnore फ़ाइल, एक हार्डकोड सूची के बजाय। वरीयताओं का पैकेज यहां उपयुक्त हो सकता है, या आप "टेम्पलेट" का एक सेट प्रदान कर सकते हैं - शायद परियोजना के प्रकार के लिए उपयोगकर्ता को संकेत दे। आप इसे के साथ एकीकृत करने पर भी विचार कर सकते हैं .itignignore.io कमांड लाइन टूल / एपीआई।

इन सब से परे, आप अतिरिक्त सत्यापन जोड़ना चाह सकते हैं, कुछ वर्गों को छोड़ देने की क्षमता प्रदान कर सकते हैं, और बहुत कुछ।

स्रोत: https://www.sitepoint.com/javascript-command-line-interface-cli-node-js/?utm_source=rss

स्पॉट_आईएमजी

नवीनतम खुफिया

स्पॉट_आईएमजी