ব্যাশে বিস্ময়কর চিহ্ন (!) ব্যবহার করতে পারবেন না?


86

আমি !তার পথে একটি বিস্ময়কর চিহ্ন ( ) সহ একটি HTTP url অ্যাক্সেস করতে কার্ল কমান্ডটি ব্যবহার করার চেষ্টা করছি । উদাহরণ:

curl -v "http://example.org/!287s87asdjh2/somepath/someresource"

কনসোল দিয়ে উত্তর bash: ... event not found

এখানে কি হচ্ছে? এবং বিস্মৃত চিহ্ন থেকে বাঁচতে উপযুক্ত বাক্য গঠন কী হবে?


4.4+ বাশ-এ সমাধান হয়েছে
আইজাক

উত্তর:


98

বিস্ময়কর চিহ্নটি ব্যাশের ইতিহাস প্রসারের অংশ। এটি ব্যবহার করতে আপনার এটি একক উদ্ধৃতিতে আবদ্ধ হওয়া প্রয়োজন (যেমন 'http://example.org/!132':) অথবা \অক্ষরটির আগে এটি সরাসরি একটি ব্যাকস্ল্যাশ ( ) সহ পালাতে হবে (যেমন "http://example.org/\!132":)।

নোট করুন যে ডাবল উক্তিগুলিতে এক্সামের আগে একটি ব্যাকস্ল্যাশ ইতিহাসের প্রসারণ রোধ করে, তবে ব্যাকস্ল্যাশ সেরকম ক্ষেত্রে সরিয়ে দেওয়া হয় না। সুতরাং একক উদ্ধৃতি ব্যবহার করা ভাল, সুতরাং আপনি curlURL এর অংশ হিসাবে আক্ষরিক ব্যাকস্ল্যাশটি পাস করছেন না ।


8
"http://example.org/\!132"ব্যাকস্ল্যাশকে ব্যাখ্যা না করেই প্রসারিত হয় (POSIX সম্মতির কারণ, আমি বিশ্বাস করি)।
ক্রিস ডাউন

@ ক্রিসডাউন, আমি এটি স্পষ্ট করে বলার চেষ্টা করেছি যে এটি আমার দ্বিতীয় বিকল্প ছিল। বিভ্রান্তির সম্ভাবনা দেখানোর জন্য ধন্যবাদ।
ড্যানিয়েল পিটম্যান

6
রেকর্ডের জন্য: "!" পালানোর চেষ্টা করা পোর্টেবল নয়। সর্বোত্তম অনুশীলনের সুপারিশটি সর্বদা উদ্ধৃত করা (সিজ-কোটস) "!"। সম্পর্কিত: "^" (ক্যারেট), একটি অ-মেটাচার্যাক্টারের, যা বহনযোগ্যতার জন্য উদ্ধৃতি প্রয়োজন। অবশেষে, "!" যদি একটি বিবৃতি ব্যবহার করা উচিত নয়; সম্ভব হলে পরিবর্তে এটি পরীক্ষার পক্ষে যুক্তি হিসাবে ব্যবহার করুন (আবার সোলারিস / বিন / শের কারণে)।
নিকোলাস উইলসন

5
শুধুমাত্র একক উদ্ধৃতি আমার পক্ষে কাজ করেছিল। zsh এখনও ব্যাখ্যামূলক \!এবং ডাবল উদ্ধৃতি ছিল।
অরকোডেন

1
সোলারিসে (আবর্জনা পূর্বের প্রি-এক্সপিজি 4 শেল), '^' এর একটি নাম |এবং পাইপ তৈরি করতে ব্যবহৃত হয়। আপনি যদি গ্রাহকদের কাছে স্ক্রিপ্টগুলি প্রেরণ করছেন এবং তারা কী শেলটি এটি চালাবেন তা নিশ্চিত করতে না পারলে আপনাকে সেগুলি দিয়ে পরীক্ষা করতে হবে!
নিকোলাস উইলসন

61

ড্যানিয়েলের দেওয়া উত্তরের পাশাপাশি আপনি যদি ইতিহাসের সম্প্রসারণটি ব্যবহার না করেন তবে আপনি কেবল পুরোপুরি বন্ধ করে দিতে পারেন set +H


19
ইতিহাসের সম্প্রসারণকে পুরোপুরি বন্ধ করে দেওয়া হ'ল আমি সারাদিন শুনেছি সেরা পরামর্শ! ইতিহাস সম্প্রসারণ বিপজ্জনক এবং বাইজেন্টাইন যখন আরও অনেক ভাল বিকল্প (এর সাথে বর্ধিত ইতিহাস অনুসন্ধান Ctrl-R) থাকে যা আপনাকে আপনার কমান্ডের পূর্বরূপ দেখতে এবং সম্পাদনা করতে দেয় যাতে আপনি !-14যে কমান্ডটি অন্ধভাবে চালিয়ে যেতে পারেন না !-12যে উফ, এমনটি ঘটেছে rm -rf *। সাবধান থাকা. ইতিহাস সম্প্রসারণ অক্ষম করুন! পালাও !!
অ্যাকুলিচ

6
সবচেয়ে বড় উত্তর: ইতিহাসের বিস্তৃতি একটি বিশাল সুরক্ষা ঝুঁকি! এটি তৈরি করা URL এর মাধ্যমে আপনার ইউনিক্স আক্রমণ করতে ব্যবহার করা যেতে পারে।
ডান

@ অ্যাকলিচ, বা কেবল এর পরিবর্তে পসিক্স -নির্দিষ্ট কমান্ডটি fc -14ব্যবহার করুন। তবে এটি সত্য যে আপনি ইতিহাসের সম্প্রসারণকে সক্ষম করা ছাড়া এটি করতে পারেন। ব্যক্তিগতভাবে, আমি ব্যবহার !$এবং !viএবং sudo !!এবং এমনকি git add !vi:$প্রায়ই যথেষ্ট ইতিহাস সম্প্রসারণ সক্রিয় রেখে পরোয়ানা রয়েছে।
ওয়াইল্ডকার্ড

আমি মনে করি আমি এটি আমার শেল আরসি ফাইলগুলিতে যুক্ত করব। আমি এটি কেবল কখনও একটি ঝরঝরে "কৌশল" হিসাবে ব্যবহার করেছি
টনিএইচ

17

আমি ব্যক্তিগতভাবে একক উদ্ধৃতি করব, তবে সম্পূর্ণতার জন্য, আমি এটিও নোট করব যেহেতু এটি একটি ইউআরএল, আপনি !যেমন এনকোড করতে পারেন %21, যেমন curl -v http://example.org/%21132


13

এটিও করতে পারে

curl -v "http://example.org/"'!'"287s87asdjh2/somepath/someresource"
অথবা
curl -v "http://example.org/"\!"287s87asdjh2/somepath/someresource"

যা কাজ করে কারণ বাশ সংলগ্ন স্ট্রিংগুলিকে সম্মতি দেয়। আপনার কাছে শেল প্রসারণের প্রয়োজন এমন অন্যান্য জিনিস থাকলে এই পদ্ধতিরটি বিশেষত কার্যকর হয়, তাই আপনি পুরো স্ট্রিংয়ের জন্য একক উদ্ধৃতি ব্যবহার করতে পারবেন না:

curl -v 'http://example.org/!'"287s87asdjh2/${basepath}/someresource"

!কমান্ড লাইন প্রম্পটে ইতিহাস বিস্তারের জন্য অক্ষর ব্যবহৃত হয়।
সুতরাং এটি প্রম্পটে সমস্যা হতে পারে তবে শেল স্ক্রিপ্ট ফাইলগুলিতে নয়।
আপনি দেখতে পাচ্ছেন ইতিহাস বিস্তৃতি এমনকি ডাবল উদ্ধৃতিতেও কাজ করে।


ইউনিক্স কমান্ড করার প্রচুর উপায় রয়েছে এবং ইংরাজী বাক্যগুলিতে তাদের প্রয়োজনের তুলনায় আরও বেশি অক্ষর ব্যবহার করা হয় এবং সেগুলি যতটা প্রয়োজন তার চেয়ে বেশি বিভ্রান্তিকর হয়। এটি কীভাবে প্রথম / গৃহীত / সর্বোচ্চ ভোট প্রাপ্ত উত্তরের চেয়ে বেশি, যেমন পুরো ইউআরএলকে একক উদ্ধৃতিতে রাখে?
জি ম্যান

2
@ জি-ম্যান: এটি ব্যাশ আর্গুমেন্ট তৈরির অন্য উপায় বলে। আমি এই পদ্ধতি সম্পর্কে অবগত ছিল না। নতুন জিনিস শেখার ক্ষেত্রে কোনও ভুল নেই।
সাহিল সিং

@ সাহিলসিংহ কীভাবে নতুন? এটি তিনটি স্ট্রিং সংমিশ্রণ করে, দুটি ডাবল উদ্ধৃতিতে এবং একটি একক উদ্ধৃতিতে আবদ্ধ। এখানে কোনও বাসা নেই।
রাফেল

@ জি-ম্যান এটি স্পষ্ট নয় যে আপনি যখন একে অপরের পাশে 2 টি স্ট্রিং রাখেন তখন তারা সম্মতিযুক্ত হয়। প্রিন্টফ ("হ্যালো" "ওয়ার্ল্ড") সি তেও কাজ করবে, তবে প্রিন্টফ ("হ্যালো" 'ডাব্লু') কাজ করবে না, তাই আপনি জানেন যে বাশ এ জাতীয় অভিব্যক্তি সমন্বিত করে আমার কাছে নতুন ছিল, তবে আমি তাতে সম্মত হই না ইউটিলিটি দৃষ্টিকোণ, এটি উচ্চতর নয়। আমি উত্তরটি পছন্দ করেছি, তাই মার্ক শস্টও করেছেন।
সাহিল সিং

2
@ জি-ম্যান এটি দরকারী যখন অন্যান্য স্ট্রিং প্রসারণও এক করে একই পংক্তিতে ঘটতে করতে চান। উদ্ধৃত আচরণের দুই ধরণের পৃথক করার এটি একটি সহজ উপায়।
ডাব্লুএফএফ

7

আমি একই সমস্যাটি দেখতে পেয়েছি এবং আমার সহজ সমাধানটি ছিল একটি ভেরিয়েবল ব্যবহার করা:

E=!  
curl -v "http://example.org/${E}287s87asdjh2/somepath/someresource"

এখানে সরলতাটি হ'ল (১) এটি শেল এবং কমান্ডগুলি জুড়ে পোর্টেবল (২) এসেস্ক সিনট্যাক্স এবং এএসসিআইআই কোডগুলি জানার দরকার নেই।


3

4.3 বাশ থেকে, আপনি এখন ইতিহাসের সম্প্রসারণের চরিত্রটি উদ্ধৃত করতে ডাবল উদ্ধৃতি ব্যবহার করতে পারেন:

$ bash --version
GNU bash, version 4.3...
[...]
$ echo "Hello World!"
Hello World!

এটি বাইরে কাজ করে না echo, প্রতিধ্বনি নিজে থেকে এটি
অন্যরকমভাবে

@ ব্লাউহিরন এর প্রতিধ্বনির সাথে কিছু করার নেই, এবং উদ্ধৃতকরণ এবং আপনি যে ধরণের দৌড়াদৌড়ি করছেন তার সংস্করণ দিয়ে কিছু করার নেই।
ফ্লাটম

2
এই উত্তরটি ভুল এবং মুছে ফেলা উচিত। আপনার bashসংস্করণটির ব্যাংটি প্রসারিত না হওয়ার সাথে কিছুই করার নেই, এটি আপনার উদাহরণে !"লাইনের শেষ" দ্বারা অনুসরণ করা এবং এটি শেলটিকে প্রসারিত করার চেষ্টা থেকে বিরত রাখার কারণে ঘটে । চেষ্টা করুন echo "!Hello World"এবং আপনি দেখতে পাবেন যে এর bashসাথে জবাব দেবে bash: !Hello: event not foundআরও তথ্যের জন্য ম্যানুয়াল দেখুন
don_crissti

0

যারা উইন্ডোতে গিট ব্যাশ ব্যবহার করছেন, তাদের কাছে @ ড্যানিয়েলপিটম্যানের গৃহীত উত্তর কাজ করে। তবে আপনার ব্যাকস্ল্যাশ (\) একটি ফরোয়ার্ড স্ল্যাশ (/) দিয়ে প্রতিস্থাপন করা উচিত।

উদাহরণস্বরূপ, ইউনিক্সে, এটি এর মতো দেখতে চাই:

curl https://abc.com/services -H 'Authorization: Bearer 111A80BBZZCnS\!ZR412543s'

উইন্ডোগুলির জন্য, এটি এর মতো কিছু হবে (অনুমোদনের শিরোনাম অংশে ফরোয়ার্ড স্ল্যাশের উপর ফোকাস করুন)

curl https://abc.com/services -H 'Authorization: Bearer 111A80BBZZCnS/!ZR412543s'


এটি খুব একটা বোঝায় না। আপনার পক্ষে যুক্তিটি এককভাবে উদ্ধৃত হয়েছে, সুতরাং এক্সটামের সাথে জড়িত স্ল্যাশ নির্বিশেষে ইতিহাসের প্রসারণের ফলসই হবে না।
ওয়াইল্ডকার্ড

ওহ, আপনি ঠিক বলেছেন। আমি কেবল এই উত্তরটি পোস্ট করেছি কারণ যখন আমি ড্যানিয়েলের উত্তর (ব্যাকস্ল্যাশ ব্যবহার করে) ব্যবহার করছিলাম তখন একটি ত্রুটি পপ আপ হয়।
স্যামুয়েলডেভ
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.