Is it "safe" / "good" practice to write the connection string in the db context?

120 Views Asked by At

Im using C#, .net8 Entity Framework and currently im using my connection String directly in my DB Context. Is this good practice and safe? Or should it be used elsewhere for safety? Here is my current Code:

public class FileSystemDBContext : DbContext {
    public DbSet<FileTree> FileTrees { get; set; }

    public FileSystemDBContext(DbContextOptions<FileSystemDBContext> options) : base(options)
    {
        // Empty constructor body
    }
}

public class FileSystemDBContextFactory : IDesignTimeDbContextFactory<FileSystemDBContext> {
    public FileSystemDBContext CreateDbContext(string[] args)
    {
        var optionsBuilder = new DbContextOptionsBuilder<FileSystemDBContext>();
        optionsBuilder.UseSqlServer(@"Data Source=(localdb)\MSSQLLocalDB;Initial Catalog=FileSystemExercise;Integrated Security=True;Connect Timeout=30;Encrypt=False;Trust Server Certificate=False;Application Intent=ReadWrite;Multi Subnet Failover=False");

        return new FileSystemDBContext(optionsBuilder.Options);
    }
}
2

There are 2 best solutions below

1
Morten Bork On

how to do it right, depends on what kind of system you deploy. And also how you maintain security.

The point of not hard coding a connection string into your code, is that almost all "real world" businesses use git or a variation thereof.

And having the connection string in plain text, in code you can make publicly available, is just a bad idea.

Moving the connection string to a configuration file, only works, if you don't also upload that config file to your repositories.

If you deploy to the cloud, it is much simpler, as you have environment variables that are specific to your deployment environments, (usually test/staging/production)

and you can simply reference them there. If you want something that can run locally, like a "development" version, I suggest you actually just use a docker container with your external components, and hardcode the passwords in that implementation (where ever you damn well please), as it will only ever work with your docker sandbox (Don't reuse production passwords in your docker). provided you don't map a port out, no one will ever be able to connect to your docker container.

0
MogliMehmet On

In case, anyone else need an example:

In appsettings.json add your Connection string/strings (that way also a dev / mainstring would be possible as example):

"ConnectionStrings": {
    "DefaultConnection": "Data Source=DESKTOP-39TACS0\\SQLEXPRESS;Integrated Security=True;Initial Catalog=ReciptApp ;Connect Timeout=30;Encrypt=False;Trust Server Certificate=False;Application Intent=ReadWrite;Multi Subnet Failover=False"
  },

In the program.cs add this for the config:

//Using the Connection String DefaultConnection from the file "appsetting.json
var connectionString = builder.Configuration.GetConnectionString("DefaultConnection");
builder.Services.AddDbContext<ReciptDBContext>(option =>
option.UseSqlServer(connectionString));

And then add it in the context:

 public class ReciptDBContext :DbContext {


    public ReciptDBContext(DbContextOptions options) : base(options)
    {
    }


    //nothing here -> could be used to create TestData with creating the DB or to add indexes
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {}

    //set all DB Tables = Enititys as DBSet to the context
    public virtual DbSet<Category> Categories { get; set; }
    public virtual DbSet<User> Users { get; set; }
    public virtual DbSet<Recipt> Recipts { get; set; }
}