এসকিউএল * প্লাস, @, এবং আপেক্ষিক পাথ


9

একরকম, মনে হয় এসকিউএল * প্লাস (কমপক্ষে উইন্ডোজটিতে) যখন ডাকা হয় @@এবং যখন পাথটি একক বা ডাবল ডট দিয়ে শুরু হয় তখন কোনও আপেক্ষিক পাথের সাথে কোনও স্ক্রিপ্ট সনাক্ত করতে অক্ষম ।

উদাহরণস্বরূপ, x:\some\whereআমার অধীনে নিম্নলিখিত ডিরেক্টরি কাঠামো রয়েছে:

script.sql
main-dir\main-sub-dir
              call-script.sql
              script.sql

এটি: দুটি script.sqlকিন্তু বিভিন্ন লোকেশনে।

বিষয়বস্তুর script.sqlশুধু অধীন x:\some\whereসহজভাবে হয়

prompt SCRIPT root

অন্যের script.sqlবিষয়বস্তু হয়

prompt SCRIPT main-dir/main-subdir

call-script.sql সার্চ

@@script.sql
@ script.sql

প্রত্যাশিত আউটপুট

যদি আমি এসকিউএল * প্লাস শুরু করি x:\some\whereএবং তারপরে একটি করি

@main-dir/main-sub-dir/call-scripts

আউটপুট হবে

SCRIPT main-dir/main-subdir
SCRIPT root 

এটি প্রত্যাশিত, যেহেতু সিঙ্গল @থেকে এসকিউএল * প্লাস শুরু হয়েছিল @@সেখান থেকে পাথ অনুসন্ধান করার কথা রয়েছে এবং এটিতে থাকা স্ক্রিপ্টের ডিরেক্টরি থেকে পাথ অনুসন্ধান করার কথা রয়েছে।

অপ্রত্যাশিত আউটপুট

এখন , আমি যদি এটি পরিবর্তন করি call-scripts.sql:

@@./script.sql
@ ./script.sql

দ্বিগুণ @@মনে হয় এটির আচরণের পরিবর্তন ঘটবে, এতে এটি এসকিউএল * প্লাস যেখান থেকে শুরু হয়েছিল সেগুলি অনুসন্ধান করে এবং আউটপুটটি এখন হবে

SCRIPT root
SCRIPT root

যা আমি প্রত্যাশা করে তা নয়


এই আচরণটি কোথাও নথিভুক্ত করা হয়েছে এবং আরও গুরুত্বপূর্ণভাবে, কীভাবে আমাকে পরিবর্তন করতে হবে call-scripts.sqlযাতে এটি আপেক্ষিক পাথগুলিকে ( @@../../other-dir/other-sub-dir/script) সঠিকভাবে ডাকে ?


আপনার এসকিউএলপ্যাট পরিবেশের পরিবর্তনশীল সেটটি কী? কোনটি ডিরেক্টরি অনুসন্ধান করা হয় তা এটি প্রভাবিত করে।
ফিলি

1
যাইহোক, দস্তাবেজগুলি এখানে রয়েছে: docs.oracle.com/cd/E11882_01/server.112/e16604/… ডকস.অরাকল.
E11882_01

লিনাক্স, FWIW এর অধীনে একই আচরণ under (এবং একটি অ্যাম্পারস্যান্ড হ'ল &, @; যা আসল নাম বলে মনে হয় না )। এটি ত্রুটিযুক্ত বলে মনে হচ্ছে এটি বাগ হতে পারে। কেবল মাথায় আসে এমনটি হ'ল একটি চলকটিকে সম্পূর্ণ পথের সাথে শীর্ষ স্তরের স্ক্রিপ্ট সেট করা এবং তার উপর ভিত্তি করে সমস্ত কিছু করা, তবে এটি নীচে ডিরেক্টরি কাঠামো স্থির না করা না হলে এটি খুব সুবিধাজনক নয়।
অ্যালেক্স পুল

@ বনাম অ্যাম্পারস্যান্ডস জিনিসটি দেখানোর জন্য ধন্যবাদ ... আমার এটি জানা উচিত ছিল, তবে আমি পোস্টটি লেখার সময় আমি সত্যিই মনোযোগ দিই নি। এটি এখন শিরোনামে স্থির।
রেনে নিনফেনিগার

2
আমি সাক্লিপ্লাসের সাথে সবেমাত্র আক্রমণ করেছি strace। এখানে প্রাসঙ্গিক কলগুলি রয়েছে: pastebin.com/cVK1QQL4 নোট করুন যে এটি পেস্টবিন আউটপুটে প্রদর্শিত ফাইলগুলি খোলার চেষ্টা করার আগে অন্য কোনও ডিরেক্টরিতে "স্ক্রিপ্ট.এসকিউএল" ফাইলগুলি স্থিত বা অ্যাক্সেস করার চেষ্টা করেনি।
ফিলি

উত্তর:


7

হ্যাঁ, এটি বাগ 2391334 যা প্রায় দীর্ঘকাল ধরে ছিল এবং সম্ভবত অদূর ভবিষ্যতে ঠিক করা হবে না।

এটিকে ঘিরে কাজ করার একটি উপায় হ'ল সেই পথটিকে কঠোর কোডিং না করেই স্ক্রিপ্টগুলির পথ "জানুন" । এসকিউএলপ্লাসে এটি করার জন্য একটি কৌশল প্রয়োজন - যদি আপনি একটি অস্তিত্বহীন ফাইল চালানোর চেষ্টা করেন তবে আপনি একটি ত্রুটি বার্তা পাবেন যাতে পথের নাম অন্তর্ভুক্ত রয়েছে।

সুতরাং এখানে কর্ম যে একটি ডেমো। আপনার দৃশ্যের নকল করতে আমি পেয়েছি:

c:\temp\demo
   script.sql
   maindir
      subdir
         call_script.sql
         script.sql

আমরা যা করতে পারি তা হ'ল কল_স্ক্রিপ্ট.এসকিউএল এর সামনের দিকে কিছু কমান্ড যুক্ত করা যা পথটি বেছে নেবে। এটি দেখতে কিছুটা অদ্ভুত লাগছে, তবে আপনাকে এটি পরিবর্তন করার দরকার নেই - এটি কেবলমাত্র একটি নির্দিষ্ট জিনিস যা আপনি আটকে রেখেছেন

set termout off
spool _path_finder.sql
@@_nonexistent_script.sql
spool off;

var path varchar2(100);
set serverout on
declare
  output varchar2(1000) := regexp_replace(replace(q'{
@_path_finder.sql
}',chr(10)),'.*"(.*)".*','\1');
begin 
  :path:=substr(output,1,length(output)-24);
end;
/
col path new_val path
select :path path from dual;
set termout on

এখানে যা ঘটছে, আমরা কি একটি অস্তিত্বহীন স্ক্রিপ্ট চালাচ্ছি যা প্রত্যাবর্তন করে:

"SP2-0310: ফাইলটি খুলতে অক্ষম" পথ n _নিস্টিস্টিস্ট_স্ক্রিপ্ট.এসকিউএল "

সুতরাং একটি সামান্য regexp দিয়ে আমরা পথটি বের করতে পারি, এটি একটি এসকিউএলপ্লাস ভেরিয়েবলে সঞ্চয় করতে পারি এবং তারপরে সেই বিন্দু থেকে ব্যবহার করতে পারি।

সুতরাং আপনার কল_স্ক্রিপ্ট.এসকিউএল এর চূড়ান্ত সংস্করণটি এর মতো দেখায়

set termout off
spool _path_finder.sql
@@_nonexistent_script.sql
spool off;

var path varchar2(100);
set serverout on
declare
  output varchar2(1000) := regexp_replace(replace(q'{
@_path_finder.sql
}',chr(10)),'.*"(.*)".*','\1');
begin 
  :path:=substr(output,1,length(output)-24);
end;
/
col path new_val path
select :path path from dual;
set termout on
prompt path was &path      

@@&path\script.sql
@&path\script.sql

এবং যখন আমরা এটি চালাই, আমরা নিম্নলিখিত পেতে

SQL> @maindir\mainsubdir\call_script
path was maindir\mainsubdir
script in subdir
script in subdir

এবং সেখানে আপনি যান :-)

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