ফাইল প্রতিস্থাপনের সময় ফাইল অনুমতি (বা পুনরুদ্ধার) বজায় রাখুন


11

আমার একটি কমান্ড রয়েছে যা কোনও ফাইলকে একটি আর্গুমেন্ট হিসাবে গ্রহণ করে, ফাইলটি পরিবর্তন করে, তারপরে দ্বিতীয় আর্গুমেন্টে উল্লিখিত ফাইলের নামটিতে এটি লিখে। আমি এই প্রোগ্রাম কল করব modifyfile

আমি এটি "জায়গায়" কাজ করতে চেয়েছিলাম তাই আমি একটি শেল স্ক্রিপ্ট (বাশ) লিখেছিলাম যা এটি একটি অস্থায়ী ফাইলে পরিবর্তিত করে আবার এটিকে সরিয়ে দেয়:

TMP=`mktemp`
modifyfile "$original" "$TMP"
mv -v "$TMP" "$original"

এটিতে এই ফাইলটির অনুমতিগুলি ধ্বংস করার দুর্ভাগ্যজনক পার্শ্ব প্রতিক্রিয়া রয়েছে। ফাইলটি ডিফল্ট অনুমতি নিয়ে পুনরায় তৈরি হয়।

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

উত্তর:


10

ব্যবহারের পরিবর্তে mv, কেবল পুনর্নির্দেশ করুন cat। উদাহরণ স্বরূপ:

TMP=$(mktemp)
modifyfile "$original" "$TMP"
cat "$TMP" > "$original"

এটি ফাইল স্তরের কোনও কিছুর ছোঁয়া ছাড়াই $originalবিষয়বস্তুগুলিকে ওভাররাইট করে $TMP


কিছু প্রোগ্রামের যদি ফাইলটিতে একটি ওপেন ফাইল হ্যান্ডেল থাকে তবে তা সমস্যাযুক্ত হতে পারে না?
মার্টিন ভন উইট্টিচ

2
আমার তখনও তা করতে rm "$TMP"হবে তবে এটি যা করতে চাই তা ঠিক করে দেবে বলে মনে হচ্ছে।
স্টিফেন অস্টেরমিলার

@ মার্টিনভনভিটিক আপনি যদি mvপরিবর্তে এটি ব্যবহার করেন তবে সমস্যা হতে পারে would আমি এই সমস্যা সমাধানের উপায় দেখছি না।
strugee

2
নিবন্ধন করুন নতুন-তারপর-সরান তৈরি করুন আপনাকে একটি পারমাণবিক পরিবর্তন দেয় এবং ফাইলগুলি উন্মুক্ত প্রোগ্রামগুলিকে প্রভাবিত করে না তবে এটি যেহেতু এটি একটি নতুন ফাইল তৈরি করে ফাইলটির মালিকানা এবং অনুমতিগুলি হারিয়ে যায়। ছাঁটাই-বিদ্যমান-তখন-লেখার অনুমতি এবং মালিকানা সংরক্ষণ করে তবে ক্র্যাশ হওয়ার সময় ডেটা হারায় এবং ফাইলটি খোলা আছে এমন প্রোগ্রামগুলির পায়ের নীচে রাগটি সোয়াইপ করে। আপনি উভয়ের ভাল অংশ একত্রিত করতে পারবেন না।
গিলস 'অশুভ হওয়া বন্ধ করুন'

1
@ মার্টিনভনভিটিক chownকেবলমাত্র মূল হিসাবে কাজ করে। chmodএবং chgrpব্যবহারকারীর অনুমতিগুলির উপর নির্ভর করে কাজ করতে পারে বা নাও করতে পারে। ACL বা ফাইল-সিস্টেম-নির্দিষ্ট বর্ধিত বৈশিষ্ট্যগুলির মতো অন্য বৈশিষ্ট্যগুলির অনুলিপিও নয়।
গিলস 'অসন্তুষ্ট হওয়া বন্ধ করুন'

10

একটি নতুন সংস্করণ দ্বারা একটি ফাইল প্রতিস্থাপন দুটি কৌশল আছে:

  1. নতুন সংস্করণ সহ একটি অস্থায়ী ফাইল তৈরি করুন, তারপরে এটি জায়গায় স্থানান্তর করুন।

    • সুবিধা: যদি কোনও প্রোগ্রাম সেই ফাইলটি খোলায়, তা সরানোর আগে বা পরে ফাইলটি খোলেনি কিনা তার উপর নির্ভর করে এটি পুরানো সামগ্রী বা নতুন সামগ্রীটি পড়বে। কোনও মিশ্রণ নেই।
    • সুবিধা: ক্র্যাশ হলে পুরানো সামগ্রী সংরক্ষণ করা হয়।
    • ডাউনসাইড: যেহেতু একটি নতুন ফাইল তৈরি হয়, তাই ফাইলের বৈশিষ্ট্যগুলি (মালিকানা, অনুমতি ইত্যাদি) সংরক্ষণ করা যায় না।
  2. পুরানো ফাইলটি জায়গায় লিখুন।

    • সুবিধা: ফাইলের বৈশিষ্ট্যগুলি সংরক্ষিত আছে।
    • ডাউনসাইড: ক্রাশের ক্ষেত্রে ফাইলটি অর্ধ-লিখিত থাকতে পারে।
    • ডাউনসাইড: কোনও প্রোগ্রামের আপডেট হওয়ার সময় যদি ফাইলটি খোলা থাকে, তবে এই প্রোগ্রামটি অসঙ্গতিপূর্ণ ডেটা পড়তে পারে।

যদি আপনি পারেন তবে পদ্ধতি 1 ব্যবহার করুন তবে প্রথমে মূল ফাইলটির বৈশিষ্ট্যগুলি প্রতিলিপি করুন cp -p --attributes-only। এর জন্য জিএনইউ কোর্টিলগুলি (যেমন- এম্বেডড লিনাক্স, বা পর্যাপ্ত পরিমাণ লিনাক্সের মতো পরিবেশ) দরকার। আপনার cpযদি না থাকে তবে --attributes-onlyএই বিকল্পটি বাদ দিন: এটি কাজ করবে তবে এটি ডেটাটিও প্রতিলিপি করবে।

tmp=$(mktemp)
cp -p --attributes-only "$original" "$tmp"
modifyfile "$original" "$tmp"
mv -f "$tmp" "$original"

আপনি যদি বিদ্যমান ফাইলটির বৈশিষ্ট্যগুলি প্রতিলিপি করতে না পারেন, উদাহরণস্বরূপ কারণ আপনার এতে লেখার অনুমতি রয়েছে তবে এটির মালিকানা নেই এবং আপনি মালিককে সংরক্ষণ করতে চান তবে কেবল 2 পদ্ধতিই সম্ভব। ডেটা ক্ষতির ঝুঁকি হ্রাস করতে:

  • উইন্ডোটি তৈরি করুন যার সময় ফাইলটি যতটা সম্ভব অসম্পূর্ণ হবে। অস্থায়ী ফাইলে প্রথমে ডেটা প্রস্তুত করুন, তারপরে এটি অনুলিপি করুন।
  • পুরানো ফাইলটির প্রথমে একটি ব্যাকআপ নিন।

tmp=$(mktemp)
backup="${original}~"
modifyfile "$original" "$tmp"
cp -p "$original" "$backup"
cp -f "$tmp" "$original"

চমৎকার উত্তর! আজকাল আমি পদ্ধতি 1 তে সিপি কমান্ডের সাহায্যে -ট্রিবিউটস- যুক্তিটি ব্যবহার করার পরামর্শ দেব । এইভাবে, ফাইলটি ফাইলের বিষয়বস্তু অনুলিপি করতে সংস্থানগুলি ব্যবহার করবে না। কোন যুক্তি থেকে এই যুক্তি যুক্ত হয়েছিল তা আমি খুঁজে পাইনি। cp -p --attributes-only "$original" "$tmp"
মার্সেলো ব্যারোস

@ মার্সেলোবারোস এটি 2010-10-15 প্রকাশিত জিএনইউ কোর্টিলস 8.6-এ যুক্ত হয়েছিল, তাই আজকাল আপনার যদি জিএনইউ কোর্টিল থাকে তবে তা আপনার উচিত। অন্যান্য cpবাস্তবায়নের সাথে এখনও এরকম কোনও কিছুই নেই ।
গিলস'স'-দুষ্ট হওয়া বন্ধ করুন '

5

প্রথম উত্তরে আমাদের আলোচনার পরে, আমি একটি আলাদা উত্তর প্রস্তাব করছি:

TMP="$(mktemp "$original".XXXXXXXXXX)"
modifyfile "$original" "$TMP"
chmod --reference="$original" "$TMP"
chown --reference="$original" "$TMP"
mv -f "$TMP" "$original"

মন্তব্য:

  • আমি ব্যবহার $originalমধ্যে mktempটেমপ্লেট তা নিশ্চিত করার জন্য অস্থায়ী ফাইল স্থাপন করা হয় না /tmpকিন্তু হিসাবে একই ফোল্ডারে $original। আমি বিশ্বাস করি যে /tmpকোনও ভিন্ন ফাইল সিস্টেমে মাউন্ট করা থাকলে অপারেশন আর পারমাণবিক হবে না।
  • mktempএতে সাদা অংশ রয়েছে এর ফলাফলের ফলাফল এখন উদ্ধৃত করা হয়েছে।
  • আমি $()instead instead এর পরিবর্তে ব্যবহার করি কারণ আমি এটিকে পরিষ্কার বিবেচনা করি।
  • ch{mod,own} --referenceএর অনুমতি স্থানান্তর করতে ব্যবহৃত $originalহয় $TMP। যদি কারও কাছে অতিরিক্ত ধারণা থাকে যা মেটাডেটা করতে পারে এবং তা স্থানান্তরিত করা উচিত, তবে দয়া করে আমার পোস্টটি সম্পাদনা করুন এবং এটি যুক্ত করুন।
  • ওহ ভাল, গিলস নির্দেশ করে বলে এর জন্য রুট অনুমতি প্রয়োজন। ঠিক আছে, আমি এখন এটি ফেলে দিচ্ছি না যে আমি এটি লিখেছি: পি
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.