ভারতে ক্যাশে ব্যবহার করে এমন একক পরীক্ষার পদ্ধতির জন্য সেরা অনুশীলনগুলি?


17

আমার কাছে প্রচুর ব্যবসায়িক যুক্তিযুক্ত পদ্ধতি রয়েছে যা ক্যাশে থেকে অবজেক্টের তালিকা এবং ফিল্টারিং (ফিল্টারিং সহ) পুনরুদ্ধার করে।

বিবেচনা

IList<TObject> AllFromCache() { ... }

TObject FetchById(guid id) { ... }

IList<TObject> FilterByPropertry(int property) { ... }

Fetch..এবং Filter..কল করবে AllFromCacheযা ক্যাশে জনবহুল করবে এবং যদি এটি না থাকে তবে ফিরে আসবে এবং যদি তা থাকে তবে তা থেকে ফিরে আসবে।

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

আমি টেস্টআইনিটিয়ালাইজে ক্যাশে জনবহুল করা এবং টেস্টক্লিনআপে অপসারণ বিবেচনা করেছি কিন্তু এটি আমার কাছে সঠিক মনে হয় না, (এটি ভাল হতে পারে)।

উত্তর:


18

আপনি যদি সত্য ইউনিট টেস্টগুলি চান, তবে আপনাকে ক্যাশে উপহাস করতে হবে: একটি মক অবজেক্ট লিখুন যা ক্যাশের মতো একই ইন্টারফেস প্রয়োগ করে, তবে এটি ক্যাশে হওয়ার পরিবর্তে এটি যে কলগুলি পেয়ে থাকে তার উপর নজর রাখে এবং সর্বদা আসল কী ফিরিয়ে দেয় ক্যাশে পরীক্ষার কেস অনুযায়ী ফিরতে হবে।

অবশ্যই ক্যাশে নিজেও তখন ইউনিট টেস্টিংয়ের প্রয়োজন হয়, যার জন্য আপনাকে যে কোনও কিছুতে এটি নির্ভর করে তা উপহাস করতে হবে, ইত্যাদি।

আপনি যা বর্ণনা করছেন, আসল ক্যাশে অবজেক্টটি ব্যবহার করে তবে এটি একটি পরিচিত অবস্থায় আরম্ভ করে এবং পরীক্ষার পরে পরিষ্কার করা, এটি আরও বেশি সংহতকরণ পরীক্ষার মতো, কারণ আপনি কনসার্টে বেশ কয়েকটি ইউনিট পরীক্ষা করছেন।


+1 এটি নির্ভুলভাবে সেরা পন্থা। যুক্তি পরীক্ষা করতে ইউনিট পরীক্ষা করে তারপরে যা প্রত্যাশা করা হয়েছে তা ক্যাশে যাচাই করার জন্য ইন্টিগ্রেশন টেস্টটি প্রকৃতপক্ষে।
টম স্কুয়ার্স

10

একক দায়িত্ব পুঁজি আপনার সেরা বন্ধু এখানে।

সবার আগে, AllFromCache () একটি সংগ্রহস্থল শ্রেণিতে সরান এবং এটিকে getAll () বলে। এটি ক্যাশে থেকে পুনরুদ্ধার করা সংগ্রহস্থলের একটি বাস্তবায়ন বিশদ এবং কলিং কোড দ্বারা জানা উচিত নয়।

এটি আপনার ফিল্টারিং ক্লাসটিকে টেস্ট করা দুর্দান্ত এবং সহজ করে তোলে। আপনি এটি কোথা থেকে পাচ্ছেন তা এখন আর চিন্তা করে না।

দ্বিতীয়ত, ক্যাচিংয়ের মোড়কে ক্লাসটি আবরণ করুন যা ডেটাবেস থেকে ডেটা (বা যেখানেই) পায়।

এওপি এটির জন্য একটি ভাল কৌশল। এটি এমন কয়েকটি জিনিসের একটি যা এটি খুব ভাল।

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

যেমন।

public class ProductManager
{
    private IProductRepository ProductRepository { get; set; }

    public ProductManager
    {
        ProductRepository = productRepository;
    }

    Product FetchById(guid id) { ... }

    IList<Product> FilterByPropertry(int property) { ... }
}

public interface IProductRepository
{
    IList<Product> GetAll();
}

public class SqlProductRepository : IProductRepository
{
    public IList<Product> GetAll()
    {
        // DB Connection, fetch
    }
}

public class CachedProductRepository : IProductRepository
{
    private IProductRepository ProductRepository { get; set; }

    public CachedProductRepository (IProductRepository productRepository)
    {
        ProductRepository = productRepository;
    }

    public IList<Product> GetAll()
    {
        // Check cache, if exists then return, 
        // if not then call GetAll() on inner repository
    }
}

আপনি কীভাবে প্রোডাক্ট ম্যানেজার থেকে সংগ্রহস্থল বাস্তবায়ন জ্ঞান সরিয়েছেন? আপনি কীভাবে একক দায়বদ্ধতার নীতিমালাকে মান্য করেছেন এমন এক ক্লাস যা ডেটা উত্তোলন পরিচালনা করে, এমন একটি শ্রেণি যা ডেটা পুনরুদ্ধার পরিচালনা করে এবং একটি শ্রেণি যা ক্যাশে পরিচালনা করে?

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

productManager = new ProductManager(
                         new SqlProductRepository()
                         );

productManager = new ProductManager(
                         new CachedProductRepository(new SqlProductRepository())
                         );

(আপনি যদি কোনও আইওসি পাত্রে ব্যবহার করেন তবে আরও ভাল how কীভাবে মানিয়ে নেবেন তা স্পষ্ট হওয়া উচিত))

এবং, আপনার প্রোডাক্ট ম্যানেজার পরীক্ষায়

IProductRepository repo = MockRepository.GenerateStrictMock<IProductRepository>();

একেবারে ক্যাশে পরীক্ষা করার দরকার নেই।

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

এবং, আমি উপরে প্রস্তাবিত পরিবর্তনগুলি করেছি, সেখানে পরীক্ষা করার মতো এত যুক্তি নেই really সত্যই গুরুত্বপূর্ণ পরীক্ষা, ফিল্টারিং পদ্ধতিটি সেখানে থাকবে এবং গেটএল () এর বিশদ থেকে সম্পূর্ণ বিমূর্ত হবে। গেটএল () ঠিক ... সবই পেয়েছে। কোথাও থেকে.


আপনি যদি প্রোডাক্ট ম্যানেজারে ক্যাশেড প্রোডাক্ট রেপোসিটরি ব্যবহার করে থাকেন তবে এসকিউএলপ্রডাক্টরেপোজিটরিতে থাকা পদ্ধতিগুলি ব্যবহার করতে চান তবে আপনি কী করবেন?
জোনাথন

@ জোনাথন: "কেবলমাত্র একটি সংগ্রহশালা এবং একটি ক্যাচিং র্যাপার রয়েছে যা একই ইন্টারফেস ব্যবহার করে" - তাদের যদি একই ইন্টারফেস থাকে তবে আপনি একই পদ্ধতি ব্যবহার করতে পারেন। কলিং কোডটি বাস্তবায়ন সম্পর্কে কিছু জানার দরকার নেই।
pdr

3

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

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


1

আমি টেস্টআইনিটাইজালাইজে ক্যাশে পপুলেশন করা এবং টেস্টক্লিনআপে অপসারণ বিবেচনা করেছি কিন্তু এটি আমার কাছে সঠিক মনে হয় না

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


0

আমি এমন কয়েকটি পরীক্ষায় কাজ করছি যা সম্প্রতি ক্যাশে ব্যবহার করে। আমি ক্লাসের চারপাশে একটি মোড়ক তৈরি করেছি যা ক্যাশে নিয়ে কাজ করে এবং তারপরে জোর দিয়েছিল যে এই মোড়কটি বলা হচ্ছে।

আমি এটি মূলত করলাম কারণ ক্যাশে নিয়ে কাজ করে এমন বিদ্যমান বর্গ স্থির ছিল।


0

দেখে মনে হচ্ছে আপনি ক্যাচিং লজিকটি পরীক্ষা করতে চান তবে জনবহুল যুক্তি নয়। সুতরাং আমি আপনাকে পরামর্শ দেব যে আপনি যা পরীক্ষা করার দরকার নেই তা উপহাস করুন - জনবহুল।

আপনার AllFromCache()পদ্ধতিটি ক্যাশেটি পপুলিংয়ের যত্ন নেয় এবং মানগুলির সরবরাহকারী হিসাবে এটি অন্য কোনও কিছুতে অর্পণ করা উচিত। সুতরাং আপনার কোড মত লাগবে

private Supplier<TObject> supplier;

IList<TObject> AllFromCache() {
    if (!cacheInitialized) {
        //whatever logic needed to fill the cache
        cache.putAll(supplier.getValues());
        cacheInitialized = true;
    }

    return  cache.getAll();
}

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

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