|
26 | 26 | #include "runtime-light/core/globals/php-script-globals.h" |
27 | 27 | #include "runtime-light/k2-platform/k2-api.h" |
28 | 28 | #include "runtime-light/server/http/http-server-state.h" |
| 29 | +#include "runtime-light/server/http/multipart.h" |
29 | 30 | #include "runtime-light/state/instance-state.h" |
30 | 31 | #include "runtime-light/stdlib/component/component-api.h" |
31 | 32 | #include "runtime-light/stdlib/diagnostics/logs.h" |
32 | 33 | #include "runtime-light/stdlib/output/output-state.h" |
33 | 34 | #include "runtime-light/stdlib/server/http-functions.h" |
34 | 35 | #include "runtime-light/stdlib/zlib/zlib-functions.h" |
| 36 | +#include "runtime-light/stdlib/file/file-system-functions.h" |
35 | 37 | #include "runtime-light/streams/stream.h" |
36 | 38 | #include "runtime-light/tl/tl-core.h" |
37 | 39 | #include "runtime-light/tl/tl-functions.h" |
@@ -319,14 +321,16 @@ void init_server(kphp::component::stream&& request_stream, kphp::stl::vector<std |
319 | 321 | break; |
320 | 322 | } |
321 | 323 | case kphp::http::method::post: { |
| 324 | + string body{reinterpret_cast<const char*>(invoke_http.body.data()), static_cast<string::size_type>(invoke_http.body.size())}; |
322 | 325 | if (!std::ranges::search(content_type, CONTENT_TYPE_APP_FORM_URLENCODED).empty()) { |
323 | | - string body{reinterpret_cast<const char*>(invoke_http.body.data()), static_cast<string::size_type>(invoke_http.body.size())}; |
324 | 326 | f$parse_str(body, superglobals.v$_POST); |
325 | 327 | http_server_instance_st.opt_raw_post_data.emplace(std::move(body)); |
326 | 328 | } else if (!std::ranges::search(content_type, CONTENT_TYPE_MULTIPART_FORM_DATA).empty()) { |
327 | | - kphp::log::error("unsupported content-type: {}", CONTENT_TYPE_MULTIPART_FORM_DATA); |
| 329 | + std::string_view boundary{parse_boundary(content_type)}; |
| 330 | + if (!boundary.empty()) { |
| 331 | + kphp::http::parse_multipart({body.c_str(), body.size()}, boundary, superglobals.v$_POST, superglobals.v$_FILES); |
| 332 | + } |
328 | 333 | } else { |
329 | | - string body{reinterpret_cast<const char*>(invoke_http.body.data()), static_cast<string::size_type>(invoke_http.body.size())}; |
330 | 334 | http_server_instance_st.opt_raw_post_data.emplace(std::move(body)); |
331 | 335 | } |
332 | 336 |
|
@@ -378,6 +382,7 @@ void init_server(kphp::component::stream&& request_stream, kphp::stl::vector<std |
378 | 382 |
|
379 | 383 | kphp::coro::task<> finalize_server() noexcept { |
380 | 384 | auto& http_server_instance_st{HttpServerInstanceState::get()}; |
| 385 | + auto& superglobals{InstanceState::get().php_script_mutable_globals_singleton.get_superglobals()}; |
381 | 386 |
|
382 | 387 | string response_body{}; |
383 | 388 | tl::HttpResponse http_response{}; |
@@ -431,6 +436,18 @@ kphp::coro::task<> finalize_server() noexcept { |
431 | 436 | [[fallthrough]]; |
432 | 437 | } |
433 | 438 | case kphp::http::response_state::completed: |
| 439 | + const array<mixed> files = superglobals.v$_FILES.to_array(); |
| 440 | + for (array<mixed>::const_iterator it = files.begin(); it != files.end(); ++it) { |
| 441 | + const mixed& file = it.get_value(); |
| 442 | + |
| 443 | + if (!file.is_array()) { |
| 444 | + kphp::log::error("$_FILES contains a value that is not an array"); |
| 445 | + continue; |
| 446 | + } |
| 447 | + |
| 448 | + const mixed tmp_filename = file.get_value(string("tmp_name")); |
| 449 | + f$unlink(tmp_filename.to_string()); |
| 450 | + } |
434 | 451 | co_return; |
435 | 452 | } |
436 | 453 | } |
|
0 commit comments