এই পৃষ্ঠাটি উইন্ডোজ-সামঞ্জস্যপূর্ণ নিয়ম, পোর্টেবল নিয়ম লেখার সাধারণ সমস্যা এবং কিছু সমাধান লেখার উপর ফোকাস করে।
পথ
সমস্যা:
দৈর্ঘ্যের সীমা : সর্বাধিক পথের দৈর্ঘ্য 259 অক্ষর।
যদিও উইন্ডোজ দীর্ঘ পথ সমর্থন করে (32767 অক্ষর পর্যন্ত), অনেক প্রোগ্রাম নিম্ন সীমার সাথে তৈরি করা হয়।
অ্যাকশনে আপনি যে প্রোগ্রামগুলি চালান সে সম্পর্কে সচেতন থাকুন।
ওয়ার্কিং ডিরেক্টরি : এছাড়াও 259 অক্ষরের মধ্যে সীমাবদ্ধ।
প্রসেস 259 অক্ষরের বেশি একটি ডিরেক্টরিতে
cd
করতে পারে না।কেস-সংবেদনশীলতা : উইন্ডোজ পাথগুলি কেস-সংবেদনশীল, ইউনিক্স পাথগুলি কেস-সংবেদনশীল।
কর্মের জন্য কমান্ড লাইন তৈরি করার সময় এটি সম্পর্কে সচেতন হন।
পাথ বিভাজক : ব্যাকস্ল্যাশ (
\`), not forward slash (
।Bazel
/
বিভাজক সহ পাথ ইউনিক্স-স্টাইল সঞ্চয় করে। যদিও কিছু উইন্ডোজ প্রোগ্রাম ইউনিক্স-স্টাইল পাথ সমর্থন করে, অন্যরা তা করে না। cmd.exe-এ কিছু বিল্ট-ইন কমান্ড তাদের সমর্থন করে, কিছু করে না।\` separators on Windows: replace
/with
`।পরম পথ : স্ল্যাশ (
/
) দিয়ে শুরু করবেন না।উইন্ডোজের সম্পূর্ণ পাথগুলি একটি ড্রাইভ লেটার দিয়ে শুরু হয়, যেমন
C:\foo\bar.txt
। কোনো একক ফাইল সিস্টেম রুট নেই।আপনার নিয়ম যদি একটি পথ পরম কিনা তা পরীক্ষা করে তাহলে এই বিষয়ে সচেতন থাকুন। সম্পূর্ণ পথগুলি এড়ানো উচিত কারণ তারা প্রায়শই অ-পোর্টেবল হয়।
সমাধান:
পথ ছোট রাখুন।
দীর্ঘ ডিরেক্টরির নাম, গভীরভাবে নেস্টেড ডিরেক্টরি কাঠামো, দীর্ঘ ফাইলের নাম, দীর্ঘ ওয়ার্কস্পেস নাম, দীর্ঘ টার্গেট নাম এড়িয়ে চলুন।
এই সবগুলি অ্যাকশনের ইনপুট ফাইলগুলির পাথ উপাদান হয়ে উঠতে পারে এবং পথের দৈর্ঘ্যের সীমা শেষ করতে পারে।
একটি ছোট আউটপুট রুট ব্যবহার করুন.
Bazel আউটপুটগুলির জন্য একটি ছোট পথ নির্দিষ্ট করতে
--output_user_root=<path>
পতাকা ব্যবহার করুন। একটি ভাল ধারণা হল শুধুমাত্র Bazel আউটপুটগুলির জন্য একটি ড্রাইভ (বা ভার্চুয়াল ড্রাইভ) থাকা (যেমনD:\`), and adding this line to your
.bazelrc` ফাইলে যুক্ত করা:build --output_user_root=D:/
বা
build --output_user_root=C:/_bzl
জংশন ব্যবহার করুন।
জংশনগুলি হল, আলগাভাবে বলতে গেলে [1] , ডিরেক্টরি সিমলিঙ্ক। জংশনগুলি তৈরি করা সহজ এবং দীর্ঘ পথ সহ ডিরেক্টরিগুলি (একই কম্পিউটারে) নির্দেশ করতে পারে। যদি একটি বিল্ড অ্যাকশন একটি জংশন তৈরি করে যার পাথ ছোট কিন্তু যার টার্গেট দীর্ঘ, তাহলে ছোট পাথ সীমা সহ টুলগুলি জংশন করা ডিরেক্টরিতে ফাইলগুলি অ্যাক্সেস করতে পারে।
.bat
ফাইলে বা cmd.exe-এ আপনি এর মতো জংশন তৈরি করতে পারেন:mklink /J c:\path\to\junction c:\path\to\very\long\target\path
[১] : কঠোরভাবে বলতে গেলে জংশনগুলি সিম্বলিক লিঙ্ক নয় , তবে বিল্ড অ্যাকশনের জন্য আপনি জংশনগুলিকে ডিরেক্টরি সিমলিঙ্ক হিসাবে বিবেচনা করতে পারেন।
অ্যাকশন/এনভার্সের পাথগুলিতে `` দিয়ে
/
প্রতিস্থাপন করুন।আপনি যখন একটি কর্মের জন্য কমান্ড লাইন বা পরিবেশের ভেরিয়েবল তৈরি করেন, তখন পাথগুলিকে উইন্ডোজ-স্টাইল করুন। উদাহরণ:
def as_path(p, is_windows): if is_windows: return p.replace("/", "\\") else: return p
পরিবেশ পরিবর্তনশীল
সমস্যা:
কেস-সংবেদনশীলতা : উইন্ডোজ এনভায়রনমেন্ট ভেরিয়েবলের নামগুলি কেস-সংবেদনশীল।
উদাহরণস্বরূপ, Java
System.getenv("SystemRoot")
এবংSystem.getenv("SYSTEMROOT")
একই ফলাফল দেয়। (এটি অন্যান্য ভাষার ক্ষেত্রেও প্রযোজ্য।)হারমেটিসিটি : অ্যাকশনগুলি যতটা সম্ভব কয়েকটি কাস্টম পরিবেশের ভেরিয়েবল ব্যবহার করা উচিত।
এনভায়রনমেন্ট ভেরিয়েবল অ্যাকশনের ক্যাশে কী-এর অংশ। যদি কোনো অ্যাকশন এনভায়রনমেন্ট ভেরিয়েবল ব্যবহার করে যা প্রায়ই পরিবর্তিত হয়, বা ব্যবহারকারীদের জন্য কাস্টম হয়, তাহলে নিয়মটি কম ক্যাশে-সক্ষম হয়।
সমাধান:
শুধুমাত্র বড় হাতের পরিবেশ পরিবর্তনশীল নাম ব্যবহার করুন।
এটি উইন্ডোজ, ম্যাকওএস এবং লিনাক্সে কাজ করে।
কর্ম পরিবেশ ন্যূনতম.
ctx.configuration.default_shell_env
ctx.actions.run
সেট করুন। যদি অ্যাকশনের আরও পরিবেশের ভেরিয়েবলের প্রয়োজন হয়, সেগুলিকে একটি অভিধানে রাখুন এবং অ্যাকশনে পাস করুন। উদাহরণ:load("@bazel_skylib//lib:dicts.bzl", "dicts") def _make_env(ctx, output_file, is_windows): out_path = output_file.path if is_windows: out_path = out_path.replace("/", "\\") return dicts.add(ctx.configuration.default_shell_env, {"MY_OUTPUT": out_path})
কর্ম
সমস্যা:
এক্সিকিউটেবল আউটপুট : প্রতিটি এক্সিকিউটেবল ফাইলের একটি এক্সিকিউটেবল এক্সটেনশন থাকতে হবে।
সবচেয়ে সাধারণ এক্সটেনশন হল
.exe
(বাইনারী ফাইল) এবং.bat
(ব্যাচ স্ক্রিপ্ট)।জেনে রাখুন যে শেল স্ক্রিপ্ট (
.sh
) উইন্ডোজে এক্সিকিউটেবল নয়; আপনি তাদেরctx.actions.run
এরexecutable
হিসাবে নির্দিষ্ট করতে পারবেন না। ফাইলগুলির কোনও+x
অনুমতি নেই, তাই আপনি লিনাক্সের মতো নির্বিচারে ফাইলগুলি চালাতে পারবেন না।ব্যাশ কমান্ড : বহনযোগ্যতার জন্য, ব্যাশ কমান্ডগুলি সরাসরি অ্যাকশনে চালানো এড়িয়ে চলুন।
ব্যাশ ইউনিক্স-এর মতো সিস্টেমে ব্যাপক, কিন্তু এটি প্রায়ই উইন্ডোজে অনুপলব্ধ। Bazel নিজেই Bash (MSYS2) এর উপর কম বেশি নির্ভর করছে, তাই ভবিষ্যতে ব্যবহারকারীদের Bazel এর সাথে MSYS2 ইনস্টল করার সম্ভাবনা কম হবে। উইন্ডোজে নিয়মগুলি ব্যবহার করা সহজ করতে, অ্যাকশনে ব্যাশ কমান্ড চালানো এড়িয়ে চলুন।
লাইন এন্ডিংস : উইন্ডোজ সিআরএলএফ ব্যবহার করে (
\r\n
), ইউনিক্স-এর মতো সিস্টেম LF (\n
) ব্যবহার করে।টেক্সট ফাইল তুলনা করার সময় এই সচেতন থাকুন. আপনার গিট সেটিংস সম্পর্কে সচেতন থাকুন, বিশেষ করে চেক আউট বা কমিট করার সময় লাইনের শেষের দিকে। (গিটের
core.autocrlf
সেটিং দেখুন।)
সমাধান:
একটি ব্যাশ-লেস উদ্দেশ্য-নির্মিত নিয়ম ব্যবহার করুন।
native.genrule()
হল Bash কমান্ডের একটি মোড়ক, এবং এটি প্রায়শই একটি ফাইল অনুলিপি করা বা একটি টেক্সট ফাইল লেখার মতো সাধারণ সমস্যার সমাধান করতে ব্যবহৃত হয়। আপনি ব্যাশের উপর নির্ভর করা এড়াতে পারেন (এবং চাকাটি পুনরায় উদ্ভাবন করা): আপনার প্রয়োজনের জন্য বেজেল-স্কাইলিবের একটি উদ্দেশ্য-নির্মিত নিয়ম আছে কিনা তা দেখুন। উইন্ডোজে বিল্ট/পরীক্ষা করার সময় এগুলির কোনটিই ব্যাশের উপর নির্ভর করে না।নিয়ম উদাহরণ তৈরি করুন:
copy_file()
( উত্স , ডকুমেন্টেশন ): অন্য কোথাও একটি ফাইল অনুলিপি করে, ঐচ্ছিকভাবে এটিকে নির্বাহযোগ্য করে তোলেwrite_file()
( উৎস , ডকুমেন্টেশন ): একটি টেক্সট ফাইল লেখে, কাঙ্খিত লাইন শেষ (auto
,unix
, orwindows
) সহ, ঐচ্ছিকভাবে এটিকে এক্সিকিউটেবল করে (যদি এটি একটি স্ক্রিপ্ট হয়)run_binary()
( উৎস , ডকুমেন্টেশন ): বিল্ড অ্যাকশন হিসেবে প্রদত্ত ইনপুট এবং প্রত্যাশিত আউটপুট সহ একটি বাইনারি (বা*_binary
নিয়ম) চালায় (এটিctx.actions.run
এর জন্য একটি বিল্ড রুল র্যাপার)native_binary()
( উত্স , ডকুমেন্টেশন ): একটি*_binary
নিয়মে একটি নেটিভ বাইনারি মোড়ানো হয়, যা আপনিrun_binary()
এরtool
অ্যাট্রিবিউট বাnative.genrule()
এরtools
অ্যাট্রিবিউটেbazel run
বা ব্যবহার করতে পারেন।
পরীক্ষার নিয়ম উদাহরণ:
diff_test()
( উৎস , ডকুমেন্টেশন ): পরীক্ষা যা দুটি ফাইলের বিষয়বস্তুর তুলনা করেnative_test()
( উত্স , ডকুমেন্টেশন ): একটি*_test
নিয়মে একটি নেটিভ বাইনারি মোড়ানো হয়, যা আপনিbazel test
করতে পারেন
উইন্ডোজে, তুচ্ছ জিনিসের জন্য
.bat
স্ক্রিপ্ট ব্যবহার করার কথা বিবেচনা করুন।.sh
স্ক্রিপ্টের পরিবর্তে, আপনি.bat
স্ক্রিপ্ট দিয়ে তুচ্ছ কাজগুলি সমাধান করতে পারেন।উদাহরণস্বরূপ, যদি আপনার এমন একটি স্ক্রিপ্টের প্রয়োজন হয় যা কিছুই করে না, বা একটি বার্তা প্রিন্ট করে, বা একটি নির্দিষ্ট ত্রুটি কোড দিয়ে প্রস্থান করে, তাহলে একটি সাধারণ
.bat
যথেষ্ট। যদি আপনার নিয়মটি একটিDefaultInfo()
প্রদানকারী প্রদান করে, তাহলেexecutable
ফিল্ডটি উইন্ডোজের সেই.bat
ফাইলটিকে উল্লেখ করতে পারে।এবং যেহেতু ম্যাকওএস এবং লিনাক্সে ফাইল এক্সটেনশন কোন ব্যাপার না, আপনি সবসময় এক্সটেনশন হিসাবে
.bat
ব্যবহার করতে পারেন, এমনকি শেল স্ক্রিপ্টের জন্যও।সচেতন থাকুন যে খালি
.bat
ফাইলগুলি চালানো যাবে না। আপনার যদি একটি খালি স্ক্রিপ্টের প্রয়োজন হয় তবে এটিতে একটি স্পেস লিখুন।একটি নীতিগত উপায়ে ব্যাশ ব্যবহার করুন।
Starlark বিল্ড এবং পরীক্ষার নিয়মে, ব্যাশ স্ক্রিপ্ট এবং ব্যাশ কমান্ডগুলিকে অ্যাকশন হিসাবে চালানোর জন্য
ctx.actions.run_shell
ব্যবহার করুন।Starlark ম্যাক্রোতে, Bash স্ক্রিপ্ট এবং কমান্ডকে একটি
native.sh_binary()
বাnative.genrule()
এ মোড়ানো। Bazel ব্যাশ উপলব্ধ কিনা তা পরীক্ষা করবে এবং ব্যাশের মাধ্যমে স্ক্রিপ্ট বা কমান্ড চালাবে।Starlark সংগ্রহস্থলের নিয়মে, Bash এড়িয়ে যাওয়ার চেষ্টা করুন। Bazel বর্তমানে রিপোজিটরি নিয়মে নীতিগত উপায়ে Bash কমান্ড চালানোর কোন উপায় অফার করে না।
ফাইল মুছে ফেলা হচ্ছে
সমস্যা:
খোলা অবস্থায় ফাইল মুছে ফেলা যাবে না।
খোলা ফাইলগুলি মুছে ফেলা যায় না (ডিফল্টরূপে), প্রচেষ্টার ফলে "অ্যাক্সেস অস্বীকার" ত্রুটি হয়৷ যদি আপনি একটি ফাইল মুছে ফেলতে না পারেন, হয়ত একটি চলমান প্রক্রিয়া এখনও এটি খোলা রাখে।
চলমান প্রক্রিয়ার ওয়ার্কিং ডিরেক্টরি মুছে ফেলা যাবে না।
প্রসেসগুলির কার্যকারী ডিরেক্টরিতে একটি খোলা হ্যান্ডেল থাকে এবং প্রক্রিয়াটি শেষ না হওয়া পর্যন্ত ডিরেক্টরিটি মুছে ফেলা যায় না।
সমাধান:
আপনার কোডে, সাগ্রহে ফাইল বন্ধ করার চেষ্টা করুন।
জাভাতে, ট্রাই
try-with-resources
ব্যবহার করুন। পাইথনে,with open(...) as f:
নীতিগতভাবে, যত তাড়াতাড়ি সম্ভব হ্যান্ডলগুলি বন্ধ করার চেষ্টা করুন।