Detectando se (e por que) o Application Insights pode enviar dados de telemetria para o Azure

Estou desenvolvendo um aplicativo da área de trabalho do Windows e vinculei com êxito os assemblies principais do Application Insights. estou a usarTrackTrace, TrackEventetc. para enviar telemetria personalizada.

Em algumas estações de trabalho, a telemetria é enviada com êxito para o portal do Azure e, em outras, não, embora chamadas paraTrackTrace, Flush, etc. ter êxito (ou pelo menos retornar sem gerar uma exceção.TelemetryClient.IsEnabled() retorna verdadeiro. Ambas as estações de trabalho usam umInMemoryChannel, com o mesmo terminalhttps://dc.services.visualstudio.com/v2/track e o intervalo de envio é de 30 segundos.

Existe uma função de API que eu possa chamar no meu aplicativo para obter o status da conexão do TelemetryClient? Algo que me diria que o cliente está conectado com sucesso ou que encontrou um errox enquanto tenta, e ainda temy pacotes de telemetria aguardando envio.

Não estou procurando uma lista de verificação comoreinstalar o pacote NuGet (Eu fiz...),Verifique se o firewall permite que o tráfego seja portado xxx (faz ...) outente instalar o kb ... 871 (Eu fiz isso também ...). O que eu gostaria é de um relatório de status que eu possa registrar em algum lugar na estação de trabalho do cliente enquanto meu aplicativo é executado, pelo menos reconhecendo na barra de status (Sim, eu sei que as barras de status são tão antiquadas hoje em dia) que há um problema.

Primeira atualização - Obtendo o tamanho da fila

Primeira vitória, consegui obter o tamanho da fila. Eu queria fazer isso sem criar minha própria implementação de canal (ainda). No entanto, isso é de pouca ajuda para detectar interrupções, porque a fila será drenada, mesmo que o transmissor não consiga transmitir os itens de telemetria (apenas os descartará) - mais sobre isso posteriormente. Pelo menos você sabe que o fio do transmissor está em execução ...

private ITelemetryChannel _TelemetryChannel;
private InMemoryChannel _InMemoryChannel;
private object _TelemetryBuffer;
private object _BufferLock;
private object _InMemoryTransmitter;

_TelemetryChannel = TelemetryConfiguration.Active?.TelemetryChannel;
if (_TelemetryChannel != null && _TelemetryChannel is InMemoryChannel)
{
  _InMemoryChannel = (InMemoryChannel)_TelemetryChannel;
  _TelemetryBuffer = GetInstanceField (_InMemoryChannel, "buffer");
  _BufferLock = GetInstanceField (_TelemetryBuffer, "lockObj");
  _InMemoryTransmitter = GetInstanceField (_InMemoryChannel, "transmitter");
}

public int GetTelemetryQueueSize ()
{
    if (_BufferLock != null)
    {
        lock (_BufferLock)
        {
            object l = GetInstanceField (_TelemetryBuffer, "items");
            if (l is List<ITelemetry>)
            {
                return ((List<ITelemetry>)l).Count;
            }
        }
    }
    return -1;
}

Você também precisa de uma função utilitária para usar a reflexão para acessar os campos particulares dos objetos (o buffer e o transmissor sãointernal sealed...) Eu os tornei o mais resistentes a erros possível, eles poderiam ser mais concisos.

private static object GetInstanceField (Type type, object instance, string fieldName)
{
    if (instance == null)
    {
        return null;
    }
    try
    {
        BindingFlags bindFlags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static;
        FieldInfo field = type.GetField (fieldName, bindFlags);
        return field.GetValue (instance);
    }
    catch
    {
        return null;
    }
}

private static object GetInstanceField (object instance, string fieldName)
{
    if (instance == null)
    {
        return null;
    }
    return GetInstanceField (instance.GetType (), instance, fieldName);
}

questionAnswers(2)

yourAnswerToTheQuestion