Inserts or replaces a single node.
(&self, node: &Node)
| 12 | impl Database { |
| 13 | /// Inserts or replaces a single node. |
| 14 | pub async fn insert_node(&self, node: &Node) -> Result<()> { |
| 15 | self.conn() |
| 16 | .execute( |
| 17 | "INSERT OR REPLACE INTO nodes |
| 18 | (id, kind, name, qualified_name, file_path, |
| 19 | start_line, end_line, start_column, end_column, |
| 20 | docstring, signature, visibility, is_async, |
| 21 | branches, loops, returns, max_nesting, |
| 22 | unsafe_blocks, unchecked_calls, assertions, updated_at, attrs_start_line, parent_id) |
| 23 | VALUES (?1, ?2, ?3, ?4, ?5, ?6, ?7, ?8, ?9, ?10, ?11, ?12, ?13, ?14, ?15, ?16, ?17, ?18, ?19, ?20, ?21, ?22, ?23)", |
| 24 | params![ |
| 25 | node.id.as_str(), |
| 26 | node.kind.as_str(), |
| 27 | node.name.as_str(), |
| 28 | node.qualified_name.as_str(), |
| 29 | node.file_path.as_str(), |
| 30 | i64::from(node.start_line), |
| 31 | i64::from(node.end_line), |
| 32 | i64::from(node.start_column), |
| 33 | i64::from(node.end_column), |
| 34 | opt_str(node.docstring.as_deref()), |
| 35 | opt_str(node.signature.as_deref()), |
| 36 | node.visibility.as_str(), |
| 37 | i64::from(node.is_async), |
| 38 | i64::from(node.branches), |
| 39 | i64::from(node.loops), |
| 40 | i64::from(node.returns), |
| 41 | i64::from(node.max_nesting), |
| 42 | i64::from(node.unsafe_blocks), |
| 43 | i64::from(node.unchecked_calls), |
| 44 | i64::from(node.assertions), |
| 45 | node.updated_at as i64, |
| 46 | i64::from(node.attrs_start_line), |
| 47 | opt_str(node.parent_id.as_deref()), |
| 48 | ], |
| 49 | ) |
| 50 | .await |
| 51 | .map_err(|e| TraceDecayError::Database { |
| 52 | message: format!("failed to insert node: {e}"), |
| 53 | operation: "insert_node".to_string(), |
| 54 | })?; |
| 55 | Ok(()) |
| 56 | } |
| 57 | |
| 58 | /// Inserts all nodes, edges, and file records in a single `execute_batch` call. |
| 59 | /// This minimizes transaction overhead by combining everything into one SQL string. |