Как использовать шаблон репозитория EF для обновления базы данных из веб-задания Azure?

Как правильно обновить SQL Azure с помощью Entity Framework из веб-задания Azure?

Я смог найти пост SQL Azure только с помощью веб-задания Azure.

Но решение выше, используя SQL Client, а не через Entity Framework!!!

может ниже код правильно работать в веб-задании Azure

public void DoSomething([TimerTrigger("*/5 *  * * * *")] TimerInfo timer, TextWriter log)
        {
            try
            {

                var tempdetails = _sampleRepository.SearchFor(x=> DateTime.UtcNow > x.DateTo);

                foreach (var detail in tempdetails)
                {
                    if (detail.ID == 2)
                    {
                        detail.ID = 5;
                    }
                    _sampleRepository.Update(detail);
                }

                 _unitOfWork.Commit();

            }
            catch (Exception ex)
            {
                log.WriteLine(ex.Message);
            }

        } 

Ninject Binding

public class NinjectBindings : NinjectModule
    {
        public override void Load()
        {
            //Register Context
            Kernel.Bind<MyDbContext>().ToSelf();
            Kernel.Bind<IUnitOfWork<MyDbContext>>().To<UnitOfWork<MyDbContext>>();

            //Register Repository
            Kernel.Bind(x => x
           .FromAssemblyContaining<MyDbContext>()
           .SelectAllClasses()
           .InheritedFrom(typeof(IRepository<>))
           .BindDefaultInterface());

        }
    }

Program.cs

static void Main()
        {
            using (IKernel kernel = new StandardKernel(new NinjectBindings()))
            {
                var config = new JobHostConfiguration()
                {
                    JobActivator = new NinjectJobActivator(kernel)
                };

                if (config.IsDevelopment)
                {
                    config.UseDevelopmentSettings();
                }

                config.UseTimers();

                var host = new JobHost(config);
                host.RunAndBlock(); 
            }
        }

App.Config

<connectionStrings>

    <add name="AzureWebJobsDashboard" connectionString="" />
    <add name="AzureWebJobsStorage" connectionString="" />
    <add name="EFContext" connectionString="Server=xxxx,1433;Initial Catalog=xxxxxx;....;User
    ID=xxxxxxx;Password=xxxxxxxx;...;Encrypt=True;TrustServerCertificate=False;Connection
    Timeout=30;App=EntityFramework" providerName="System.Data.SqlClient" /> </connectionStrings>

"Настройка портала Azure для запуска веб-задания"

Как обсуждалось с [ MS Support ], после того, как мы добавили строки подключения AzureWebJobsStorage и AzureWebJobDashboard в качестве блейда параметров приложения в портале Azure, веб-работа начала работать без исключения.

Как узнать первопричину сильфонной проблемы

[Рабочий код - обновление базы данных]

var tempdetails = _myRepository.SearchFor(condifiotn);

if(tempdetails != null)
{
    foreach (var detail in tempdetails)
    {
      _unitOfWork.GetContext.Entry(detail).State = EntityState.Detached;

       //Do Some Modification
       detail.Name = "Test";

     _unitOfWork.GetContext.Entry(detail).State = EntityState.Modified;
    }

    //Save Changes
     _unitOfWork.Commit();
}

[Не работает код - невозможно обновить базу данных]

var tempdetails = _myRepository.SearchFor(condifiotn);

if(tempdetails != null)
{
    foreach (var detail in tempdetails)
    {            
       //Do Some Modification
       detail.Name = "Test";

     _myRepository.Update(detail);
    }

    //Save Changes
     _unitOfWork.Commit();
}

Метод обновления

 public void Update(E entity)
        {

            //_dbSet.Attach(entity);
            UnitOfWork.GetContext.Entry(entity).State = System.Data.Entity.EntityState.Modified;
        }

2 ответа

Решение

Ninject связывание в Singleton Scope сделать работу в качестве исключения. Я знаю, что это не лучшее решение. В ожидании лучших ответов. Если что-то, как я настраиваю Ninject в Call Scope.

// Зарегистрировать контекст

    Kernel.Bind<MyDbContext>().ToSelf().InSingletonScope();
    Kernel.Bind<IUnitOfWork<MyDbContext>>().To<UnitOfWork<MyDbContext>>().InSingletonScope();

[ используя InSingletonScope ниже работает, как и ожидалось ]

var tempdetails = _myRepository.SearchFor(condifiotn);

if(tempdetails != null)
{
    foreach (var detail in tempdetails)
    {            
       //Do Some Modification
       detail.Name = "Test";

     _myRepository.Update(detail);
    }

    //Save Changes
     _unitOfWork.Commit();
}

Согласно вашему описанию, я следовал этому руководству, чтобы внедрить свой шаблон репозитория и единицы работы в свои веб-задания Azure. Вы можете следовать приведенному ниже фрагменту кода, чтобы проверить свой код.

NinjectBindings:

public class NinjectBindings : Ninject.Modules.NinjectModule
{
    public override void Load()
    {
        Bind<DbContext>().ToMethod(ctx=> {
            return new BruceDbContext();
        });
        Bind<IUnitOfWork>().To<UnitOfWork>();
    }
}

BruceDbContext:

public class BruceDbContext : DbContext
{
    public BruceDbContext()
        : base("name=brucedbcontext")
    {
    }

    public BruceDbContext(string nameOrConnectionString) : base(nameOrConnectionString)
    {
    }

    //...
}

UnitOfWork:

public class UnitOfWork : IUnitOfWork
{
    private readonly DbContext _dbContext;
    public UnitOfWork(DbContext dbContext)
    {
        _dbContext = dbContext;
    }
    public IRepository<Author> AuthorRepository =>
       new GenericRepository<Author>(_dbContext);

    public void SaveChanges()
    {
        _dbContext.SaveChanges();
    }

    public void Dispose()
    {
        _dbContext.Dispose();
    }
}

Functions.cs

public class Functions
{
    private static IUnitOfWork _iUnitOfWork;
    public Functions(IUnitOfWork iUnitOfWork)
    {
        _iUnitOfWork = iUnitOfWork;
    }

    public void DoSomething([TimerTrigger("*/30 *  * * * *")] TimerInfo timer, TextWriter log)
    {
        _iUnitOfWork.AuthorRepository.Add(new Author()
        {
            Name = Guid.NewGuid().ToString()
        });
        _iUnitOfWork.Commit();

        var allRecords=_iUnitOfWork.AuthorRepository.GetAll().ToList();
        Console.WriteLine(JsonConvert.SerializeObject(allRecords));
    }
}

Примечание: так как вы используете TimerTriggerнужно позвонить config.UseTimers(); перед построением JobHost, Кроме того, вы можете отладить свою веб-работу локально, чтобы найти подробную ошибку. Или вы можете обновить свой вопрос и предоставить более подробные ошибки (например, ex.StackTrace), чтобы мы могли сузить эту проблему.

Другие вопросы по тегам