Monitorare il flusso dei programmi con MioDebug()

Quante volte un utilizzatore di un vostro software vi ha detto: "boh, mi ha dato errore!" E' buona norma, in fase di debug e in versione release, dotarsi di uno strumento che salva in un file testo, le operazioni ritenute cruciali per il corretto proseguimento del programma stesso. E' un concetto che sicuramente è già chiaro nella mente di un programmatore, ma solitamente si evita di scrivere quella riga, che invece è basilare per la verifica che il codice esegua veramente quello che si è pensato. Imponendosi di inserire tale strumento saprete se:

  1.  Il vostro codice esegue inutilmente porzioni di programma, o le esegue più volte.

  2.  Gli input dell'utente non sono corretti, e se il codice attua le opportune verifiche in maniera adeguata.

  3.  La generazione di percorsi/percorsirete con concatenazioni di stringhe sono corretti, stesso discorso per gli indirizzi web.

  4.  Il contenuto di alcune variabili hanno i valori nel range prefissato.

  5.  Ad una condizione viene effettivamente eseguita la routine assegnata.

  6.  Il programma usato è la versione corretta.

  7.  Il programma (apertura, chiusura, quante volte, ecc ecc), viene utilizzato.

la subroutine è molto semplice:

Private Sub MioDebug(ByVal Messaggio As String)
    If MioDebugON = False Then Exit Sub ' la subroutine non viene eseguita con MioDebugON=False
    Dim PercorsoLog As String = Application.StartupPath & "MioLog.txt"
    Dim AppLogger As System.IO.StreamWriter ' preparo per la scrittura del file
    AppLogger = My.Computer.FileSystem.OpenTextFileWriter(PercorsoLog, True) ' apro un file in scrittura append
    Dim OraData As String = Date.Now.ToString ' leggo la data e l'ora del computer
    AppLogger.WriteLine(OraData & " - " & Messaggio) ' scrivo il file
    AppLogger.Close() ' chiudo il file
End Sub

Prima di richiamare la subroutine con MioDebug(testo), impostare la variabile Booleana MioDebugON a TRUE.

Consiglio di inserire a inizio testo ! quando si esegue un'operazione, ? quando si eseguono correttivi, = quando una operazione condizionata è stata correttamente svolta.

Nell'esempio che segue in Vb .NET, ma il concetto è valido per tutti i linguaggi, spero di convincervi che i benefici ricavati da tale approcio sono di gran lunga superiori al fastidio di scrivere quella riga di programma in più.

In questo esempio l'uso di MioDebug(Messaggio) è volutamente esagerato.

Public Class Form1

    '**************************************************************
    '*                                                            *         
    '*              Esempio di uso MioDebug(Messaggio)            *
    '*                                                            *
    '* dopo aver visto l'esempio                                  *  
    '* copia e incolla sui tuoi progetti la sub:                  *
    '* Private Sub MioDebug(ByVal Messaggio As String)            *
    '* inizializza la variabile: Dim MioDebugON As Boolean = True *
    '*                                                            *  
    '* richiama la routine quando vuoi, ed avrai un log che       *
    '* monitorizza il flusso del tuo programma, salvato nella     *
    '* cartella di lavoro con nome MioLog.txt                     *
    '*                                                            *
    '**************************************************************

    ' inutile solo per l'esempio
    Dim lblInfo As Label
    Dim lblPercorso As Label
    Dim texInput As TextBox
    Dim butVedi As Button
    Dim butOk As Button
    Dim lboxVedi As ListBox
    '---------------------------

    '--------------------------------------------------------------------------------------
    Dim MioDebugON As Boolean = True ' attenzione abilita e disabilita la scrittura del log
    '--------------------------------------------------------------------------------------

    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load

        MioDebug("--------------------------------")
        MioDebug("Programma avviato versione 2.0.0")
        MioDebug("--------------------------------")

        '-  vostro codice
        '-
        '-
        '-
        '-  creazione del form inutile solo per esempio
        '-
        Me.Width = 600
        lblPercorso = New Label
        lblPercorso.Top = Me.Height - 50
        lblPercorso.Left = 20
        lblPercorso.AutoSize = True
        Me.Controls.Add(lblPercorso)
        lblInfo = New Label
        lblInfo.Top = 50
        lblInfo.Left = 20
        lblInfo.AutoSize = True
        Me.Controls.Add(lblInfo)
        lblInfo.Font = New Font("Microsoft San Serif", 12, FontStyle.Bold)
        lblInfo.Text = "Inserisci un valore tra 10 e 100"

        MioDebug("! Label ""lblInfo"" e ""lblPercorso"" posizionate sul form")

        texInput = New TextBox
        texInput.Left = 300
        texInput.Top = 50
        texInput.Width = 50
        texInput.AcceptsReturn = True
        Me.Controls.Add(texInput)

        MioDebug("! TextBox ""texInput""  posizionata sul form")

        butVedi = New Button
        butVedi.Left = 20
        butVedi.Top = 90
        butVedi.Text = "vedi log"
        Me.Controls.Add(butVedi)
        AddHandler butVedi.Click, AddressOf butVedi_OnClick ' evento click
        butOk = New Button
        butOk.Left = 355
        butOk.Top = 49
        butOk.Width = 40
        butOk.Text = "Ok"
        Me.Controls.Add(butOk)
        AddHandler butOk.Click, AddressOf butOk_OnClick ' evento click

        MioDebug("! Buttons ""butVedi"" e ""butOk"" posizionati sul form")

        lboxVedi = New ListBox
        lboxVedi.Left = 100
        lboxVedi.Top = 90
        lboxVedi.Width = Me.Width - 120
        lboxVedi.Height = 150
        lboxVedi.Text = ""
        Me.Controls.Add(lboxVedi)

        MioDebug("! ListBox ""lbVedi""  posizionato sul form")
        '-
        '- fine creazione form inutile
        '-
        '-
        '-
        '- vostro codice
    End Sub

    Private Sub butVedi_OnClick(ByVal sender As System.Object, ByVal e As System.EventArgs)

        MioDebug("! Chiamata visualizzazione del log")

        Dim QuanteRighe As Integer = 0
        lboxVedi.Items.Clear()
        Dim PercorsoLog As String = Application.StartupPath & "MioLog.txt"
        Dim AppLogger As System.IO.StreamReader
        AppLogger = My.Computer.FileSystem.OpenTextFileReader(PercorsoLog)
        Dim Letto As String = AppLogger.ReadLine() ' leggo la prima riga
        Do Until (Letto = Nothing)
            QuanteRighe += 1
            lboxVedi.Items.Add(Letto)
            Letto = AppLogger.ReadLine() ' leggo le successive
        Loop
        AppLogger.Close()

        MioDebug("! Ho letto " & QuanteRighe & " righe da MioLog.txt")

    End Sub

    Private Sub butOk_OnClick(ByVal sender As System.Object, ByVal e As System.EventArgs)
        Dim InputUtente As Integer = 0
        Dim Esci As Boolean = False

        If texInput.Text = "" Then MioDebug("? L'utente ha cliccato Ok senza aver inserito un valore") : Exit Sub

        Try
            InputUtente = Convert.ToInt32(texInput.Text)
        Catch ex As Exception
            MioDebug("? L'utente ha inserito """ & texInput.Text & """ invece di un valore numerico")
            Esci = True
        End Try

        If Esci Then Exit Sub
        If InputUtente < 10 Or InputUtente > 100 Then
            MioDebug("? L'utente ha inserito """ & texInput.Text & """ invece di un valore tra 10 e 100")
        Else
            MioDebug("= L'utente ha inserito """ & texInput.Text & """ numero accettato")
        End If
    End Sub

    Private Sub Form1_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
        MioDebug("! Programma chiuso")
        End
    End Sub

    ' SUBROUTINE DA COPIARE L'unica cosa che serve veramente
    Private Sub MioDebug(ByVal Messaggio As String)
        ' Poche righe per fare tanto
        If MioDebugON = False Then Exit Sub ' attenzione alla Boolean MioDebugON
        Dim PercorsoLog As String = Application.StartupPath & "MioLog.txt"
        Try ' evita l'errore se la label non c'è...
            lblPercorso.Text = PercorsoLog
        Catch
        End Try
        Dim AppLogger As System.IO.StreamWriter ' preparo per la scrittura del file
        AppLogger = My.Computer.FileSystem.OpenTextFileWriter(PercorsoLog, True) ' apro un file in scrittura append
        Dim OraData As String = Date.Now.ToString ' leggo la data e l'ora del computer
        AppLogger.WriteLine(OraData & " - " & Messaggio) ' scrivo il file
        AppLogger.Close() ' chiudo il file
    End Sub
    '--------------------
End Class

Esempio dell'output