0

I have the following entities:

public partial class ApplicationIntegration
{
    public int IntegrationId { get; set; }
    public int ApplicationId { get; set; }
    public bool ReceivesData { get; set; }
    public bool SendsData { get; set; }

    public virtual Application Application { get; set; }
}

public partial class Application
{
    [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors")]
    public Application()
    {
        this.ApplicationIntegrations = new HashSet<ApplicationIntegration>();
    }

    public int ApplicationId { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
    public bool IsActive { get; set; }

    [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
    public virtual ICollection<ApplicationIntegration> ApplicationIntegrations { get; set; }
}

Now, this is my class where I add and get a application integration:

public class ApplicationIntegrationsRepository : Repository
    {
        /// <summary>
        /// Method to add a new application integration
        /// </summary>
        /// <param name="applicationIntegration"></param>
        /// <returns></returns>
        public ApplicationIntegration AddApplicationIntegration(ApplicationIntegration applicationIntegration)
        {
            if (applicationIntegration != null)
            {
                Db.ApplicationIntegrations.Add(applicationIntegration);
                int outPut = Db.SaveChanges();

                //If record was inserted correctly
                if (outPut > 0)
                {
                    //Revive object
                    Db.Entry(applicationIntegration).GetDatabaseValues();
                    applicationIntegration = GetApplicationIntegrationById(applicationIntegration.IntegrationId);
                }
            }

            return applicationIntegration;
        }

        /// <summary>
        /// Method to get a specific application integration by ID
        /// </summary>
        /// <param name="applicationIntegrationId"></param>
        /// <returns></returns>
        public ApplicationIntegration GetApplicationIntegrationById(int applicationIntegrationId)
        {
            ApplicationIntegration applicationIntegration = Db.ApplicationIntegrations.FirstOrDefault(a => a.IntegrationId == applicationIntegrationId);
            return applicationIntegration;
        }
    }


public abstract class Repository
    {
        /// <summary>
        /// Example Entities Connection String
        /// </summary>
        protected ExampleEntities Db { get; set; }

        /// <summary>
        /// Repository Constructor
        /// </summary>
        protected Repository()
        {
            Db = new ExampleEntities();
        }
    }

When passing the variable onto AddApplicationIntegration, I only include the simple variables (IntegrationId = 0, ApplicationId = {id of the application}, ReceivesData = {true or false}, SendsData = {true or false}). I leave Application as null.

Then I add to DB, it inserts correctly. However once I retrieve the object even if calling GetApplicationIntegrationById afterwards, it will always return the property Application as null.

I found a work around to this.

ApplicationIntegrationsRepository _applicationIntegrationsRepository = new ApplicationIntegrationsRepository();
ApplicationIntegration applicationIntegration = new ApplicationIntegration{IntegrationId = 0, ApplicationId = 1, ReceivesData = false, SendsData = true};
ApplicationIntegration entityObject = _applicationIntegrationsRepository.AddApplicationIntegration(applicationIntegration);
ApplicationIntegration applicationNull = _applicationIntegrationsRepository.GetApplicationIntegrationById(entityObject.IntegrationId);
ApplicationIntegration applicationNotNull = new ApplicationIntegrationsRepository().GetApplicationIntegrationById(entityObject.IntegrationId);

If I declare another instance, it will get the full object. I believe this has to do something with the db connection that is created.

Any ideas on how to retrieve using the same instance?

Victor
  • 1,108
  • 9
  • 29
  • 53

1 Answers1

1

Have you tried explicitly including application?

ApplicationIntegration applicationIntegration = Db.ApplicationIntegrations.Include(ap => ap.Application).FirstOrDefault(a => a.IntegrationId == applicationIntegrationId);

Hope this help. Here are some examples for Include on lambdas.

EF Code First - Include(x => x.Properties.Entity) a 1 : Many association

Missing Entity Framework Include(lambda) extension

Using Include in Entity Framework 4 with lambda expressions

Regards

Community
  • 1
  • 1
David Espino
  • 2,177
  • 14
  • 21
  • the problem is not lazy loading. EF won't load related entries lazily once the entries have been retrieved completely with the FirstOrDefault() call. the problem is simply the related entries have not been included and not lazily loaded on the IQueryable. – DevilSuichiro Jun 28 '16 at 10:27
  • Got it @DevilSuichiro... with the `Include` sentence the code will explicitly instruct EF to load related entities... doesn't that work? – David Espino Jun 28 '16 at 15:42
  • yes it does work - at least if the relationship is configured correctly. just wanted to correct your explanation. – DevilSuichiro Jun 28 '16 at 15:44
  • Include expects a string, not a lambda. Is this has anything to do with the EF version or a library that I'm missing? – Victor Jun 28 '16 at 16:08
  • Even though you can enter the path in string format, you can also enter the lambda expression and it should fly. I don't know any version of EF that didnt work with lambda. – DevilSuichiro Jun 28 '16 at 16:13
  • I added using Data.Entity – Victor Jun 30 '16 at 14:02