আপনি কি আমাকে মোক কলব্যাক বুঝতে সাহায্য করতে পারেন?


100

মোক ব্যবহার করে দেখেছি Callbackকিন্তু কীভাবে এটি ব্যবহার করতে হয় তা বোঝার জন্য আমি একটি সাধারণ উদাহরণ খুঁজে পাইনি।

আপনার কাছে একটি ছোট কাজ করার স্নিপেট রয়েছে যা এটি কখন এবং কখন ব্যবহার করতে হবে তা স্পষ্টভাবে ব্যাখ্যা করে?

উত্তর:


85

Https://github.com/Moq/moq4/wiki/Quickstart এ বীট করা শক্ত

যদি এটি যথেষ্ট পরিমাণে পরিষ্কার না হয় তবে আমি ডক বাগটি কল করব ...

সম্পাদনা: আপনার স্পষ্টির জবাবে ...

আপনার সম্পাদিত প্রতিটি উপহাসের পদ্ধতির Setupজন্য, আপনি এই জাতীয় জিনিসগুলি নির্দেশ করতে পারবেন:

  • ইনপুটগুলিতে বাধা
  • যে পথে / ফেরতের মান (যদি সেখানে থাকে) প্রাপ্ত করতে হয় তার জন্য মান

.Callbackপ্রক্রিয়া বলে "আমি এখন এটি ব্যাখ্যা করতে পারবেন না, কিন্তু একটি কল ভালো আকৃতির ঘটে, আমাকে ফিরিয়ে কল এবং নিজের কৃতকর্মের করা প্রয়োজন করব"। একই অনর্গল কল চেইনের অংশ হিসাবে, আপনি .Returns"এর মাধ্যমে ফলাফলটি (যদি থাকে তবে) নিয়ন্ত্রণ করতে পারেন । কিউএস উদাহরণগুলিতে, একটি উদাহরণ হ'ল তারা প্রতিবার ফেরত আসা মানকে বাড়িয়ে তোলে।

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

জাস্টিন ইথেরেজের মক সিরিজের 4 অংশের 3 টি এটি কভার করে, এবং এখানে কলব্যাকের আরও একটি উদাহরণ রয়েছে

কলব্যাকের একটি সহজ উদাহরণ মক পোস্টের সাথে কলব্যাকগুলি ব্যবহার করে পাওয়া যাবে ।


4
হাই রুবেন আমি মোক শিখছি এবং আপনার যদি ভাল লাগে তবে কীভাবে কীভাবে এটি ব্যবহার করতে হয় তা বোঝার জন্য আমি প্রচুর উদাহরণ বোল্ড করছি। আমার সমস্যাটি হ'ল আমি কখন এটি ব্যবহার করব তা বুঝতে পারি না Oএই সমস্যাটি সমাধান হয়ে গেলে আমি নিজের কোডটি লিখব I আপনি যদি নিজের কথায় এটি ব্যাখ্যা করে থাকেন আপনি কখন কলব্যাক ব্যবহার করবেন? ধন্যবাদ আপনার
সময়টির

17
মারতে কষ্ট [লিংক]? একদমই না. এই লিঙ্কটি আপনাকে কয়েক ডজন বিভিন্ন জিনিস কীভাবে করতে হবে তা দেখায় , তবে আপনাকে কেন সেগুলির কোনও প্রয়োজনের কথা বলবে না । যেগুলি ডকুমেন্টেশন উপহাস করার ক্ষেত্রে একটি সাধারণ সমস্যা, আমি এটি পেয়েছি। আমি খুঁজে পেয়েছি যে টিডিডি + বিদ্রূপের ভাল, স্পষ্ট ব্যাখ্যাগুলির সংখ্যা শূন্য আঙ্গুলের উপর নির্ভর করতে পারি। বেশিরভাগ জ্ঞানের একটি স্তর ধরে নিয়েছেন যা আমার কাছে থাকলে এটি আমার নিবন্ধটি পড়ার দরকার পড়েনি।
রায়ান লুন্ডি

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

"আমি যা করার দরকার তা করব এবং ফলাফলটি ফিরে আসতে বলি (যদি থাকে)" আমি মনে করি এটি বিভ্রান্তিকর, এএফআইইউর Callbackরিটার্ন মানটির সাথে কোনও সম্পর্ক নেই (যদি আপনি কোডের মাধ্যমে এটি সংযুক্ত না করেন)। মূলত এটি কেবল নিশ্চিত করে যে প্রতিটি আহ্বানের আগে বা পরে কলব্যাক বলা হয়েছিল (আপনি Returnsযথাক্রমে আগে বা পরে এটি বেঁধে ছিলেন কিনা তার উপর নির্ভর করে ), সরল এবং সাধারণ।
ওহাদ স্নাইডার

4
@ ওহাদস্কিনিডার আমার লিঙ্কটি অনুসরণ করছে ... আপনি সঠিক! আশ্চর্য (তবে সত্যিকার অর্থে যথেষ্ট আগ্রহী নয় যেমন মূককে দীর্ঘ সময়ের জন্য ব্যবহার করেননি) যদি ফ্লুয়েন্ট ইন্টারফেস বদলে যায় (সম্ভবত মনে হয় না, আমি ভুল ধারণা নিয়েছি এবং আমি যে জিনিসটির সাথে লিঙ্ক করেছি তা পড়ি না কারণ আমি সাধারণত এটি কাজ করব) স্বতঃপূরণ থেকে আমার)। আশা করি এই
সমাধানটি

60

একটি ডেটা পরিষেবাতে প্রেরিত কোনও সত্তা যা একটি সন্নিবেশ পরিচালনা করে তা পরীক্ষা করার জন্য কলব্যাক ব্যবহার করার উদাহরণ এখানে।

var mock = new Mock<IDataService>();
DataEntity insertedEntity = null;

mock.Setup(x => x.Insert(It.IsAny<DataEntity>())).Returns(1) 
           .Callback((DataEntity de) => insertedEntity = de);

বিকল্প জেনেরিক পদ্ধতি বাক্য গঠন:

mock.Setup(x => x.Insert(It.IsAny<DataEntity>())).Returns(1) 
           .Callback<DataEntity>(de => insertedEntity = de);

তারপরে আপনি এরকম কিছু পরীক্ষা করতে পারেন

Assert.AreEqual("test", insertedEntity.Description, "Wrong Description");

4
তর্কসাপেক্ষ যে নির্দিষ্ট ক্ষেত্রে (আপনি রাষ্ট্র বা আচরণ বিরুদ্ধে পরীক্ষার প্রকাশ করার চেষ্টা করছেন কিনা উপর নির্ভর করে) জন্য, এটি কিছু দৃষ্টান্ত ক্লিনার একটি ব্যবহার করতে হতে পারে It.Is<T>একটি Mock.Verifyতেম্প্স সঙ্গে পরীক্ষা যত্র তত্র আবর্জনা ফেলার পরিবর্তে। তবে +1 কারণ আমি বাজি ধরেছি যে প্রচুর লোক রয়েছে যা উদাহরণ থেকে সবচেয়ে ভাল কাজ করবে।
রুবেন বারটেলিংক

10

Callbackমোকে দুই ধরণের রয়েছে । কলটি ফিরে আসার আগেই ঘটে; কলটি রিটার্ন হওয়ার পরে অন্যটি ঘটে।

var message = "";
mock.Setup(foo => foo.Execute(arg1: "ping", arg2: "pong"))
    .Callback((x, y) =>
    {
        message = "Rally on!";
        Console.WriteLine($"args before returns {x} {y}");
    })
    .Returns(message) // Rally on!
    .Callback((x, y) =>
    {
        message = "Rally over!";
        Console.WriteLine("arg after returns {x} {y}");
    });

উভয় কলব্যাকগুলিতে, আমরা এটি করতে পারি:

  1. পদ্ধতির যুক্তিগুলি পরিদর্শন করুন
  2. ক্যাপচার পদ্ধতি আর্গুমেন্ট
  3. প্রাসঙ্গিক অবস্থা পরিবর্তন করুন

4
প্রকৃতপক্ষে, কলটি রিটার্নের আগে উভয়ই ঘটে (যতক্ষণ কলারের সাথে সম্পর্কিত)। স্ট্যাকওভারফ্লো . com/a/28727099/67824 দেখুন ।
ওহাদ স্নাইডার

8

Callbackমক এর কোনও পদ্ধতিতে কল করা হলে আপনি যে কোনও কাস্টম কোড চান তা কার্যকর করার একটি উপায় to এখানে একটি সাধারণ উদাহরণ:

public interface IFoo
{
    int Bar(bool b);
}

var mock = new Mock<IFoo>();

mock.Setup(mc => mc.Bar(It.IsAny<bool>()))
    .Callback<bool>(b => Console.WriteLine("Bar called with: " + b))
    .Returns(42);

var ret = mock.Object.Bar(true);
Console.WriteLine("Result: " + ret);

// output:
// Bar called with: True
// Result: 42

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

var cq = new ConcurrentQueue<bool>();
mock.Setup(f => f.Bar(It.IsAny<bool>())).Callback<bool>(cq.Enqueue);
Parallel.Invoke(() => mock.Object.Bar(true), () => mock.Object.Bar(false));
Console.WriteLine("Invocations: " + String.Join(", ", cq));

// output:
// Invocations: True, False

বিটিডব্লিউ "আগে Returns" এবং "পরে Returns" পার্থক্য বিভ্রান্তিকর দ্বারা বিভ্রান্ত করবেন না । আপনার কাস্টম কোডটি Returnsমূল্যায়ন করার পরে বা তার আগে চলবে কিনা এটি কেবল প্রযুক্তিগত পার্থক্য । কলারের দৃষ্টিতে, মানটি ফেরতের আগে দু'জনেই চলবে। প্রকৃতপক্ষে, যদি পদ্ধতিটি voidপুনরুদ্ধার হয় তবে আপনি কল করতে পারবেন না Returnsএবং এখনও এটি একই কাজ করে। আরও তথ্যের জন্য https://stackoverflow.com/a/28727099/67824 দেখুন


1

এখানে অন্যান্য ভাল উত্তরের উপরে, আমি একটি ব্যতিক্রম ছোঁড়ার আগে যুক্তি সম্পাদন করতে এটি ব্যবহার করেছি। উদাহরণস্বরূপ, আমাকে পরে যাচাইকরণের জন্য কোনও পদ্ধতিতে পাস করা সমস্ত বস্তু সংরক্ষণ করতে হবে এবং সেই পদ্ধতিটি (কিছু পরীক্ষার ক্ষেত্রে) একটি ব্যতিক্রম ছুঁড়ে ফেলার দরকার ছিল। কল .Throws(...)করা ক্রিয়াকে Mock.Setup(...)ওভাররাইড করে Callback()এবং কখনই কল করে না। যাইহোক, কলব্যাকের মধ্যে একটি ব্যতিক্রম ছুঁড়ে ফেলে দিয়ে, আপনি কলব্যাকের যে সমস্ত ভাল জিনিস কলব্যাক অফার করতে হবে তার সবকটি করতে পারেন এবং এখনও একটি ব্যতিক্রম ছুঁড়ে ফেলতে পারেন।

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