response.cpp 2.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566
  1. #include "response.h"
  2. #include <util/generic/vector.h>
  3. #include <util/stream/output.h>
  4. #include <util/stream/mem.h>
  5. #include <util/string/cast.h>
  6. THttpResponse& THttpResponse::AddMultipleHeaders(const THttpHeaders& headers) {
  7. for (THttpHeaders::TConstIterator i = headers.Begin(); i != headers.End(); ++i) {
  8. this->Headers.AddHeader(*i);
  9. }
  10. return *this;
  11. }
  12. THttpResponse& THttpResponse::SetContentType(const TStringBuf& contentType) {
  13. Headers.AddOrReplaceHeader(THttpInputHeader("Content-Type", ToString(contentType)));
  14. return *this;
  15. }
  16. void THttpResponse::OutTo(IOutputStream& os) const {
  17. TVector<IOutputStream::TPart> parts;
  18. const size_t FIRST_LINE_PARTS = 3;
  19. const size_t HEADERS_PARTS = Headers.Count() * 4;
  20. const size_t CONTENT_PARTS = 5;
  21. parts.reserve(FIRST_LINE_PARTS + HEADERS_PARTS + CONTENT_PARTS);
  22. // first line
  23. parts.push_back(IOutputStream::TPart(TStringBuf("HTTP/1.1 ")));
  24. parts.push_back(IOutputStream::TPart(HttpCodeStrEx(Code)));
  25. parts.push_back(IOutputStream::TPart::CrLf());
  26. // headers
  27. for (THttpHeaders::TConstIterator i = Headers.Begin(); i != Headers.End(); ++i) {
  28. parts.push_back(IOutputStream::TPart(i->Name()));
  29. parts.push_back(IOutputStream::TPart(TStringBuf(": ")));
  30. parts.push_back(IOutputStream::TPart(i->Value()));
  31. parts.push_back(IOutputStream::TPart::CrLf());
  32. }
  33. char buf[50];
  34. if (!Content.empty()) {
  35. TMemoryOutput mo(buf, sizeof(buf));
  36. mo << Content.size();
  37. parts.push_back(IOutputStream::TPart(TStringBuf("Content-Length: ")));
  38. parts.push_back(IOutputStream::TPart(buf, mo.Buf() - buf));
  39. parts.push_back(IOutputStream::TPart::CrLf());
  40. }
  41. // content
  42. parts.push_back(IOutputStream::TPart::CrLf());
  43. if (!Content.empty()) {
  44. parts.push_back(IOutputStream::TPart(Content));
  45. }
  46. os.Write(parts.data(), parts.size());
  47. }
  48. template <>
  49. void Out<THttpResponse>(IOutputStream& os, const THttpResponse& resp) {
  50. resp.OutTo(os);
  51. }