using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
namespace Sdaleo
{
///
/// Core Class to Parse / Generate a UDL String
///
internal class UDL : ICloneable, IComparable
{
#region Internal ReadWrite Properties
///
/// Credential Object can point to different databases
///
internal string DataBase { get; set; }
///
/// Default Connection Timeout
///
internal const uint DEFAULT_CONNECTION_TIMEOUT_UDL = 15;
///
/// Allow Caller to set connection timeout
///
internal uint ConnectionTimeout = DEFAULT_CONNECTION_TIMEOUT_UDL;
///
/// Defaulted to 'true'. When set uses the ConnectionTimeout value, when false it won't
///
internal bool UseConnectionTimeout = true;
// * Secured Password *
private SecuredPassword _Password = new SecuredPassword();
///
/// Secured Password Object that stores the password in a secure manner in memory
///
internal string Password
{
get
{
return _Password.Password;
}
private set
{
_Password.Password = value;
}
}
///
///
///
internal string DataSource
{
get
{
if (!String.IsNullOrEmpty(ServerAddress) && !String.IsNullOrEmpty(InstanceName))
return ServerAddress + "\\" + InstanceName;
else if (!String.IsNullOrEmpty(ServerAddress))
return ServerAddress;
else
return string.Empty;
}
private set
{
if (!String.IsNullOrEmpty(value))
{
string[] values = value.Split('\\');
if (values.Length == 2)
{
ServerAddress = values[0];
InstanceName = values[1];
}
else if (values.Length > 2)
{
int nIndx = value.LastIndexOf('\\');
ServerAddress = value.Substring(0, nIndx);
InstanceName = value.Substring(nIndx + 1);
}
else
{
ServerAddress = value;
}
}
}
}
#endregion
#region Internal ReadOnly Properties
#region ReadOnly String Getters
///
///
///
internal string Username { get; private set; }
///
///
///
internal string ServerAddress { get; private set; }
///
///
///
internal string InstanceName { get; private set; }
///
///
///
internal string IntegratedSecurity { get; private set; }
///
///
///
internal string AttachDBFilename { get; private set; }
///
///
///
internal string ServerType { get; private set; }
#endregion
#region ReadOnly Bool Getters
///
///
///
internal bool TrustedConnection { get; private set; }
///
///
///
internal bool PersistSecurityInfo { get; private set; }
///
///
///
internal bool UserInstance { get; private set; }
///
///
///
internal bool Encrypt { get; private set; }
#endregion
#endregion
#region Constructors
///
/// Construction (Set all UDL Settings via Connection String)
///
/// Pass in a valid Connection String To correctly instantiate the UDL Object
internal UDL(String ConnectionString)
{
Parse(ConnectionString);
}
#region SQL CE Constructors
///
/// Construction SQL CE (Set common UDL Settings for SQL CE)
///
///
///
///
internal UDL(string FileNameNPath, string Password)
{
this.DataSource = FileNameNPath;
UseConnectionTimeout = false;
if (!String.IsNullOrEmpty(Password))
{
this.Password = Password;
this.Encrypt = true;
}
}
#endregion
#region Advantage Constructors
///
/// Construction Advantage (Set common UDL Settings for Advantage)
///
///
///
///
///
internal UDL(string FileNameNPath, string UserID, string Password, string ServerType)
{
UseConnectionTimeout = false;
this.DataSource = FileNameNPath;
this.Username = UserID;
this.Password = Password;
this.ServerType = ServerType;
}
#endregion
#region SQL Server Constructors
///
/// Construction SQL Server (Using SQL Login Credential)
///
/// Name of Database To Use
/// Username to Connect With
/// Password to Connect With
/// ServerAddress to use as DataSource
/// Name of Instance to use as DataSource
internal UDL(string DataBase, string Username, string Password, string ServerAddress, string InstanceName)
{
this.DataBase = DataBase.Trim();
this.Username = Username.Trim();
this.Password = Password;
this.ServerAddress = (String.IsNullOrEmpty(ServerAddress)) ? "." : ServerAddress.Trim().ToUpper();
this.InstanceName = InstanceName.Trim().ToUpper();
}
///
/// Construction SQL Server (Set common UDL Settings for SQL Server)
///
/// Name of Database To Use
/// Username to Connect With
/// Password to Connect With
/// ServerAddress to use as DataSource
/// Name of Instance to use as DataSource
/// Set to True to use Windows Authentication instead of SQL Auth
internal UDL(string DataBase, string Username, string Password, string ServerAddress, string InstanceName, bool TrustedConnection)
{
this.DataBase = DataBase.Trim();
this.Username = Username.Trim();
this.Password = Password;
this.ServerAddress = (String.IsNullOrEmpty(ServerAddress)) ? "." : ServerAddress.Trim().ToUpper();
this.InstanceName = InstanceName.Trim().ToUpper();
this.TrustedConnection = TrustedConnection;
this.IntegratedSecurity = TrustedConnection ? "SSPI" : "";
}
///
/// Construction SQL Server (Set all UDL Settings for SQL Server)
///
/// Name of Database To Use
/// Username to Connect With
/// Password to Connect With
/// ServerAddress to use as DataSource
/// Name of Instance to use as DataSource
/// Set to SQL Express .mdf file to attach to (Creates a User Instance)
/// Set to True to use Windows Authentication instead of SQL Auth
/// Legacy Setting that Persists the Security Information
internal UDL(string DataBase, string Username, string Password, string ServerAddress, string InstanceName,
string AttachDBFilename, bool TrustedConnection, bool PersistSecurityInfo)
{
this.DataBase = DataBase.Trim();
this.Username = Username.Trim();
this.Password = Password;
this.ServerAddress = (String.IsNullOrEmpty(ServerAddress)) ? "." : ServerAddress.Trim().ToUpper();
this.InstanceName = InstanceName.Trim().ToUpper();
this.AttachDBFilename = AttachDBFilename.Trim();
this.UserInstance = !String.IsNullOrEmpty(AttachDBFilename);
this.TrustedConnection = TrustedConnection;
this.IntegratedSecurity = TrustedConnection? "SSPI" : "";
this.PersistSecurityInfo = PersistSecurityInfo;
}
#endregion
#endregion
#region Connection String N' Parse
///
/// Returns the Connection String formed from the UDL Properties
///
///
///
/// Data Source=myServerAddress;Initial Catalog=myDataBase;User Id=myUsername;Password=myPassword;
/// Server=myServerAddress;Database=myDataBase;User ID=myUsername;Password=myPassword;Trusted_Connection=False;
/// Data Source=myServerAddress;Initial Catalog=myDataBase;Integrated Security=SSPI;
/// Server=myServerAddress;Database=myDataBase;Trusted_Connection=True;
/// Server=myServerName\theInstanceName;Database=myDataBase;Trusted_Connection=True;
/// Data Source=myServerAddress;Initial Catalog=myDataBase;Integrated Security=SSPI;User ID=myDomain\myUsername;Password=myPassword;
///
internal string ConnectionString
{
get
{
string strUDL = String.Empty;
// * Data Source Must Always be Specified *
if (!String.IsNullOrEmpty(ServerAddress) && !String.IsNullOrEmpty(InstanceName))
{
strUDL = String.Format(@"Data Source={0}\{1};", ServerAddress, InstanceName);
}
else if (!String.IsNullOrEmpty(ServerAddress))
{
strUDL = String.Format(@"Data Source={0};", ServerAddress);
}
else
throw new Exception("Invalid DataSource Parameter");
// Add Database?
if (!String.IsNullOrEmpty(DataBase))
{
string strAddMore = String.Format(@"Initial Catalog={0};", DataBase);
strUDL += strAddMore;
}
// Add User Information?
if (!String.IsNullOrEmpty(Username))
{
string strAddMore = String.Format(@"User ID={0};", Username);
strUDL += strAddMore;
}
// Add Password Information?
if (!String.IsNullOrEmpty(Password))
{
string strAddMore = String.Format(@"Password={0};", Password);
strUDL += strAddMore;
}
// Should we use User Instance?
if (UserInstance && !String.IsNullOrEmpty(AttachDBFilename))
{
string strAddMore = String.Format(@"User Instance={0};AttachDBFilename={1};", UserInstance.ToString(), AttachDBFilename);
strUDL += strAddMore;
}
// Should we use Integrated Security?
if (TrustedConnection && !String.IsNullOrEmpty(IntegratedSecurity))
{
string strAddMore = String.Format(@"Trusted_Connection={0};Integrated Security={1};", TrustedConnection.ToString(), IntegratedSecurity);
strUDL += strAddMore;
}
// Persist Security Info?
if (PersistSecurityInfo)
{
string strAddMore = String.Format(@"Persist Security Info={0};", PersistSecurityInfo.ToString());
strUDL += strAddMore;
}
// SQL CE Encryption
if (Encrypt)
{
string strAddMore = "Encrypt=TRUE;Encryption Mode=platform default;";
strUDL += strAddMore;
}
// Advantage DB
if (!String.IsNullOrEmpty(ServerType))
{
string strAddMore = String.Format("ServerType={0};", ServerType);
strUDL += strAddMore;
strUDL += "TableType=ADT;";
}
// At the end, specifically add the connection timeout * If asked to *
if (UseConnectionTimeout)
{
string strAddMore = String.Format(@"Connection Timeout={0};", ConnectionTimeout.ToString());
strUDL += strAddMore;
}
return strUDL;
}
}
///
/// Returns a Connection String for use with Legacy ADO
///
internal string ConnectionStringADO
{
get
{
// Force Persist Security Info
bool bPersistSecurity = PersistSecurityInfo;
PersistSecurityInfo = true;
string retString = "Provider=SQLOLEDB.1;OLE DB Services=-2;" + ConnectionString;
PersistSecurityInfo = bPersistSecurity;
return retString;
}
}
///
/// Parses (fills in) UDL properties from the passed in Connection String
///
///
private void Parse(String ConnectionString)
{
if (!String.IsNullOrEmpty(ConnectionString))
{
String[] tokens = ConnectionString.Split(';');
foreach (string Pair in tokens)
{
string[] KeyValuePair = Pair.Split('=');
try
{
string left = KeyValuePair[0];
string right = KeyValuePair[1];
switch (KeyValuePair[0].ToUpper().Trim())
{
case "INITIAL CATALOG":
DataBase = right.Trim();
break;
case "USER ID":
Username = right.Trim();
break;
case "PASSWORD":
Password = right;
break;
case "DATA SOURCE":
DataSource = right.Trim();
break;
case "ATTACHDBFILENAME":
AttachDBFilename = right.Trim();
break;
case "USER INSTANCE":
UserInstance = Boolean.Parse(right.Trim());
break;
case "CONNECTION TIMEOUT":
ConnectionTimeout = UInt32.Parse(right.Trim());
break;
case "TRUSTED_CONNECTION":
TrustedConnection = Boolean.Parse(right.Trim());
break;
case "INTEGRATED SECURITY":
IntegratedSecurity = KeyValuePair[1].Trim().ToUpper();
break;
case "PERSIST SECURITY INFO":
PersistSecurityInfo = Boolean.Parse(KeyValuePair[1].Trim());
break;
case "ENCRYPT":
Encrypt = true;
break;
case "ENCRYPTION MODE":
Encrypt = true;
break;
case "SERVERTYPE":
ServerType = KeyValuePair[1].Trim();
break;
}
}
catch (Exception e) { string m = e.Message; /* ignore and continue iteration */ }
}
}
}
#endregion
#region ICloneable Members
///
///
///
///
public object Clone()
{
return new UDL(this.ConnectionString);
}
#endregion
#region IComparable Members
///
///
///
///
///
public int CompareTo(object obj)
{
UDL otherUDL = obj as UDL;
if (otherUDL != null)
{
int nCompare = String.Compare(this.ConnectionString, otherUDL.ConnectionString, true);
return nCompare;
}
else
{
throw new ArgumentException("Object is not a UDL");
}
}
#endregion
#region UDL File Reading / Writing
///
/// Use this to Parse a UDL object from a text File
///
/// Full Path to File to Read and Parse
/// true if the Text file is encrypted, false otherwise
/// a valid UDL object if successful, null otherwise
internal static UDL UDLReadInFromFile(string FileNameNPath, bool bFileIsEncrypted)
{
if (!File.Exists(FileNameNPath))
return null;
try
{
// Read In the file
string UDLFileContents = string.Empty;
FileStream fs = new FileStream(FileNameNPath, FileMode.Open);
StreamReader sr = new StreamReader(fs, Encoding.Unicode);
string line;
while ((line = sr.ReadLine()) != null)
{
// UDL File is encrypted * Decrypt line by line *
//if (bFileIsEncrypted)
//line = Encryption.DecryptText(line);
if (line.StartsWith("[oledb]") ||
line.StartsWith(";"))
continue; // skip first 2 lines
// Read the line
UDLFileContents += line;
}
sr.Close();
fs.Close();
UDLFileContents = UDLFileContents.Trim();
if (String.IsNullOrEmpty(UDLFileContents))
return null;
// Parse out the UDL Info
UDL udl = new UDL(UDLFileContents);
return udl;
}
catch (Exception) {/* ignore */}
return null;
}
///
/// Use this to Write a UDL Object to a Text File
///
/// Full Path to File to Write To
/// UDL Object to write out
/// True to encrypt File Contents, False Otherwise
/// true if successful, false otherwise
internal static bool UDLWriteOutToToFile(string FileNameNPath, UDL udl, bool bEncryptFile)
{
try
{
string UDLFileContents = string.Empty;
// Create the Directory (if it doesn't exist) * Otherwise an error occurs *
if (!Directory.Exists(Path.GetDirectoryName(FileNameNPath)))
Directory.CreateDirectory(Path.GetDirectoryName(FileNameNPath));
// Write to File
FileStream fs = new FileStream(FileNameNPath, FileMode.Create);
StreamWriter sw = new StreamWriter(fs, Encoding.Unicode);
// UDL File is Encrypted Now, so we encrypte Line-by-line
if (bEncryptFile)
{
// sw.WriteLine(Encryption.EncryptText("[oledb]"));
// sw.WriteLine(Encryption.EncryptText("; Everything after this line is an OLE DB initstring"));
// write out the Connection string,
// sw.WriteLine(Encryption.EncryptText(udl.ConnectionStringLegacy));
}
else
{
sw.WriteLine("[oledb]");
sw.WriteLine("; Everything after this line is an OLE DB initstring");
sw.WriteLine(udl.ConnectionString);
}
sw.Close();
fs.Close();
return true;
}
catch (Exception) { /* ignore */ }
return false;
}
#endregion
}
}