requirement.txt बनाम setup.py


111

मैंने पायथन के साथ काम करना शुरू कर दिया। मैंने जोड़ा है requirements.txtऔर setup.pyअपनी परियोजना के लिए। लेकिन, मैं अभी भी दोनों फाइलों के उद्देश्य को लेकर उलझन में हूं। मैंने पढ़ा है कि setup.pyयह पुनर्वितरण योग्य चीजों के लिए बनाया गया है और यह requirements.txtगैर-पुनर्वितरण योग्य चीजों के लिए बनाया गया है। लेकिन मुझे यकीन नहीं है कि यह सही है।

कैसे उन दो फ़ाइलों का सही मायने में उपयोग करने का इरादा है?


1
क्या आपने अपने सटीक शीर्षक का उपयोग करके वेब खोजा है? यह लेख (जब मैंने खोजा तो पहली हिट) सबसे अच्छा विषय पर मैंने पढ़ा है।
क्रिस

2
यह लेख उपयोगी हो सकता है: caremad.io/posts/2013/07/setup-vs-requirement (क्षमा करें, एक उचित उत्तर में आवश्यक निकालने के लिए बहुत आलसी)। एक और बात है, कुछ उपकरण (उदाहरण के लिए परीक्षण) में एक या दूसरे के प्रति उनके पूर्वाग्रह हो सकते हैं - लेकिन अगर आपने अभी-अभी पायथन पर काम करना शुरू किया है, तो इसे परेशान न होने दें।
शराबी

जवाबों:


83

requirements.txt

यह आपको अपने विकास के वातावरण को स्थापित करने में मदद करता है। प्रोग्राम की तरह pipएक झपट्टा में फ़ाइल में सूचीबद्ध सभी संकुल को स्थापित करने के लिए इस्तेमाल किया जा सकता है। उसके बाद आप अपनी अजगर लिपि को विकसित करना शुरू कर सकते हैं। विशेष रूप से उपयोगी है यदि आप दूसरों को विकास या आभासी वातावरण का उपयोग करने की योजना बनाते हैं। आप इसका उपयोग कैसे करते हैं:

pip install -r requirements.txt

setup.py

यह आपको संकुल बनाने की अनुमति देता है जिसे आप पुनर्वितरित कर सकते हैं। यह स्क्रिप्ट अंत उपयोगकर्ता के सिस्टम पर आपके पैकेज को स्थापित करने के लिए है, न कि विकास के माहौल को तैयार करने के लिए pip install -r requirements.txt। Setup.py पर अधिक जानकारी के लिए यह उत्तर देखें ।

आपके प्रोजेक्ट की निर्भरताएँ दोनों फ़ाइलों में सूचीबद्ध हैं।


2
किन मामलों में मैं उनमें से केवल एक होगा? किस में मैं दोनों होगा?
मार्टिन थॉमा

27
एर्म ... आप अपने स्थानीय मशीन पर मज़े के लिए सिर्फ स्क्रिप्ट: न तो। स्क्रिप्ट को कई मशीनों / vitualenvs पर विकसित किया गया है लेकिन पुनर्वितरित नहीं किया गया है: आवश्यकताएँ। स्क्रिप्ट केवल आपकी मशीन पर विकसित की जाती है, लेकिन इसे पुनर्वितरित किया जाना चाहिए: setup.py स्क्रिप्ट को कई वातावरणों में पुनर्वितरित और विकसित किया जाएगा: दोनों।
एंड्रियास

क्या आप इसे उत्तर में जोड़ सकते हैं?
मार्टिन थोमा

58

संक्षिप्त उत्तर यह है कि requirements.txtकेवल पैकेज आवश्यकताओं को सूचीबद्ध करने के लिए है। setup.pyदूसरी ओर एक स्थापना स्क्रिप्ट की तरह अधिक है। यदि आप अजगर कोड को स्थापित करने की योजना नहीं बनाते हैं, तो आमतौर पर आपको केवल आवश्यकता होगीrequirements.txt

फ़ाइल का setup.pyवर्णन करता है, पैकेज निर्भरता के अलावा, फ़ाइलों और मॉड्यूल का सेट जिसे पैक किया जाना चाहिए (या मूल मॉड्यूल के मामले में संकलित किया जाता है (यानी, सी में लिखा है), और मेटाडेटा को अजगर पैकेज लिस्टिंग में जोड़ना होगा जैसे पैकेज का नाम, पैकेज संस्करण, पैकेज विवरण, लेखक, ...)।

क्योंकि दोनों फाइलें निर्भरता को सूचीबद्ध करती हैं, इससे कुछ दोहराव हो सकता है। जानकारी के लिए नीचे पढ़ें।

requirements.txt


यह फ़ाइल अजगर पैकेज आवश्यकताओं को सूचीबद्ध करती है। यह एक सादा पाठ फ़ाइल है (वैकल्पिक रूप से टिप्पणियों के साथ) जो आपके अजगर परियोजना (प्रति पंक्ति एक) की पैकेज निर्भरता को सूचीबद्ध करती है । यह आपके अजगर पैकेज स्थापित करने के तरीके का वर्णन नहीं करता है। आप आम तौर पर आवश्यकताओं फ़ाइल के साथ उपभोग करेंगेpip install -r requirements.txt

पाठ फ़ाइल का फ़ाइल नाम मनमाना है, लेकिन अक्सर requirements.txtसम्मेलन द्वारा होता है। अन्य पायथन पैकेजों के स्रोत कोड रिपोजिटरी की खोज करते समय, आप अन्य नामों पर ठोकर खा सकते हैं, जैसे कि dev-dependencies.txtया dependencies-dev.txt। वे एक ही उद्देश्य के रूप में सेवा करते हैं, dependencies.txtलेकिन आम तौर पर विशेष पैकेज के डेवलपर्स के लिए ब्याज की अतिरिक्त निर्भरता को सूचीबद्ध करते हैं, अर्थात् रिलीज से पहले स्रोत कोड (जैसे pytest, pylint, आदि) के परीक्षण के लिए। पैकेज के उपयोगकर्ताओं को आमतौर पर पैकेज चलाने के लिए डेवलपर निर्भरता के पूरे सेट की आवश्यकता नहीं होती है।

यदि कई requirements-X.txtवेरिएंट मौजूद हैं, तो आमतौर पर एक रनटाइम निर्भरता, और अन्य बिल्ड-टाइम या टेस्ट निर्भरता को सूचीबद्ध करेगा। कुछ परियोजनाएं अपनी आवश्यकताओं की फ़ाइल को भी कैस्केड करती हैं, अर्थात जब एक आवश्यकता फ़ाइल में दूसरी फ़ाइल ( उदाहरण ) शामिल होती है। ऐसा करने से पुनरावृत्ति को कम किया जा सकता है।

setup.py


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

जब एक अजगर उपयोगकर्ता करता है pip install ./pkgdir_my_module(या pip install my-module), setup.pyदी गई निर्देशिका (या मॉड्यूल) में पाइप चलेगा । इसी तरह, किसी भी मॉड्यूल को एक ही फ़ोल्डर से चलाकर, इंस्टाल setup.pyकिया जा सकता है pip, जैसे pip install .

क्या मुझे वास्तव में दोनों की आवश्यकता है?


संक्षिप्त उत्तर नहीं है, लेकिन दोनों के लिए अच्छा है। वे विभिन्न उद्देश्यों को प्राप्त करते हैं, लेकिन इन दोनों का उपयोग आपकी निर्भरता को सूचीबद्ध करने के लिए किया जा सकता है।

वहाँ एक चाल आप के बीच निर्भरता की अपनी सूची को डुप्लिकेट से बचने के लिए विचार कर सकते हैं है requirements.txtऔर setup.py। यदि आपने setup.pyअपने पैकेज के लिए पहले से ही पूरी तरह से काम कर लिखा है , और आपकी निर्भरताएं ज्यादातर बाहरी हैं, तो आप requirements.txtकेवल निम्नलिखित के साथ एक साधारण विचार कर सकते हैं :

 # requirements.txt
 #
 # installs dependencies from ./setup.py, and the package itself,
 # in editable mode
 -e .

 # (the -e above is optional). you could also just install the package
 # normally with just the line below (after uncommenting)
 # .

-eएक विशेष है pip installविकल्प है, जिसमें दिए गए पैकेज को स्थापित करता है संपादन योग्य मोड। जब pip -r requirements.txtइस फ़ाइल पर चलाया जाता है, तो पाइप सूची के माध्यम से आपकी निर्भरता को स्थापित करेगा ./setup.py। संपादन योग्य विकल्प आपकी इंस्टॉल डायरेक्टरी (अंडे या आर्काइव्ड कॉपी के बजाय) में एक सिमलिंक लगाएगा। यह डेवलपर्स को पुन: स्थापित किए बिना रिपॉजिटरी से कोड को संपादित करने की अनुमति देता है।

जब आप अपने पैकेज रिपॉजिटरी में दोनों फाइल रखते हैं, तो आप "सेटप्टूल एक्स्ट्रा" भी कह सकते हैं। आप एक कस्टम श्रेणी के तहत setup.py में वैकल्पिक पैकेज को परिभाषित कर सकते हैं, और उन पैकेजों को पाइप के साथ बस उस श्रेणी से स्थापित कर सकते हैं:

# setup.py
from setuptools import setup
setup(
   name="FOO"
   ...
   extras_require = {
       'dev': ['pylint'],
       'build': ['requests']
   }
   ...
)

और फिर, आवश्यकताओं फ़ाइल में:

# install packages in the [build] category, from setup.py
# (path/to/mypkg is the directory where setup.py is)
-e path/to/mypkg[build]

यह आपके सभी निर्भरता सूचियों को setup.py के अंदर रखेगा।

नोट : आप आम तौर पर सैंडबॉक्स से पाइप और setup.py को निष्पादित करेंगे, जैसे कि प्रोग्राम के साथ बनाए गए virtualenv। यह आपकी परियोजना के विकास के वातावरण के संदर्भ में अजगर पैकेज स्थापित करने से बचाएगा।


7
और आप अंदर सिर्फ .w / o भी कर सकते हैं । यह विधि सिर्फ सभी आवश्यकताओं को दर्शाती है और आपको किसी को भी संपादन योग्य मोड में लाने की आवश्यकता नहीं है। यूजर्स चाहें तो फिर भी कर सकते हैं। -erequirements.txtsetup.pypip install -e .
स्टैस्टन

1
के साथ दिलचस्प चाल "-ई।" आवश्यकताएँ.txt में, लेकिन क्या यह आवश्यकताओं के उद्देश्य को नहीं हराता है। उस मामले में भी एक क्यों है?
बेन ओगोरक

आपके पास सेटअप सिस्टम के अंदर सटीक सिस्टम आवश्यकताएँ हो सकती हैं। होने "" आवश्यकताएँ में। यह मौजूदा फ़ोल्डर में setup.py का उपयोग करता है। उपयोग -e .निर्भरता खोजने के लिए setup.py का उपयोग करता है, लेकिन पाइप स्थापित फ़ोल्डर में वर्तमान फ़ोल्डर (जगह में, एक सिमलिंक के साथ) लिंक करता है, कॉपी लेने के बजाय - आप -eपैकेज का विकास कर रहे हैं, तो आप आम तौर पर उपयोग करेंगे । साथ -e, अपने अजगर पैकेज फ़ाइलों में परिवर्तन (* .py) प्रभाव तुरंत अपने पिप वातावरण में नहीं बल्कि प्रत्येक परिवर्तन के बाद पैकेज फिर से स्थापित बल के लिए होने से लेते हैं, करेंगे।
init_js

@init_js आवश्यकताओं फ़ाइल या CWD के सापेक्ष "वर्तमान फ़ोल्डर" है जिसमें से पाइप कहा जाता है? Ie अगर आप ऐसा करते हैं तो cd foo && pip install -r ./bar/requirements.txtयह setup.py foo/barया में खोज करेगा foo? यदि उत्तरार्द्ध है, तो क्या पूर्व को प्राप्त करने का एक तरीका है?
डैन एम।

pip -r REQREQ है जिसमें निर्देशिका के बारे में परवाह नहीं है। आप फीफो भले ही आप चाहते हैं एक से फ़ीड कर सकते हैं: pip install -r <(echo "mylib1"; echo "mylib2";)। जहां <(CMD)बैश कमांड प्रतिस्थापन है, स्टड पुनर्निर्देशन नहीं।
init_js

12

पूर्णता की खातिर, यहां मैं इसे 3 4 अलग-अलग कोणों में देखता हूं ।

  1. उनके डिजाइन उद्देश्य अलग हैं

यह आधिकारिक प्रलेखन (जोर मेरा) से उद्धृत सटीक विवरण है :

जबकि install_requires (setup.py में) किसी एक परियोजना के लिए निर्भरता को परिभाषित करता है, आवश्यकताओं को पूर्ण पायथन वातावरण के लिए आवश्यकताओं को परिभाषित करने के लिए अक्सर फ़ाइलों का उपयोग किया जाता है

जबकि install_requires आवश्यकताएं न्यूनतम हैं, आवश्यकताओं की फ़ाइलों में अक्सर एक पूर्ण वातावरण के दोहराए जाने वाले प्रतिष्ठानों को प्राप्त करने के उद्देश्य से पिन किए गए संस्करणों की एक विस्तृत सूची होती है।

लेकिन इसे समझना अब भी आसान नहीं होगा, इसलिए अगले भाग में, 2 तथ्यात्मक उदाहरणों को प्रदर्शित करना है कि कैसे 2 दृष्टिकोणों का उपयोग किया जाना चाहिए, अलग तरीके से।

  1. इसलिए उनका वास्तविक उपयोग अलग-अलग है

    • यदि आपकी परियोजना fooएक स्टैंडअलोन लाइब्रेरी के रूप में जारी होने वाली है (मतलब, अन्य शायद करेंगे import foo), तो आप (और आपके डाउनस्ट्रीम उपयोगकर्ता) निर्भरता की एक लचीली घोषणा करना चाहेंगे, ताकि आपकी लाइब्रेरी (और यह नहीं होनी चाहिए) ) "picky" हो जो आपकी निर्भरता का सटीक संस्करण होना चाहिए। इसलिए, आम तौर पर, आपके setup.py में इस तरह की लाइनें होंगी:

      install_requires=[
          'A>=1,<2',
          'B>=2'
      ]
    • यदि आप किसी भी तरह से अपने दस्तावेज़ के लिए "दस्तावेज़" या "पिन" अपने वर्तमान वातावरण को "पिन" barकरना चाहते हैं, तो इसका अर्थ है कि आप या आपके उपयोगकर्ता आपके आवेदन का उपयोग करना चाहते हैं bar, जैसे कि, चल रहा है python bar.py, आप अपने वातावरण को फ्रीज करना चाहते हैं ताकि यह हमेशा वैसा ही व्यवहार करेगा। ऐसे मामले में, आपकी आवश्यकताओं की फाइल इस तरह दिखाई देगी:

      A==1.2.3
      B==2.3.4
      # It could even contain some dependencies NOT strickly required by your library
      pylint==3.4.5
  2. वास्तव में, मैं किसका उपयोग करता हूं?

    • यदि आप एक एप्लिकेशन विकसित कर रहे हैं , barजिसका उपयोग किया जाएगा python bar.py, भले ही वह "मज़े के लिए स्क्रिप्ट" हो, फिर भी आपको आवश्यकताओं का उपयोग करने की अनुशंसा की जाती है। क्योंकि, कौन जानता है, अगले सप्ताह (जो क्रिसमस होता है) एक उपहार के रूप में नया कंप्यूटर, इसलिए आपको फिर से अपना सटीक वातावरण सेट करना होगा।

    • यदि आप एक पुस्तकालय विकसित कर रहे हैं , fooजिसका उपयोग किया जाएगा import foo, तो आपको एक सेटअप-बैंक तैयार करना होगा। अवधि। लेकिन आप अभी भी एक ही समय में एक आवश्यकताएँ प्रदान कर सकते हैं।

      (ए) या तो A==1.2.3शैली में हो (जैसा कि ऊपर # 2 में समझाया गया है);

      (बी) या सिर्फ एक जादुई एकल होते हैं .

      .

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

  3. विभिन्न निचले सीमा।

    इसके बाद भी जब आपने उपरोक्त 3 मानदंडों का पालन किया है और सही ढंग से निर्णय लिया है कि आपकी लाइब्रेरी अपनी निर्भरता की घोषणा करने के hybrid-engineलिए एक setup.pyका उपयोग करेगी engine>=1.2.0, और आपका नमूना आवेदन अपनी निर्भरता को घोषित करने के लिए reliable-carउपयोग करेगा , भले ही नवीनतम संस्करण 1.4.0 पर हो। जैसा कि आप देखते हैं, उनकी निचली बाउंड संख्या के लिए आपकी पसंद अभी भी अलग-अलग है। और यहाँ क्यों है।requirements.txtengine>=1.2.3engine

    • hybrid-engineइस पर निर्भर करता है engine>=1.2.0कि, काल्पनिक रूप से, आवश्यक "आंतरिक दहन" क्षमता को पहली बार पेश किया गया था engine 1.2.0, और उस क्षमता की आवश्यकता है hybrid-engine, चाहे इस तरह के संस्करण के अंदर कुछ (मामूली) बग हो सकते हैं और बाद के संस्करणों में तय किए गए 1.2.1 , 1.2.2, और 1.2.3।

    • reliable-carइस बात पर निर्भर करता है engine>=1.2.3कि अब तक ज्ञात मुद्दों के बिना यह सबसे पुराना संस्करण है। सुनिश्चित करें कि बाद के संस्करणों में नई क्षमताएं हैं, कहते हैं, "इलेक्ट्रिक मोटर" में पेश किया गया है engine 1.3.0, और "परमाणु रिएक्टर" में पेश किया गया है engine 1.4.0, लेकिन वे परियोजना के लिए आवश्यक नहीं हैं reliable-car


"आपकी लाइब्रेरी (आपकी निर्भरता का सटीक संस्करण क्या होना चाहिए, इस बारे में 'picky' नहीं होगा)।" क्या आप इस बिंदु पर थोड़ा विस्तार कर सकते हैं? मुझे लगता है कि आपके कोड का आमतौर पर केवल विशिष्ट संस्करणों पर निर्भरता के साथ परीक्षण किया जाता है, और यह दृष्टिकोण थोड़ा खतरनाक हो सकता है। मुझे लगता है कि एक पुस्तकालय को कई प्रकार के संस्करणों के साथ काम करना चाहिए क्योंकि आप निर्भरता के कई संस्करण स्थापित नहीं करना चाहते हैं? डिस्क स्थान बचाने के लिए?
तारो किरीटनी

@TaroKiritani वास्तव में मैंने 2 अलग-अलग परिदृश्यों को साइड-बाय-साइड, लाइब्रेरी केस और एप्लिकेशन केस में सूचीबद्ध किया है। शायद आपने पहले एक पुस्तकालय पर काम नहीं किया था? एक पुस्तकालय के रूप में, यह डाउनस्ट्रीम पैकेज द्वारा खपत होने की उम्मीद है। इसलिए यदि आप अपनी निर्भरता को चुस्त करने के लिए योग्य हैं A==1.2.3, और फिर यदि आपकी लाइब्रेरी का डाउनस्ट्रीम पैकेज निर्भर करता है A==1.2.4, तो अब दोनों को संतुष्ट करने का कोई तरीका नहीं होगा। इस संघर्ष को कम करने का उपाय यह है कि आपकी लाइब्रेरी एक ऐसी सीमा को परिभाषित करे जो आपको पता हो कि वह काम करेगी। कई upstream पुस्तकालय पहले से ही semver.org निम्नानुसार , A>=1,<2काम करेगा मान लिया ।
रायलूओ

मुझे महसूस नहीं हुआ कि किसी एक वातावरण में पैकेज के केवल एक संस्करण को स्थापित किया जा सकता है। stackoverflow.com/a/6572017/5686692 स्पष्टीकरण के लिए धन्यवाद।
तारो किरीटानी

1
@TaroKiritani, हाँ, अन्यथा आपके एप्लिकेशन द्वारा पता का कौन सा संस्करण होगा fooकरता है import fooआप दे? उस हैक किए गए उत्तर को आपने जो लिंक प्रदान किया है, वह इस बात का एक आदर्श उदाहरण है कि पैकेज मेंटेनर को "पिकी नहीं होना चाहिए और क्यों नहीं" होना चाहिए। :-) अब मेरे पास आपका उत्थान हो सकता है?
रायलूओ जूल

1
मैं उस नए विचार पर भी टिप्पणी कर सकता था, लेकिन फिर यह टिप्पणी अनुभाग पहले से ही विषय से हटकर है और नए साथियों के लिए चलना मुश्किल है। मैं आपको एक नया प्रश्न पूछना चाहता हूं "क्या हम अपनी लाइब्रेरी को निर्भरता के विभिन्न संयोजनों पर काम करने की गारंटी देने के लिए विषाक्त या कुछ का उपयोग करते हैं", और फिर लोग झंकार कर सकते हैं।
रायलूओ
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.