| 2102 | } |
| 2103 | |
| 2104 | void DataStorageController::HandlePUT_nodes_uid_properties(const httplib::Request& req, httplib::Response& res) |
| 2105 | { |
| 2106 | if (!m_Bridge.HasDataStorage()) |
| 2107 | { |
| 2108 | this->SendErrorResponse(res, 503, ErrorResponse::DataStorageNotAvailable(req.path)); |
| 2109 | return; |
| 2110 | } |
| 2111 | |
| 2112 | const std::string uid = req.path_params.at("uid"); |
| 2113 | if (!ValidateUid(uid)) |
| 2114 | { |
| 2115 | this->SendErrorResponse(res, 400, ErrorResponse::InvalidRequest("Invalid UID format", req.path)); |
| 2116 | return; |
| 2117 | } |
| 2118 | |
| 2119 | // Check if node exists |
| 2120 | auto nodeCheck = m_Bridge.GetNode(uid); |
| 2121 | if (!nodeCheck.has_value()) |
| 2122 | { |
| 2123 | this->SendErrorResponse(res, 404, ErrorResponse::NodeNotFound(uid, req.path)); |
| 2124 | return; |
| 2125 | } |
| 2126 | |
| 2127 | // Parse property query parameters for context and scope |
| 2128 | // Per API spec: PUT /properties defaults to "node" scope |
| 2129 | PropertyQueryParams params; |
| 2130 | try |
| 2131 | { |
| 2132 | params = this->ParsePropertyQueryParams(req, PropertyScope::Node); |
| 2133 | } |
| 2134 | catch (const InvalidQueryParam& e) |
| 2135 | { |
| 2136 | this->SendErrorResponse(res, 400, ErrorResponse::InvalidRequest(e.detail, req.path)); |
| 2137 | return; |
| 2138 | } |
| 2139 | |
| 2140 | // Mutation endpoints do not support scope "all" |
| 2141 | if (params.scope == PropertyScope::All) |
| 2142 | { |
| 2143 | this->SendErrorResponse(res, 400, ErrorResponse::InvalidRequest( |
| 2144 | "Scope 'all' is not supported for property mutation operations. Use 'node' or 'data'.", req.path)); |
| 2145 | return; |
| 2146 | } |
| 2147 | |
| 2148 | // Parse request body |
| 2149 | nlohmann::json properties; |
| 2150 | try |
| 2151 | { |
| 2152 | properties = nlohmann::json::parse(req.body); |
| 2153 | } |
| 2154 | catch (const nlohmann::json::parse_error& e) |
| 2155 | { |
| 2156 | this->SendErrorResponse(res, 400, ErrorResponse::InvalidRequest("Invalid JSON: " + std::string(e.what()), req.path)); |
| 2157 | return; |
| 2158 | } |
| 2159 | |
| 2160 | if (!properties.is_object()) |
| 2161 | { |