void CTextModeTestMultiTrans::ValidateBodyL(RHTTPTransaction aTransaction) { // In this test, the test URLs point to resources that contain just characters from the test number // i.e. http:/xxx/1.txt will contain only the char 1, CR or LF. // These numbers should also align with the transaction ID, since they were created in order RHTTPResponse resp = aTransaction.Response(); MHTTPDataSupplier* body = resp.Body(); TPtrC8 data; body->GetNextDataPart(data); TChar reqdCh = (TChar)(aTransaction.Id() + 48); for (TInt ii = 0; ii < data.Length(); ii++) { TChar ch = data[ii]; if ((ch != reqdCh) && (ch != (TChar)0x0d) && (ch != (TChar)0x0a)) User::Leave(KMultiTransFailed); } // OK - release the block body->ReleaseData(); }
void CHttpEventHandler::MHFRunL(RHTTPTransaction aTransaction, const THTTPEvent& aEvent) { switch (aEvent.iStatus) { case THTTPEvent::EGotResponseHeaders: { // HTTP response headers have been received. We can determine now if there is // going to be a response body to save. RHTTPResponse resp = aTransaction.Response(); TInt status = resp.StatusCode(); if (iVerbose) { RStringF statusStr = resp.StatusText(); TBuf<32> statusStr16; statusStr16.Copy(statusStr.DesC()); iTest->Console()->Printf(_L("Status: %d (%S)\n"), status, &statusStr16); // Dump the headers if we're being verbose DumpRespHeadersL(aTransaction); } // Determine if the body will be saved to disk iSavingResponseBody = EFalse; if (resp.HasBody() && (status >= 200) && (status < 300) && (status != 204)) { if (iVerbose) { TInt dataSize = resp.Body()->OverallDataSize(); if (dataSize >= 0) iTest->Console()->Printf(_L("Response body size is %d\n"), dataSize); else iTest->Console()->Printf(_L("Response body size is unknown\n")); } iSavingResponseBody = ETrue; } else { if (iVerbose) iTest->Console()->Printf(_L("Response status is bad\n")); } if ((status >= 200) && (status < 300) && (status != 204)) { ParseCookieL(aTransaction); } if (iSavingResponseBody) // If we're saving, then open a file handle for the new file { if ( iUsingFile ) { iHttpFileManager->GetNewFile(iRespBodyFilePath, iRespBodyFileName, EFalse); // Check it exists and open a file handle TInt valid = iFileServ.IsValidName(iRespBodyFilePath); if (!valid) { if (iVerbose) iTest->Console()->Printf(_L("The specified filename is not valid!.\n")); iSavingResponseBody = EFalse; } else { TInt err = iRespBodyFile.Create(iFileServ, iRespBodyFilePath, EFileWrite|EFileShareExclusive); if (err) { iSavingResponseBody = EFalse; User::Leave(err); } } } else { TInt dataSize = resp.Body()->OverallDataSize(); if ( iResBodyBuffer ) delete iResBodyBuffer; iResBodyBuffer = NULL; if ( dataSize > 50 * 1024) //skip large chunks of data { iSavingResponseBody = false; //try to stop current connection if (iVerbose) iTest->Console()->Printf(_L("Transaction Failed\n")); aTransaction.Close(); CActiveScheduler::Stop(); } else { iResBodyBuffer = HBufC8::NewMaxL(dataSize); iResBodyBufferPtr.Set(iResBodyBuffer->Des()); } iCurPos = 0; } } } break; case THTTPEvent::EGotResponseBodyData: { // Get the body data supplier iRespBody = aTransaction.Response().Body(); // Some (more) body data has been received (in the HTTP response) if (iVerbose) DumpRespBody(aTransaction); // Append to the output file if we're saving responses if (iSavingResponseBody) { TPtrC8 bodyData; TBool lastChunk = iRespBody->GetNextDataPart(bodyData); if ( iUsingFile ) { iRespBodyFile.Write(bodyData); if (lastChunk) { iRespBodyFile.Flush(); iRespBodyFile.Rename(iRespBodyFileName); iRespBodyFile.Close(); } } else { Mem::Copy((void*)(iResBodyBuffer->Ptr()+iCurPos), (void*)bodyData.Ptr(), bodyData.Size()); iCurPos += bodyData.Size(); } } // Done with that bit of body data iRespBody->ReleaseData(); } break; case THTTPEvent::EResponseComplete: { // The transaction's response is complete if (iVerbose) iTest->Console()->Printf(_L("\nTransaction Complete\n")); } break; case THTTPEvent::ESucceeded: { if (iVerbose) iTest->Console()->Printf(_L("Transaction Successful\n")); aTransaction.Close(); CActiveScheduler::Stop(); } break; case THTTPEvent::EFailed: { if (iVerbose) iTest->Console()->Printf(_L("Transaction Failed\n")); aTransaction.Close(); CActiveScheduler::Stop(); } break; case THTTPEvent::ERedirectedPermanently: { if (iVerbose) iTest->Console()->Printf(_L("Permanent Redirection\n")); } break; case THTTPEvent::ERedirectedTemporarily: { if (iVerbose) iTest->Console()->Printf(_L("Temporary Redirection\n")); } break; default: { if (iVerbose) iTest->Console()->Printf(_L("<unrecognised event: %d>\n"), aEvent.iStatus); // close off the transaction if it's an error if (aEvent.iStatus < 0) { aTransaction.Close(); CActiveScheduler::Stop(); } } break; } }
// MHTTPTransactionCallback interface functions void CXmlHandler::MHFRunL(RHTTPTransaction aTransaction, const THTTPEvent& aEvent) { switch (aEvent.iStatus) { case THTTPEvent::EGotResponseHeaders: { iObserver.GIEStateChanged(eStateFoundServer); iModel.iState = eStateFoundServer; /* Not interested in the received header */ } break; case THTTPEvent::EGotResponseBodyData: { #ifdef _INCREMENTAL_H #else /* The non incremental version of the parser will just build up a string of the data until the EReponseComplete code is received. Then the string is sent to parser in one go */ RHTTPResponse response = aTransaction.Response(); MHTTPDataSupplier* bodyPtr = response.Body(); /* Received data is appended to the existing block (if there is a block), otherwise a new block is created */ TPtrC8 bodypart; bodyPtr->GetNextDataPart(bodypart); if (iQueryResponse == NULL) { iQueryResponse = HBufC8::NewL( bodypart.Length() ); } else { const TInt newSize = iQueryResponse->Length() + bodypart.Length(); iQueryResponse = iQueryResponse->ReAllocL( newSize ); } TPtr8 tmp = iQueryResponse->Des(); tmp.Append(bodypart); bodyPtr->ReleaseData(); #endif } break; case THTTPEvent::EResponseComplete: { iObserver.GIEStateChanged(eStateReceivedResponse); iModel.iState = eStateReceivedResponse; #ifdef _INCREMENTAL_H #else #ifdef LOG_RESONSE LogMessage(iFs, KResponseFilename, *iQueryResponse); #endif /* Data block ready. Parse and fill data model */ OneTripParse(iQueryResponse->Des(), iModel.iError, iModel.iResult, iModel.iItems); #endif CleanupQueryText(); iObserver.GIEStateChanged(eStateComplete); iModel.iState = eStateComplete; } break; case THTTPEvent::ESucceeded: { // transaction successful // we do not do this in the response complete phase or error // phase as it is nicer to break it up because if the parser // is working non incrementally we have potientionally done // a lot of work in the ReponseComplete phase iObserver.GIEStateChanged(eStateComplete); iModel.iState = eStateComplete; } break; case THTTPEvent::EFailed: { // Transaction failed MHFRunError(aEvent.iStatus, aTransaction, aEvent); } break; default: { /* All errors will fall through to the generic event handler The only exceptional error handling is done when the soap request itself fails and it reports an error */ MHFRunError(aEvent.iStatus, aTransaction, aEvent); } break; } }