সিক্যুয়েন্স.নেক্সটভ্যাল কীভাবে ওরাকলে নਾਲ হতে পারে?


11

আমার কাছে ওরাকল সিকোয়েন্সটি এর মতো সংজ্ঞায়িত হয়েছে:

CREATE SEQUENCE  "DALLAS"."X_SEQ"  
    MINVALUE 0 
    MAXVALUE 999999999999999999999999999 
    INCREMENT BY 1 START WITH 0 NOCACHE  NOORDER  NOCYCLE ;

এটি একটি সঞ্চিত পদ্ধতিতে একটি রেকর্ড সন্নিবেশ করানোর জন্য ব্যবহৃত হয়:

PROCEDURE Insert_Record
                (p_name    IN  VARCHAR2,                
                 p_userid  IN  INTEGER,
                 cur_out   OUT TYPES_PKG.RefCursor)
    IS
        v_id NUMBER := 0;
    BEGIN
        -- Get id value from sequence
        SELECT x_seq.nextval
          INTO v_id
          FROM dual;

        -- Line below is X_PKG line 40
        INSERT INTO X
            (the_id,            
             name,                        
             update_userid)
          VALUES
            (v_id,
             p_name,                        
             p_userid);

        -- Return new id
        OPEN cur_out FOR
            SELECT v_id the_id
              FROM dual;
    END;

কখনও কখনও, অ্যাপ্লিকেশন কোড থেকে কার্যকর করার সময় এই পদ্ধতিটি একটি ত্রুটি ফেরায়।

ORA-01400: cannot insert NULL into ("DALLAS"."X"."THE_ID") 
ORA-06512: at "DALLAS.X_PKG", line 40 
ORA-06512: at line 1

প্রাসঙ্গিক বা নাও হতে পারে এমন বিশদ:

  • ওরাকল ডেটাবেস 11 জি এন্টারপ্রাইজ সংস্করণ প্রকাশ 11.2.0.1.0 - 64 বিট উত্পাদন
  • প্রক্রিয়াটি মাইক্রোসফ্ট.প্র্যাকটিসেস.এন্টারপ্রাইজলিবারি - ডেটা.অরাকল.অরাকল্যাড ডাটাবেস.এক্সেকিউট রেডার (ডিবিকম্যান্ড কমান্ড) এর মাধ্যমে কার্যকর করা হয়
  • অ্যাপ্লিকেশনটি সুস্পষ্ট লেনদেনে কলটি মোড়ায় না।
  • সন্নিবেশ মাঝে মাঝে ব্যর্থ হয় - 1% এরও কম

কোন পরিস্থিতিতে x_seq.nextvalনাল হতে পারে?


নির্বাচন এবং সন্নিবেশকরণের মধ্যে কতটি কোড? Code কোডটিতে কোনও বিগইন..এইন্ড ব্লক বা কোনও ছাড়ের বিবৃতি রয়েছে? V_id কোডটিতে কি আদৌ রেফারেন্স হয়? দেখতে কিছুটা অদ্ভুত লাগছে। আপনি যদি বিবৃতি দেওয়ার পরে সরাসরি "যদি আইফ ভি_আইডি হয় তবে .... শেষ অবধি" ব্লক স্থাপন করতে পারেন এবং যদি ক্রমটি v_id এ নাল বরাদ্দ করে তবে কোথাও কিছু ডিবাগিং আউটপুট ছেড়ে যেতে পারেন? এটি বা মোড়কটি একটি বিগইন..এক্সসিপিশন ব্লকে নির্বাচন করুন, কারণ এমন কিছু ঘটতে পারে যা ধরা পড়ে নি। একটি শেষ কথা - আপনি যে টেবিলটি serোকাচ্ছেন তাতে কোনও ট্রিগার রয়েছে যা এর কারণ হতে পারে?
ফিলি

@ ফিল - নির্বাচনটি সন্নিবেশ করার আগেই হয়। প্রাগ বিগইন / শেষ ব্যতীত আর কোনও বিগইন, সমাপ্তি বা এক্সেসপশন নেই। v_idকেবল সিক্যুয়েন্স সিলেক্ট, সন্নিবেশ এবং চূড়ান্ত কার্সারে উল্লেখ করা হয়। আমাদের পরবর্তী পদক্ষেপটি ছিল ডিবাগিং কোড যুক্ত করা। আমাদের ফলাফলগুলির জন্য অপেক্ষা করতে হতে পারে কারণ এটি কেবলমাত্র উত্পাদন এবং খুব কম সময়ে ঘটে। একটি ট্রিগার রয়েছে যা নিরীক্ষার টেবিলটিতে প্রবেশ করে। আমি ধূমপান বন্দুক দিয়ে ঝাঁকুনি করেছি। ট্রিগার ছাড়াই অন্যান্য টেবিলেও সমস্যাটি মাঝেমধ্যে ঘটে। দেখার জন্য ধন্যবাদ।
কর্বিন মার্চ

5
এই মুহুর্তে আমি কেবলমাত্র সত্যিই ভাবতে পারি তা হ'ল: নতুন.টি_আইডিটি কোনওভাবে টেবিল এক্স
ট্রিগারটিতে

@ ফিল: এটি অবশ্যই সমস্যার কারণ। আপনি এটি একটি উত্তর করা উচিত।
রেনে নিনফেনিগার

@ রেননিফেনিগার - এটি সমস্যাগুলি প্রোগগুলিতেও দেখা যায় যা ট্রিগার ছাড়াই টেবিলগুলিতে .োকানো হয়। এটি একটি সমান সুযোগ বাগ বলে মনে হচ্ছে।
কর্বিন মার্চ

উত্তর:


4

আমি বেশ নিশ্চিত যে এটি আপনার কোড, বা আপনি যে নেট নেট ড্রাইভারটি ব্যবহার করছেন তার একটি নিদর্শন হিসাবে শেষ হবে। খাঁটি এসকিউএল - পিএল / এসকিউএল ব্যবহার করে আমি আপনার জন্য একটি চটজলদি ডেমো ছুঁড়েছি এবং হারিয়ে যাওয়া অনুক্রমের মানটি কখনই পাই না। ঘটনাক্রমে আপনি যে রেফ কার্সারটি ব্যবহার করছেন সম্ভবত এটি অপ্রয়োজনীয় এবং সম্ভবত প্রভাবের প্রভাব এবং কোডের পাঠযোগ্যতা - আমার ডেমোতে একটি insert_record2 পদ্ধতি অন্তর্ভুক্ত রয়েছে যা রেফ কার্সার সংস্করণের জন্য আমার ল্যাপটপে 26 সেকেন্ডের প্রায় 26% প্রায় 10 শতাংশের বেশি দ্রুত সম্পাদন করে। আমি কমপক্ষে আরও সহজে বুঝতে সহজ মনে করি। আপনি অবশ্যই অডিট ট্রিগার সহ আপনার টেস্ট ডাটাবেস সম্পূর্ণরূপে একটি সংশোধিত সংস্করণ চালাতে পারেন।

/* 
demo for dbse 
assumes a user with create table, create sequence, create procedure pivs and quota. 

*/

drop table dbse13142 purge;

create table dbse13142(
    the_id number not null
,   name   varchar2(20)
,   userid number)
;

drop sequence x_seq;
CREATE SEQUENCE  X_SEQ NOCACHE  NOORDER  NOCYCLE ;

create or replace PROCEDURE Insert_Record
                (p_name    IN  VARCHAR2,                
                 p_userid  IN  INTEGER,
                 cur_out   OUT sys_refcursor)
    IS
        v_id NUMBER := 0;
    BEGIN
        -- Get id value from sequence
        SELECT x_seq.nextval
          INTO v_id
          FROM dual;

        -- Line below is X_PKG line 40
        INSERT INTO dbse13142
            (the_id,            
             name,                        
             userid)
          VALUES
            (v_id,
             p_name,                        
             p_userid);

        -- Return new id
        OPEN cur_out FOR
            SELECT v_id the_id
              FROM dual;
    END;
/


create or replace PROCEDURE Insert_Record2
                (p_name    IN  VARCHAR2,                
                 p_userid  IN  INTEGER,
                 p_theid   OUT dbse13142.the_id%type)
    IS
    BEGIN
        -- Get id value from sequence
        SELECT x_seq.nextval
          INTO p_theid
          FROM dual;

        -- Line below is X_PKG line 40
        INSERT INTO dbse13142
            (the_id,            
             name,                        
             userid)
          VALUES
            (p_theid,
             p_name,                        
             p_userid);
    END;
/

set timing on

declare
   c sys_refcursor;
begin   
for i in 1..100000 loop
   insert_record('User '||i,i,c);
   close c;
end loop;
commit;
end;
/

select count(*) from dbse13142;
truncate table dbse13142;

declare
  x number;
begin   
for i in 1..100000 loop
   insert_record2('User '||i,i,x);
end loop;
commit;
end;
/

select count(*) from dbse13142;
truncate table dbse13142;

1
উপায় অনুসারে the_id কলামের জন্য একটি ট্রিগার ব্যবহারের প্রচলিত পদ্ধতির সাথে সংস্করণ এবং নীচের পদ্ধতিটি দ্রুত প্রসেসার ইনসার্ট_রেকর্ড 3 তৈরি করুন বা প্রতিস্থাপন করুন (dbse13142.Name% প্রকারের p_name, pbuserid in dbse13142.userid% প্রকার, p_theid OUT dbse13142 .the_id% টাইপ) dbse13142 এর মধ্যে প্রবেশ শুরু করা হয়েছে (নাম, ইউজারিড) VALUES (পি_নেম, পি_উসারিড )__ পি তেথায় ফেরত দিচ্ছে; শেষ; /
নিলাল লিচফিল্ড

সম্মত হয়েছেন যে এটি অ্যাপ কোড বা ড্রাইভারের ক্ষেত্রে সম্ভবত সমস্যা। আমি শুধু কৌতূহলী যা পার্শ্ব প্রতিক্রিয়া হিসাবে নাল পরের কারণ হতে পারে। বিরক্তিকর। পারফরম্যান্স টিপ জন্য ধন্যবাদ। এটি দলকে পরামর্শ দেওয়ার পক্ষে ভাল পরামর্শ।
কর্বিন মার্চ

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

আমি তৈরি পয়েন্টগুলি বুঝতে পারি। ট্রিগারগুলির সাথে এবং ছাড়াই টেবিলগুলিতে সন্নিবেশ করানোতে প্রোসগুলিতে সমস্যাটি উপস্থিত থাকে যাতে ট্রিগারটির প্রয়োজন হয় না। ট্রিগার উপস্থিত থাকলে এটি কেবল নিরীক্ষার টেবিলের মধ্যে সন্নিবেশ করে। আমি নিশ্চিত করেছি :new.the_idযে অচ্ছুত। আমি বুঝতে পারি আমার প্রশ্নটি দীর্ঘ শট। এটি আমার গুগল-ফু প্রতিরোধী এবং এখানে বেশ কয়েক জন লোকের মাথা আঁচড়ান। আমি ঠিক বুঝতে পেরেছি যে কেউ পর্যাপ্ত চক্ষুদানের লক্ষণটি (এবং চিকিত্সা) চিনতে পারে। দেখার জন্য ধন্যবাদ।
কর্বিন মার্চ

2

একটি পরীক্ষা কেস করার চেষ্টা করুন। একটি ডামি টেবিল তৈরি করুন এবং ডাটাবেস থেকে আপনার সিকোয়েন্স ব্যবহার করে 100,000 রেকর্ড সন্নিবেশ করুন। আমি বাজি ধরছি আপনার কোনও সমস্যা হবে না। পরবর্তী আপনার অ্যাপ্লিকেশন থেকে একই জিনিস thingোকানোর চেষ্টা করুন।

এটি কি অন্য সমস্যা যেমন ওরাকল ক্লায়েন্টের অমিলের কারণে ঘটতে পারে?

সমস্যা সমাধান না করেও সমস্যার সমাধান করবে এমন আরও একটি সমাধান হ'ল টেবিলে একটি ট্রিগার যুক্ত করা।
ডালাস.এক্সএফ টেবিলে সন্নিবেশ করার আগে: যদি_দুটি নাল হয় তবে তারা দ্বিগুণ থেকে নির্বাচন করুন শেষ যদি;


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

0

আমার কাছে এখনও মন্তব্য করার জন্য প্রাইভেলডেজ নেই, সুতরাং এটি উত্তর হিসাবে লিখছেন: যেহেতু আপনি ওরাকল সংস্করণ> = 11.1 ব্যবহার করছেন, এটি এসকিউএল এর পরিবর্তে পিএল / এসকিউএল এক্সপ্রেশনগুলিতে সিকোয়েন্সগুলি মঞ্জুরি দেয় , তাই চেষ্টা করে দেখুন:

   v_id := x_seq.nextval;

এর পরিবর্তে:

 -- Get id value from sequence
    SELECT x_seq.nextval
      INTO v_id
      FROM dual;

অথবা, যদিও আমি ".currval" ব্যবহার করার সময় সন্দেহ / সমস্যাগুলি শুনেছি, তবে v_id এর পৃথক কার্যভারটি বাদ দিতে পারেন এবং কেবল এই কোডটি ব্যবহার করবেন ?:

 -- Line below is X_PKG line 40
        INSERT INTO X
            (the_id,            
             name,                        
             update_userid)
          VALUES
            (x_seq.nextval,
             p_name,                        
             p_userid);

        -- Return new id
        OPEN cur_out FOR
            SELECT x_seq.currval the_id
              FROM dual;

দুঃখিত, এটি চেষ্টা করার জন্য আমার কাছে এখন 11-ইগাস্টের উদাহরণ নেই।


এটি অবশ্যই কোনও পার্থক্য করে না। আমি select into...9 আই এবং 10 জি হিসাবে 11 তে ব্যবহার করি । 11+ এর একমাত্র উপকারিতা আপনি উল্লেখ করেছেন হিসাবে এটি সুস্পষ্টভাবে উল্লেখ করতে সক্ষম হয়।
বেন
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.