-----------------------------------

Acquista i software ArcGIS tramite Studio A&T srl, rivenditore autorizzato dei prodotti Esri.

I migliori software GIS, il miglior supporto tecnico!

I migliori software GIS, il miglior supporto tecnico!
Azienda operante nel settore GIS dal 2001, specializzata nell’utilizzo della tecnologia ArcGIS e aderente ai programmi Esri Italia Business Network ed Esri Partner Network

-----------------------------------



lunedì 23 novembre 2009

Geoprocessing message & log4net in arcgis desktop

Quando eseguiamo un processo di Geoprocessing attraverso gli ArcObjects, possiamo a runtime ricevere i messaggi che il processo stesso genera. Per poter 'catturare' i messaggi possiamo creare una classe che implementa l'interfaccia IGeoProcessorEvents.

public class GPMessageEventHandler : IGeoProcessorEvents
{

    private MessageDetails messageDetails = null;


    public GPMessageEventHandler(MessageDetails messageDetails)
    {
        this.messageDetails = messageDetails;
    }


    public void OnMessageAdded(IGPMessage message)
    {
        this.messageDetails(message);
    }


    public void PostToolExecute(IGPTool tool, IArray values, int result, IGPMessages messages)
    {
    }


    public void PreToolExecute(IGPTool tool, IArray values, int processID)
    {
    }


    public void ToolboxChange()
    {
    }
}

Prima di eseguire il geoprocesso registriamo l'istanza della classe che riceve gli eventi mediante RegisterGeoProcessorEvents.


private static readonly log4net.ILog log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
    private static readonly bool isDebugEnabled = log.IsDebugEnabled;

    public static void RunTool(Geoprocessor geoprocessor, IGPProcess process, ESRI.ArcGIS.esriSystem.ITrackCancel trackCancel, MessageDetails messageDetails)
    {
        try
        {
            // Set the overwrite output option to true
            geoprocessor.OverwriteOutput = true;

            IGeoProcessorEvents geoProcessorEvents = new GPMessageEventHandler(messageDetails);
            if (isDebugEnabled)
            {
                log.Debug("RegisterGeoProcessorEvents");
            }
            geoprocessor.RegisterGeoProcessorEvents(geoProcessorEvents);
            if (isDebugEnabled)
            {
                log.Debug("Execute the tool");
            }
            geoprocessor.Execute(process, trackCancel);

            if (isDebugEnabled)
            {
                log.Debug("UnRegisterGeoProcessorEvents");
            }
            geoprocessor.UnRegisterGeoProcessorEvents(geoProcessorEvents);
        }
        catch(Exception ex)
        {
            ExceptionHandler.ThrowException(ex, typeof(Helper));
        }
    }


Nel costruttore della classe, che riceve gli eventi, passiamo il delegato che si occupa di visualizzare i messaggi ( messageDetails ).

Nel nostro caso il delegato è dichiarato nel seguente modo:

public delegate void MessageDetails(IGPMessage data);

e nella windows form, il metodo di tipo MessageDetails, che visualizza i messaggi è:

public void WriteDetails(IGPMessage message)
    {
        // Font font = new Font("Tahoma", 8, FontStyle.Regular);
        // richTextBox1.SelectionFont = font;
        Color color = Color.Black;
        if (message.IsError())
        {
            color = Color.Red;
        }
        else if (message.IsWarning())
        {
            color = Color.Green;
        }
        else if (message.IsAbort())
        {
            color = Color.DarkMagenta;
        }

        rtbDetails.SelectionColor = color;
        rtbDetails.SelectedText = message.Description;
        rtbDetails.SelectionStart = rtbDetails.Text.Length;
        rtbDetails.ScrollToCaret();
        rtbDetails.AppendText(System.Environment.NewLine);
    }

Poichè il controllo di output è di tipo RichTextBox, possiamo formattarlo in funzione del tipo di messaggio (come fa il GeoProcessing degli ArcToolBox).

Volevo aprire una parentesi riguardo alla possibilità di utilizzare log4net come logger per la dll.

Impostiamo il file di appender a runtime:



XmlConfigurator.Configure(new System.IO.FileInfo(string.Format("{0}\\logging.config", codeBase)));
        IAppender appender = log4net.LogManager.GetRepository().GetAppenders()[0];

        FileAppender fileAppender = appender as FileAppender;
        fileAppender.File = Path.Combine(codeBase, "GPExtensionLog.txt");
        fileAppender.ActivateOptions();


e  utilizziamo una classe di handler per le eccezioni:

public static class ExceptionHandler
{
    private static readonly log4net.ILog log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

    public static void ThrowException(Exception e, Type source, string message)
    {
        log.Error("Exception: " + message);
        log.Error("{" + source + "} " + e.Message + ", StackTrace: " + e.StackTrace);
        throw e;
    }

    public static void ThrowException(Exception e, Type source)
    {
        log.Error("{" + source + "} " + e.Message + ", StackTrace: " + e.StackTrace);
        throw e;
    }
}


per poi utilizzarla:

   geoprocessor.UnRegisterGeoProcessorEvents(geoProcessorEvents);
        }
        catch(Exception ex)
        {
            ExceptionHandler.ThrowException(ex, typeof(Helper));
        }



Scarica qui la soluzione

1 commento:

Stefano Pili ha detto...

Salve a tutti,
Vorrei sapere se qualcuno ha una soluzione per questo problema riguardante un custom toolset di arcmap 10.0. Uno dei modelli (fatto col model builder e che ho già usato molte volte con successo) che sta dentro il mio toolset ha fatto errore bloccandosi; come spesso mi accade anche arcmap si è bloccato ed ho dovuto chiuderlo forzatamente dal task manager di windows. Questa volta però al riavvio del programma tutto il toolset è sparito dal mio toolbox, al tentativo di reinserimento il mio custom toolset è visibile ma il programma (sia arcmap che arccatalog) non sembra in grado di importarlo o di accederci in alcun modo. I comandi del menù del tasto destro (copia, rimuovi, rinomina,...) sono attivi ma non danno risultati, l'unico funzionante è item descriptions che da il messagio "The item's XML contains errors". Ho provato a recuperalo in altri pc anche con versioni diverse di arcmap, ma nulla; al contrario windows sembra essere in grado di copiare, incollare e rinominare il file, interrogando le proprietà non sembrano esserci problemi la dimensione del file è corretta.
Dentro il toolset ci sono diversi modelli che mi sono fondamentali per completare la mia ricerca qualcuno conosce un modo per aprirlo e recuperare i contenuti di questi file tbx?
Grazie in anticipo