@@ -863,6 +863,96 @@ int cbm_remove_editor_mcp(const char *config_path) {
863863 return rc ;
864864}
865865
866+ /* ── OpenClaw MCP (nested mcp.servers with command + args) ────── */
867+
868+ int cbm_install_openclaw_mcp (const char * binary_path , const char * config_path ) {
869+ if (!binary_path || !config_path ) {
870+ return CLI_ERR ;
871+ }
872+
873+ yyjson_mut_doc * mdoc = yyjson_mut_doc_new (NULL );
874+ if (!mdoc ) {
875+ return CLI_ERR ;
876+ }
877+
878+ yyjson_doc * doc = read_json_file (config_path );
879+ yyjson_mut_val * root ;
880+ if (doc ) {
881+ root = yyjson_val_mut_copy (mdoc , yyjson_doc_get_root (doc ));
882+ yyjson_doc_free (doc );
883+ } else {
884+ root = yyjson_mut_obj (mdoc );
885+ }
886+ if (!root ) {
887+ yyjson_mut_doc_free (mdoc );
888+ return CLI_ERR ;
889+ }
890+ yyjson_mut_doc_set_root (mdoc , root );
891+
892+ yyjson_mut_val * mcp = yyjson_mut_obj_get (root , "mcp" );
893+ if (!mcp || !yyjson_mut_is_obj (mcp )) {
894+ mcp = yyjson_mut_obj (mdoc );
895+ yyjson_mut_obj_add_val (mdoc , root , "mcp" , mcp );
896+ }
897+
898+ yyjson_mut_val * servers = yyjson_mut_obj_get (mcp , "servers" );
899+ if (!servers || !yyjson_mut_is_obj (servers )) {
900+ servers = yyjson_mut_obj (mdoc );
901+ yyjson_mut_obj_add_val (mdoc , mcp , "servers" , servers );
902+ }
903+
904+ yyjson_mut_obj_remove_key (servers , "codebase-memory-mcp" );
905+
906+ yyjson_mut_val * entry = yyjson_mut_obj (mdoc );
907+ yyjson_mut_obj_add_bool (mdoc , entry , "enabled" , true);
908+ yyjson_mut_obj_add_str (mdoc , entry , "command" , binary_path );
909+ yyjson_mut_val * args = yyjson_mut_arr (mdoc );
910+ yyjson_mut_obj_add_val (mdoc , entry , "args" , args );
911+ yyjson_mut_obj_add_val (mdoc , servers , "codebase-memory-mcp" , entry );
912+
913+ int rc = write_json_file (config_path , mdoc );
914+ yyjson_mut_doc_free (mdoc );
915+ return rc ;
916+ }
917+
918+ int cbm_remove_openclaw_mcp (const char * config_path ) {
919+ if (!config_path ) {
920+ return CLI_ERR ;
921+ }
922+
923+ yyjson_doc * doc = read_json_file (config_path );
924+ if (!doc ) {
925+ return CLI_ERR ;
926+ }
927+
928+ yyjson_mut_doc * mdoc = yyjson_mut_doc_new (NULL );
929+ yyjson_mut_val * root = yyjson_val_mut_copy (mdoc , yyjson_doc_get_root (doc ));
930+ yyjson_doc_free (doc );
931+ if (!root ) {
932+ yyjson_mut_doc_free (mdoc );
933+ return CLI_ERR ;
934+ }
935+ yyjson_mut_doc_set_root (mdoc , root );
936+
937+ yyjson_mut_val * mcp = yyjson_mut_obj_get (root , "mcp" );
938+ if (!mcp || !yyjson_mut_is_obj (mcp )) {
939+ yyjson_mut_doc_free (mdoc );
940+ return 0 ;
941+ }
942+
943+ yyjson_mut_val * servers = yyjson_mut_obj_get (mcp , "servers" );
944+ if (!servers || !yyjson_mut_is_obj (servers )) {
945+ yyjson_mut_doc_free (mdoc );
946+ return 0 ;
947+ }
948+
949+ yyjson_mut_obj_remove_key (servers , "codebase-memory-mcp" );
950+
951+ int rc = write_json_file (config_path , mdoc );
952+ yyjson_mut_doc_free (mdoc );
953+ return rc ;
954+ }
955+
866956/* ── VS Code MCP (servers key with type:stdio) ────────────────── */
867957
868958int cbm_install_vscode_mcp (const char * binary_path , const char * config_path ) {
@@ -3293,7 +3383,7 @@ static void install_editor_agent_configs(const cbm_detected_agents_t *agents, co
32933383 char cp [CLI_BUF_1K ];
32943384 snprintf (cp , sizeof (cp ), "%s/.openclaw/openclaw.json" , home );
32953385 install_generic_agent_config ("OpenClaw" , binary_path , cp , NULL , dry_run ,
3296- cbm_install_editor_mcp );
3386+ cbm_install_openclaw_mcp );
32973387 }
32983388 if (agents -> kiro ) {
32993389 char cp [CLI_BUF_1K ];
@@ -3822,7 +3912,7 @@ static void uninstall_editor_agents(const cbm_detected_agents_t *agents, const c
38223912 char cp [CLI_BUF_1K ];
38233913 snprintf (cp , sizeof (cp ), "%s/.openclaw/openclaw.json" , home );
38243914 uninstall_agent_mcp_instr ((mcp_uninstall_args_t ){"OpenClaw" , cp , NULL }, dry_run ,
3825- cbm_remove_editor_mcp );
3915+ cbm_remove_openclaw_mcp );
38263916 }
38273917 if (agents -> kiro ) {
38283918 char cp [CLI_BUF_1K ];
0 commit comments