0

I am creating a test app in VS C# to allow production to search for product information within a database and to create a csv file. The app currently works with 1 AccessDB which I added as a datasource in the IDE Data tab.

There is ~50 product databases and having to add each of these in the datasource tab is not viable especially if there are new databases created later on.

I was hoping something like the following would be possible to pass the databasePath as a parameter.

    databasePath = txtBox.Text;
    OleDbConnection conn1 = new OleDbConnection(@"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=databasePath");

Is it possible to do this without having to go to the IDE and add a new datasource?

5
  • Designer is supposed to facilitate the development and make things easier. Everything that you can do using designer is possible without designer as well. Of course you can keep list of database paths or connection strings in a config file and use them later to connect to DB, same for creating DataSet, TableAdapter, and etc. Commented Jan 25, 2022 at 14:41
  • Hi Reza, I'm not sure what you mean by using/not using designer. My problem is that I seem to only be able to read from a database if I add it as a new data source in the VS IDE data tab 1 at a time. I want a way to read databases without adding them manually as that would take some time. Commented Jan 26, 2022 at 12:04
  • You don't necessarily need to use IDE/Designer features to connect to DB. All the designer stuff are generated codes. Look at those generated codes to see how they work and you can do the same. For example, to connect to db, you can simple create a connection (by having a connection string) and create a command (by having a command text) then open the connection and execute the command and read the data and then close the command. There are tones of examples around. Commented Jan 26, 2022 at 12:09
  • OleDbConnection, OleDbCommand, OleDbDataAdapter, and etc. Commented Jan 26, 2022 at 12:14
  • Ah ok Thanks I'll have a look there Commented Jan 26, 2022 at 12:55

1 Answer 1

0

If all the databases have the exact same tables and columns and you are using TableAdapter try the following out.

Caveat It appears the following will not work when changing the connection string after the form has loaded. If you were to change it in a main form than open a child form the connection string works but not when changing the connection string in the same form as the TableAdapter. Best guess is connection string is set when the form initializes thus does not see the changed connection string.

Usage

var source = Path.Combine(ConnectionHelper.BasePath, "Database1.accdb");
ConnectionHelper.ChangeConnection(source,2);

Change BasePath to match your path to the databases.

using System.Configuration;
using System.Data.OleDb;
using System.IO;
using static System.Configuration.ConfigurationManager;

namespace AccessMultiConnections.Classes
{
    public class ConnectionHelper
    {
        /// <summary>
        /// Location of all databases
        /// </summary>
        public static string BasePath = 
            "C:\\Dotnetland\\Databases";

        /// <summary>
        /// Change database connection by index in connection string section
        /// </summary>
        /// <param name="source">Path and database name</param>
        /// <param name="index">ordinal index of connection string</param>
        /// <remarks>
        /// Can change index parameter to a string name representing the connection
        /// string if desire.
        /// </remarks>
        public static void ChangeConnection(string source, int index)
        {
            var config = OpenExeConfiguration(ConfigurationUserLevel.None);
            var connectionStringsSection = (ConnectionStringsSection)config
                .GetSection("connectionStrings");

            // in this case the index to the connection string is 2
            var current = connectionStringsSection.ConnectionStrings[index]
                .ConnectionString;

            var builder = new OleDbConnectionStringBuilder(current)
            {
                DataSource = source
            };

            connectionStringsSection.ConnectionStrings[index].ConnectionString = 
                builder.ConnectionString;

            config.Save();

            RefreshSection("connectionStrings");
            Properties.Settings.Default.Reload();

        }

        /// <summary>
        /// Provides the current database name without a path in appsettings.config
        /// </summary>
        /// <returns>File name for current connection</returns>
        public static string CurrentConnectionString()
        {
            var config = OpenExeConfiguration(ConfigurationUserLevel.None);
            var connectionStringsSection = (ConnectionStringsSection)config
                .GetSection("connectionStrings");

            var builder = 
                new OleDbConnectionStringBuilder(
                    connectionStringsSection.ConnectionStrings[2]
                        .ConnectionString);

            return Path.GetFileName(builder.DataSource);
        }
    }
}

Edit - noticed I hard coded the connection string in CurrentConnectionString, here is the proper code.

/// <summary>
/// Provides the current database name without a path in appsettings.config
/// </summary>
/// <param name="index">ordinal index of connection string</param>
/// <returns>File name for current connection</returns>
public static string CurrentConnectionString(int index = 2)
{
    var config = OpenExeConfiguration(ConfigurationUserLevel.None);
    var connectionStringsSection = (ConnectionStringsSection)config
        .GetSection("connectionStrings");

    var builder = 
        new OleDbConnectionStringBuilder(
            connectionStringsSection.ConnectionStrings[index]
                .ConnectionString);

    return Path.GetFileName(builder.DataSource);
}
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks Karen I'll try this
I made a slight change, see edit in my answer.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.