void PrintConnectionResults()

in ctsTraffic/ctsConfig.cpp [3629:3771]


void PrintConnectionResults(const ctSockaddr& localAddr, const ctSockaddr& remoteAddr, uint32_t error, const ctsUdpStatistics& stats) noexcept try
{
    ctsConfigInitOnce();

    // write even after shutdown so can print the final summaries
    auto writeToConsole = false;
    // ReSharper disable once CppDefaultCaseNotHandledInSwitchStatement
    switch (g_consoleVerbosity) // NOLINT(hicpp-multiway-paths-covered)
    {
        // case 0: // nothing
        // case 1: // status updates
        // case 2: // error info
        case 3: // connection info
        case 4: // connection info + error info
        case 5: // connection info + error info + status updates
        case 6: // above + debug info
        {
            writeToConsole = true;
        }
    }

    enum class ErrorType
    {
        Success,
        NetworkError,
        ProtocolError
    } errorType{};

    if (0 == error)
    {
        errorType = ErrorType::Success;
    }
    else if (ctsIoPattern::IsProtocolError(error))
    {
        errorType = ErrorType::ProtocolError;
    }
    else
    {
        errorType = ErrorType::NetworkError;
    }

    const float currentTime = GetStatusTimeStamp();
    const int64_t elapsedTime(stats.m_endTime.GetValue() - stats.m_startTime.GetValue());
    const int64_t bitsPerSecond = elapsedTime > 0LL ? stats.m_bitsReceived.GetValue() * 1000LL / elapsedTime : 0LL;

    wstring csvString;
    wstring textString;
    wstring errorString;
    if (ErrorType::ProtocolError != errorType)
    {
        if (0 == error)
        {
            errorString = L"Succeeded";
        }
        else
        {
            errorString = wil::str_printf<std::wstring>(
                L"%lu: %ws",
                error,
                ctString::ctFormatMessage(error).c_str());
            // remove any commas from the formatted string - since that will mess up csv files
            ctString::ctReplaceAll(errorString, L",", L" ");
        }
    }

    if (g_connectionLogger && g_connectionLogger->IsCsvFormat())
    {
        // csv format : "TimeSlice,LocalAddress,RemoteAddress,Bits/Sec,Completed,Dropped,Repeated,Errors,Result,ConnectionId"
        static const auto* udpResultCsvFormat = L"%.3f,%ws,%ws,%llu,%llu,%llu,%llu,%llu,%ws,%hs\r\n";
        csvString = wil::str_printf<std::wstring>(
            udpResultCsvFormat,
            currentTime,
            localAddr.WriteCompleteAddress().c_str(),
            remoteAddr.WriteCompleteAddress().c_str(),
            bitsPerSecond,
            stats.m_successfulFrames.GetValue(),
            stats.m_droppedFrames.GetValue(),
            stats.m_duplicateFrames.GetValue(),
            stats.m_errorFrames.GetValue(),
            ErrorType::ProtocolError == errorType ?
            ctsIoPattern::BuildProtocolErrorString(error) :
            errorString.c_str(),
            stats.m_connectionIdentifier);
    }
    // we'll never write csv format to the console so we'll need a text string in that case
    // - and/or in the case the g_ConnectionLogger isn't writing to csv
    if (writeToConsole || g_connectionLogger && !g_connectionLogger->IsCsvFormat())
    {
        if (0 == error)
        {
            static const auto* udpSuccessfulResultTextFormat = L"[%.3f] UDP connection succeeded : [%ws - %ws] [%hs] : BitsPerSecond [%llu]  Completed [%llu]  Dropped [%llu]  Repeated [%llu]  Errors [%llu]";
            textString = wil::str_printf<std::wstring>(
                udpSuccessfulResultTextFormat,
                currentTime,
                localAddr.WriteCompleteAddress().c_str(),
                remoteAddr.WriteCompleteAddress().c_str(),
                stats.m_connectionIdentifier,
                bitsPerSecond,
                stats.m_successfulFrames.GetValue(),
                stats.m_droppedFrames.GetValue(),
                stats.m_duplicateFrames.GetValue(),
                stats.m_errorFrames.GetValue());
        }
        else
        {
            static const auto* udpProtocolFailureResultTextFormat = L"[%.3f] UDP connection failed with the protocol error %ws : [%ws - %ws] [%hs] : BitsPerSecond [%llu]  Completed [%llu]  Dropped [%llu]  Repeated [%llu]  Errors [%llu]";
            static const auto* udpNetworkFailureResultTextFormat = L"[%.3f] UDP connection failed with the error %ws : [%ws - %ws] [%hs] : BitsPerSecond [%llu]  Completed [%llu]  Dropped [%llu]  Repeated [%llu]  Errors [%llu]";
            textString = wil::str_printf<std::wstring>(
                ErrorType::ProtocolError == errorType ? udpProtocolFailureResultTextFormat : udpNetworkFailureResultTextFormat,
                currentTime,
                ErrorType::ProtocolError == errorType ?
                ctsIoPattern::BuildProtocolErrorString(error) :
                errorString.c_str(),
                localAddr.WriteCompleteAddress().c_str(),
                remoteAddr.WriteCompleteAddress().c_str(),
                stats.m_connectionIdentifier,
                bitsPerSecond,
                stats.m_successfulFrames.GetValue(),
                stats.m_droppedFrames.GetValue(),
                stats.m_duplicateFrames.GetValue(),
                stats.m_errorFrames.GetValue());
        }
    }

    if (writeToConsole)
    {
        // text strings always go to the console
        wprintf(L"%ws\n", textString.c_str());
    }

    if (g_connectionLogger)
    {
        if (g_connectionLogger->IsCsvFormat())
        {
            g_connectionLogger->LogMessage(csvString.c_str());
        }
        else
        {
            g_connectionLogger->LogMessage(
                wil::str_printf<std::wstring>(L"%ws\r\n", textString.c_str()).c_str());
        }
    }
}