Add Windows clipboard support

This commit is contained in:
Yukino Song
2024-09-28 03:31:50 +08:00
parent c72fb4544e
commit 1ae7157bba
9 changed files with 304 additions and 22 deletions

View File

@@ -592,12 +592,7 @@ namespace nvhttp {
std::ostringstream data;
pt::write_xml(data, tree);
response->write(data.str());
*response
<< "HTTP/1.1 404 NOT FOUND\r\n"
<< data.str();
response->write(SimpleWeb::StatusCode::client_error_not_found, data.str());
response->close_connection_after_response = true;
}
@@ -1268,6 +1263,112 @@ namespace nvhttp {
response->close_connection_after_response = true;
}
void
getClipboard(resp_https_t response, req_https_t request) {
print_req<SunshineHTTPS>(request);
auto named_cert_p = get_verified_cert(request);
if (
!(named_cert_p->perm & PERM::_allow_view)
|| !(named_cert_p->perm & PERM::clipboard_read)
) {
BOOST_LOG(debug) << "Permission Read Clipboard denied for [" << named_cert_p->name << "] (" << (uint32_t)named_cert_p->perm << ")";
response->write(SimpleWeb::StatusCode::client_error_unauthorized);
response->close_connection_after_response = true;
return;
}
auto args = request->parse_query_string();
auto clipboard_type = get_arg(args, "type");
if (clipboard_type != "text"sv) {
BOOST_LOG(debug) << "Clipboard type [" << clipboard_type << "] is not supported!";
response->write(SimpleWeb::StatusCode::client_error_bad_request);
response->close_connection_after_response = true;
return;
}
std::list<std::string> connected_uuids = rtsp_stream::get_all_session_uuids();
bool found = !connected_uuids.empty();
if (found) {
found = (std::find(connected_uuids.begin(), connected_uuids.end(), named_cert_p->uuid) != connected_uuids.end());
}
if (!found) {
BOOST_LOG(debug) << "Client ["<< named_cert_p->name << "] trying to get clipboard is not connected to a stream";
response->write(SimpleWeb::StatusCode::client_error_forbidden);
response->close_connection_after_response = true;
return;
}
std::string content = platf::get_clipboard();
response->write(content);
return;
}
void
setClipboard(resp_https_t response, req_https_t request) {
print_req<SunshineHTTPS>(request);
auto named_cert_p = get_verified_cert(request);
if (
!(named_cert_p->perm & PERM::_allow_view)
|| !(named_cert_p->perm & PERM::clipboard_set)
) {
BOOST_LOG(debug) << "Permission Write Clipboard denied for [" << named_cert_p->name << "] (" << (uint32_t)named_cert_p->perm << ")";
response->write(SimpleWeb::StatusCode::client_error_unauthorized);
response->close_connection_after_response = true;
return;
}
auto args = request->parse_query_string();
auto clipboard_type = get_arg(args, "type");
if (clipboard_type != "text"sv) {
BOOST_LOG(debug) << "Clipboard type [" << clipboard_type << "] is not supported!";
response->write(SimpleWeb::StatusCode::client_error_bad_request);
response->close_connection_after_response = true;
return;
}
std::list<std::string> connected_uuids = rtsp_stream::get_all_session_uuids();
bool found = !connected_uuids.empty();
if (found) {
found = (std::find(connected_uuids.begin(), connected_uuids.end(), named_cert_p->uuid) != connected_uuids.end());
}
if (!found) {
BOOST_LOG(debug) << "Client ["<< named_cert_p->name << "] trying to set clipboard is not connected to a stream";
response->write(SimpleWeb::StatusCode::client_error_forbidden);
response->close_connection_after_response = true;
return;
}
std::string content = request->content.string();
bool success = platf::set_clipboard(content);
if (!success) {
BOOST_LOG(debug) << "Setting clipboard failed!";
response->write(SimpleWeb::StatusCode::server_error_internal_server_error);
response->close_connection_after_response = true;
}
response->write();
return;
}
void
start() {
auto shutdown_event = mail::man->event<bool>(mail::shutdown);
@@ -1351,6 +1452,8 @@ namespace nvhttp {
https_server.resource["^/launch$"]["GET"] = [&host_audio](auto resp, auto req) { launch(host_audio, resp, req); };
https_server.resource["^/resume$"]["GET"] = [&host_audio](auto resp, auto req) { resume(host_audio, resp, req); };
https_server.resource["^/cancel$"]["GET"] = cancel;
https_server.resource["^/actions/clipboard$"]["GET"] = getClipboard;
https_server.resource["^/actions/clipboard$"]["POST"] = setClipboard;
https_server.config.reuse_address = true;
https_server.config.address = net::af_to_any_address_string(address_family);