std::shared_ptr<Aws::Http::HttpRequest> NetlibHttpClientFactory::CreateHttpRequest( const Aws::String& uri, Aws::Http::HttpMethod method, const Aws::IOStreamFactory& streamFactory) const { return CreateHttpRequest(Aws::Http::URI(uri), method, streamFactory); }
void FCrashUpload::PostReportComplete() { if (PauseState == EUploadState::PostingReportComplete) { // Wait for confirmation SetCurrentState(EUploadState::WaitingToPostReportComplete); return; } AssignReportIdToPostDataBuffer(); auto Request = CreateHttpRequest(); Request->SetVerb( TEXT( "POST" ) ); Request->SetURL(UrlPrefix / TEXT("UploadComplete")); Request->SetHeader( TEXT( "Content-Type" ), TEXT( "text/plain; charset=us-ascii" ) ); Request->SetContent(PostData); UE_LOG( CrashReportClientLog, Log, TEXT( "Sending HTTP request: %s" ), *Request->GetURL() ); if (Request->ProcessRequest()) { SetCurrentState(EUploadState::PostingReportComplete); } else { CheckPendingReportsForFilesToUpload(); } }
bool FCrashUpload::SendCheckReportRequest() { FString XMLString; UE_LOG(CrashReportClientLog, Log, TEXT("Sending HTTP request (checking report)")); auto Request = CreateHttpRequest(); if (State == EUploadState::CheckingReport) { AssignReportIdToPostDataBuffer(); Request->SetURL(UrlPrefix / TEXT("CheckReport")); Request->SetHeader(TEXT("Content-Type"), TEXT("text/plain; charset=us-ascii")); } else { // This part is Windows-specific on the server ErrorReport.LoadWindowsReportXmlFile( XMLString ); // Convert the XMLString into the UTF-8. FTCHARToUTF8 Converter( (const TCHAR*)*XMLString, XMLString.Len() ); const int32 Length = Converter.Length(); PostData.Reset( Length ); PostData.AddUninitialized( Length ); CopyAssignItems( (ANSICHAR*)PostData.GetData(), Converter.Get(), Length ); Request->SetURL(UrlPrefix / TEXT("CheckReportDetail")); Request->SetHeader(TEXT("Content-Type"), TEXT("text/plain; charset=utf-8")); } UE_LOG( CrashReportClientLog, Log, TEXT( "PostData Num: %i" ), PostData.Num() ); Request->SetVerb(TEXT("POST")); Request->SetContent(PostData); return Request->ProcessRequest(); }
void FCrashUpload::UploadNextFile() { UE_LOG(CrashReportClientLog, Log, TEXT("UploadNextFile: have %d pending files"), PendingFiles.Num()); // Loop to keep trying files until a send succeeds or we run out of files while (PendingFiles.Num() != 0) { FString PathOfFileToUpload = PendingFiles.Pop(); // Remember if there was already a diagnostics file in the report, so we don't send it twice if (PathOfFileToUpload.EndsWith(GDiagnosticsFilename)) { bDiagnosticsFileSent = true; } if (FPlatformFileManager::Get().GetPlatformFile().FileSize(*PathOfFileToUpload) > MaxFileSizeToUpload) { UE_LOG(CrashReportClientLog, Warning, TEXT("Skipping large crash report file")); continue; } if (!FFileHelper::LoadFileToArray(PostData, *PathOfFileToUpload)) { UE_LOG(CrashReportClientLog, Warning, TEXT("Failed to load crash report file")); continue; } UE_LOG(CrashReportClientLog, Log, TEXT("UploadNextFile: uploading %d bytes ('%s')"), PostData.Num(), *PathOfFileToUpload); FString Filename = FPaths::GetCleanFilename(PathOfFileToUpload); if (Filename == "diagnostics.txt") { // Ensure diagnostics file is capitalized for server Filename[0] = 'D'; } // Set up request for upload UE_LOG(CrashReportClientLog, Log, TEXT("Sending HTTP request (posting file)")); auto Request = CreateHttpRequest(); Request->SetVerb(TEXT("POST")); Request->SetHeader(TEXT("Content-Type"), TEXT("application/octet-stream")); Request->SetURL(UrlPrefix / TEXT("UploadReportFile")); Request->SetContent(PostData); Request->SetHeader(TEXT("DirectoryName"), *ErrorReport.GetReportDirectoryLeafName()); Request->SetHeader(TEXT("FileName"), Filename); Request->SetHeader(TEXT("FileLength"), FString::FromInt(PostData.Num())); if (Request->ProcessRequest()) { return; } UE_LOG(CrashReportClientLog, Warning, TEXT("Failed to send file upload request")); } PostReportComplete(); }
void FCrashUpload::SendPingRequest() { SetCurrentState(EUploadState::PingingServer); auto Request = CreateHttpRequest(); Request->SetVerb(TEXT("GET")); Request->SetURL(UrlPrefix / TEXT("Ping")); UE_LOG( CrashReportClientLog, Log, TEXT( "Sending HTTP request: %s" ), *Request->GetURL() ); if (Request->ProcessRequest()) { FTicker::GetCoreTicker().AddTicker(FTickerDelegate::CreateRaw(this, &FCrashUpload::PingTimeout), PingTimeoutSeconds); } else { PingTimeout(0); } }
void FCrashUpload::CompressAndSendData() { UE_LOG(CrashReportClientLog, Log, TEXT("CompressAndSendData have %d pending files"), PendingFiles.Num()); // Compress all files into one archive. const int32 BufferSize = 16*1024*1024; TArray<uint8> UncompressedData; UncompressedData.Reserve( BufferSize ); FMemoryWriter MemoryWriter( UncompressedData, false, true ); int32 CurrentFileIndex = 0; // Loop to keep trying files until a send succeeds or we run out of files while (PendingFiles.Num() != 0) { const FString PathOfFileToUpload = PendingFiles.Pop(); if (FPlatformFileManager::Get().GetPlatformFile().FileSize(*PathOfFileToUpload) > MaxFileSizeToUpload) { UE_LOG(CrashReportClientLog, Warning, TEXT("Skipping large crash report file")); continue; } if (!FFileHelper::LoadFileToArray(PostData, *PathOfFileToUpload)) { UE_LOG(CrashReportClientLog, Warning, TEXT("Failed to load crash report file")); continue; } const bool bSkipLogFile = !FCrashReportClientConfig::Get().GetSendLogFile() && PathOfFileToUpload.EndsWith( TEXT( ".log" ) ); if (bSkipLogFile) { UE_LOG( CrashReportClientLog, Warning, TEXT( "Skipping the log file" ) ); continue; } UE_LOG(CrashReportClientLog, Log, TEXT("CompressAndSendData compressing %d bytes ('%s')"), PostData.Num(), *PathOfFileToUpload); FString Filename = FPaths::GetCleanFilename(PathOfFileToUpload); if (Filename == "diagnostics.txt") { // Ensure diagnostics file is capitalized for server Filename[0] = 'D'; } FCompressedCrashFile FileToCompress( CurrentFileIndex, Filename, PostData ); CurrentFileIndex++; MemoryWriter << FileToCompress; } uint8* CompressedDataRaw = new uint8[BufferSize]; int32 CompressedSize = BufferSize; int32 UncompressedSize = UncompressedData.Num(); const bool bResult = FCompression::CompressMemory( COMPRESS_ZLIB, CompressedDataRaw, CompressedSize, UncompressedData.GetData(), UncompressedSize ); if( !bResult ) { UE_LOG(CrashReportClientLog, Warning, TEXT("Couldn't compress the crash report files")); SetCurrentState(EUploadState::Cancelled); return; } const FString Filename = ErrorReport.GetReportDirectoryLeafName() + TEXT(".ue4crash"); // Copy compressed data into the array. TArray<uint8> CompressedData; CompressedData.Append( CompressedDataRaw, CompressedSize ); delete [] CompressedDataRaw; CompressedDataRaw = nullptr; // Set up request for upload auto Request = CreateHttpRequest(); Request->SetVerb(TEXT("POST")); Request->SetHeader(TEXT("Content-Type"), TEXT("application/octet-stream")); Request->SetURL(UrlPrefix / TEXT("UploadReportFile")); Request->SetContent(CompressedData); Request->SetHeader(TEXT("DirectoryName"), *ErrorReport.GetReportDirectoryLeafName()); Request->SetHeader(TEXT("FileName"), Filename); Request->SetHeader(TEXT("FileLength"), TTypeToString<int32>::ToString(CompressedData.Num()) ); Request->SetHeader(TEXT("CompressedSize"), TTypeToString<int32>::ToString(CompressedSize) ); Request->SetHeader(TEXT("UncompressedSize"), TTypeToString<int32>::ToString(UncompressedSize) ); Request->SetHeader(TEXT("NumberOfFiles"), TTypeToString<int32>::ToString(CurrentFileIndex) ); UE_LOG( CrashReportClientLog, Log, TEXT( "Sending HTTP request: %s" ), *Request->GetURL() ); if (Request->ProcessRequest()) { return; } else { UE_LOG(CrashReportClientLog, Warning, TEXT("Failed to send file upload request")); SetCurrentState(EUploadState::Cancelled); } }