From 1fe4729a9a5064978e465b3ac739ebd2f8b447e4 Mon Sep 17 00:00:00 2001 From: ajcvickers Date: Sun, 20 Sep 2020 11:57:20 -0700 Subject: [PATCH 1/3] Update API docs * Document connection obtained from DatabaseFacade.GetDbConnection() should normally not be disposed Fixes #11415 * Add XML docs referencing how to determine the default CommandTimeout Fixes #17503 * Clarify behavior for EnsureExists with an empty database Fixes #17563 * A hyperlink to the DbContext.Database.Migrate() method would be useful Fixes #17571 * Default values for maxRetryCount, maxRetryDelay, and errorNumbersToAdd Fixes #17574 * Document that modifying entity states while iterating over entries can result in "Collection was modified" exception Fixes #18389 * Update API doc links to correctly reference external dependencies Fixes #18580 * Make it clearer how to access EF.Functions Fixes #21424 * Improve API docs for TrackGraph Fixes #22529 --- .../RelationalDatabaseFacadeExtensions.cs | 29 +++++- .../SqlServerDbContextOptionsBuilder.cs | 34 +++++-- .../SqlServerMigrationsSqlGenerator.cs | 4 +- .../SqlServerRetryingExecutionStrategy.cs | 40 ++++++-- src/EFCore/ChangeTracking/ChangeTracker.cs | 15 ++- .../ChangeTracking/EntityEntryGraphNode.cs | 32 ++++++- src/EFCore/DbContextOptionsBuilder`.cs | 4 +- src/EFCore/DbSet.cs | 4 + src/EFCore/Diagnostics/InterceptionResult.cs | 2 +- src/EFCore/Diagnostics/InterceptionResult`.cs | 2 +- .../WarningsConfigurationBuilder.cs | 53 +++++++++-- src/EFCore/EF.cs | 20 +++- src/EFCore/Infrastructure/DatabaseFacade.cs | 95 +++++++++++++++---- src/EFCore/Infrastructure/IModelCustomizer.cs | 2 +- 14 files changed, 270 insertions(+), 66 deletions(-) diff --git a/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs b/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs index 0873a5545da..350e5c6d5a1 100644 --- a/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs +++ b/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs @@ -408,7 +408,15 @@ public static async Task ExecuteSqlRawAsync( } /// - /// Gets the underlying ADO.NET for this . + /// + /// Gets the underlying ADO.NET for this . + /// + /// + /// This connection should not be disposed if it was created by Entity Framework. Connections are created by + /// Entity Framework when a connection string rather than a DbConnection object is passed to the the 'UseMyProvider' + /// method for the database provider in use. Conversely, the application is responsible for disposing a DbConnection + /// passed to Entity Framework in 'UseMtyProvider'. + /// /// /// The for the context. /// The @@ -605,8 +613,19 @@ public static Task UseTransactionAsync( /// Sets the timeout (in seconds) to use for commands executed with this . /// /// - /// Note that the command timeout is distinct from the connection timeout, which is commonly - /// set on the database connection string. + /// If this value is set, then it is used to set whenever Entity Framework creates a + /// to execute a query. + /// + /// + /// If this value is not set, then the default value used is defined by the underlying ADO.NET data provider. + /// Consult the documentation for the implementation of in the ADO.NET data provider for details of + /// default values, etc. + /// + /// + /// Note that the command timeout is distinct from the connection timeout. Connection timeouts are usually + /// configured in the connection string. More recently, some ADO.NET data providers are adding the capability + /// to also set a command timeout in the connection string. A value set with this API for the command timeout + /// will override any value set in the connection string. /// /// /// The for the context. @@ -619,8 +638,8 @@ public static void SetCommandTimeout([NotNull] this DatabaseFacade databaseFacad /// Sets the timeout to use for commands executed with this . /// /// - /// Note that the command timeout is distinct from the connection timeout, which is commonly - /// set on the database connection string. + /// This is a sugar method allowing a to be used to set the value. It delegates to + /// . /// /// /// The for the context. diff --git a/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs b/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs index cf557e4d543..08687e51534 100644 --- a/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs +++ b/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs @@ -14,9 +14,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure /// Allows SQL Server specific configuration to be performed on . /// /// - /// Instances of this class are returned from a call to - /// + /// Instances of this class are returned from a call to /// and it is not designed to be directly constructed in your application code. /// /// @@ -33,19 +31,43 @@ public SqlServerDbContextOptionsBuilder([NotNull] DbContextOptionsBuilder option } /// - /// Configures the context to use the default retrying . + /// + /// Configures the context to use the default retrying . + /// + /// + /// This strategy is specifically tailored to SQL Server (including SQL Azure). It is pre-configured with + /// error numbers for transient errors that can be retried. + /// + /// + /// Default values of 6 for the maximum retry count and 30 seconds for the maximum default delay are used. + /// /// public virtual SqlServerDbContextOptionsBuilder EnableRetryOnFailure() => ExecutionStrategy(c => new SqlServerRetryingExecutionStrategy(c)); /// - /// Configures the context to use the default retrying . + /// + /// Configures the context to use the default retrying . + /// + /// + /// This strategy is specifically tailored to SQL Server (including SQL Azure). It is pre-configured with + /// error numbers for transient errors that can be retried. + /// + /// + /// A default value 30 seconds for the maximum default delay is used. + /// /// public virtual SqlServerDbContextOptionsBuilder EnableRetryOnFailure(int maxRetryCount) => ExecutionStrategy(c => new SqlServerRetryingExecutionStrategy(c, maxRetryCount)); /// - /// Configures the context to use the default retrying . + /// + /// Configures the context to use the default retrying . + /// + /// + /// This strategy is specifically tailored to SQL Server (including SQL Azure). It is pre-configured with + /// error numbers for transient errors that can be retried, but additional error numbers can also be supplied. + /// /// /// The maximum number of retry attempts. /// The maximum delay between retries. diff --git a/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs b/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs index 16c3d26df4f..9343d3ad63c 100644 --- a/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs +++ b/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs @@ -79,8 +79,8 @@ public override IReadOnlyList Generate( /// . /// /// - /// This method uses a double-dispatch mechanism to call one of the 'Generate' methods that are - /// specific to a certain subtype of . Typically database providers + /// This method uses a double-dispatch mechanism to call one of the methods + /// that are specific to a certain subtype of . Typically database providers /// will override these specific methods rather than this method. However, providers can override /// this methods to handle provider-specific operations. /// diff --git a/src/EFCore.SqlServer/SqlServerRetryingExecutionStrategy.cs b/src/EFCore.SqlServer/SqlServerRetryingExecutionStrategy.cs index ea88676c3d0..161eddd64b6 100644 --- a/src/EFCore.SqlServer/SqlServerRetryingExecutionStrategy.cs +++ b/src/EFCore.SqlServer/SqlServerRetryingExecutionStrategy.cs @@ -12,20 +12,27 @@ namespace Microsoft.EntityFrameworkCore { /// - /// An implementation for retrying failed executions - /// on SQL Server. + /// + /// An implementation for retrying failed executions on SQL Server. + /// + /// + /// This strategy is specifically tailored to SQL Server (including SQL Azure). It is pre-configured with + /// error numbers for transient errors that can be retried. Additional error numbers to retry on can also be supplied. + /// /// public class SqlServerRetryingExecutionStrategy : ExecutionStrategy { private readonly ICollection _additionalErrorNumbers; /// - /// Creates a new instance of . + /// + /// Creates a new instance of . + /// + /// + /// Default values of 6 for the maximum retry count and 30 seconds for the maximum default delay are used. + /// /// /// The context on which the operations will be invoked. - /// - /// The default retry limit is 6, which means that the total amount of time spent before failing is about a minute. - /// public SqlServerRetryingExecutionStrategy( [NotNull] DbContext context) : this(context, DefaultMaxRetryCount) @@ -33,7 +40,12 @@ public SqlServerRetryingExecutionStrategy( } /// - /// Creates a new instance of . + /// + /// Creates a new instance of . + /// + /// + /// Default values of 6 for the maximum retry count and 30 seconds for the maximum default delay are used. + /// /// /// Parameter object containing service dependencies. public SqlServerRetryingExecutionStrategy( @@ -43,7 +55,12 @@ public SqlServerRetryingExecutionStrategy( } /// - /// Creates a new instance of . + /// + /// Creates a new instance of . + /// + /// + /// A default value 30 seconds for the maximum default delay is used. + /// /// /// The context on which the operations will be invoked. /// The maximum number of retry attempts. @@ -55,7 +72,12 @@ public SqlServerRetryingExecutionStrategy( } /// - /// Creates a new instance of . + /// + /// Creates a new instance of . + /// + /// + /// A default value 30 seconds for the maximum default delay is used. + /// /// /// Parameter object containing service dependencies. /// The maximum number of retry attempts. diff --git a/src/EFCore/ChangeTracking/ChangeTracker.cs b/src/EFCore/ChangeTracking/ChangeTracker.cs index fed5b921161..e5574dcc7de 100644 --- a/src/EFCore/ChangeTracking/ChangeTracker.cs +++ b/src/EFCore/ChangeTracking/ChangeTracker.cs @@ -153,8 +153,19 @@ public virtual CascadeTiming CascadeDeleteTiming } /// - /// Gets an for each entity being tracked by the context. - /// The entries provide access to change tracking information and operations for each entity. + /// + /// Returns an for each entity being tracked by the context. + /// The entries provide access to change tracking information and operations for each entity. + /// + /// + /// This method calls to ensure all entries returned reflect up-to-date state. + /// Use to prevent DetectChanges from being called automatically. + /// + /// + /// Note that modification of entity state while iterating over the returned enumeration may result in + /// an indicating that the collection was modified while enumerating. + /// To avoid this, create a defensive copy using or similar before iterating. + /// /// /// An entry for each entity being tracked. public virtual IEnumerable Entries() diff --git a/src/EFCore/ChangeTracking/EntityEntryGraphNode.cs b/src/EFCore/ChangeTracking/EntityEntryGraphNode.cs index 5057ae49b95..c3a927eb782 100644 --- a/src/EFCore/ChangeTracking/EntityEntryGraphNode.cs +++ b/src/EFCore/ChangeTracking/EntityEntryGraphNode.cs @@ -11,8 +11,13 @@ namespace Microsoft.EntityFrameworkCore.ChangeTracking { /// - /// Provides access to change tracking information and operations for a node in a - /// graph of entities that is being traversed. + /// + /// Provides access to change tracking information and operations for a node in a + /// graph of entities that is being traversed. + /// + /// + /// See for information on how graph nodes are used. + /// /// public class EntityEntryGraphNode : IInfrastructure { @@ -40,18 +45,34 @@ public EntityEntryGraphNode( } /// - /// Gets the entry tracking information about this entity. + /// + /// An for the entity instance from which a navigation property was traversed to the the instance + /// represented by this node. + /// + /// + /// See for information on how graph nodes are used. + /// /// public virtual EntityEntry SourceEntry => _sourceEntry == null ? null : new EntityEntry(_sourceEntry); /// - /// Gets the navigation property that is being traversed to reach this node in the graph. + /// + /// Gets the navigation property that is being traversed to reach this node in the graph. + /// + /// + /// See for information on how graph nodes are used. + /// /// public virtual INavigationBase InboundNavigation { get; } /// - /// Gets the entry tracking information about this entity. + /// + /// An for the entity instance represented by this node. + /// + /// + /// See for information on how graph nodes are used. + /// /// public virtual EntityEntry Entry => new EntityEntry(_entry); @@ -65,6 +86,7 @@ public virtual EntityEntry Entry /// application code. /// /// + [EntityFrameworkInternal] InternalEntityEntry IInfrastructure.Instance => _entry; diff --git a/src/EFCore/DbContextOptionsBuilder`.cs b/src/EFCore/DbContextOptionsBuilder`.cs index f58155e525a..dba16ee93cb 100644 --- a/src/EFCore/DbContextOptionsBuilder`.cs +++ b/src/EFCore/DbContextOptionsBuilder`.cs @@ -69,8 +69,8 @@ public DbContextOptionsBuilder([NotNull] DbContextOptions options) /// for logging done by this context. /// /// - /// There is no need to call this method when using one of the 'AddDbContext' methods. - /// 'AddDbContext' will ensure that the used by EF is obtained from the + /// There is no need to call this method when using one of the + /// methods. 'AddDbContext' will ensure that the used by EF is obtained from the /// application service provider. /// /// diff --git a/src/EFCore/DbSet.cs b/src/EFCore/DbSet.cs index 871c445e23e..7e17c55be6e 100644 --- a/src/EFCore/DbSet.cs +++ b/src/EFCore/DbSet.cs @@ -92,6 +92,10 @@ public virtual IQueryable AsQueryable() /// for WPF binding, or /// for WinForms. /// + /// + /// Note that this method calls unless + /// has been set to . + /// /// public virtual LocalView Local => throw new NotImplementedException(); diff --git a/src/EFCore/Diagnostics/InterceptionResult.cs b/src/EFCore/Diagnostics/InterceptionResult.cs index a789c3dbcd0..754ede0b283 100644 --- a/src/EFCore/Diagnostics/InterceptionResult.cs +++ b/src/EFCore/Diagnostics/InterceptionResult.cs @@ -5,7 +5,7 @@ namespace Microsoft.EntityFrameworkCore.Diagnostics { /// /// - /// Represents a result from an such as an 'IDbConnectionInterceptor' to allow + /// Represents a result from an such as an to allow /// suppression of the normal operation being intercepted. /// /// diff --git a/src/EFCore/Diagnostics/InterceptionResult`.cs b/src/EFCore/Diagnostics/InterceptionResult`.cs index 1e1994e26b8..cf6e6d0fe19 100644 --- a/src/EFCore/Diagnostics/InterceptionResult`.cs +++ b/src/EFCore/Diagnostics/InterceptionResult`.cs @@ -8,7 +8,7 @@ namespace Microsoft.EntityFrameworkCore.Diagnostics { /// /// - /// Represents a result from an such as an 'IDbCommandInterceptor' to allow + /// Represents a result from an such as an to allow /// suppression of the normal operation being intercepted. /// /// diff --git a/src/EFCore/Diagnostics/WarningsConfigurationBuilder.cs b/src/EFCore/Diagnostics/WarningsConfigurationBuilder.cs index bb401b3d598..e6a44a10159 100644 --- a/src/EFCore/Diagnostics/WarningsConfigurationBuilder.cs +++ b/src/EFCore/Diagnostics/WarningsConfigurationBuilder.cs @@ -36,7 +36,14 @@ public WarningsConfigurationBuilder([NotNull] DbContextOptionsBuilder optionsBui } /// - /// Sets the default behavior when a warning is generated. + /// + /// Sets the default behavior when a warning is generated. + /// + /// + /// Event ID values can be found in and + /// . + /// The database provider being used may also define provider-specific event IDs in a similar class. + /// /// /// The desired behavior. /// The same builder instance so that multiple calls can be chained. @@ -44,10 +51,17 @@ public virtual WarningsConfigurationBuilder Default(WarningBehavior warningBehav => WithOption(e => e.WithDefaultBehavior(warningBehavior)); /// - /// Causes an exception to be thrown when the specified event occurs, regardless of default configuration. + /// + /// Causes an exception to be thrown when the specified event occurs, regardless of default configuration. + /// + /// + /// Event ID values can be found in and + /// . + /// The database provider being used may also define provider-specific event IDs in a similar class. + /// /// /// - /// The and 'RelationalEventId' for the warnings. + /// The IDs for events to configure. /// /// The same builder instance so that multiple calls can be chained. public virtual WarningsConfigurationBuilder Throw( @@ -59,10 +73,17 @@ public virtual WarningsConfigurationBuilder Throw( } /// - /// Causes an event to be logged, regardless of default configuration. + /// + /// Causes an event to be logged, regardless of default configuration. + /// + /// + /// Event ID values can be found in and + /// . + /// The database provider being used may also define provider-specific event IDs in a similar class. + /// /// /// - /// The and 'RelationalEventId' for EF Core events. + /// The IDs for events to configure. /// /// The same builder instance so that multiple calls can be chained. public virtual WarningsConfigurationBuilder Log( @@ -74,10 +95,17 @@ public virtual WarningsConfigurationBuilder Log( } /// - /// Causes an event to be logged at the specified level, regardless of default configuration. + /// + /// Causes an event to be logged at the specified level, regardless of default configuration. + /// + /// + /// Event ID values can be found in and + /// . + /// The database provider being used may also define provider-specific event IDs in a similar class. + /// /// /// - /// The and 'RelationalEventId' for EF Core events. + /// The event IDs and levels to configure. /// /// The same builder instance so that multiple calls can be chained. public virtual WarningsConfigurationBuilder Log( @@ -89,10 +117,17 @@ [NotNull] params (EventId Id, LogLevel Level)[] eventsAndLevels) } /// - /// Causes nothing to happen when the specified event occurs, regardless of default configuration. + /// + /// Causes nothing to happen when the specified event occurs, regardless of default configuration. + /// + /// + /// Event ID values can be found in and + /// . + /// The database provider being used may also define provider-specific event IDs in a similar class. + /// /// /// - /// The and 'RelationalEventId' for EF Core events. + /// The IDs for events to configure. /// /// The same builder instance so that multiple calls can be chained. public virtual WarningsConfigurationBuilder Ignore( diff --git a/src/EFCore/EF.cs b/src/EFCore/EF.cs index 0be0c3be6c6..f42d6f484c3 100644 --- a/src/EFCore/EF.cs +++ b/src/EFCore/EF.cs @@ -20,9 +20,14 @@ internal static readonly MethodInfo PropertyMethod = typeof(EF).GetTypeInfo().GetDeclaredMethod(nameof(Property)); /// - /// Addresses a given property on an entity instance. This is useful when you want to reference a shadow state property in a - /// LINQ query. Currently this method can only be used in LINQ queries and can not be used to access the value assigned to a - /// property in other scenarios. + /// + /// Addresses a given property on an entity instance. This is useful when you want to reference a shadow state property in a + /// LINQ query. Currently this method can only be used in LINQ queries and can not be used to access the value assigned to a + /// property in other scenarios. + /// + /// + /// Note that this is a static method accessed through the top-level static type. + /// /// /// /// @@ -43,8 +48,13 @@ public static TProperty Property( => throw new InvalidOperationException(CoreStrings.PropertyMethodInvoked); /// - /// Provides CLR methods that get translated to database functions when used in LINQ to Entities queries. - /// Calling these methods in other contexts (e.g. LINQ to Objects) will throw a . + /// + /// Provides CLR methods that get translated to database functions when used in LINQ to Entities queries. + /// Calling these methods in other contexts (e.g. LINQ to Objects) will throw a . + /// + /// + /// Note that this is a static property accessed through the top-level static type. + /// /// public static DbFunctions Functions => DbFunctions.Instance; diff --git a/src/EFCore/Infrastructure/DatabaseFacade.cs b/src/EFCore/Infrastructure/DatabaseFacade.cs index 647111d6d34..71e74d58e00 100644 --- a/src/EFCore/Infrastructure/DatabaseFacade.cs +++ b/src/EFCore/Infrastructure/DatabaseFacade.cs @@ -41,15 +41,38 @@ private IDatabaseFacadeDependencies Dependencies /// /// - /// Ensures that the database for the context exists. If it exists, no action is taken. If it does not - /// exist then the database and all its schema are created. If the database exists, then no effort is made - /// to ensure it is compatible with the model for this context. + /// Ensures that the database for the context exists. /// + /// + /// + /// + /// If the database exists and has any tables, then no action is taken. Nothing is done to ensure + /// the database schema is compatible with the Entity Framework model. + /// + /// + /// + /// + /// If the database exists but does not have any tables, then the Entity Framework model is used to + /// populate the database schema. + /// + /// + /// + /// + /// If the database does not exist, then the database is created and the Entity Framework model is used to + /// populate the database schema. + /// + /// + /// /// - /// Note that this API does not use migrations to create the database. In addition, the database that is + /// It is common to use immediately following when + /// testing or prototyping using Entity Framework. This ensures that the database is in a clean state before each + /// execution of the test/prototype. Note, however, that data in the database is not preserved. + /// + /// + /// Note that this API does **not** use migrations to create the database. In addition, the database that is /// created cannot be later updated using migrations. If you are targeting a relational database and using migrations, - /// you can use the DbContext.Database.Migrate() method to ensure the database is created and all migrations - /// are applied. + /// then you can use + /// to ensure the database is created using migrations and that all migrations have been applied. /// /// /// if the database is created, false if it already existed. @@ -58,15 +81,38 @@ public virtual bool EnsureCreated() /// /// - /// Asynchronously ensures that the database for the context exists. If it exists, no action is taken. If it does not - /// exist then the database and all its schema are created. If the database exists, then no effort is made - /// to ensure it is compatible with the model for this context. + /// Ensures that the database for the context exists. + /// + /// + /// + /// + /// If the database exists and has any tables, then no action is taken. Nothing is done to ensure + /// the database schema is compatible with the Entity Framework model. + /// + /// + /// + /// + /// If the database exists but does not have any tables, then the Entity Framework model is used to + /// populate the database schema. + /// + /// + /// + /// + /// If the database does not exist, then the database is created and the Entity Framework model is used to + /// populate the database schema. + /// + /// + /// + /// + /// It is common to use immediately following when + /// testing or prototyping using Entity Framework. This ensures that the database is in a clean state before each + /// execution of the test/prototype. Note, however, that data in the database is not preserved. /// /// - /// Note that this API does not use migrations to create the database. In addition, the database that is + /// Note that this API does **not** use migrations to create the database. In addition, the database that is /// created cannot be later updated using migrations. If you are targeting a relational database and using migrations, - /// you can use the DbContext.Database.Migrate() method to ensure the database is created and all migrations - /// are applied. + /// then you can use + /// to ensure the database is created using migrations and that all migrations have been applied. /// /// /// A to observe while waiting for the task to complete. @@ -86,6 +132,11 @@ public virtual Task EnsureCreatedAsync(CancellationToken cancellationToken /// Warning: The entire database is deleted, and no effort is made to remove just the database objects that are used by /// the model for this context. /// + /// + /// It is common to use immediately following when + /// testing or prototyping using Entity Framework. This ensures that the database is in a clean state before each + /// execution of the test/prototype. Note, however, that data in the database is not preserved. + /// /// /// if the database is deleted, false if it did not exist. public virtual bool EnsureDeleted() @@ -100,6 +151,11 @@ public virtual bool EnsureDeleted() /// Warning: The entire database is deleted, and no effort is made to remove just the database objects that are used by /// the model for this context. /// + /// + /// It is common to use immediately following when + /// testing or prototyping using Entity Framework. This ensures that the database is in a clean state before each + /// execution of the test/prototype. Note, however, that data in the database is not preserved. + /// /// /// A to observe while waiting for the task to complete. /// @@ -211,13 +267,15 @@ public virtual IExecutionStrategy CreateExecutionStrategy() /// if no transaction is in use. /// /// - /// This property will be null unless one of the 'BeginTransaction' or 'UseTransaction' methods has - /// been called, some of which are available as extension methods installed by EF providers. + /// This property will be null unless one of the , , + /// , or + /// + /// has been called. /// No attempt is made to obtain a transaction from the current DbConnection or similar. /// /// - /// For relational databases, the underlying DbTransaction can be obtained using the - /// 'Microsoft.EntityFrameworkCore.Storage.GetDbTransaction' extension method + /// For relational databases, the underlying DbTransaction can be obtained using + /// /// on the returned . /// /// @@ -249,8 +307,9 @@ public virtual IDbContextTransaction CurrentTransaction /// /// Returns the name of the database provider currently in use. /// The name is typically the name of the provider assembly. - /// It is usually easier to use a sugar method such as 'IsSqlServer()' instead of - /// calling this method directly. + /// It is usually easier to use a sugar method such as + /// + /// instead of calling this method directly. /// /// /// This method can only be used after the has been configured because diff --git a/src/EFCore/Infrastructure/IModelCustomizer.cs b/src/EFCore/Infrastructure/IModelCustomizer.cs index 365d25d5e66..7b7286585c1 100644 --- a/src/EFCore/Infrastructure/IModelCustomizer.cs +++ b/src/EFCore/Infrastructure/IModelCustomizer.cs @@ -16,7 +16,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure /// /// /// When replacing this service consider deriving the implementation from or - /// 'RelationalModelCustomizer' to preserve the default behavior. + /// to preserve the default behavior. /// /// /// The service lifetime is . This means a single instance From 4172bf98b364046f5d002db470c0395e85646e8b Mon Sep 17 00:00:00 2001 From: ajcvickers Date: Mon, 21 Sep 2020 09:39:51 -0700 Subject: [PATCH 2/3] Review feedback --- .../Extensions/RelationalDatabaseFacadeExtensions.cs | 2 +- .../Migrations/SqlServerMigrationsSqlGenerator.cs | 4 ++-- src/EFCore/Infrastructure/DatabaseFacade.cs | 12 ++++++------ 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs b/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs index 350e5c6d5a1..4d6385998a9 100644 --- a/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs +++ b/src/EFCore.Relational/Extensions/RelationalDatabaseFacadeExtensions.cs @@ -415,7 +415,7 @@ public static async Task ExecuteSqlRawAsync( /// This connection should not be disposed if it was created by Entity Framework. Connections are created by /// Entity Framework when a connection string rather than a DbConnection object is passed to the the 'UseMyProvider' /// method for the database provider in use. Conversely, the application is responsible for disposing a DbConnection - /// passed to Entity Framework in 'UseMtyProvider'. + /// passed to Entity Framework in 'UseMyProvider'. /// /// /// The for the context. diff --git a/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs b/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs index 9343d3ad63c..5458e3cf90b 100644 --- a/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs +++ b/src/EFCore.SqlServer/Migrations/SqlServerMigrationsSqlGenerator.cs @@ -79,8 +79,8 @@ public override IReadOnlyList Generate( /// . /// /// - /// This method uses a double-dispatch mechanism to call one of the methods - /// that are specific to a certain subtype of . Typically database providers + /// This method uses a double-dispatch mechanism to call the method + /// that is specific to a certain subtype of . Typically database providers /// will override these specific methods rather than this method. However, providers can override /// this methods to handle provider-specific operations. /// diff --git a/src/EFCore/Infrastructure/DatabaseFacade.cs b/src/EFCore/Infrastructure/DatabaseFacade.cs index 71e74d58e00..fce69f07e5b 100644 --- a/src/EFCore/Infrastructure/DatabaseFacade.cs +++ b/src/EFCore/Infrastructure/DatabaseFacade.cs @@ -53,13 +53,13 @@ private IDatabaseFacadeDependencies Dependencies /// /// /// If the database exists but does not have any tables, then the Entity Framework model is used to - /// populate the database schema. + /// create the database schema. /// /// /// /// /// If the database does not exist, then the database is created and the Entity Framework model is used to - /// populate the database schema. + /// create the database schema. /// /// /// @@ -93,13 +93,13 @@ public virtual bool EnsureCreated() /// /// /// If the database exists but does not have any tables, then the Entity Framework model is used to - /// populate the database schema. + /// create the database schema. /// /// /// /// /// If the database does not exist, then the database is created and the Entity Framework model is used to - /// populate the database schema. + /// create the database schema. /// /// /// @@ -267,14 +267,14 @@ public virtual IExecutionStrategy CreateExecutionStrategy() /// if no transaction is in use. /// /// - /// This property will be null unless one of the , , + /// This property is null unless one of , , /// , or /// /// has been called. /// No attempt is made to obtain a transaction from the current DbConnection or similar. /// /// - /// For relational databases, the underlying DbTransaction can be obtained using + /// For relational databases, the underlying can be obtained using /// /// on the returned . /// From 186a9748c34804b69952e419bf820c568ccb4724 Mon Sep 17 00:00:00 2001 From: Arthur Vickers Date: Wed, 23 Sep 2020 14:58:09 -0700 Subject: [PATCH 3/3] Update src/EFCore/EF.cs Co-authored-by: Shay Rojansky --- src/EFCore/EF.cs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/EFCore/EF.cs b/src/EFCore/EF.cs index f42d6f484c3..94a22f1cd34 100644 --- a/src/EFCore/EF.cs +++ b/src/EFCore/EF.cs @@ -21,8 +21,7 @@ internal static readonly MethodInfo PropertyMethod /// /// - /// Addresses a given property on an entity instance. This is useful when you want to reference a shadow state property in a - /// LINQ query. Currently this method can only be used in LINQ queries and can not be used to access the value assigned to a + /// References a given property on an entity instance. This is useful for shadow state properties, for which no CLR property exists. Currently this method can only be used in LINQ queries and can not be used to access the value assigned to a /// property in other scenarios. /// ///