HttpRequest.cpp 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. #include "libhv_bindings.hpp"
  2. #include "HttpMessage.h"
  3. struct libhv_HttpRequest {
  4. HttpRequestPtr ptr;
  5. libhv_HttpRequest(HttpRequestPtr ptr) : ptr(ptr) {}
  6. };
  7. void libhv_HttpRequest_create(py_OutRef out, HttpRequestPtr ptr) {
  8. py_Type type = py_gettype("libhv", py_name("HttpRequest"));
  9. libhv_HttpRequest* self =
  10. (libhv_HttpRequest*)py_newobject(out, type, 2, sizeof(libhv_HttpRequest));
  11. new (self) libhv_HttpRequest(ptr);
  12. }
  13. py_Type libhv_register_HttpRequest(py_GlobalRef mod) {
  14. py_Type type = py_newtype("HttpRequest", tp_object, mod, [](void* ud) {
  15. ((libhv_HttpRequest*)ud)->~libhv_HttpRequest();
  16. });
  17. py_bindmagic(type, __new__, [](int argc, py_Ref argv) {
  18. return py_exception(tp_NotImplementedError, "");
  19. });
  20. py_bindproperty(
  21. type,
  22. "method",
  23. [](int argc, py_Ref argv) {
  24. PY_CHECK_ARGC(1);
  25. libhv_HttpRequest* req = (libhv_HttpRequest*)py_touserdata(argv);
  26. py_newstr(py_retval(), req->ptr->Method());
  27. return true;
  28. },
  29. NULL);
  30. py_bindproperty(
  31. type,
  32. "url",
  33. [](int argc, py_Ref argv) {
  34. PY_CHECK_ARGC(1);
  35. libhv_HttpRequest* req = (libhv_HttpRequest*)py_touserdata(argv);
  36. py_newstr(py_retval(), req->ptr->Url().c_str());
  37. return true;
  38. },
  39. NULL);
  40. py_bindproperty(
  41. type,
  42. "path",
  43. [](int argc, py_Ref argv) {
  44. PY_CHECK_ARGC(1);
  45. libhv_HttpRequest* req = (libhv_HttpRequest*)py_touserdata(argv);
  46. py_newstr(py_retval(), req->ptr->Path().c_str());
  47. return true;
  48. },
  49. NULL);
  50. // headers (cache in slots[0])
  51. py_bindproperty(
  52. type,
  53. "headers",
  54. [](int argc, py_Ref argv) {
  55. PY_CHECK_ARGC(1);
  56. libhv_HttpRequest* req = (libhv_HttpRequest*)py_touserdata(argv);
  57. py_Ref headers = py_getslot(argv, 0);
  58. if(py_isnil(headers)) {
  59. py_newdict(headers);
  60. py_Ref _0 = py_pushtmp();
  61. py_Ref _1 = py_pushtmp();
  62. for(auto& kv: req->ptr->headers) {
  63. py_newstr(_0, kv.first.c_str()); // TODO: tolower
  64. py_newstr(_1, kv.second.c_str());
  65. py_dict_setitem(headers, _0, _1);
  66. }
  67. py_shrink(2);
  68. }
  69. py_assign(py_retval(), headers);
  70. return true;
  71. },
  72. NULL);
  73. // data (cache in slots[1])
  74. py_bindproperty(
  75. type,
  76. "data",
  77. [](int argc, py_Ref argv) {
  78. PY_CHECK_ARGC(1);
  79. libhv_HttpRequest* req = (libhv_HttpRequest*)py_touserdata(argv);
  80. py_Ref data = py_getslot(argv, 1);
  81. if(py_isnil(data)) {
  82. auto content_type = req->ptr->ContentType();
  83. bool is_text_data = content_type == TEXT_PLAIN ||
  84. content_type == APPLICATION_JSON ||
  85. content_type == APPLICATION_XML || content_type == TEXT_HTML ||
  86. content_type == CONTENT_TYPE_NONE;
  87. if(is_text_data) {
  88. c11_sv sv;
  89. sv.data = req->ptr->body.data();
  90. sv.size = req->ptr->body.size();
  91. py_newstrv(data, sv);
  92. } else {
  93. unsigned char* buf = py_newbytes(data, req->ptr->body.size());
  94. memcpy(buf, req->ptr->body.data(), req->ptr->body.size());
  95. }
  96. }
  97. py_assign(py_retval(), data);
  98. return true;
  99. },
  100. NULL);
  101. return type;
  102. }