जब php में बुराई बुराई है?


84

सभी वर्षों में मैं php में विकास कर रहा हूं, मैंने हमेशा सुना है कि उपयोग eval()करना बुराई है।

निम्नलिखित कोड को ध्यान में रखते हुए, क्या यह दूसरा (और अधिक सुरुचिपूर्ण) विकल्प का उपयोग करने के लिए समझ में नहीं आएगा? यदि नहीं, तो क्यों?

// $type is the result of an SQL statement
// e.g. SHOW COLUMNS FROM a_table LIKE 'a_column';
// hence you can be pretty sure about the consistency
// of your string
$type = "enum('a','b','c')";

// possibility one
$type_1 = preg_replace('#^enum\s*\(\s*\'|\'\s*\)\s*$#', '', $type);
$result = preg_split('#\'\s*,\s*\'#', $type_1);

// possibility two
eval('$result = '.preg_replace('#^enum#','array', $type).';');

2
eval बुरी तरह से है, हमेशा कोड लिखने का एक बेहतर तरीका है, क्योंकि PHP ने गुमनाम कार्यों को प्रस्तुत किया है। इस उदाहरण में मैं इस्तेमाल करूंगा$result = array(); preg_replace_callback('#^enum\s*\(\s*\'|\'\s*\)\s*$#', function($m) use($result) { $result[] = $m[1]; }, $type);
ज्योफ्री

खैर, ईमानदारी से, मुझे लगता है कि php के साथ मुख्य समस्या भाषा ही नहीं बल्कि लोग हैं, जो इसका उपयोग करते हैं। इस सवाल के तीन सही उत्तर (thomasrutter's, braincracking's और me) सभी को बिना किसी के खिलाफ एक बिंदु के मिला। दूसरी ओर एक उत्तर में दावा किया गया है कि "कभी-कभी eval (केवल एकमात्र / सही समाधान है) उदाहरण या स्पष्टीकरण के बिना और इसके लिए शीर्ष-मतदान हो जाता है ...
फ्रेंकोइस बुर्जुआ

जवाबों:


133

मैं eval () को शुद्ध बुराई कहने में सतर्क रहूंगा। गतिशील मूल्यांकन एक शक्तिशाली उपकरण है और कभी-कभी एक जीवन रक्षक हो सकता है। Eval () के साथ व्यक्ति PHP की कमियों के आसपास काम कर सकता है (नीचे देखें)।

Eval () के साथ मुख्य समस्याएं हैं:

  • संभावित असुरक्षित इनपुट। एक अविश्वसनीय पैरामीटर पास करना असफल होने का एक तरीका है। यह सुनिश्चित करने के लिए अक्सर एक तुच्छ कार्य नहीं है कि एक पैरामीटर (या इसका हिस्सा) पूरी तरह से विश्वसनीय है।
  • Trickiness। Eval () का उपयोग कोड को चतुर बनाता है, इसलिए इसका पालन करना अधिक कठिन है। ब्रायन कर्निघन को उद्धृत करने के लिए " डिबगिंग पहली जगह में कोड लिखने के रूप में दोगुना कठिन है। इसलिए, यदि आप कोड को जितना संभव हो सके उतना चतुराई से लिखते हैं, तो आप परिभाषा के अनुसार, इसे डिबग करने के लिए पर्याप्त स्मार्ट नहीं हैं "

Eval () के वास्तविक उपयोग के साथ मुख्य समस्या केवल एक है:

  • अनुभवहीन डेवलपर्स जो इसे पर्याप्त विचार के बिना उपयोग करते हैं।

अंगूठे के एक नियम के रूप में मैं इसका पालन करता हूं:

  1. कभी-कभी eval () एकमात्र / सही समाधान होता है।
  2. अधिकांश मामलों के लिए व्यक्ति को कुछ और प्रयास करना चाहिए।
  3. यदि अनिश्चित है, तो गोटो 2।
  4. वरना, बहुत, बहुत सावधान रहना होगा।

4
यह eval () से बचने के लिए भी रिफैक्ट किया जा सकता है, खासकर अगर $ className को सफेद किया जाता है, जो कि eval () के उपयोग का मनोरंजन करने के लिए होना चाहिए। हालांकि अच्छी खबर यह है कि 5.3 के रूप में $ f :: बार () मान्य है।
रोजा

@rojoca: क्या आप हमें उदाहरण दे सकते हैं कि PHP 5.2 में कृपया इसे eval () के बिना कैसे करें?
मिचेल रुडिकि

30
मुझे यकीन नहीं है कि यह स्पष्ट या नहीं के रूप में गिना जाता है, लेकिन $ परिणाम = call_user_func (सरणी ('फू', 'बार')); एक जादू की तरह काम करता है।
आयनू जी। स्टेन

3
चालबाजी के बारे में अच्छी बात - आपके (सरल) उदाहरण में, एक चर "कहीं से भी नहीं" निकलता है। यदि कोड को बस थोड़ा और अधिक जटिल हो जाता है, तो अगले व्यक्ति को शुभकामनाएं जो कोड को देखता है और उस चर को नीचे गिराने की कोशिश करता है (वहां किया गया, ऐसा किया गया, जो मुझे मिला वह सब सिरदर्द और यह घटिया टी-शर्ट था)।
पिस्कोर ने

असुरक्षित इनपुट से बचा जा सकता है
12-12

40

eval बुराई है जब केवल थोड़ी सी संभावना है कि मूल्यांकन किए गए स्ट्रिंग में userinput शामिल है। जब आप एक उपयोगकर्ता से आए बिना सामग्री का उपयोग करते हैं, तो आपको सुरक्षित होना चाहिए।

फिर भी आप को कम से कम दो बार विचार करना चाहिए eval का उपयोग करने से पहले, यह भ्रामक रूप से सरल दिखता है, लेकिन त्रुटि से निपटने (VBAssassins टिप्पणी देखें), डीबगैबिलिटी आदि को ध्यान में रखते हुए, यह इतना सरल नहीं है।

तो अंगूठे के एक नियम के रूप में: इसके बारे में भूल जाओ। जब eval जवाब है तो आप गलत सवाल पूछ रहे हैं! ;-)


6
कभी-कभी eval जवाब है। हम ऑनलाइन-गेम एप्लिकेशन पर काम करते हैं और संस्थाओं के बीच बहुत ही जटिल संबंधों के कारण वहां से बचने के लिए बहुत कठिन है ... लेकिन 90% मामलों में आईएमएचओ का जवाब नहीं है।
जेट

19
मैं वास्तव में एक ऐसी स्थिति को देखने के लिए उत्सुक होऊंगा, जहां केवल एक ही उत्तर हो।
इयोनू जी। स्टेन

2
@Ionut G. स्टेन डेटाबेस-संग्रहित कस्टम ट्रिगर्स ऑब्जेक्ट्स / संस्थाओं के लिए?
कुरोकी काज

8
मैं वास्तव में नहीं खरीदता है कि उनमें से कोई भी eval () के उचित उपयोग हैं। प्रत्येक मामले में, eval () का उपयोग किए बिना एक ही काम करना अभी भी कम से कम संभव है। यह ऐसा नहीं है कि PHP eval () के बिना अपंग है। दी गई, निष्कासन () इन जैसे मामलों में एक शॉर्टकट है, लेकिन यह अभी भी आपके कोड का मार्ग बनाता है, जिसका पालन करना थोड़ा कठिन है और समस्याओं को कम करना मुश्किल है। ऐसी मेरी राय है।
थोमसट्रेटर

4
@ क्रिसियन: आपको पहले एक उदाहरण लिखना चाहिए ( pastebin.com का उपयोग करें , और यहां लिंक पेस्ट करें), जहां आपको लगता है कि उपयोग से बचना eval()असंभव है, यह एक बेहतर दृष्टिकोण है। बहुत से लोग कहते हैं कि eval()कुछ मामलों में यह अपरिहार्य है, लेकिन वे किसी भी विशिष्ट उदाहरण का उल्लेख नहीं करते हैं, जिस पर हम बहस कर सकते हैं - इस तरह इस बहस का कोई मतलब नहीं है। तो कृपया, जो लोग कहते हैं eval()कि अपरिहार्य है, पहले इसे साबित करें!
Sk8erPeter

18

eval () हर समय समान रूप से बुराई है।

"जब eval () बुराई नहीं है?" मेरी राय में पूछने के लिए गलत सवाल है, क्योंकि यह स्पष्ट रूप से लगता है कि eval () का उपयोग करने के लिए कमियां कुछ संदर्भों में जादुई रूप से गायब हो जाती हैं।

Eval () का उपयोग करना आम तौर पर एक बुरा विचार है क्योंकि इससे कोड की पठनीयता कम हो जाती है, रनटाइम से पहले आपके लिए कोड पथ (और उस के संभावित सुरक्षा निहितार्थ) की भविष्यवाणी करने की क्षमता, और इसलिए कोड डिबग करने की क्षमता। Eval () का उपयोग करके मूल्यांकन किए गए कोड और उसके आसपास के कोड को भी opcode कैश द्वारा अनुकूलित किया जा सकता है जैसे कि Zend Opcache PHP 5.5 और इसके बाद के संस्करण में, या HHVM में एक जैसे JIT कंपाइलर द्वारा एकीकृत।

इसके अलावा, ऐसी कोई स्थिति नहीं है जिसके लिए eval () का उपयोग करना बिल्कुल आवश्यक है - PHP इसके बिना पूरी तरह से सक्षम प्रोग्रामिंग भाषा है।

आप वास्तव में इन्हें बुराइयों के रूप में देखते हैं या नहीं या आप कुछ मामलों में व्यक्तिगत रूप से eval () का उपयोग करना उचित ठहरा सकते हैं। कुछ के लिए, बुराइयाँ कभी भी इसे सही ठहराने के लिए बहुत बढ़िया हैं, और दूसरों के लिए, eval () एक आसान शॉर्टकट है।

हालांकि, यदि आप बुराई () को बुराई के रूप में देखते हैं, तो यह हर समय बुराई है। यह संदर्भ के आधार पर जादुई रूप से अपनी बुराई नहीं खोता है।


1
आप एक प्रोग्रामर का नरक बनाते हैं।
क्रिश्चियन

1
"इसके अलावा, ऐसी कोई स्थिति नहीं है जिसके लिए eval () का उपयोग करना बिल्कुल आवश्यक है" - क्या होगा यदि मैं एक डेटाबेस में संग्रहीत कोड को निष्पादित करना चाहता हूं, उदाहरण के लिए PHP डॉक्स में दिए गए उदाहरण के अनुसार?
यारिन

4
उसके लिए मैं कहूंगा कि डेटाबेस में PHP कोड को संग्रहीत करना उतना ही बुरा है, और उतना ही अनावश्यक है। आप जो कुछ भी हासिल करना चाहते हैं, उसे डेटाबेस में PHP स्टोर करने या eval () का उपयोग करने की तुलना में करने के अन्य तरीके हैं। अगर आपको यह पसंद है, और यदि यह आपके लिए एक उपयोगी शॉर्टकट है, तो करें, लेकिन यदि आप ईवैल () को बुराई मानते हैं, तो शायद आपको डेटाबेस में PHP को बुराई के रूप में संग्रहीत करने का इलाज करना होगा।
थोमसट्रेटर

12
यह एक और हमला वेक्टर जोड़ता है - एक SQL इंजेक्शन फिर वेब सर्वर पर मनमाना PHP कोड चला सकता है। इसके लिए eval () का उपयोग आवश्यक है। यह बायोटेक कैश द्वारा अनुकूलित नहीं किया जा सकता है। यह आपके कोड और डेटा को अलग करने के सिद्धांत का उल्लंघन करता है। यह आपके एप्लिकेशन को कम पोर्टेबल बना सकता है - पीएचपी को अपडेट / फिक्स करने के लिए आपको डेटाबेस को भी अपडेट करना होगा।
१२:११

3
मैं यह कहूंगा कि यदि कुछ केवल निष्कासन के उपयोग के माध्यम से प्राप्त किया जा सकता है, तो ऐसा कुछ करने पर पुनर्विचार करना अच्छा हो सकता है। गतिशील रूप से रनटाइम पर कक्षाएं बनाना एक बुरे विचार की तरह लगता है। कुछ कोड पीढ़ी को रोजगार क्यों नहीं दिया और उस कोड को उत्पन्न करें जो उन्हें समय से पहले परिभाषित करता है?
थोमसट्रेटर

15

इस मामले में, eval शायद पर्याप्त रूप से सुरक्षित है, जब तक कि उपयोगकर्ता द्वारा तालिका में बनाए जाने वाले मनमाने स्तंभों के लिए यह संभव नहीं है।

यह वास्तव में किसी भी अधिक सुंदर नहीं है, हालांकि। यह मूल रूप से एक पाठ पार्सिंग समस्या है, और हैंडल करने के लिए PHP के पार्सर को गाली देना थोड़ा हैकिंग लगता है। यदि आप भाषा सुविधाओं का दुरुपयोग करना चाहते हैं, तो JSON पार्सर का दुरुपयोग क्यों नहीं करते हैं? कम से कम JSON पार्सर के साथ, कोड इंजेक्शन के सभी पर कोई संभावना नहीं है।

$json = str_replace(array(
    'enum', '(', ')', "'"), array)
    '',     '[', ']', "'"), $type);
$result = json_decode($json);

एक नियमित अभिव्यक्ति शायद सबसे स्पष्ट तरीका है। आप इस स्ट्रिंग से सभी मान निकालने के लिए एक एकल नियमित अभिव्यक्ति का उपयोग कर सकते हैं:

$extract_regex = '/
    (?<=,|enum\()   # Match strings that follow either a comma, or the string "enum("...
    \'      # ...then the opening quote mark...
    (.*?)       # ...and capture anything...
    \'      # ...up to the closing quote mark...
    /x';
preg_match_all($extract_regex, $type, $matches);
$result = $matches[1];

1
भले ही यह प्रति प्रश्न का उत्तर नहीं दिया था, यह सवाल का एक बहुत अच्छा जवाब है: एक एनम () ... शुक्रिया अदा करने का सबसे अच्छा तरीका क्या होगा?)
पियरे स्प्रिंग

13

eval() धीमा है, लेकिन मैं इसे बुराई नहीं कहूंगा।

इसका बुरा उपयोग हम इसे बनाते हैं जो कोड इंजेक्शन और बुराई हो सकती है।

एक सरल उदाहरण:

$_GET = 'echo 5 + 5 * 2;';
eval($_GET); // 15

एक सामंजस्यपूर्ण उदाहरण:

$_GET = 'system("reboot");';
eval($_GET); // oops

मैं आपको सलाह दूंगा कि आप इसका उपयोग न करें eval()लेकिन यदि आप करते हैं, तो सुनिश्चित करें कि आप सभी इनपुट को सत्यापित / श्वेतसूची में सत्यापित करें।


12

जब आप eval के अंदर विदेशी डेटा (जैसे यूजर इनपुट) का उपयोग कर रहे हों।

ऊपर आपके उदाहरण में, यह कोई समस्या नहीं है।


7

मैं यहाँ सामग्री को स्पष्ट रूप से चुरा लूंगा:

  1. अपनी प्रकृति के आधार पर सुरक्षा हमेशा एक सुरक्षा चिंता का विषय है।

  2. सुरक्षा चिंताओं के अलावा भी अविश्वसनीय रूप से धीमी गति से होने की समस्या है। PHP 4.3.10 पर मेरे परीक्षण में इसका 10 गुना धीमा फिर सामान्य कोड और PHP 5.1 बीटा 1 पर 28 गुना धीमा।

blog.joshuaeichorn.com: उपयोग-eval-in-php


5

eval()है हमेशा बुराई।

  • सुरक्षा कारणो से
  • प्रदर्शन कारणों से
  • पठनीयता / पुन: प्रयोज्य कारणों से
  • आईडीई / उपकरण कारणों के लिए
  • डिबगिंग कारणों के लिए
  • हमेशा एक बेहतर तरीका है

@bracketworks: लेकिन आप गलत हैं - ये सभी अंतर्निहित समस्याएं कुछ स्थितियों में जादुई रूप से गायब नहीं होती हैं। उन्हें क्यों करना चाहिए? उदाहरण के लिए प्रदर्शन करें: क्या आपको लगता है कि दुभाषिया अत्यंत धीमी गति से विकसित होने वाले निष्कासन () को केवल बढ़ी हुई गति के साथ निष्पादित करेगा क्योंकि आपने इसे कुछ रहस्यमय "नहीं-बुराई" तरीके से इस्तेमाल किया है? या वह चरण-दर-चरण डिबगिंग आपके भाग्यशाली दिन में किसी भी तरह के निष्कासन के अंदर काम करेगा?
फ्रेंकोइस बुर्जुआ

3
सच कहूं, तो मुझे लगता है कि @ MichałRudnicki का जवाब सबसे अच्छा है। मुझे गलत मत समझो, जब भी मैं ( खुद से ) एक सवाल पूछता हूं , और जवाब होता है eval(), मैं बस यह मानूंगा कि मैंने सवाल गलत पूछा है; शायद ही कभी यह "सही" उत्तर हो, लेकिन कंबल-राज्य के लिए यह हमेशा बुराई है बस गलत है।
डैन लग्ग

अगर मैं डेटाबेस में कोड स्टोर करना चाहता हूं? मैं इसे कैसे निष्पादित कर सकता हूं?
कॉन्स्टेंटिन एक्सफ़्लाश स्ट्रेटजेनस

@KonstantinXFlashStratigenas आपको अपने आप से पूछना चाहिए कि आप एक डेटाबेस में निष्पादन योग्य कोड क्यों संग्रहीत कर रहे हैं। एक डेटाबेस आपके कोड के परिणामस्वरूप होने वाले डेटा के लिए है - आपका कोड नहीं। बहुत कम से कम, आप हमले वैक्टर बढ़ा रहे हैं।
जैक बी

4

मैं आपके कोड को बनाए रखने वाले लोगों पर भी कुछ विचार करूंगा।

eval () केवल देखने और जानने के लिए आसान नहीं है। आपका उदाहरण इतना बुरा नहीं है, लेकिन अन्य स्थानों पर यह एक सही दुःस्वप्न हो सकता है।


4

व्यक्तिगत रूप से, मुझे लगता है कि कोड अभी भी बहुत बुरा है क्योंकि आप टिप्पणी नहीं कर रहे हैं कि यह क्या कर रहा है। यह वैधता के लिए इसके इनपुट का परीक्षण भी नहीं कर रहा है, जिससे यह बहुत नाजुक हो गया है।

मुझे यह भी लगता है कि, निष्कासन के उपयोग का 95% (या अधिक) सक्रिय रूप से खतरनाक है, छोटे संभावित समय की बचत जो इसे अन्य मामलों में प्रदान कर सकती है, इसका उपयोग करने के बुरे अभ्यास में लिप्त होने के लायक नहीं है। साथ ही, आपको बाद में अपने minions को यह समझाना होगा कि आपके eval का उपयोग अच्छा क्यों है, और उनका बुरा।

और, ज़ाहिर है, आपका PHP पर्ल की तरह लग रहा है;)

Eval के साथ दो मुख्य समस्याएं हैं (), ("इंजेक्शन हमले" परिदृश्य के रूप में):

1) इससे नुकसान हो सकता है 2) यह बस दुर्घटनाग्रस्त हो सकता है

और एक जो अधिक सामाजिक-से-तकनीकी है:

3) यह एक शॉर्टकट के रूप में अनुचित रूप से इसका उपयोग करने के लिए लोगों को लुभाएगा

पहले मामले में, आप मनमाना कोड निष्पादन के जोखिम (जाहिर है, तब नहीं जब आप एक ज्ञात स्ट्रिंग को निकाल रहे हों) चलाते हैं। हालाँकि, आपके इनपुट्स ज्ञात या तय नहीं किए जा सकते हैं।

अधिक संभावना (इस मामले में) आप बस दुर्घटनाग्रस्त हो जाएंगे, और आपका स्ट्रिंग गंभीर रूप से अस्पष्ट त्रुटि संदेश के साथ समाप्त हो जाएगा। IMHO, सभी कोड को यथासंभव बड़े करीने से विफल करना चाहिए, यह विफल होना चाहिए कि इसे एक अपवाद फेंकना चाहिए (जैसा कि त्रुटि का सबसे अधिक अप्रचलित रूप है)।

मेरा सुझाव है कि, इस उदाहरण में, आप व्यवहार के लिए कोडिंग के बजाय संयोग से कोडिंग कर रहे हैं। हाँ, एसक्यूएल एनम स्टेटमेंट (और क्या आपको यकीन है कि फील्ड की एनम? - क्या आपने डेटाबेस के राइट वर्जन के राइट टेबल के राइट फील्ड को कॉल किया था? क्या वास्तव में इसका जवाब था?) PHP में ऐरे डिक्लेरेशन सिंटैक्स जैसा दिखता है? लेकिन मैं सुझाव दूंगा कि आप वास्तव में क्या करना चाहते हैं, इनपुट से आउटपुट तक का सबसे छोटा रास्ता नहीं है, बल्कि निर्दिष्ट कार्य से निपटना है:

  • पहचानें कि आपके पास एक एनम है
  • भीतरी सूची निकालें
  • सूची मूल्यों को अनपैक करें

जो मोटे तौर पर आपका विकल्प एक करता है, लेकिन मैं कुछ स्पष्ट और सुरक्षा के लिए इसके चारों ओर टिप्पणी करता हूं (जैसे, यदि पहला मैच मेल नहीं खाता है, तो अपवाद छोड़ दें या शून्य परिणाम सेट करें)।

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

Preg_version के साथ आपका सबसे बुरा परिणाम $ result = null होने की संभावना है, eval संस्करण के साथ सबसे खराब अज्ञात है, लेकिन कम से कम एक दुर्घटना।


3

eval कोड के रूप में एक स्ट्रिंग का मूल्यांकन करता है, इसके साथ समस्या यह है कि अगर स्ट्रिंग किसी भी तरह से "दागी" है तो यह भारी सुरक्षा खतरों को उजागर कर सकता है। आम तौर पर समस्या एक ऐसे मामले में होती है जहाँ उपयोगकर्ता इनपुट का मूल्यांकन स्ट्रिंग में किया जाता है कई मामलों में उपयोगकर्ता इनपुट कोड (php या ssi उदाहरण के लिए) कर सकता है जो तब eval के भीतर चलाया जाता है, यह आपकी php स्क्रिप्ट के समान अनुमतियों के साथ चल सकता है और हो सकता है अपने सर्वर तक जानकारी / पहुंच प्राप्त करने के लिए उपयोग किया जाता है। यह सुनिश्चित करने के लिए उपयोगकर्ता इनपुट को अच्छी तरह से साफ करने से पहले इसे स्पष्ट करने के लिए काफी मुश्किल हो सकता है। अन्य समस्याएं हैं ... जिनमें से कुछ बहस योग्य हैं


3

PHP सलाह देता है कि आप अपना कोड इस तरह से लिखें कि वह स्पष्ट विवरण करने के बजाय call_user_func के माध्यम से निष्पादित हो सके।


2

एक और कारण evalबुरा है, कि यह PHP bytecode कैश जैसे eAccelertor या ACP द्वारा कैश नहीं किया जा सकता है।


2

यह खराब प्रोग्रामिंग है जो स्पष्ट है () बुराई है, फ़ंक्शन नहीं। मैं कभी-कभी इसका उपयोग करता हूं, क्योंकि मैं कई साइटों पर गतिशील प्रोग्रामिंग में इसके आसपास नहीं पहुंच सकता। मुझे PHP एक साइट पर पार्स नहीं किया जा सकता है, क्योंकि मुझे उन चीजों को प्राप्त नहीं होगा जो मैं चाहता हूं। मुझे बस एक परिणाम प्राप्त होगा! मुझे खुशी है कि एक समारोह विकसित हुआ () मौजूद है, क्योंकि यह मेरे जीवन को बहुत आसान बनाता है। उपयोगकर्ता का निवेश? केवल खराब प्रोग्रामर ही हैकर्स से आक्रांत हो जाते हैं। मुझे इसकी चिंता नहीं है।


2

यह खराब प्रोग्रामिंग है जो स्पष्ट है () बुराई है, फ़ंक्शन नहीं। मैं कभी-कभी इसका उपयोग करता हूं, क्योंकि मैं कई साइटों पर गतिशील प्रोग्रामिंग में इसके आसपास नहीं पहुंच सकता। मुझे PHP एक साइट पर पार्स नहीं किया जा सकता है, क्योंकि मुझे उन चीजों को प्राप्त नहीं होगा जो मैं चाहता हूं। मुझे बस एक परिणाम प्राप्त होगा! मुझे खुशी है कि एक समारोह विकसित हुआ () मौजूद है, क्योंकि यह मेरे जीवन को बहुत आसान बनाता है। उपयोगकर्ता का निवेश? केवल खराब प्रोग्रामर ही हैकर्स से आक्रांत हो जाते हैं। मुझे इसकी चिंता नहीं है।

मुझे लगता है कि आपको जल्द ही गंभीर समस्याएं होंगी ...

सभी ईमानदारी में, PHP जैसी व्याख्या की गई भाषा में, एक्सॉर्बिटेंट फ़ंक्शन के लिए बिल्कुल अच्छा उपयोग नहीं है। मैंने कभी भी निष्कासन कार्यक्रम कार्यक्रम नहीं देखे हैं जिन्हें अन्य, सुरक्षित तरीकों का उपयोग करके निष्पादित नहीं किया जा सकता था ...

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

मैंने अपनी खुद की रचनात्मकता को पार करने वाले eval फ़ंक्शन का दुरुपयोग करने के लिए तैयार किए गए उदाहरण देखे हैं। एक सुरक्षा रुख से, हर कीमत पर बचें, और मैं यह भी कहूंगा कि यह 'दिए' के ​​बजाय PHP कॉन्फ़िगरेशन में बहुत कम से कम विकल्प होने की मांग करता है।


के तर्क "चाहे कितना ध्यान से आप इस सुविधा का एक्स के बारे में अपने कोड को हासिल करने का प्रयास करें, स्मार्ट हैकर्स एक कदम आगे हमेशा से रहे हैं ..." , न सिर्फ एक्स == किसी भी अन्य तकनीक को लागू किया जा सकता है eval। और इसलिए, किसी भी सुविधा के लिए X: X सभी eval की जड़ है ... er ... बुराई, इसलिए बेहतर प्रोग्रामिंग को पूरी तरह से छोड़ दें (इस तरह उन मूर्ख हैकर्स के नीचे से कालीन खींच रहा है, फिर भी अंततः उन्हें आउटसोर्स कर रहा है)।
एस.जे.

"एक अतिरंजित समारोह जैसे कि निष्कासन के लिए कोई अच्छा उपयोग नहीं है" -> कोई भी जो 'बिल्कुल' जैसे शब्दों का उपयोग कर सकता है, या तो प्रोग्रामिंग के लिए नया है, या एक बुरा प्रोग्रामर है।
२००

2

यहाँ eval का उपयोग किए बिना एक डेटाबेस से खींचे गए PHP कोड को चलाने का एक उपाय है। सभी कार्यों और अपवादों के लिए अनुमति देता है:

$rowId=1;  //database row id
$code="echo 'hello'; echo '\nThis is a test\n'; echo date(\"Y-m-d\");"; //php code pulled from database

$func="func{$rowId}";

file_put_contents('/tmp/tempFunction.php',"<?php\nfunction $func() {\n global \$rowId;\n$code\n}\n".chr(63).">");

include '/tmp/tempFunction.php';
call_user_func($func);
unlink ('/tmp/tempFunction.php');

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


यह एक उत्तर की प्रतिक्रिया की तरह दिखता है; कृपया इसे ऐसे पोस्ट करें जब आप कर सकते हैं।
rfornal

1

मैं eval () का उपयोग बहुत करता था, लेकिन मैंने पाया कि अधिकांश मामलों में आपको ट्रिक्स करने के लिए eval का उपयोग नहीं करना पड़ता है। वैसे, आपके पास PHP में call_user_func () और call_user_func_array () हैं। यह सांख्यिकीय रूप से और गतिशील रूप से किसी भी विधि को कॉल करने के लिए पर्याप्त है।

एक स्थिर कॉल करने के लिए अपने कॉलबैक को सरणी ('class_name', 'method_name') के रूप में बनाएं, या 'class_name :: method_name' जैसे साधारण स्ट्रिंग के रूप में भी। डायनेमिक कॉल उपयोग सरणी ($ ऑब्जेक्ट, 'विधि') स्टाइल कॉलबैक करने के लिए।

Eval () के लिए एकमात्र समझदार उपयोग एक कस्टम कंपाइलर लिखना है। मैंने एक बना दिया, लेकिन अभी भी बुराई है, क्योंकि यह डिबग करना बहुत कठिन है। सबसे खराब बात यह है कि खाली कोड में घातक त्रुटि उस कोड को क्रैश कर देती है जिसे उसने कहा था। मैंने कम से कम वाक्यविन्यास की जांच करने के लिए पार्सेकिट PECL एक्सटेंशन का उपयोग किया, लेकिन अभी भी कोई खुशी नहीं है - अज्ञात वर्ग और पूरे ऐप क्रैश का उल्लेख करने का प्रयास करें।


0

सुरक्षा चिंताओं के अलावा, eval () संकलित, अनुकूलित या opcode कैश नहीं किया जा सकता है, इस प्रकार यह सामान्य php कोड की तुलना में धीमा - धीमा हो जाएगा । यह इस प्रकार गैर-प्रदर्शन करने वाले का उपयोग करने के लिए है, हालांकि यह बुराई नहीं करता है। ( gotoबुराई है, evalकेवल बुरा व्यवहार है / बदबूदार कोड / बदसूरत)


evalकी तुलना में कम दुष्ट रेटिंग मिलती है goto? क्या यह विपरीत दिन है?
JLRishe

यह सिर्फ इतना है कि मैं वास्तव gotoमें 5.3 में लागू करने के लिए php देवों के खिलाफ एक शिकायत है ।
एरन सीडरहोम

1
नाह, टू- gotoफोबियंस: उपकरण हैं, और शिल्पकार हैं, जो उनका उपयोग करते हैं (या नहीं)। यह कभी भी उपकरण नहीं है जो गलती करते समय एक पेशेवर की तरह एक बेवकूफ की तरह दिखता है, बल्कि उचित उपकरण (ठीक से) का उपयोग करने में असमर्थता है। लेकिन यह हमेशा दोष देने का उपकरण है ...
एस.जे.

0

अधिकांश लोग इस तथ्य को इंगित करेंगे कि यह खतरनाक हो सकता है जब आप उपयोगकर्ता इनपुट के साथ काम कर रहे हैं (जो कि सौदा करना संभव है)।

मेरे लिए सबसे बुरी बात यह है कि यह कम कर देता है रख-रखाव के लिए अपने कोड की:

  • डिबग करना मुश्किल है
  • अपडेट करना मुश्किल है
  • उपकरण और सहायकों का उपयोग सीमित करता है (जैसे IDEs)
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.