using System;
using System.CodeDom.Compiler;
using Microsoft.CSharp;
using System.Reflection;
using System.Text;
using System.CodeDom;
using System.IO;
namespace ConsoleApplication1
{
/// <summary>
/// Class1 的摘要說明。
/// </summary>
class Class1
{
/// <summary>
/// 應用程式的主入口點。
/// </summary>
[STAThread]
static void Main(string[] args)
{
//
// TODO: 在此處添加代碼以啟動應用程式
//
object i = Calc("38+44*4/2");
Console.WriteLine(i.ToString());
Console.ReadLine();
}
public static object Calc(string expression)
{
string classNamespace = "BS2.Custom"; //命名空間
string className = "MF"+"Job"; //類名或表名
string methodName = "Run";
expression = expression.Replace("/", "*1.0/"); ///
//生成一個可編譯的單元,這是最根部的東西
CodeCompileUnit compunit = new CodeCompileUnit();
// 建立編譯器執行個體//設定編譯器對象
CSharpCodeProvider csprovider = new CSharpCodeProvider();
ICodeCompiler complier = csprovider.CreateCompiler();
ICodeGenerator gen = csprovider.CreateGenerator(); //生成CS檔案
//StreamWriter sw = new StreamWriter("testywm.cs", false);
//StreamWriter writer = new StreamWriter(@"c:\testywm.cs", false);
StreamWriter sw = new StreamWriter(@"c:\testywm.cs",false);
gen.GenerateCodeFromCompileUnit(compunit, sw, new CodeGeneratorOptions());
// 設定編譯參數。
CompilerParameters paras = new CompilerParameters();
paras.GenerateExecutable = false; //編譯成exe還是dll
paras.GenerateInMemory = false; //是否寫入記憶體,不寫入記憶體就寫入磁盤
paras.OutputAssembly = "c:\\test.dll"; //輸出路徑
paras.IncludeDebugInformation = false; //是否産生pdb調試檔案 預設是false
#region 動态添加dll引用
paras.ReferencedAssemblies.Add("System.dll");//添加引用DLL
paras.ReferencedAssemblies.Add("System.Data.dll");//添加引用DLL
paras.ReferencedAssemblies.Add("D:\\BS2\\BSCore\\bin\\Debug\\BS2.Core.dll");//添加引用DLL
paras.ReferencedAssemblies.Add("D:\\BS2\\BSHelp\\bin\\Debug\\BS2.Help.dll");//添加引用DLL
paras.ReferencedAssemblies.Add("D:\\BS2\\csla20cs\\Csla\\bin\\Debug\\Csla.dll");//添加引用DLL
#endregion
StringBuilder classSource = new StringBuilder();
#region 加載引用
classSource.Append("using System;\r\n");
classSource.Append("using System.Collections.Generic;\r\n");
classSource.Append("using System.Text;\r\n");
classSource.Append("using System.Data;\r\n");
classSource.Append("using System.Data.SqlClient;\r\n");
classSource.Append("using Csla;\r\n");
classSource.Append("using Csla.Data;\r\n");
classSource.Append("using BS2.Help;\r\n");
classSource.Append("using BS2.Help.Enum;\r\n");
#endregion
#region 命名空間及類名
classSource.Append("namespace " + classNamespace + " \r\n");
classSource.Append("{ \r\n");
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// 職務 (可編輯根對象) \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" [Serializable()] \r\n ");
classSource.Append(" public class "+ className +" : BusinessBase<"+ className +"> \r\n");
classSource.Append(" { \r\n");
#endregion
#region 構造函數
classSource.Append(" private "+ className +"() \r\n");
classSource.Append(" { /* require use of factory methods */ } \r\n");
classSource.Append(" private "+ className +"(SafeDataReader dr) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" //Fetch(dr); \r\n");
classSource.Append(" } \r\n");
#endregion
#region 業務屬性
classSource.Append(" private int _id; \r\n");
classSource.Append(" private string _jobNo = string.Empty; \r\n");
classSource.Append(" private string _jobName = string.Empty; \r\n");
classSource.Append(" private string _jobNote = string.Empty; \r\n");
classSource.Append(" private byte[] _timestamp = new byte[8]; \r\n");
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// ID \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" [System.ComponentModel.DataObjectField(true, true)] \r\n");
classSource.Append(" [System.ComponentModel.Browsable(false)] \r\n");
classSource.Append(" public int Id \r\n");
classSource.Append(" { \r\n");
classSource.Append(" get \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanReadProperty(true); \r\n");
classSource.Append(" return _id; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" set \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanWriteProperty(true); \r\n");
classSource.Append(" if (_id != value) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" _id = value; \r\n");
classSource.Append(" PropertyHasChanged(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// 職務編号 \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" [System.ComponentModel.DisplayName(\"職務編号\")] \r\n");
classSource.Append(" public string JobNo \r\n");
classSource.Append(" { \r\n");
classSource.Append(" get \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanReadProperty(true); \r\n");
classSource.Append(" return _jobNo; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" set \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanWriteProperty(true); \r\n");
classSource.Append(" if (value == null) value = string.Empty; \r\n");
classSource.Append(" if (_jobNo != value) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" _jobNo = value; \r\n");
classSource.Append(" PropertyHasChanged(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// 職務名稱 \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" [System.ComponentModel.DisplayName(\"職務名稱\")] \r\n");
classSource.Append(" public string JobName \r\n");
classSource.Append(" { \r\n");
classSource.Append(" get \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanReadProperty(true); \r\n");
classSource.Append(" return _jobName; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" set \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanWriteProperty(true); \r\n");
classSource.Append(" if (value == null) value = string.Empty; \r\n");
classSource.Append(" if (_jobName != value) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" _jobName = value; \r\n");
classSource.Append(" PropertyHasChanged(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// 職務描述 \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" [System.ComponentModel.DisplayName(\"職務描述\")] \r\n");
classSource.Append(" public string JobNote \r\n");
classSource.Append(" { \r\n");
classSource.Append(" get \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanReadProperty(true); \r\n");
classSource.Append(" return _jobNote; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" set \r\n");
classSource.Append(" { \r\n");
classSource.Append(" CanWriteProperty(true); \r\n");
classSource.Append(" if (value == null) value = string.Empty; \r\n");
classSource.Append(" if (_jobNote != value) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" _jobNote = value; \r\n");
classSource.Append(" PropertyHasChanged(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" protected override object GetIdValue() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return _id; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public override string ToString() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return _jobNo + \"[\" + _jobName + \"]\"; \r\n");
classSource.Append(" } \r\n");
#endregion
#region 業務方法
#endregion
#region 限制規則
classSource.Append(" protected override void AddBusinessRules() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" base.AddBusinessRules(); \r\n");
classSource.Append(" ValidationRules.AddRule(BS2.Core.Validation.BSCommonRules.BSStringRequired, \"JobNo\"); \r\n");
classSource.Append(" ValidationRules.AddRule(BS2.Core.Validation.BSCommonRules.BSStringRequired, \"JobName\"); \r\n");
classSource.Append(" } \r\n");
#endregion
#region 權限規則
classSource.Append(" public static bool CanAddObject() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return true; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static bool CanGetObject() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return true; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static bool CanDeleteObject() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return true; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static bool CanEditObject() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return true; \r\n");
classSource.Append(" } \r\n");
#endregion
#region Save方法
classSource.Append(" public override "+ className +" Save() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (IsNew) this.ValidationRules.CheckRules(); \r\n");
classSource.Append(" if ((!IsNew) && (IsDirty) && (!this.IsChild) && (IsValid) && (EditLevel == 0)) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" EnumBussinessObjState state = BS2.Core.Command.BussinessIsChanged.Execute(\"MF_JOB\", _id, _timestamp, EnumDataBase.SecurityDataBase); \r\n");
classSource.Append(" if (state == EnumBussinessObjState.Deleted) throw new BS2.Core.BSUpdateBussinessException(\"目前要儲存的對象已經被删除!\"); \r\n");
classSource.Append(" if (state == EnumBussinessObjState.Modifed) \r\n");
classSource.Append(" { \r\n");
//classSource.Append(" if (BS2.Help.ShowMesssage.Confirm(\"目前要儲存的對象已經被他人修改過!\n儲存操作将覆寫他人修改的内容,是否繼續?\") == false) { throw new BS2.Core.BSNormalBussinessException(); } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" if (state == EnumBussinessObjState.UnKnown) { throw new BS2.Core.BSUpdateBussinessException(\"檢查目前要儲存的對象時發生未知情況!\"); } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" return base.Save(); \r\n");
classSource.Append(" } \r\n");
#endregion
#region 工廠方法(靜态)
classSource.Append(" public static "+ className +" NewJob() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (!CanAddObject()) \r\n");
classSource.Append(" throw new System.Security.SecurityException( \r\n");
classSource.Append(" \"User not authorized to add a project\"); \r\n");
classSource.Append(" return DataPortal.Create<"+ className +">(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static "+ className +" GetJob(int id) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (!CanGetObject()) \r\n");
classSource.Append(" throw new System.Security.SecurityException( \r\n");
classSource.Append(" \"User not authorized to view a project\"); \r\n");
classSource.Append(" return DataPortal.Fetch<"+ className +">(new Criteria(id)); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static "+ className +" GetJob(SafeDataReader dr) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" return new "+ className +"(dr); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public static void DeleteJob(int id) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (!CanDeleteObject()) \r\n");
classSource.Append(" throw new System.Security.SecurityException( \r\n");
classSource.Append(" \"User not authorized to remove a project\"); \r\n");
classSource.Append(" DataPortal.Delete(new Criteria(id)); \r\n");
classSource.Append(" } \r\n");
#endregion
#region 資料通路方法
classSource.Append(" [Serializable()] \r\n");
classSource.Append(" private class Criteria \r\n");
classSource.Append(" { \r\n");
classSource.Append(" private int _id; \r\n");
classSource.Append(" public int Id \r\n");
classSource.Append(" { \r\n");
classSource.Append(" get { return _id; } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" public Criteria(int id) \r\n");
classSource.Append(" { _id = id; } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" [RunLocal()] \r\n");
classSource.Append(" private new void DataPortal_Create() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" ; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" private void DataPortal_Fetch(Criteria criteria) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" using (SqlConnection cn = new SqlConnection(BS2.Help.DataBaseConn.SecurityConnection)) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" cn.Open(); \r\n");
classSource.Append(" using (SqlCommand cm = cn.CreateCommand()) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" string sSQL = \" SELECT MID,PID,JB_NO,JB_NAME,JB_NOTE,LastChanged FROM MF_JOB WHERE MID=\" + criteria.Id.ToString(); \r\n");
classSource.Append(" cm.CommandType = CommandType.Text; \r\n");
classSource.Append(" cm.CommandText = sSQL; \r\n");
classSource.Append(" using (SafeDataReader dr = new SafeDataReader(cm.ExecuteReader())) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (dr.Read()) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" Fetch(dr); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" [Transactional(TransactionalTypes.TransactionScope)] \r\n");
classSource.Append(" protected override void DataPortal_Insert() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" using (SqlConnection cn = new SqlConnection(BS2.Help.DataBaseConn.SecurityConnection)) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" cn.Open(); \r\n");
classSource.Append(" using (SqlCommand cm = cn.CreateCommand()) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" string sSQL = \"INSERT INTO MF_JOB (JB_NO,JB_NAME,JB_NOTE) VALUES('\" + _jobNo + \"','\" + _jobName + \"','\" + _jobNote + \"')\"; \r\n");
classSource.Append(" cm.CommandType = CommandType.StoredProcedure; \r\n");
classSource.Append(" cm.CommandText = \"addBussiness\"; \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@InsertSQL\", sSQL); \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@TableName\", \"MF_JOB\"); \r\n");
classSource.Append(" SqlParameter param = new SqlParameter(\"@id\", SqlDbType.Int); \r\n");
classSource.Append(" param.Direction = ParameterDirection.Output; \r\n");
classSource.Append(" cm.Parameters.Add(param); \r\n");
classSource.Append(" param = new SqlParameter(\"@newLastChanged\", SqlDbType.Timestamp); \r\n");
classSource.Append(" param.Direction = ParameterDirection.Output; \r\n");
classSource.Append(" cm.Parameters.Add(param); \r\n");
classSource.Append(" cm.ExecuteNonQuery(); \r\n");
classSource.Append(" _id = (int)cm.Parameters[\"@id\"].Value; \r\n");
classSource.Append(" _timestamp = (byte[])cm.Parameters[\"@newLastChanged\"].Value; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" [Transactional(TransactionalTypes.TransactionScope)] \r\n");
classSource.Append(" protected override void DataPortal_Update() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" if (base.IsDirty) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" using (SqlConnection cn = new SqlConnection(BS2.Help.DataBaseConn.SecurityConnection)) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" cn.Open(); \r\n");
classSource.Append(" using (SqlCommand cm = cn.CreateCommand()) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" string sSQL = \"UPDATE MF_JOB SET JB_NO = '\" + _jobNo + \"',JB_NAME ='\" + _jobName + \"',JB_NOTE ='\" + _jobNote + \"'\" + \r\n");
classSource.Append(" \" WHERE MID=\" + _id.ToString(); \r\n");
classSource.Append(" cm.CommandType = CommandType.StoredProcedure; \r\n");
classSource.Append(" cm.CommandText = \"updateBussiness\"; \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@UpdateSQL\", sSQL); \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@TableName\", \"MF_JOB\"); \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@id\", _id); \r\n");
classSource.Append(" SqlParameter param = new SqlParameter(\"@newLastChanged\", SqlDbType.Timestamp); \r\n");
classSource.Append(" param.Direction = ParameterDirection.Output; \r\n");
classSource.Append(" cm.Parameters.Add(param); \r\n");
classSource.Append(" cm.ExecuteNonQuery(); \r\n");
classSource.Append(" _timestamp = (byte[])cm.Parameters[\"@newLastChanged\"].Value; \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" [Transactional(TransactionalTypes.TransactionScope)] \r\n");
classSource.Append(" protected override void DataPortal_DeleteSelf() \r\n");
classSource.Append(" { \r\n");
classSource.Append(" DataPortal_Delete(new Criteria(_id)); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" [Transactional(TransactionalTypes.TransactionScope)] \r\n");
classSource.Append(" private void DataPortal_Delete(Criteria criteria) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" using (SqlConnection cn = new SqlConnection(BS2.Help.DataBaseConn.SecurityConnection)) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" cn.Open(); \r\n");
classSource.Append(" using (SqlCommand cm = cn.CreateCommand()) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" cm.CommandType = CommandType.StoredProcedure; \r\n");
classSource.Append(" cm.CommandText = \"deleteJob\"; \r\n");
classSource.Append(" cm.Parameters.AddWithValue(\"@id\", criteria.Id); \r\n");
classSource.Append(" cm.ExecuteNonQuery(); \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
classSource.Append(" } \r\n");
#endregion
#region 資料通路方法(記憶體通路器通路)
classSource.Append(" /// <summary> \r\n");
classSource.Append(" /// 從資料通路器擷取資料 \r\n");
classSource.Append(" /// </summary> \r\n");
classSource.Append(" /// <param name=\"dr\"></param> \r\n");
classSource.Append(" private void Fetch(SafeDataReader dr) \r\n");
classSource.Append(" { \r\n");
classSource.Append(" _id = dr.GetInt32(\"MID\"); \r\n");
classSource.Append(" _jobNo = dr.GetString(\"JB_NO\"); \r\n");
classSource.Append(" _jobName = dr.GetString(\"JB_NAME\"); \r\n");
classSource.Append(" _jobNote = dr.GetString(\"JB_NOTE\"); \r\n");
classSource.Append(" dr.GetBytes(\"LastChanged\", 0, _timestamp, 0, 8); \r\n");
classSource.Append(" MarkOld(); \r\n");
classSource.Append(" } \r\n");
#endregion
#region 命名空間及類名結尾
classSource.Append(" } \r\n");
classSource.Append("} \r\n");
#endregion
sw.Write(classSource.ToString()); //輸出檔案
sw.Close(); //關閉檔案
//System.Diagnostics.Debug.WriteLine(classSource.ToString()); 調試用。注釋掉
// 編譯代碼。
CompilerResults result = complier.CompileAssemblyFromSource(paras, classSource.ToString());
// 擷取編譯後的程式集。
Assembly assembly = result.CompiledAssembly;
//// 動态調用方法。
//object eval = assembly.CreateInstance(className);
//MethodInfo method = eval.GetType().GetMethod(methodName);
object reobj = "生成dll成功";// method.Invoke(eval, null);
//GC.Collect();
return reobj;
}
}
}