Pass parameters to factory pattern Architecture in C# - c#

I want to implement factory pattern Architecture. I have created Interface with parameterized function.
1) Step 1 :
public interface IDatabase
{
bool Create(string userId,string password,string host,string dbName);
bool Delete(string userId, string password, string host, string dbName);
}
Step 2:
This interface is Implemented in below class:-
public class IntialDBSetup : IDatabase
{
public bool Create(string userId, string password, string host, string dbName)
{
SqlConnection con = new SqlConnection("Data Source=" + host + ";uid=" + userId + ";pwd=" + password + "");
try
{
string strCreatecmd = "create database " + dbName + "";
SqlCommand cmd = new SqlCommand(strCreatecmd, con);
con.Open();
cmd.ExecuteNonQuery();
con.Close();
var file = new System.IO.FileInfo(System.Web.HttpContext.Current.Server.MapPath(ConfigurationManager.AppSettings["ScriptLocation"]));
string strscript = file.OpenText().ReadToEnd();
string strupdatescript = strscript.Replace("[OWpress]", dbName);
var server = new Microsoft.SqlServer.Management.Smo.Server(new Microsoft.SqlServer.Management.Common.ServerConnection(con));
server.ConnectionContext.ExecuteNonQuery(strupdatescript);
con.Close();
return true;
}
catch (Exception ex)
{
return false;
}
}
public bool Delete(string userId, string password, string host, string dbName)
{
throw new NotImplementedException();
}
}
Step 3:
created factory class
public class DBFactory
{
public static IDatabase DbSetup(string DbType, string userId, string password, string host, string dbName)
{
try
{
if (DbType == DBTypeEnum.IntialDB.ToString())
{
return new IntialDBSetup();
}
}
catch (Exception ex)
{
throw new ArgumentException("DB Type Does not exist in our Record");
}
return null;
}
}
Here I want to pass some parameter to my class, Hgow can I get this?

Add a constructor to your class.
If DBFactory and IntialDBSetup are in the same assembly then that constructor can be marked internal (preventing code outside the assembly creating instances directly).
If the factory method was a static member of IntialDBSetup then the constructor can be private preventing direct creation even in the same assembly.

Related

'SqlServerService' does not implement interface member (C#)

I am creating a system with C# and Windows Forms, and when I tried to implement an interface to generate the base model with the methods for any database that I implement in the system I get an error when trying to pass parameters to the child class of the interface.
I have the following interface:
It is responsible for generating the contract with all the classes that will inherit it.
public interface iDatabase
{
void createConnection();
void CreateUser();
}
and the class DbService:
which is responsible for containing the contract's fixation and allow me not to generate dependency on the project's dependencies, this way I can change the database at any time, I just need to send a new database class as parameter for it to work...
public class DbService
{
private iDatabase _database;
public DbService(iDatabase databaseService)
{
this._database = databaseService;
}
public void connect()
{
this._database.createConnection();
}
public void insertUser()
{
this._database.CreateUser();
}
}
and the dependency's class of SQL Server: this class is responsible for implementing SQL Server specific rules.
namespace TravelCompany.app.repository
{
internal class SqlServerService : iDatabase
{
SqlConnection sqlCon = null;
private string strCon = "Data Source=DESKTOP-UD6EQCL;Initial Catalog=immigration;Integrated Security=True";
private string strSql = string.Empty;
SqlDataAdapter adapt;
SqlCommand command;
public void createConnection()
{
try
{
sqlCon = new SqlConnection(strCon);
sqlCon.Open();
MessageBox.Show("Connection Open !");
}
catch (Exception e)
{
MessageBox.Show("Error to connect Database!", e.Message);
}
}
public void CreateUser()
{
try
{
strSql = "INSERT INTO users (full_name, email, password, cpf, birthday, cep, street, neighborhood, city, uf, complement, passport_number, stack, xp, seniority) VALUES (#full_name, #email, #password, #cpf, #birthday, #cep, #street, #neighborhood, #city, #uf, #complement, #passport_number, #stack, #xp, #seniority)";
command = new SqlCommand(strSql, sqlCon);
command.Parameters.AddWithValue("#full_name", full_name);
command.Parameters.AddWithValue("#email", email);
command.Parameters.AddWithValue("#password", password);
command.Parameters.AddWithValue("#cpf", cpf);
command.Parameters.AddWithValue("#birthday", birthday);
command.Parameters.AddWithValue("#cep", cep);
command.Parameters.AddWithValue("#street", street);
command.Parameters.AddWithValue("#neighborhood", neighborhood);
command.Parameters.AddWithValue("#city", city);
command.Parameters.AddWithValue("#uf", uf);
command.Parameters.AddWithValue("#complement", complement);
command.Parameters.AddWithValue("#passport_number", passport_number);
command.Parameters.AddWithValue("#stack", stack);
command.Parameters.AddWithValue("#xp", xp);
command.Parameters.AddWithValue("#seniority", seniority);
command.ExecuteNonQuery();
MessageBox.Show("User created successfully!");
}
catch (Exception e)
{
MessageBox.Show("Error to create user!", e.Message);
}
throw new NotImplementedException();
}
}
}
and every time that i try to pass values to the public void CreateUser() of public class SqlServerService i receive an error message:
ERROR: 'iDatabase.CreateUser']1 'SqlServerService' does not implement interface member
The method databaseService.connect(); is working!
the problem is with the 'create user' function of SqlServerService...
but the error appears only when I try to pass parameters to the SqlServerService class methods, and I don't know why this happens because I am implementing the interface method with the same name, can someone help?
I would like to solve this error problem and be able to use the create user function of the SqlServerService class with the implementation of the interface
solved the problem, I basically had to pass the same parameters to all the other methods, so the code looks like this:
class SqlServerService
namespace TravelCompany.app.repository
{
internal class SqlServerService : iDatabase
{
SqlConnection sqlCon = null;
private string strCon = "Data Source=DESKTOP-UD6EQCL;Initial Catalog=immigration;Integrated Security=True";
private string strSql = string.Empty;
SqlDataAdapter adapt;
SqlCommand command;
public void createConnection()
{
try
{
sqlCon = new SqlConnection(strCon);
sqlCon.Open();
MessageBox.Show("Connection Open !");
}
catch (Exception e)
{
MessageBox.Show("Error to connect Database!", e.Message);
}
}
public void CreateUser(string userName, string userBirthday, string userCpf, string userCep, string userStreet, string userNeighborhood, string userCity, string userUf, string userComplement, string userEmail, string userPassport, string stack, string xp, string seniority)
{
MessageBox.Show("User created!");
//try
//{
// strSql = "INSERT INTO users (full_name, email, password, cpf, birthday, cep, street, neighborhood, city, uf, complement, passport_number, stack, xp, seniority) VALUES (#full_name, #email, #password, #cpf, #birthday, #cep, #street, #neighborhood, #city, #uf, #complement, #passport_number, #stack, #xp, #seniority)";
// command = new SqlCommand(strSql, sqlCon);
// command.Parameters.AddWithValue("#full_name", userName);
// command.Parameters.AddWithValue("#email", userEmail);
// command.Parameters.AddWithValue("#password", userPassword);
// command.Parameters.AddWithValue("#cpf", userCpf);
// command.Parameters.AddWithValue("#birthday", userBirthday);
// command.Parameters.AddWithValue("#cep", userCep);
// command.Parameters.AddWithValue("#street", userStreet);
// command.Parameters.AddWithValue("#neighborhood", userNeighborhood);
// command.Parameters.AddWithValue("#city", userCity);
// command.Parameters.AddWithValue("#uf", userUf);
// command.Parameters.AddWithValue("#complement", userComplement);
// command.Parameters.AddWithValue("#passport_number", userPassport);
// command.Parameters.AddWithValue("#stack", userStack);
// command.Parameters.AddWithValue("#xp", userXp);
// command.Parameters.AddWithValue("#seniority", userSeniority);
// command.ExecuteNonQuery();
// MessageBox.Show("User created successfully!");
// }
// catch (Exception e)
// {
// MessageBox.Show("Error to create user!", e.Message);
// }
//throw new NotImplementedException();
}
}
}
interface:
public interface iDatabase
{
void createConnection();
void CreateUser(string userName, string userBirthday, string userCpf, string userCep, string userStreet, string userNeighborhood, string userCity, string userUf, string userComplement, string userEmail, string userPassport, string stack, string xp,
string seniority);
}
and the class DbService:
public void insertUser(string userName, string userBirthday, string userCpf, string userCep, string userStreet, string userNeighborhood, string userCity, string userUf, string userComplement, string userEmail, string userPassport, string stack, string xp, string seniority)
{
this._database.CreateUser(userName, userBirthday, userCpf, userCep, userStreet, userNeighborhood, userCity, userUf, userComplement, userEmail, userPassport, stack, xp, seniority);
}
For a reason that i dont know, i have to pass the parameters to all the classes.

Connection to sql database from visual studio

I'm trying to connect to a database, I also have a bool function to check if the connection worked. I searched all over the internet but can't really find how to do it properly.
public class DBConnection : DBLabsDLL.DBConnectionBase
{
///*
// * The constructor
// */
public DBConnection()
{
string connectionString = null;
SqlConnection connection;
connectionString = "Data Source=SQL Server;Initial Catalog=www3.idt.mdh.se;User ID=ezi15001;Password=********";
connection = new SqlConnection(connectionString);
}
public override bool login(string username, string password)
{
try
{
using (var connection = new SqlConnection(connectionString)
{
connection.Open();
return true;
}
catch (SqlException)
{
return false;
}
}

How can i sign-out and redirect to the login page from a public static class?

How can i sign-out and redirect to the login page from a public static class?
I have tried the following but it does not stop page execution..
public static DatabaseNameEntities CreateEntitiesForSpecificDatabaseName(bool contextOwnsConnection = true)
{
string database_name = "";
try
{
database_name = System.Web.HttpContext.Current.Application["DB_NAME"].ToString();
}
catch (NullReferenceException)
{
FormsAuthentication.SignOut();
FormsAuthentication.RedirectToLoginPage();
}
//Initialize the SqlConnectionStringBuilder
//Initialize the EntityConnectionStringBuilder
//Create entity connection
EntityConnection connection = new EntityConnection(entityBuilder.ConnectionString);
return new DatabaseNameEntities(connection);
}
I have tried the following but it does not stop page execution..
That's because it's simply not the MVC way. It's also breaks the Single Responsibility Principle, that is, why would a method named CreateEntitiesForSpecificDatabaseName() know anything about MVC or logging out a user. The code you posted generally breaks this principle multiple times (application state, signing out a user).
Additionally, catching an exception you can prevent is also poor practice (or as the Lead Developer for the C# Compiler team called it, Boneheaded Exceptions).
Consider the following code.
public static ControllerBaseExtensions
{
private const string DBNAME = "DB_NAME";
public static bool TryGetDatabaseName(this ControllerBase instance,
out string DbName)
{
DbName = null;
var app = GetApp(instance);
var result = app.Any(k => k == DBNAME);
if (result)
{
DbName = instance.Application[DBNAME] as string;
result = DbName != null;
}
return result;
}
public static void SetDatabaseName(this ControllerBase instance,
string DbName)
{
var app = GetApp(instance);
app[DBNAME] = DbName;
}
private static HttpApplication GetApp(ControllerBase instance)
{
return instance.ControllerContext.HttpContext.Application;
}
}
public ActionResult MyMethod()
{
string DbName;
if (!this.TryGetDatabaseName(out DbName))
{
FormsAuthentication.SignOut();
// http://stackoverflow.com/questions/30509980
RedirectToAction("Login", "Account");
}
CreateEntitiesForSpecificDatabaseName(Dbname);
}
public static DatabaseNameEntities CreateEntitiesForSpecificDatabaseName(
string dbName,
bool contextOwnsConnection = true)
{
//Initialize the SqlConnectionStringBuilder
//Initialize the EntityConnectionStringBuilder
//Create entity connection
EntityConnection connection = new
EntityConnection(entityBuilder.ConnectionString);
return new DatabaseNameEntities(connection);
}
Does simply ie, no try or catch work as expected
public static DatabaseNameEntities CreateEntitiesForSpecificDatabaseName(bool contextOwnsConnection = true)
{
FormsAuthentication.SignOut();
FormsAuthentication.RedirectToLoginPage();
}

Cannot connect to the business Layer which is in the form of DLL in Bin folder

How do i call the Businesslayer that is in the bin folder as a DLL. 'BusinessLogic' is my dll.
namespace BusinessLogic
{
public class BizLogic
{
string DbConnString = DbConnectionStrings.GetDbConnectionString();
public Dataset SignIn(string Username, string Password)
{
string strReturn = string.Empty;
DataSet pds = new DataSet();
try
{
SqlParameter[] parameters = new SqlParameter[]
{
new SqlParameter("#UserName", UserName )
,new SqlParameter("#Password", Password )
};
SqlHelper.FillDataset(DbConnString, System.Data.CommandType.StoredProcedure, "RepSignIn", pds, new string[] { "SignIn" }, parameters);
return pds;
}
catch (Exception ex)
{
return null;
}
}
}
}
The below part of the code used to work earlier but i changed the database from SQl 2008 R2 Express to 2008 R2 Web Edition with Windows Authentication, it stopped working. I cannot debug because its a DLL and when i have the Quickwatch on BusinssLogic, i see an error " BusinessLogic 'BusinessLogic' is a 'namespace', which is not valid in the given context
". This is in VS 2008.
DataSet ds = new BusinessLogic.BizLogic().SignIn(string Username, string Password);
Can someone please help me what is that i am missing. The connectionString in Web.config is like this
namespace BusinessLogic
{
public class DbConnectionStrings
{
private const string dbConnectionString = "ConnectionString";
public static string GetDbConnectionString()
{
return GetConnectionStringFromConfigFile(dbConnectionString);
}
private static string GetConnectionStringFromConfigFile(string ConnectionName)
{
string connstring = string.Empty;
try
{
connstring = System.Configuration.ConfigurationSettings.AppSettings[ConnectionName];
}
catch
{
}
return connstring;
}
public DbConnectionStrings()
{
}
}
}
Please let me know if you need to know anything else to guide me!
Thank you very much in advance!

WCF TransactionScope doesnt RollBack

I have used this guid: http://www.c-sharpcorner.com/uploadfile/shivprasadk/wcf-faq-part-5-transactions/
Why doesnt it rollback?? I dont understand!
I have a service and client Application and I dont have a clue what is the problem with this code.
after doing this line perfectly and save it in my DB,
proxy.AddEmployee("Stav", "20");
the next line throw Exception becouse I didnt send a number to the Age parameter, but the Transaction doesnt RollBack the first line so the Information : Stav, 20 still exsist in my DB!
proxy.AddEmployee("Stav123", "Not a Number(-->will do Exception)")
EDIT 1:
I add the AddEmployee implement.
client:
static void Main(string[] args)
{
ServiceReference1.IJob proxy = new ServiceReference1.JobClient();
using (TransactionScope ts = new TransactionScope(TransactionScopeOption.Required))
{
try
{
proxy.AddEmployee("Stav", "20");
proxy.AddEmployee("Stav123", "Not a Number(-->will do Exception) ");//stop the running and show the Exception but keep the stav,20 in DB
ts.Complete();
}
catch
{
ts.Dispose();
}
}
}
service:
[ServiceContract]
public interface IJob
{
[OperationContract]
[TransactionFlow(TransactionFlowOption.Allowed)]
void AddEmployee(string Name, string Age);
}
public class JobImplement:IJob
{
[OperationBehavior(TransactionScopeRequired = true)]
public void AddEmployee(string Name, string Age)
{
string strConnection = #"Data Source=.\SQLEXPRESS;AttachDbFilename=C:\Users\stavalfi\Desktop\WCF2\ConsoleApplication4\WCF_DB.mdf;Integrated Security=True;Connect Timeout=30;User Instance=True";
SqlConnection objConnection = new SqlConnection(strConnection);
objConnection.Open();
SqlCommand objCommand = new SqlCommand("INSERT INTO Employee (Name,Age) " + "VALUES ('" + Name + "' ,'" + Age + "')", objConnection);
objCommand.ExecuteNonQuery();
objConnection.Close();
}
}
static void Main(string[] args)
{
WSHttpBinding Basic = new WSHttpBinding();
Basic.TransactionFlow = true;
ServiceHost host = new ServiceHost(typeof(JobImplement), new Uri("http://localhost:8080"));
//
ServiceMetadataBehavior behavior = new ServiceMetadataBehavior();
behavior.HttpGetEnabled = true;
host.Description.Behaviors.Add(behavior);
//
host.AddServiceEndpoint(typeof(IJob), new BasicHttpBinding(), "Request123");
host.Open();
//
Console.WriteLine("opened");
Console.ReadLine();
//
host.Close();
}
It looks like you have a possible typo in your code here:
static void Main(string[] args)
{
...
host.AddServiceEndpoint(typeof(IJob), new BasicHttpBinding(), "Request123");
...
}
You are adding an endpoint of type BasicHttpBinding - a binding protocol that does not support transactions.
I am thinking that you actually meant to do this:
static void Main(string[] args)
{
WSHttpBinding Basic = new WSHttpBinding();
Basic.TransactionFlow = true;
...
host.AddServiceEndpoint(typeof(IJob), Basic, "Request123");
...
}
That would give you a WSHttpBinding endpoint - a binding protocol that does support transactions.
You should implement your own rollback function. Here's a basic way to do it. In your Service class interface add the [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession, ConcurrencyMode = ConcurrencyMode.Single)] attribute. Then add these codes:
private SqlCommand Command { get; set; }
[OperationContract]
public void BeginTransaction()
{
this.Command = new SqlCommand();
string strConnection = #"Data Source=.\SQLEXPRESS;AttachDbFilename=C:\Users\stavalfi\Desktop\WCF2\ConsoleApplication4\WCF_DB.mdf;Integrated Security=True;Connect Timeout=30;User Instance=True";
SqlConnection objConnection = new SqlConnection(strConnection);
objConnection.Open();
this.Command.Connection = objConnection;
}
[OperationContract]
public void RollBackTransaction()
{
this.Command.Transaction.Rollback();
}
[OperationContract]
public void CommitTransaction()
{
this.Command.Transaction.Commit();
}
[OperationContract]
public void CloseConnection()
{
this.Command.Connection.Close();
this.Command = null;
}
[OperationBehavior(TransactionScopeRequired = true)]
public void AddEmployee(string Name, string Age)
{
this.Command.CommandText = "INSERT INTO Employee (Name,Age) " + "VALUES ('" + Name + "' ,'" + Age + "')";
this.Command.ExecuteNonQuery();
}
Then you can access it in the Client code like this:
try
{
proxy.BeginTransaction();
proxy.AddEmployee("Stav", "20");
proxy.AddEmployee("Stav123", "Not a Number(-->will do Exception)");
proxy.CommitTransaction();
}
catch
{
proxy.RollBackTransaction();
}
finally
{
proxy.CloseConnection();
}
Hope this helps.

Categories

Resources