void DiagnosticsWorkflow_DiscoverAndUploadLogs()

in src/diagnostics_component/diagnostics_workflow/src/diagnostics_workflow.c [247:432]


void DiagnosticsWorkflow_DiscoverAndUploadLogs(const DiagnosticsWorkflowData* workflowData, const char* jsonString)
{
    Log_Info("Starting Diagnostics Log Upload");

    Diagnostics_Result result = Diagnostics_Result_Failure;

    JSON_Value* cloudMsgJson = NULL;
    char* deviceName = NULL;
    STRING_HANDLE operationId = NULL;

    STRING_HANDLE storageSasCredential = NULL;
    char* storageSasCredentialMemory = NULL;

    VECTOR_HANDLE logComponentFileNames = NULL;

    if (jsonString == NULL)
    {
        goto done;
    }

    if (workflowData == NULL)
    {
        result = Diagnostics_Result_NoDiagnosticsComponents;
        goto done;
    }

    const size_t numComponents = VECTOR_size(workflowData->components);

    if (numComponents == 0)
    {
        result = Diagnostics_Result_NoDiagnosticsComponents;
        goto done;
    }

    cloudMsgJson = json_parse_string(jsonString);

    if (cloudMsgJson == NULL)
    {
        goto done;
    }

    JSON_Object* cloudMsgObj = json_value_get_object(cloudMsgJson);

    if (cloudMsgObj == NULL)
    {
        goto done;
    }

    operationId = STRING_construct(json_object_get_string(cloudMsgObj, DIAGNOSTICSITF_FIELDNAME_OPERATIONID));

    if (operationId == NULL)
    {
        result = Diagnostics_Result_NoOperationId;
        goto done;
    }

    storageSasCredential = DiagnosticsComponent_CreateSasCredential(
        json_object_get_string(cloudMsgObj, DIAGNOSTICSITF_FIELDNAME_SASURL), &storageSasCredentialMemory);

    if (storageSasCredential == NULL)
    {
        result = Diagnostics_Result_NoSasCredential;
        goto done;
    }

    const long long uploadSizePerComponent = workflowData->maxBytesToUploadPerLogPath;

    if (uploadSizePerComponent == 0)
    {
        goto done;
    }

    if (!DiagnosticsComponent_GetDeviceName(&deviceName))
    {
        goto done;
    }

    logComponentFileNames = VECTOR_create(sizeof(VECTOR_HANDLE));

    if (logComponentFileNames == NULL)
    {
        goto done;
    }

    //
    // Perform Discovery
    //
    for (size_t i = 0; i < numComponents; ++i)
    {
        const DiagnosticsLogComponent* logComponent =
            DiagnosticsConfigUtils_GetLogComponentElem(workflowData, (unsigned int)i);

        if (logComponent == NULL || logComponent->componentName == NULL || logComponent->logPath == NULL)
        {
            Log_Error("DiagnosticsWorkflow_UploadLogs WorkflowData has uninitialized components");
            goto done;
        }

        VECTOR_HANDLE discoveredFileNames = NULL;

        result = DiagnosticsWorkflow_GetFilesForComponent(&discoveredFileNames, logComponent, uploadSizePerComponent);

        if (result != Diagnostics_Result_Success || discoveredFileNames == NULL)
        {
            goto done;
        }

        if (VECTOR_push_back(logComponentFileNames, &discoveredFileNames, 1) != 0)
        {
            goto done;
        }
    }

    //
    // Perform Upload
    //
    for (size_t i = 0; i < numComponents; ++i)
    {
        const DiagnosticsLogComponent* logComponent =
            DiagnosticsConfigUtils_GetLogComponentElem(workflowData, (unsigned int)i);

        if (logComponent == NULL || logComponent->componentName == NULL || logComponent->logPath == NULL)
        {
            Log_Error("DiagnosticsWorkflow_UploadLogs WorkflowData has uninitialized components");
            goto done;
        }

        const VECTOR_HANDLE* discoveredLogFileNames = VECTOR_element(logComponentFileNames, i);

        if (discoveredLogFileNames == NULL)
        {
            goto done;
        }

        result = DiagnosticsWorkflow_UploadFilesForComponent(
            *discoveredLogFileNames,
            logComponent,
            deviceName,
            STRING_c_str(operationId),
            STRING_c_str(storageSasCredential));

        if (result != Diagnostics_Result_Success)
        {
            goto done;
        }
    }

    result = Diagnostics_Result_Success;

done:

    //
    // Report state back to the iothub
    //
    if (operationId == NULL)
    {
        DiagnosticsInterface_ReportStateAndResultAsync(result, "");
    }
    else
    {
        DiagnosticsInterface_ReportStateAndResultAsync(result, STRING_c_str(operationId));

        //
        // Required to prevent duplicate requests coming down from the service after
        // restart or a connection refresh
        //
        if (!OperationIdUtils_StoreCompletedOperationId(STRING_c_str(operationId)))
        {
            Log_Warn("Unable to record completed operation-id: %s", STRING_c_str(operationId));
        }
    }

    if (logComponentFileNames != NULL)
    {
        DiagnosticsWorkflow_UnInitLogComponentFileNames(logComponentFileNames);
        VECTOR_destroy(logComponentFileNames);
    }

    free(deviceName);

    STRING_delete(operationId);

    DiagnosticsComponent_SecurelyFreeSasCredential(&storageSasCredential, &storageSasCredentialMemory);

    json_value_free(cloudMsgJson);
}