From 3abbb94727331743dc5d38c964e5cfaaae17de3f Mon Sep 17 00:00:00 2001 From: Nick Gammon Date: Wed, 9 Apr 2014 15:59:34 +1000 Subject: [PATCH] Added option 'log_script_errors' for logging script errors --- doc.h | 5 +++ doc_construct.cpp | 1 + plugins/Config_Option_Changer.xml | 1 + scripting/lua_scripting.cpp | 74 ++++++++++++++++++++++++------- scripting/scripting.cpp | 42 +++++++++++++++++- scriptingoptions.cpp | 1 + 6 files changed, 106 insertions(+), 18 deletions(-) diff --git a/doc.h b/doc.h index afbf989f..4d4df9f2 100644 --- a/doc.h +++ b/doc.h @@ -899,6 +899,10 @@ class CMUSHclientDoc : public CDocument unsigned int m_iToolTipVisibleTime; // Time tooltip stays visible (milliseconds) unsigned int m_iToolTipStartTime; // Time before tooltip appears (milliseconds) + + // version 4.92 + unsigned short m_bLogScriptErrors; // write scripting error messages to log file? + // end of stuff saved to disk ************************************************************** // stuff from pre version 11, read from disk but not saved @@ -1914,6 +1918,7 @@ class CMUSHclientDoc : public CDocument ); void ShowErrorLines (const int iLine); // show script file around the error point + void WriteErrorLines (const int iLine, FILE * f); // write script file around the error point to file f void ShowStatusLine (const bool bNow = false); // update the status line diff --git a/doc_construct.cpp b/doc_construct.cpp index c7350595..e6aff5e0 100644 --- a/doc_construct.cpp +++ b/doc_construct.cpp @@ -112,6 +112,7 @@ int i; m_bDoNotShowOutstandingLines = false; m_bDoNotTranslateIACtoIACIAC = false; m_bAutoResizeCommandWindow = false; + m_bLogScriptErrors = false; m_iAutoResizeMinimumLines = 1; m_iAutoResizeMaximumLines = 20; m_bDoNotAddMacrosToCommandHistory = false; diff --git a/plugins/Config_Option_Changer.xml b/plugins/Config_Option_Changer.xml index 3c184338..ad27b669 100644 --- a/plugins/Config_Option_Changer.xml +++ b/plugins/Config_Option_Changer.xml @@ -66,6 +66,7 @@ boolean_options = { do_not_add_macros_to_command_history = { desc = 'Add macros to command history?' , invert = true }, do_not_show_outstanding_lines = { desc = 'Show outstanding lines count?' , invert = true }, do_not_translate_iac_to_iac_iac = { desc = 'Translate IAC to IAC IAC?' , invert = true }, + log_script_errors = { desc = 'Log scripting errors?' }, play_sounds_in_background = { desc = 'Play sounds in background?' }, send_keep_alives = { desc = 'Send keep-alives?' }, wrap_input = { desc = 'Wrap command window at output wrap column' }, diff --git a/scripting/lua_scripting.cpp b/scripting/lua_scripting.cpp index 9cd14a5b..d50f5849 100644 --- a/scripting/lua_scripting.cpp +++ b/scripting/lua_scripting.cpp @@ -372,18 +372,36 @@ void LuaError (lua_State *L, dlg.m_strRaisedBy = "World: " + pDoc->m_mush_name; } + // work out the line number where the error is + bool bImmediate = true; + int nLine = 0; + + if (dlg.m_strDescription.Left (18) == "[string \"Plugin\"]:") + { + bImmediate = false; + nLine = atoi (dlg.m_strDescription.Mid (18)); + } + else if (dlg.m_strDescription.Left (23) == "[string \"Script file\"]:") + { + bImmediate = false; + nLine = atoi (dlg.m_strDescription.Mid (23)); + } + + // if no document, or errors to the output window are not wanted, display the dialog box if (!pDoc || !pDoc->m_bScriptErrorsToOutputWindow) { if (pDoc) dlg.m_bHaveDoc = true; dlg.DoModal (); + + // do they want to change from the dialog box to the output window? if (pDoc && dlg.m_bUseOutputWindow) { pDoc->m_bScriptErrorsToOutputWindow = true; pDoc->SetModifiedFlag (TRUE); - } + } // end of future errors wanted in output window - } + } // end of dialog box wanted else { pDoc->ColourNote (SCRIPTERRORFORECOLOUR, SCRIPTERRORBACKCOLOUR, strEvent); @@ -391,26 +409,48 @@ void LuaError (lua_State *L, pDoc->ColourNote (SCRIPTERRORFORECOLOUR, SCRIPTERRORBACKCOLOUR, dlg.m_strCalledBy); pDoc->ColourNote (SCRIPTERRORFORECOLOUR, SCRIPTERRORBACKCOLOUR, dlg.m_strDescription); -// show bad lines? + // show bad lines? + if (!bImmediate) + pDoc->ShowErrorLines (nLine); + + } // end of showing in output window - bool bImmediate = true; - int nLine = 0; - if (dlg.m_strDescription.Left (18) == "[string \"Plugin\"]:") + // if option "log_script_errors" is active, append to the error log file + if (pDoc && pDoc->m_bLogScriptErrors) + { + string fileName = App.m_strDefaultLogFileDirectory; + fileName += "script_error_log.txt"; + + FILE * errorLogFile = fopen (fileName.c_str(), "a+"); + if (!errorLogFile) { - bImmediate = false; - nLine = atoi (dlg.m_strDescription.Mid (18)); + pDoc->ColourTell (SCRIPTERRORFORECOLOUR, SCRIPTERRORBACKCOLOUR, "Cannot open error log file: "); + pDoc->ColourNote (SCRIPTERRORFORECOLOUR, SCRIPTERRORBACKCOLOUR, fileName.c_str()); } - else if (dlg.m_strDescription.Left (23) == "[string \"Script file\"]:") + else { - bImmediate = false; - nLine = atoi (dlg.m_strDescription.Mid (23)); - } - - if (!bImmediate) - pDoc->ShowErrorLines (nLine); - - } // end of showing in output window + CTime timeNow = CTime::GetCurrentTime(); + + CString strConnected = timeNow.Format ( + TranslateTime ("\n\n--- Scripting error on %A, %B %d, %Y, %#I:%M %p ---\n\n")); + fputs ((LPCTSTR) strConnected, errorLogFile); + fputs (strEvent, errorLogFile); + fputs ("\n", errorLogFile); + fputs (dlg.m_strRaisedBy, errorLogFile); + fputs ("\n", errorLogFile); + fputs (dlg.m_strCalledBy, errorLogFile); + fputs ("\n", errorLogFile); + fputs (dlg.m_strDescription, errorLogFile); + fputs ("\n", errorLogFile); + // show bad lines? + if (!bImmediate) + pDoc->WriteErrorLines (nLine, errorLogFile); + fclose (errorLogFile); + } // end of file opened OK + + + } // end of have a document, and the error file is wanted } // end of LuaError diff --git a/scripting/scripting.cpp b/scripting/scripting.cpp index d0236ec8..fdbc0752 100644 --- a/scripting/scripting.cpp +++ b/scripting/scripting.cpp @@ -532,5 +532,45 @@ vector v; } // end of line in range - } + } // end of CMUSHclientDoc::ShowErrorLines + + +void CMUSHclientDoc::WriteErrorLines (const int iLine, FILE * f) // show script file around the error point + { + +string sScript; +vector v; + + if (m_CurrentPlugin) + sScript = m_CurrentPlugin->m_strScript; + else + sScript = m_strScript; + + StringToVector (sScript, v, "\n", false); // break script into lines so we can easily show each one + + // provided wanted line is in the table + if (!sScript.empty () && v.size () >= iLine) + { + fputs (Translate ("Error context in script:\n"), f); + + int iStart = iLine - 4; // start 4 lines back + if (iStart < 1) + iStart = 1; // can't be lower than first line + + int iEnd = iLine + 4; // end 4 lines onwards + + if (iEnd > v.size ()) + iEnd = v.size (); // or at last line in script + + // show that range, marking error line with an asterisk + for (int i = iStart; i <= iEnd; i++) + fputs (CFormat ("%4i%s: %s\n", + i, // line number + i == iLine ? "*" : " ", // mark current line + (v [i - 1]).c_str ()), // vector is zero-relative + f); + + } // end of line in range + + } // end of CMUSHclientDoc::WriteErrorLines diff --git a/scriptingoptions.cpp b/scriptingoptions.cpp index caddb264..f5171745 100644 --- a/scriptingoptions.cpp +++ b/scriptingoptions.cpp @@ -135,6 +135,7 @@ tConfigurationNumericOption OptionsTable [] = { {"log_notes", false, O(m_bLogNotes)}, {"log_output", true, O(m_bLogOutput)}, {"log_raw", false, O(m_bLogRaw)}, +{"log_script_errors", false, O(m_bLogScriptErrors)}, {"lower_case_tab_completion", false, O(m_bLowerCaseTabCompletion)}, {"map_failure_regexp", false, O(m_bMapFailureRegexp)}, {"max_output_lines", 5000, O(m_maxlines), 200, 500000, OPT_FIX_OUTPUT_BUFFER},