जवाबों:
जिस तरह से मैंने इसे हल किया वह विज़ुअल स्टूडियो का एक नया उदाहरण खोलने के लिए था और फिर विज़ुअल स्टूडियो के इस नए उदाहरण में एक ही समाधान खोलें। फिर मैंने इस नए उदाहरण में डिबगर को पुराने डेटाबेस (devenv.exe) से अपडेट-डेटाबेस कमांड चलाते हुए संलग्न किया। इसने मुझे बीज विधि को डीबग करने की अनुमति दी।
बस यह सुनिश्चित करने के लिए कि मैंने ब्रेकपॉइंट को समय से न जोड़कर याद किया, मैंने ब्रेकप्वाइंट से पहले एक थ्रेड मिला दिया।
मुझे उम्मीद है इससे किसी को सहायता मिलेगी।
एक क्लीनर समाधान (मुझे लगता है कि इसके लिए EF 6 की आवश्यकता है) IMHO कोड से अपडेट-डेटाबेस को कॉल करने के लिए होगा:
var configuration = new DbMigrationsConfiguration<TContext>();
var databaseMigrator = new DbMigrator(configuration);
databaseMigrator.Update();
यह आपको बीज विधि को डीबग करने की अनुमति देता है।
आप इसे एक कदम आगे ले जा सकते हैं और एक इकाई परीक्षण का निर्माण कर सकते हैं (या, अधिक सटीक रूप से, एक एकीकरण परीक्षण) जो एक खाली परीक्षण डेटाबेस बनाता है, सभी EF माइग्रेशन लागू करता है, बीज विधि चलाता है, और फिर से परीक्षण डेटाबेस को गिराता है:
var configuration = new DbMigrationsConfiguration<TContext>();
Database.Delete("TestDatabaseNameOrConnectionString");
var databaseMigrator = new DbMigrator(configuration);
databaseMigrator.Update();
Database.Delete("TestDatabaseNameOrConnectionString");
लेकिन अपने विकास डेटाबेस के खिलाफ इसे चलाने के लिए सावधान रहें!
मुझे पता है कि यह एक पुराना सवाल है, लेकिन अगर आप चाहते हैं कि सभी संदेश हैं, और आप अपने प्रोजेक्ट में WinForms के संदर्भों को शामिल करने की परवाह नहीं करते हैं, तो मैंने कुछ सरल डिबग विंडो बनाई जहां मैं ट्रेस इवेंट भेज सकता हूं।
अधिक गंभीर और चरण-दर-चरण डिबगिंग के लिए, मैं एक और विज़ुअल स्टूडियो इंस्टेंस खोलूंगा, लेकिन यह साधारण सामान के लिए आवश्यक नहीं है।
यह पूरा कोड है:
SeedApplicationContext.cs
using System;
using System.Data.Entity;
using System.Diagnostics;
using System.Drawing;
using System.Windows.Forms;
namespace Data.Persistence.Migrations.SeedDebug
{
public class SeedApplicationContext<T> : ApplicationContext
where T : DbContext
{
private class SeedTraceListener : TraceListener
{
private readonly SeedApplicationContext<T> _appContext;
public SeedTraceListener(SeedApplicationContext<T> appContext)
{
_appContext = appContext;
}
public override void Write(string message)
{
_appContext.WriteDebugText(message);
}
public override void WriteLine(string message)
{
_appContext.WriteDebugLine(message);
}
}
private Form _debugForm;
private TextBox _debugTextBox;
private TraceListener _traceListener;
private readonly Action<T> _seedAction;
private readonly T _dbcontext;
public Exception Exception { get; private set; }
public bool WaitBeforeExit { get; private set; }
public SeedApplicationContext(Action<T> seedAction, T dbcontext, bool waitBeforeExit = false)
{
_dbcontext = dbcontext;
_seedAction = seedAction;
WaitBeforeExit = waitBeforeExit;
_traceListener = new SeedTraceListener(this);
CreateDebugForm();
MainForm = _debugForm;
Trace.Listeners.Add(_traceListener);
}
private void CreateDebugForm()
{
var textbox = new TextBox {Multiline = true, Dock = DockStyle.Fill, ScrollBars = ScrollBars.Both, WordWrap = false};
var form = new Form {Font = new Font(@"Lucida Console", 8), Text = "Seed Trace"};
form.Controls.Add(tb);
form.Shown += OnFormShown;
_debugForm = form;
_debugTextBox = textbox;
}
private void OnFormShown(object sender, EventArgs eventArgs)
{
WriteDebugLine("Initializing seed...");
try
{
_seedAction(_dbcontext);
if(!WaitBeforeExit)
_debugForm.Close();
else
WriteDebugLine("Finished seed. Close this window to continue");
}
catch (Exception e)
{
Exception = e;
var einner = e;
while (einner != null)
{
WriteDebugLine(string.Format("[Exception {0}] {1}", einner.GetType(), einner.Message));
WriteDebugLine(einner.StackTrace);
einner = einner.InnerException;
if (einner != null)
WriteDebugLine("------- Inner Exception -------");
}
}
}
protected override void Dispose(bool disposing)
{
if (disposing && _traceListener != null)
{
Trace.Listeners.Remove(_traceListener);
_traceListener.Dispose();
_traceListener = null;
}
base.Dispose(disposing);
}
private void WriteDebugText(string message)
{
_debugTextBox.Text += message;
Application.DoEvents();
}
private void WriteDebugLine(string message)
{
WriteDebugText(message + Environment.NewLine);
}
}
}
और अपने मानक configuration.cs पर
// ...
using System.Windows.Forms;
using Data.Persistence.Migrations.SeedDebug;
// ...
namespace Data.Persistence.Migrations
{
internal sealed class Configuration : DbMigrationsConfiguration<MyContext>
{
public Configuration()
{
// Migrations configuration here
}
protected override void Seed(MyContext context)
{
// Create our application context which will host our debug window and message loop
var appContext = new SeedApplicationContext<MyContext>(SeedInternal, context, false);
Application.Run(appContext);
var e = appContext.Exception;
Application.Exit();
// Rethrow the exception to the package manager console
if (e != null)
throw e;
}
// Our original Seed method, now with Trace support!
private void SeedInternal(MyContext context)
{
// ...
Trace.WriteLine("I'm seeding!")
// ...
}
}
}
SeedInternal
कर सकते हैं ताकि विधि इसका उपयोग कर सके)
उह डिबगिंग एक बात है, लेकिन कॉल करना न भूलें: संदर्भ।
कंसोल के लिए एक अच्छा आंतरिक अपवाद स्पिल के बिना ट्रैप कैच में न लपेटें।
https://coderwall.com/p/fbcyaw/debug-into-entity-framework-code-first
with catch (DbEntityValidationException ex)
मेरे पास 2 वर्कअराउंड हैं ( Debugger.Launch()
चूंकि यह मेरे लिए काम नहीं करता है):
पैकेज मैनेजर कंसोल में संदेश प्रिंट करने के लिए अपवाद का उपयोग करें:
throw new Exception("Your message");
एक अन्य तरीका यह है कि आप एक cmd
प्रक्रिया बनाकर फाइल में संदेश प्रिंट करें :
// Logs to file {solution folder}\seed.log data from Seed method (for DEBUG only)
private void Log(string msg)
{
string echoCmd = $"/C echo {DateTime.Now} - {msg} >> seed.log";
System.Diagnostics.Process.Start("cmd.exe", echoCmd);
}
migrate.exe
वर्तमान में चल रहे दृश्य स्टूडियो को संलग्न करने के लिए आप कंसोल से कॉल कर सकते हैं। इस उत्तर में एमओआरई जानकारी: stackoverflow.com/a/52700520/350384