protected virtual void Page_Command(Object sender, CommandEventArgs e)
        {
            try
            {
                DataTable dtFields = ViewState["dtFields"] as DataTable;
                //ctlLayoutButtons.ErrorText = e.CommandName + ": " + e.CommandArgument.ToString();
                if (e.CommandName == "Layout.Delete")
                {
                    int nFieldIndex = Sql.ToInteger(e.CommandArgument);
                    DynamicTableDelete(dtFields, nFieldIndex);
                    ViewState["dtFields"] = dtFields;
                    LayoutView_Bind(dtFields);
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                    }
                }
                else if (e.CommandName == "Layout.MoveUp")
                {
                    int nFieldIndex = Sql.ToInteger(e.CommandArgument);
                    int nRowMinimum = Sql.ToInteger(ViewState["ROW_MINIMUM"]);
                    DynamicTableMoveUp(dtFields, nFieldIndex, nRowMinimum);
                    ViewState["dtFields"] = dtFields;
                    LayoutView_Bind(dtFields);
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                    }
                }
                else if (e.CommandName == "Layout.MoveDown")
                {
                    int nFieldIndex = Sql.ToInteger(e.CommandArgument);
                    DynamicTableMoveDown(dtFields, nFieldIndex);
                    ViewState["dtFields"] = dtFields;
                    LayoutView_Bind(dtFields);
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                    }
                }
                else if (e.CommandName == "Layout.Edit")
                {
                }
                else if (e.CommandName == "NewRecord.Save")
                {
                }
                else if (e.CommandName == "NewRecord.Cancel")
                {
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                    }
                }
                else if (e.CommandName == "Layout.Insert")
                {
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                        int nFieldIndex = Sql.ToInteger(e.CommandArgument);
                        ctlNewRecord.FIELD_ID    = Guid.NewGuid();
                        ctlNewRecord.FIELD_INDEX = nFieldIndex;
                        ctlNewRecord.Visible     = true;
                    }
                }
                else if (e.CommandName == "New")
                {
                    if (ctlNewRecord != null)
                    {
                        ctlNewRecord.Clear();
                        int nFieldIndex = Sql.ToInteger(e.CommandArgument);
                        ctlNewRecord.FIELD_ID = Guid.NewGuid();
                        ctlNewRecord.Visible  = true;
                    }
                }
                else if (e.CommandName == "Defaults")
                {
                }
                else if (e.CommandName == "Save")
                {
                    DbProviderFactory dbf = DbProviderFactories.GetFactory();
                    using (IDbConnection con = dbf.CreateConnection())
                    {
                        con.Open();
                        using (IDbTransaction trn = con.BeginTransaction())
                        {
                            try
                            {
                                IDbCommand cmdUpdate = SqlProcs.Factory(con, LayoutUpdateProcedure());
                                cmdUpdate.Transaction = trn;
                                foreach (IDataParameter par in cmdUpdate.Parameters)
                                {
                                    par.Value = DBNull.Value;
                                }
                                IDbDataParameter parMODIFIED_USER_ID = Sql.FindParameter(cmdUpdate, "@MODIFIED_USER_ID");
                                if (parMODIFIED_USER_ID != null)
                                {
                                    parMODIFIED_USER_ID.Value = Security.USER_ID;
                                }

                                DataView vwFields = new DataView(dtFields);
                                vwFields.RowFilter = "DELETED = 0";
                                foreach (DataRowView row in vwFields)
                                {
                                    if (row.Row.RowState == DataRowState.Modified || row.Row.RowState == DataRowState.Added)
                                    {
                                        foreach (IDataParameter par in cmdUpdate.Parameters)
                                        {
                                            string sFieldName = Sql.ExtractDbName(cmdUpdate, par.ParameterName);
                                            if (dtFields.Columns.Contains(sFieldName) && (sFieldName != "MODIFIED_USER_ID"))
                                            {
                                                // 01/09/2006 Paul.  Make sure to use ToDBString to convert empty stings to NULL.
                                                switch (par.DbType)
                                                {
                                                case DbType.Guid:  par.Value = Sql.ToGuid(row[sFieldName]);  break;

                                                case DbType.Int16:  par.Value = Sql.ToDBInteger(row[sFieldName]);  break;

                                                case DbType.Int32:  par.Value = Sql.ToDBInteger(row[sFieldName]);  break;

                                                case DbType.Int64:  par.Value = Sql.ToDBInteger(row[sFieldName]);  break;

                                                case DbType.Double:  par.Value = Sql.ToDBFloat(row[sFieldName]);  break;

                                                case DbType.Decimal:  par.Value = Sql.ToDBDecimal(row[sFieldName]);  break;

                                                case DbType.Byte:  par.Value = Sql.ToDBBoolean(row[sFieldName]);  break;

                                                case DbType.DateTime:  par.Value = Sql.ToDBDateTime(row[sFieldName]);  break;

                                                default:  par.Value = Sql.ToDBString(row[sFieldName]);  break;
                                                }
                                            }
                                        }
                                        cmdUpdate.ExecuteNonQuery();
                                    }
                                }

                                IDbCommand cmdDelete = SqlProcs.Factory(con, LayoutDeleteProcedure());
                                cmdDelete.Transaction = trn;
                                IDbDataParameter parID = Sql.FindParameter(cmdDelete, "@ID");
                                parMODIFIED_USER_ID = Sql.FindParameter(cmdDelete, "@MODIFIED_USER_ID");
                                if (parMODIFIED_USER_ID != null)
                                {
                                    parMODIFIED_USER_ID.Value = Security.USER_ID;
                                }

                                vwFields.RowFilter = "DELETED = 1";
                                foreach (DataRowView row in vwFields)
                                {
                                    parID.Value = Sql.ToDBGuid(row["ID"]);
                                    cmdDelete.ExecuteNonQuery();
                                }
                                trn.Commit();
                                // 01/09/2006 Paul.  Make sure to clear the cache so that the changes will take effect immediately.
                                ClearCache(Sql.ToString(ViewState["LAYOUT_VIEW_NAME"]));
                                Response.Redirect("default.aspx");
                            }
                            catch (Exception ex)
                            {
                                trn.Rollback();
                                throw(new Exception("Failed to update, transaction aborted; " + ex.Message, ex));
                            }
                        }
                    }
                }
                else if (e.CommandName == "Cancel")
                {
                    Response.Redirect("default.aspx");
                }
            }
            catch (Exception ex)
            {
                SplendidError.SystemError(new StackTrace(true).GetFrame(0), ex.Message);
                ctlLayoutButtons.ErrorText = ex.Message;
            }
        }
Exemplo n.º 2
0
        public static void Import(XmlDocument xml, ArrayList arrTables, bool bTruncate)
        {
            HttpResponse Response = HttpContext.Current.Response;
            // 12/16/2005 Paul.  First create a hash table to convert tab name to a uppercase table name.
            Hashtable   hashTables = new Hashtable();
            XmlNodeList nlTables   = xml.DocumentElement.ChildNodes;

            foreach (XmlNode node in nlTables)
            {
                if (!hashTables.ContainsKey(node.Name.ToUpper()))
                {
                    hashTables.Add(node.Name.ToUpper(), node.Name);
                }
            }

            ArrayList lstReservedTables = new ArrayList();

            lstReservedTables.Add("CONFIG");
            lstReservedTables.Add("DETAILVIEWS");
            lstReservedTables.Add("DETAILVIEWS_FIELDS");
            lstReservedTables.Add("DETAILVIEWS_RELATIONSHIPS");
            lstReservedTables.Add("EDITVIEWS");
            lstReservedTables.Add("EDITVIEWS_FIELDS");
            lstReservedTables.Add("GRIDVIEWS");
            lstReservedTables.Add("GRIDVIEWS_COLUMNS");
            lstReservedTables.Add("LANGUAGES");
            lstReservedTables.Add("MODULES");
            lstReservedTables.Add("SHORTCUTS");
            lstReservedTables.Add("TERMINOLOGY");
            lstReservedTables.Add("TIMEZONES");

            StringBuilder     sbErrors = new StringBuilder();
            DbProviderFactory dbf      = DbProviderFactories.GetFactory();

            if (arrTables == null)
            {
                arrTables = new ArrayList();
                using (IDbConnection con = dbf.CreateConnection())
                {
                    con.Open();
                    using (IDbCommand cmd = con.CreateCommand())
                    {
                        cmd.CommandText = "select * from vwSqlTableDependencies order by 2, 1";
                        using (DbDataAdapter da = dbf.CreateDataAdapter())
                        {
                            ((IDbDataAdapter)da).SelectCommand = cmd;
                            using (DataTable dt = new DataTable())
                            {
                                da.Fill(dt);
                                for (int i = 0; i < dt.Rows.Count; i++)
                                {
                                    DataRow row = dt.Rows[i];
                                    arrTables.Add(row["name"].ToString());
                                }
                            }
                        }
                        if (bTruncate)
                        {
                            cmd.CommandText = "select * from vwSqlTableDependencies order by 2 desc, 1 desc";
                            using (DbDataAdapter da = dbf.CreateDataAdapter())
                            {
                                ((IDbDataAdapter)da).SelectCommand = cmd;
                                using (DataTable dt = new DataTable())
                                {
                                    da.Fill(dt);
                                    for (int i = 0; i < dt.Rows.Count && Response.IsClientConnected; i++)
                                    {
                                        DataRow row         = dt.Rows[i];
                                        string  sTABLE_NAME = row["name"].ToString().ToUpper();
                                        // 12/18/2005 Paul.  Some tables are reserved and should not be truncated or imported.
                                        if (lstReservedTables.Contains(sTABLE_NAME))
                                        {
                                            continue;
                                        }
                                        // 12/18/2005 Paul.  Only truncate tables that are being imported.
                                        if (hashTables.ContainsKey(sTABLE_NAME))
                                        {
                                            try
                                            {
                                                if (sTABLE_NAME == "USERS")
                                                {
                                                    // 12/17/2005 Paul.  Don't delete the existing user, otherwise it will cause a login problem in the future.
                                                    cmd.CommandText = "delete from USERS where ID != @ID";
                                                    Sql.AddParameter(cmd, "@ID", Security.USER_ID);
                                                }
                                                else
                                                {
                                                    cmd.CommandText = "delete from " + sTABLE_NAME;
                                                }
                                                cmd.ExecuteNonQuery();
                                                Response.Write(" ");                                                 // Write a singe byte to keep the connection open.
                                            }
                                            catch (Exception ex)
                                            {
                                                LogError(ref sbErrors, Sql.ExpandParameters(cmd), ex.Message);
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
            for (int i = 0; i < arrTables.Count && Response.IsClientConnected; i++)
            {
                string sTABLE_NAME = arrTables[i].ToString().ToUpper();
                // 12/18/2005 Paul.  Some tables are reserved and should not be truncated or imported.
                if (lstReservedTables.Contains(sTABLE_NAME))
                {
                    continue;
                }
                if (hashTables.ContainsKey(sTABLE_NAME))
                {
                    string sXML_TABLE_NAME = hashTables[sTABLE_NAME].ToString();

                    XmlNodeList nlRows = xml.DocumentElement.SelectNodes(sXML_TABLE_NAME);
                    if (nlRows.Count > 0)
                    {
                        SplendidError.SystemWarning(new StackTrace(true).GetFrame(0), "Import Database Table: " + sTABLE_NAME);
                        // 12/17/2005 Paul.  Use a new connection for each table import so that connection state will be reset.
                        // My main concern is that the identity_insert gets reset.
                        using (IDbConnection con = dbf.CreateConnection())
                        {
                            con.Open();
                            try
                            {
                                if (Sql.IsSQLServer(con))
                                {
                                    // 12/17/2005 Paul.  In SQL Server, turn on identity_insert.
                                    string sIDENTITY_NAME = String.Empty;
                                    switch (sIDENTITY_NAME)
                                    {
                                    case "BUGS": sIDENTITY_NAME = "BUGS";  break;

                                    case "CASES": sIDENTITY_NAME = "CASES";  break;

                                    case "CAMPAIGNS": sIDENTITY_NAME = "CAMPAIGNS";  break;

                                    case "PROSPECTS": sIDENTITY_NAME = "PROSPECTS";  break;
                                    }
                                    if (!Sql.IsEmptyString(sIDENTITY_NAME))
                                    {
                                        IDbCommand cmdIdentity = con.CreateCommand();
                                        cmdIdentity.CommandText = "set identity_insert " + sIDENTITY_NAME + " on";
                                        cmdIdentity.ExecuteNonQuery();
                                    }
                                }
                                else if (Sql.IsOracle(con))
                                {
                                    // 12/17/2005 Paul.  In Oracle, disable sequence triggers.
                                    string sTRIGGER_NAME = String.Empty;
                                    switch (sTABLE_NAME)
                                    {
                                    case "BUGS": sTRIGGER_NAME = "TR_S_BUGS_BUG_NUMBER";  break;

                                    case "CASES": sTRIGGER_NAME = "TR_S_CASES_CASE_NUMBER";  break;

                                    case "CAMPAIGNS": sTRIGGER_NAME = "TR_S_CAMPAIGNS_TRACKER_KEY";  break;

                                    case "PROSPECTS": sTRIGGER_NAME = "TR_S_PROSPECTS_TRACKER_KEY";  break;
                                    }
                                    if (!Sql.IsEmptyString(sTRIGGER_NAME))
                                    {
                                        IDbCommand cmdTrigger = con.CreateCommand();
                                        cmdTrigger.CommandText = "alter trigger " + sTRIGGER_NAME + " disable";
                                        cmdTrigger.ExecuteNonQuery();
                                    }
                                }

                                int        nTableErrors = 0;
                                IDbCommand cmdImport    = Sql.CreateInsertParameters(con, sTABLE_NAME);
                                foreach (XmlNode node in nlRows)
                                {
                                    if (!Response.IsClientConnected)
                                    {
                                        break;
                                    }
                                    foreach (IDataParameter par in cmdImport.Parameters)
                                    {
                                        par.Value = DBNull.Value;
                                    }
                                    for (int j = 0; j < node.ChildNodes.Count; j++)
                                    {
                                        // 12/18/2005 Paul.  A short-sighted programmer at SugarCRM created GUIDs with invalid characters.
                                        // We need to convert them to valid GUIDs.
                                        string sText = node.ChildNodes[j].InnerText;
                                        // 08/20/2006 Paul.  Dynamically attempt to fix invalid GUIDs. It really only works for the ones defined below.
                                        string sName = node.ChildNodes[j].Name.ToUpper();
                                        if (sName == "ID" || sName.EndsWith("_ID"))
                                        {
                                            if (sText.Length < 36)
                                            {
                                                sText = "00000000-0000-0000-0000-000000000000".Substring(0, 36 - sText.Length) + sText;
                                            }
                                        }
                                        switch (sText)
                                        {
                                        case "00000000-0000-0000-0000-000000jim_id":  sText = "00000000-0000-0000-0001-000000000000";  break;

                                        case "00000000-0000-0000-0000-000000max_id":  sText = "00000000-0000-0000-0002-000000000000";  break;

                                        case "00000000-0000-0000-0000-00000will_id":  sText = "00000000-0000-0000-0003-000000000000";  break;

                                        case "00000000-0000-0000-0000-0000chris_id":  sText = "00000000-0000-0000-0004-000000000000";  break;

                                        case "00000000-0000-0000-0000-0000sally_id":  sText = "00000000-0000-0000-0005-000000000000";  break;

                                        case "00000000-0000-0000-0000-0000sarah_id":  sText = "00000000-0000-0000-0006-000000000000";  break;
                                        }
                                        Sql.SetParameter(cmdImport, node.ChildNodes[j].Name, sText);
                                    }
                                    // 12/18/2005 Paul.  ID can never be NULL.  SugarCRM does not use an ID in the CONFIG or USERS_FEEDS table.
                                    IDbDataParameter parID = Sql.FindParameter(cmdImport, "@ID");
                                    if (parID != null)
                                    {
                                        // 12/18/2005 Paul. GUIDs from SugarCRM may not be 36 characters.
                                        string sID = Sql.ToString(parID.Value);
                                        if (parID.Value != DBNull.Value)
                                        {
                                            if (sID.Length < 36)
                                            {
                                                // 07/31/2006 Paul.  Stop using VisualBasic library to increase compatibility with Mono.
                                                parID.Value = "00000000-0000-0000-0000-000000000000".Substring(0, 36 - sID.Length) + sID;
                                            }
                                        }
                                        if (Sql.IsEmptyGuid(parID.Value))
                                        {
                                            if (parID.DbType == DbType.Guid)
                                            {
                                                parID.Value = Guid.NewGuid();
                                            }
                                            else
                                            {
                                                parID.Value = Guid.NewGuid().ToString();
                                            }
                                        }
                                    }
                                    // 12/18/2005 Paul.  DATE_ENTERED can never be NULL.  SugarCRM does not use DATE_ENTERED in a number of tables.
                                    IDbDataParameter parDATE_ENTERED = Sql.FindParameter(cmdImport, "@DATE_ENTERED");
                                    if (parDATE_ENTERED != null)
                                    {
                                        if (parDATE_ENTERED.Value == DBNull.Value)
                                        {
                                            parDATE_ENTERED.Value = DateTime.Now;
                                        }
                                    }
                                    // 12/18/2005 Paul.  DATE_MODIFIED can never be NULL.  SugarCRM does not use DATE_MODIFIED in a number of tables.
                                    IDbDataParameter parDATE_MODIFIED = Sql.FindParameter(cmdImport, "@DATE_MODIFIED");
                                    if (parDATE_MODIFIED != null)
                                    {
                                        if (parDATE_MODIFIED.Value == DBNull.Value)
                                        {
                                            parDATE_MODIFIED.Value = DateTime.Now;
                                        }
                                    }
                                    try
                                    {
                                        cmdImport.ExecuteNonQuery();
                                        Response.Write(" ");
                                    }
                                    catch (Exception ex)
                                    {
                                        LogError(ref sbErrors, Sql.ExpandParameters(cmdImport), ex.Message);
                                        // 12/17/2005 Paul.  If there is an error, stop importing from this table.
                                        // 12/18/2005 Paul.  I'd like to see the first 100 errors.
                                        nTableErrors++;
                                        if (nTableErrors > 100)
                                        {
                                            break;
                                        }
                                    }
                                }
                            }
                            catch (Exception ex)
                            {
                                LogError(ref sbErrors, sTABLE_NAME, ex.Message);
                            }
                            finally
                            {
                                try
                                {
                                    if (Sql.IsSQLServer(con))
                                    {
                                        // 12/17/2005 Paul.  In SQL Server, turn off identity_insert.
                                        string sIDENTITY_NAME = String.Empty;
                                        switch (sIDENTITY_NAME)
                                        {
                                        case "BUGS": sIDENTITY_NAME = "BUGS";  break;

                                        case "CASES": sIDENTITY_NAME = "CASES";  break;

                                        case "CAMPAIGNS": sIDENTITY_NAME = "CAMPAIGNS";  break;

                                        case "PROSPECTS": sIDENTITY_NAME = "PROSPECTS";  break;
                                        }
                                        if (!Sql.IsEmptyString(sIDENTITY_NAME))
                                        {
                                            IDbCommand cmdIdentity = con.CreateCommand();
                                            cmdIdentity.CommandText = "set identity_insert " + sIDENTITY_NAME + " off";
                                            cmdIdentity.ExecuteNonQuery();
                                        }
                                    }
                                    else if (Sql.IsOracle(con))
                                    {
                                        // 12/17/2005 Paul.  In Oracle, enable sequence triggers.
                                        string sTRIGGER_NAME = String.Empty;
                                        switch (sTABLE_NAME)
                                        {
                                        case "BUGS": sTRIGGER_NAME = "TR_S_BUGS_BUG_NUMBER";  break;

                                        case "CASES": sTRIGGER_NAME = "TR_S_CASES_CASE_NUMBER";  break;

                                        case "CAMPAIGNS": sTRIGGER_NAME = "TR_S_CAMPAIGNS_TRACKER_KEY";  break;

                                        case "PROSPECTS": sTRIGGER_NAME = "TR_S_PROSPECTS_TRACKER_KEY";  break;
                                        }
                                        if (!Sql.IsEmptyString(sTRIGGER_NAME))
                                        {
                                            IDbCommand cmdTrigger = con.CreateCommand();
                                            cmdTrigger.CommandText = "alter trigger " + sTRIGGER_NAME + " enable";
                                            cmdTrigger.ExecuteNonQuery();
                                        }
                                    }
                                }
                                catch (Exception ex)
                                {
                                    LogError(ref sbErrors, sTABLE_NAME, ex.Message);
                                }
                            }
                        }
                        Response.Write(" ");                         // Write a singe byte to keep the connection open.
                    }
                }
            }
            // 12/18/2005 Paul.  Reserved tables will still be imported, but we use the associated spXXX_Update procedure.
            for (int i = 0; i < arrTables.Count && Response.IsClientConnected; i++)
            {
                string sTABLE_NAME = arrTables[i].ToString().ToUpper();
                if (hashTables.ContainsKey(sTABLE_NAME) && lstReservedTables.Contains(sTABLE_NAME))
                {
                    string sXML_TABLE_NAME = hashTables[sTABLE_NAME].ToString();

                    XmlNodeList nlRows = xml.DocumentElement.SelectNodes(sXML_TABLE_NAME);
                    if (nlRows.Count > 0)
                    {
                        SplendidError.SystemWarning(new StackTrace(true).GetFrame(0), "Import Database Table: " + sTABLE_NAME);
                        // 12/17/2005 Paul.  Use a new connection for each table import so that connection state will be reset.
                        // My main concern is that the identity_insert gets reset.
                        using (IDbConnection con = dbf.CreateConnection())
                        {
                            con.Open();
                            try
                            {
                                int        nTableErrors = 0;
                                IDbCommand cmdImport    = SqlProcs.Factory(con, "sp" + sTABLE_NAME + "_Update");
                                foreach (XmlNode node in nlRows)
                                {
                                    if (!Response.IsClientConnected)
                                    {
                                        break;
                                    }
                                    foreach (IDataParameter par in cmdImport.Parameters)
                                    {
                                        par.Value = DBNull.Value;
                                    }
                                    for (int j = 0; j < node.ChildNodes.Count; j++)
                                    {
                                        string sText = node.ChildNodes[j].InnerText;
                                        Sql.SetParameter(cmdImport, node.ChildNodes[j].Name, sText);
                                    }
                                    // 12/18/2005 Paul.  ID can never be NULL.  SugarCRM does not use an ID in the CONFIG or USERS_FEEDS table.
                                    IDbDataParameter parID = Sql.FindParameter(cmdImport, "@ID");
                                    if (parID != null)
                                    {
                                        // 12/18/2005 Paul. GUIDs from SugarCRM may not be 36 characters.
                                        string sID = Sql.ToString(parID.Value);
                                        if (parID.Value != DBNull.Value)
                                        {
                                            if (sID.Length < 36)
                                            {
                                                // 07/31/2006 Paul.  Stop using VisualBasic library to increase compatibility with Mono.
                                                parID.Value = "00000000-0000-0000-0000-000000000000".Substring(0, 36 - sID.Length) + sID;
                                            }
                                        }
                                    }
                                    try
                                    {
                                        cmdImport.ExecuteNonQuery();
                                        Response.Write(" ");
                                    }
                                    catch (Exception ex)
                                    {
                                        LogError(ref sbErrors, Sql.ExpandParameters(cmdImport), ex.Message);
                                        // 12/17/2005 Paul.  If there is an error, stop importing from this table.
                                        // 12/18/2005 Paul.  I'd like to see the first 100 errors.
                                        nTableErrors++;
                                        if (nTableErrors > 100)
                                        {
                                            break;
                                        }
                                    }
                                }
                            }
                            catch (Exception ex)
                            {
                                LogError(ref sbErrors, sTABLE_NAME, ex.Message);
                            }
                        }
                        Response.Write(" ");                         // Write a singe byte to keep the connection open.
                    }
                }
            }
            if (sbErrors.Length > 0)
            {
                throw(new Exception(sbErrors.ToString()));
            }
        }