কত বেশি নির্ভরশীল ইনজেকশন?


38

আমি এমন একটি প্রকল্পে কাজ করি যা (স্প্রিং) ডিপেন্ডেন্সি ইনজেকশনটি আক্ষরিক অর্থে সমস্ত শ্রেণীর নির্ভরতা uses আমরা এমন এক পর্যায়ে আছি যেখানে স্প্রিং কনফিগারেশন ফাইলটি প্রায় 4000 লাইনে বেড়েছে। কিছুক্ষণ আগেই আমি ইউটিউবে চাচা ববের একটি আলোচনা দেখেছি (দুর্ভাগ্যক্রমে, আমি লিঙ্কটি খুঁজে পাইনি) যেখানে তিনি কেবলমাত্র কয়েকটি কেন্দ্রীয় নির্ভরতা (উদাহরণস্বরূপ কারখানা, ডাটাবেস,…) মূল উপাদানটিতে ইনজেকশন দেওয়ার পরামর্শ দিয়েছিলেন যা থেকে তারা তখন থাকবে will বিতরণ করা।

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

সুতরাং আমার প্রশ্নটি হ'ল আপনি যে কোনও সুবিধা বা অসুবিধাগুলি এক বা অন্য পদ্ধতির মধ্যে দেখেন। কোন ভাল অনুশীলন আছে? আপনার উত্তরের জন্য অনেক ধন্যবাদ!


3
4000 লাইন কনফিগারেশন ফাইল থাকা নির্ভরতা ইনজেকশনটির দোষ নয় ... এটি সমাধানের প্রচুর উপায় রয়েছে: ফাইলটিকে একাধিক ছোট ফাইলগুলিতে রূপান্তর করুন, টীকাগুলি ভিত্তিক ইনজেকশনে স্যুইচ করুন, এক্সএমএল এর পরিবর্তে জাভা কনফিগ ফাইলগুলি ব্যবহার করুন। মূলত, আপনি যে সমস্যার মুখোমুখি হচ্ছেন তা হ'ল আপনার অ্যাপ্লিকেশনটির নির্ভরতা ইনজেকশন প্রয়োজনের জটিলতা এবং আকার পরিচালনা করতে ব্যর্থতা।
পারে_ফ্যাক্টর

1
@ মায়াবে_ফ্যাক্টর টিএল; ডিআর প্রকল্পটিকে ছোট ছোট ভাগে বিভক্ত করে।
ওয়ালফ্র্যাট

উত্তর:


44

সর্বদা হিসাবে, এটি নির্ভর করে ™। উত্তরটি যে সমস্যার সমাধান করার চেষ্টা করা হচ্ছে তার উপর নির্ভর করে। এই উত্তরে আমি কয়েকটি সাধারণ অনুপ্রেরণাকারী বাহিনীকে সম্বোধন করার চেষ্টা করব:

ছোট কোড বেসগুলিতে পছন্দ করুন

আপনার কাছে স্প্রিং কনফিগারেশন কোডের 4,000 লাইন থাকলে, আমি মনে করি যে কোড বেসটিতে কয়েক হাজার ক্লাস রয়েছে।

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

আমি আমার সীমাবদ্ধ অভিজ্ঞতার ভিত্তিতে এই পরামর্শটি ভিত্তি করে চলেছি, যেহেতু আমি আমার বেশিরভাগ ক্যারিয়ারের জন্য ওয়েব-ভিত্তিক লাইন অফ বিজনেস কোড লিখেছি। আমি কল্পনা করতে পারি যে আপনি যদি কোনও ডেস্কটপ অ্যাপ্লিকেশন, বা একটি এমবেডেড সিস্টেম বা অন্যগুলি বিকাশ করেন তবে জিনিসগুলি আলাদা করা শক্ত।

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

খাঁটি ডিআই

আমি এখনও বুঝতে পারি যে এই প্রশ্নটি একটি বিদ্যমান পরিস্থিতি উপস্থাপন করে, আমি খাঁটি ডিআই-র প্রস্তাব দিই । ডিআই কনটেইনার ব্যবহার করবেন না, তবে আপনি যদি করেন তবে কমপক্ষে কনভেনশন-ভিত্তিক রচনাটি প্রয়োগ করতে এটি ব্যবহার করুন

স্প্রিংয়ের সাথে আমার কোনও ব্যবহারিক অভিজ্ঞতা নেই তবে আমি ধরে নিচ্ছি যে কনফিগারেশন ফাইল দ্বারা একটি এক্সএমএল ফাইল অন্তর্ভুক্ত।

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

সমস্যার সমাধানের জন্য তুলনামূলকভাবে তুলনা করে, নির্ভরতা ইনজেকশন কনফিগারেশন ফাইলগুলি কনফিগারেশন জটিলতার ঘড়িতে ভুল জায়গা দখল করে ।

মোটা দানাদার নির্ভরতা ইনজেকশনের ক্ষেত্রে

আমি মোটা দানাযুক্ত নির্ভরতা ইনজেকশনের জন্য একটি মামলা করতে পারি। আমি সূক্ষ্ম দানযুক্ত নির্ভরতা ইনজেকশনের জন্যও একটি মামলা করতে পারি (পরবর্তী বিভাগটি দেখুন)।

আপনি যদি কেবলমাত্র কয়েকটি 'কেন্দ্রীয়' নির্ভরতা ইনজেকশন করেন তবে বেশিরভাগ শ্রেণি এটির মতো দেখাবে:

public class Foo
{
    private readonly Bar bar;

    public Foo()
    {
        this.bar = new Bar();
    }

    // Members go here...
}

এই এখনও ফিট নকশা নিদর্শন এর বর্গ উত্তরাধিকার উপর অনুগ্রহ বস্তুর রচনা , কারণ Fooরচনা Bar। একটি রক্ষণাবেক্ষণের দৃষ্টিকোণ থেকে, এটি এখনও রক্ষণাবেক্ষণযোগ্য হিসাবে বিবেচিত হতে পারে, কারণ যদি আপনার রচনাটি পরিবর্তন করতে হয় তবে আপনি কেবল উত্স কোডটি সম্পাদনা করুন Foo

এটি নির্ভরতা ইনজেকশনের চেয়ে কমই রক্ষণাবেক্ষণযোগ্য। প্রকৃতপক্ষে, আমি বলব যে Barনির্ভরতা ইনজেকশন সহ অন্তর্নিহিত নির্দেশ অনুসরণ না করে সরাসরি যে শ্রেণিটি ব্যবহার করে সেগুলি সম্পাদনা করা আরও সহজ ।

নির্ভরতা ইনজেকশন সম্পর্কিত আমার বইয়ের প্রথম সংস্করণে , আমি অস্থির এবং স্থিতিশীল নির্ভরতার মধ্যে পার্থক্য করি।

উদ্বায়ী নির্ভরতাগুলি সেই নির্ভরতাগুলি যেগুলি আপনাকে ইনজেকশন বিবেচনা করা উচিত। তারা সহ

  • নির্ভরতা যা সংকলনের পরে পুনরায় কনফিগার করতে হবে
  • অন্য দলের সমান্তরালে নির্ভরতা বিকাশ
  • অ-নিষেধাজ্ঞামূলক আচরণ, বা পার্শ্ব-প্রতিক্রিয়া সহ আচরণের সাথে নির্ভরশীলতা

অন্যদিকে স্থিতিশীল নির্ভরতা হ'ল নির্ভরতা যা সঠিকভাবে সংজ্ঞায়িত পদ্ধতিতে আচরণ করে। এক অর্থে, আপনি তর্ক করতে পারেন যে এই পার্থক্যটি মোটা-দানাদার নির্ভরতা ইনজেকশনের ক্ষেত্রে তৈরি করে, যদিও আমি অবশ্যই স্বীকার করতে পারি যে বইটি লেখার সময় আমি পুরোপুরি বুঝতে পারি নি।

তবে পরীক্ষার দৃষ্টিকোণ থেকে এটি ইউনিট পরীক্ষাকে শক্ত করে তোলে testing আপনি আর Fooস্বতন্ত্র ইউনিট পরীক্ষা করতে পারবেন না Barজেবি রেইনসবার্গার যেমন ব্যাখ্যা করেছেন , ইন্টিগ্রেশন টেস্টগুলি জটিলতার সমন্বয় বিস্ফোরণে ভুগছে। আপনি যদি 4-5 ক্লাসের একীকরণের মাধ্যমে সমস্ত পথ কভার করতে চান তবে আপনাকে আক্ষরিকভাবে কয়েক হাজার পরীক্ষার কেস লিখতে হবে।

এর পাল্টা যুক্তিটি হ'ল প্রায়শই, আপনার কাজটি কোনও ক্লাস প্রোগ্রাম করা নয়। আপনার কাজটি এমন একটি সিস্টেম বিকাশ করা যা কিছু নির্দিষ্ট সমস্যা সমাধান করে। এটি আচরণ-চালিত বিকাশের পিছনে অনুপ্রেরণা (বিডিডি)।

এ সম্পর্কে আর একটি মতামত উপস্থাপন করেছেন ডিএইচএইচ, যিনি দাবি করেছেন যে টিডিডি পরীক্ষা-প্ররোচিত নকশার ক্ষতি হতে পারে । তিনি মোটা দানাযুক্ত ইন্টিগ্রেশন পরীক্ষার পক্ষেও রয়েছেন।

আপনি যদি সফ্টওয়্যার বিকাশের বিষয়ে এই দৃষ্টিভঙ্গি গ্রহণ করেন, তবে মোটা-দানাদার নির্ভরতা ইনজেকশনটি বোঝায় makes

সূক্ষ্ম দানযুক্ত নির্ভরতা ইনজেকশনের ক্ষেত্রে

অন্যদিকে সূক্ষ্ম দানযুক্ত নির্ভরতা ইনজেকশনটিকে সমস্ত জিনিস ইনজেক্ট হিসাবে বর্ণনা করা যেতে পারে !

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

বিডিডি-র প্রবক্তারা এই যুক্তিটির সাথে পাল্টাবেন যে আপনাকে কোনও কোডের পাথ পরীক্ষার সাথে আবরণ করার দরকার নেই। আপনার কেবল ব্যবসায়ের মান উত্পন্ন করে তাদের কভার করতে হবে।

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

এটি আমাকে সূক্ষ্ম-শস্যযুক্ত নির্ভরতা ইনজেকশনের পক্ষে তুলনা করেছে, কারণ এটি আমাকে বিচ্ছিন্নভাবে সমস্ত বস্তুর আক্রমণকারীদের পরীক্ষা করতে সক্ষম করে।

কার্যকরী প্রোগ্রামিং পছন্দ

আমি জরিমানা-নির্ভরশীল নির্ভরতা ইনজেকশনটির দিকে ঝুঁকতে থাকাকালীন, আমি অন্য কারণগুলির মধ্যে আমার জোরকে ফাংশনাল প্রোগ্রামিংয়ের দিকে সরিয়ে নিয়েছি কারণ এটি অভ্যন্তরীণভাবে পরীক্ষামূলক

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

স্ট্যাটিকালি টাইপড ফাংশনাল প্রোগ্রামিং পছন্দ করুন Favor

এই মুহুর্তে, আমি মূলত অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিং (ওওপি) ছেড়ে দিয়েছি, যদিও ওওপির অনেকগুলি সমস্যা অন্তর্নিহিতভাবে জাভা এবং সি # এর মতো মূলধারার ভাষাগুলির সাথে ধারণার চেয়েও বেশি রয়েছে।

মূলধারার ওওপি ভাষাগুলির সমস্যা হ'ল সংযুক্ত বিস্ফোরণজনিত সমস্যা এড়ানো অসম্ভবের কাছাকাছি, যা অনিচ্ছাকৃত, রান-টাইম ব্যতিক্রমগুলির দিকে পরিচালিত করে। অন্যদিকে হাস্কেল এবং এফ # এর মতো স্ট্যাটিকালি টাইপ করা ভাষাগুলি আপনাকে টাইপ সিস্টেমে অনেক সিদ্ধান্ত পয়েন্টকে এনকোড করতে সক্ষম করে। এর অর্থ হ'ল হাজার টেস্ট লেখার পরিবর্তে, সংকলকটি আপনাকে কেবলমাত্র সমস্ত সম্ভাব্য কোড পাথ (কিছুটা হলেও এটি রূপোর বুলেট) মোকাবেলা করেছেন কিনা তা আপনাকে জানায়।

এছাড়াও, নির্ভরতা ইনজেকশন কার্যকর নয় । সত্যিকারের ক্রিয়ামূলক প্রোগ্রামিং অবশ্যই নির্ভরতার সম্পূর্ণ ধারণাটি প্রত্যাখ্যান করতে পারে । ফলাফলটি সহজ কোড।

সারাংশ

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

শেষ পর্যন্ত, আমার অনুপ্রেরণা দ্রুত প্রতিক্রিয়া। তবুও, ইউনিট টেস্টিং প্রতিক্রিয়া পাওয়ার একমাত্র উপায় নয়


1
আমি এই উত্তরটি সত্যিই পছন্দ করি এবং বিশেষত বসন্তের প্রসঙ্গে ব্যবহৃত এই বিবৃতি: "এক্সএমএল ব্যবহার করে নির্ভরতা কনফিগার করা উভয় পৃথিবীর মধ্যে সবচেয়ে খারাপ First ফাইলটি যে কোডটি প্রতিস্থাপনের চেষ্টা করে তার চেয়ে সহজেই বড় হতে পারে। "
থমাস

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

1

বিশাল ডিআই সেটআপ ক্লাস একটি সমস্যা। তবে কোডটি এটি প্রতিস্থাপন করে দেখুন।

আপনাকে সেই সমস্ত পরিষেবা এবং কী নন তা ইনস্ট্যান্ট করতে হবে। এটি করার কোডটি হয় হয় app.main()প্রারম্ভিক বিন্দুতে এবং ম্যানুয়ালি ইনজেকশনের মাধ্যমে, বা this.myService = new MyService();ক্লাসের মতো শক্তভাবে মিলিত হবে ।

আপনার সেটআপ শ্রেণীর আকারটিকে একাধিক সেটআপ ক্লাসে বিভক্ত করে হ্রাস করুন এবং প্রোগ্রামের সূচনা পয়েন্ট থেকে তাদের কল করুন। অর্থাত।

main()
{
   var c = new diContainer();
   var service1 = diSetupClass.SetupService1(c);
   var service2 = diSetupClass.SetupService2(c, service1); //if service1 is required by service2
   //etc

   //main logic
}

অন্যান্য সিআই সেটআপ পদ্ধতিতে সেগুলি দেওয়া ব্যতীত আপনার পরিষেবা 1 বা 2 উল্লেখ করার দরকার নেই।

এটি কনটেইনার থেকে নেওয়ার চেষ্টা করার চেয়ে এটি ভাল কারণ এটি সেটআপগুলি কল করার ক্রম কার্যকর করে।


1
যারা এই ধারণাটি আরও খতিয়ে দেখতে চান (প্রোগ্রাম স্টার্ট পয়েন্টে আপনার শ্রেণি গাছ তৈরি করা), তাদের সন্ধানের জন্য সেরা শব্দটি হল "কম্পোজিশন রুট"
e_i_pi

@ ইয়ান যে ciপরিবর্তনশীল কি ?
সুপারজোজ

স্থিতিশীল পদ্ধতি সহ আপনার সিআই সেটআপ ক্লাস
ইভান

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