Skip to content
This repository was archived by the owner on Jul 4, 2025. It is now read-only.

Commit 77414c6

Browse files
nguyenhoangthuan99namchuaivansangpfiev
authored
Feat/new model folder (#1327)
* feat: pulling interact with new model.list * feat: return model id when download model success * feat: model delete for new model.list (#1317) * feat: models delete for new models data folder structure * feat: delete model * feat: cortex chat/run/models start with new model data structure (#1301) * feat: cortex chat/run/models start with new model data structure * temp * fix: use model_id from model service and std::get_line * f:m * Model update command/api (#1309) * Model update command/api * fix: resume download failed Signed-off-by: James <[email protected]> * fix: align github syntax for cuda (#1316) * fix: require sudo for cortex update (#1318) * fix: require sudo for cortex update * fix: comment * refactor code * Format code * Add clean up when finish test * remove model.list after finish test * Fix windows CI build --------- Signed-off-by: James <[email protected]> Co-authored-by: James <[email protected]> Co-authored-by: vansangpfiev <[email protected]> * Add more fields to handle when update --------- Signed-off-by: James <[email protected]> Co-authored-by: James <[email protected]> Co-authored-by: vansangpfiev <[email protected]>
1 parent 623e870 commit 77414c6

29 files changed

+984
-268
lines changed

engine/commands/chat_cmd.cc

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
#include "server_start_cmd.h"
77
#include "trantor/utils/Logger.h"
88
#include "utils/logging_utils.h"
9+
#include "utils/modellist_utils.h"
910

1011
namespace commands {
1112
namespace {
@@ -36,23 +37,36 @@ struct ChunkParser {
3637
}
3738
};
3839

39-
ChatCmd::ChatCmd(std::string host, int port, const config::ModelConfig& mc)
40-
: host_(std::move(host)), port_(port), mc_(mc) {}
40+
void ChatCmd::Exec(const std::string& host, int port,
41+
const std::string& model_handle, std::string msg) {
42+
modellist_utils::ModelListUtils modellist_handler;
43+
config::YamlHandler yaml_handler;
44+
try {
45+
auto model_entry = modellist_handler.GetModelInfo(model_handle);
46+
yaml_handler.ModelConfigFromFile(model_entry.path_to_model_yaml);
47+
auto mc = yaml_handler.GetModelConfig();
48+
Exec(host, port, mc, std::move(msg));
49+
} catch (const std::exception& e) {
50+
CLI_LOG("Fail to start model information with ID '" + model_handle +
51+
"': " + e.what());
52+
}
53+
}
4154

42-
void ChatCmd::Exec(std::string msg) {
55+
void ChatCmd::Exec(const std::string& host, int port,
56+
const config::ModelConfig& mc, std::string msg) {
57+
auto address = host + ":" + std::to_string(port);
4358
// Check if server is started
4459
{
45-
if (!commands::IsServerAlive(host_, port_)) {
60+
if (!commands::IsServerAlive(host, port)) {
4661
CLI_LOG("Server is not started yet, please run `"
4762
<< commands::GetCortexBinary() << " start` to start server!");
4863
return;
4964
}
5065
}
5166

52-
auto address = host_ + ":" + std::to_string(port_);
5367
// Only check if llamacpp engine
54-
if ((mc_.engine.find("llamacpp") != std::string::npos) &&
55-
!commands::ModelStatusCmd().IsLoaded(host_, port_, mc_)) {
68+
if ((mc.engine.find("llamacpp") != std::string::npos) &&
69+
!commands::ModelStatusCmd().IsLoaded(host, port, mc)) {
5670
CLI_LOG("Model is not loaded yet!");
5771
return;
5872
}
@@ -78,12 +92,12 @@ void ChatCmd::Exec(std::string msg) {
7892
new_data["role"] = kUser;
7993
new_data["content"] = user_input;
8094
histories_.push_back(std::move(new_data));
81-
json_data["engine"] = mc_.engine;
95+
json_data["engine"] = mc.engine;
8296
json_data["messages"] = histories_;
83-
json_data["model"] = mc_.name;
97+
json_data["model"] = mc.name;
8498
//TODO: support non-stream
8599
json_data["stream"] = true;
86-
json_data["stop"] = mc_.stop;
100+
json_data["stop"] = mc.stop;
87101
auto data_str = json_data.dump();
88102
// std::cout << data_str << std::endl;
89103
cli.set_read_timeout(std::chrono::seconds(60));

engine/commands/chat_cmd.h

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,12 @@
77
namespace commands {
88
class ChatCmd {
99
public:
10-
ChatCmd(std::string host, int port, const config::ModelConfig& mc);
11-
void Exec(std::string msg);
10+
void Exec(const std::string& host, int port, const std::string& model_handle,
11+
std::string msg);
12+
void Exec(const std::string& host, int port, const config::ModelConfig& mc,
13+
std::string msg);
1214

1315
private:
14-
std::string host_;
15-
int port_;
16-
const config::ModelConfig& mc_;
1716
std::vector<nlohmann::json> histories_;
1817
};
1918
} // namespace commands

engine/commands/model_del_cmd.cc

Lines changed: 34 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -2,55 +2,47 @@
22
#include "cmd_info.h"
33
#include "config/yaml_config.h"
44
#include "utils/file_manager_utils.h"
5+
#include "utils/modellist_utils.h"
56

67
namespace commands {
7-
bool ModelDelCmd::Exec(const std::string& model_id) {
8-
// TODO this implentation may be changed after we have a decision
9-
// on https://github.com/janhq/cortex.cpp/issues/1154 but the logic should be similar
10-
CmdInfo ci(model_id);
11-
std::string model_file =
12-
ci.branch == "main" ? ci.model_name : ci.model_name + "-" + ci.branch;
13-
auto models_path = file_manager_utils::GetModelsContainerPath();
14-
if (std::filesystem::exists(models_path) &&
15-
std::filesystem::is_directory(models_path)) {
16-
// Iterate through directory
17-
for (const auto& entry : std::filesystem::directory_iterator(models_path)) {
18-
if (entry.is_regular_file() && entry.path().extension() == ".yaml") {
19-
try {
20-
config::YamlHandler handler;
21-
handler.ModelConfigFromFile(entry.path().string());
22-
auto cfg = handler.GetModelConfig();
23-
if (entry.path().stem().string() == model_file) {
24-
// Delete data
25-
if (cfg.files.size() > 0) {
26-
std::filesystem::path f(cfg.files[0]);
27-
auto rel = std::filesystem::relative(f, models_path);
28-
// Only delete model data if it is stored in our models folder
29-
if (!rel.empty()) {
30-
if (cfg.engine == "cortex.llamacpp") {
31-
std::filesystem::remove_all(f.parent_path());
32-
} else {
33-
std::filesystem::remove_all(f);
34-
}
35-
}
36-
}
8+
bool ModelDelCmd::Exec(const std::string& model_handle) {
9+
modellist_utils::ModelListUtils modellist_handler;
10+
config::YamlHandler yaml_handler;
3711

38-
// Delete yaml file
39-
std::filesystem::remove(entry);
40-
CLI_LOG("The model " << model_id << " was deleted");
41-
return true;
12+
try {
13+
auto model_entry = modellist_handler.GetModelInfo(model_handle);
14+
yaml_handler.ModelConfigFromFile(model_entry.path_to_model_yaml);
15+
auto mc = yaml_handler.GetModelConfig();
16+
// Remove yaml file
17+
std::filesystem::remove(model_entry.path_to_model_yaml);
18+
// Remove model files if they are not imported locally
19+
if (model_entry.branch_name != "imported") {
20+
if (mc.files.size() > 0) {
21+
if (mc.engine == "cortex.llamacpp") {
22+
for (auto& file : mc.files) {
23+
std::filesystem::path gguf_p(file);
24+
std::filesystem::remove(gguf_p);
4225
}
43-
} catch (const std::exception& e) {
44-
CTL_WRN("Error reading yaml file '" << entry.path().string()
45-
<< "': " << e.what());
46-
return false;
26+
} else {
27+
std::filesystem::path f(mc.files[0]);
28+
std::filesystem::remove_all(f);
4729
}
30+
} else {
31+
CTL_WRN("model config files are empty!");
4832
}
4933
}
50-
}
51-
52-
CLI_LOG("Model does not exist: " << model_id);
5334

54-
return false;
35+
// update model.list
36+
if (modellist_handler.DeleteModelEntry(model_handle)) {
37+
CLI_LOG("The model " << model_handle << " was deleted");
38+
return true;
39+
} else {
40+
CTL_ERR("Could not delete model: " << model_handle);
41+
return false;
42+
}
43+
} catch (const std::exception& e) {
44+
CLI_LOG("Fail to delete model with ID '" + model_handle + "': " + e.what());
45+
false;
46+
}
5547
}
5648
} // namespace commands

engine/commands/model_del_cmd.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,6 @@ namespace commands {
66

77
class ModelDelCmd {
88
public:
9-
bool Exec(const std::string& model_id);
9+
bool Exec(const std::string& model_handle);
1010
};
1111
}

engine/commands/model_import_cmd.cc

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
11
#include "model_import_cmd.h"
22
#include <filesystem>
3-
#include <iostream>
43
#include <vector>
54
#include "config/gguf_parser.h"
65
#include "config/yaml_config.h"
7-
#include "trantor/utils/Logger.h"
86
#include "utils/file_manager_utils.h"
97
#include "utils/logging_utils.h"
108
#include "utils/modellist_utils.h"
@@ -45,7 +43,7 @@ void ModelImportCmd::Exec() {
4543
}
4644

4745
} catch (const std::exception& e) {
48-
// don't need to remove yml file here, because it's written only if model entry is successfully added,
46+
// don't need to remove yml file here, because it's written only if model entry is successfully added,
4947
// remove file here can make it fail with edge case when user try to import new model with existed model_id
5048
CLI_LOG("Error importing model path '" + model_path_ + "' with model_id '" +
5149
model_handle_ + "': " + e.what());

engine/commands/model_start_cmd.cc

Lines changed: 38 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -7,43 +7,59 @@
77
#include "trantor/utils/Logger.h"
88
#include "utils/file_manager_utils.h"
99
#include "utils/logging_utils.h"
10+
#include "utils/modellist_utils.h"
1011

1112
namespace commands {
12-
ModelStartCmd::ModelStartCmd(std::string host, int port,
13-
const config::ModelConfig& mc)
14-
: host_(std::move(host)), port_(port), mc_(mc) {}
13+
bool ModelStartCmd::Exec(const std::string& host, int port,
14+
const std::string& model_handle) {
1515

16-
bool ModelStartCmd::Exec() {
16+
modellist_utils::ModelListUtils modellist_handler;
17+
config::YamlHandler yaml_handler;
18+
try {
19+
auto model_entry = modellist_handler.GetModelInfo(model_handle);
20+
yaml_handler.ModelConfigFromFile(model_entry.path_to_model_yaml);
21+
auto mc = yaml_handler.GetModelConfig();
22+
return Exec(host, port, mc);
23+
} catch (const std::exception& e) {
24+
CLI_LOG("Fail to start model information with ID '" + model_handle +
25+
"': " + e.what());
26+
return false;
27+
}
28+
}
29+
30+
bool ModelStartCmd::Exec(const std::string& host, int port,
31+
const config::ModelConfig& mc) {
1732
// Check if server is started
18-
if (!commands::IsServerAlive(host_, port_)) {
33+
if (!commands::IsServerAlive(host, port)) {
1934
CLI_LOG("Server is not started yet, please run `"
2035
<< commands::GetCortexBinary() << " start` to start server!");
2136
return false;
2237
}
38+
2339
// Only check for llamacpp for now
24-
if ((mc_.engine.find("llamacpp") != std::string::npos) &&
25-
commands::ModelStatusCmd().IsLoaded(host_, port_, mc_)) {
40+
if ((mc.engine.find("llamacpp") != std::string::npos) &&
41+
commands::ModelStatusCmd().IsLoaded(host, port, mc)) {
2642
CLI_LOG("Model has already been started!");
2743
return true;
2844
}
2945

30-
httplib::Client cli(host_ + ":" + std::to_string(port_));
46+
httplib::Client cli(host + ":" + std::to_string(port));
3147

3248
nlohmann::json json_data;
33-
if (mc_.files.size() > 0) {
49+
if (mc.files.size() > 0) {
3450
// TODO(sang) support multiple files
35-
json_data["model_path"] = mc_.files[0];
51+
json_data["model_path"] = mc.files[0];
3652
} else {
3753
LOG_WARN << "model_path is empty";
3854
return false;
3955
}
40-
json_data["model"] = mc_.name;
41-
json_data["system_prompt"] = mc_.system_template;
42-
json_data["user_prompt"] = mc_.user_template;
43-
json_data["ai_prompt"] = mc_.ai_template;
44-
json_data["ctx_len"] = mc_.ctx_len;
45-
json_data["stop"] = mc_.stop;
46-
json_data["engine"] = mc_.engine;
56+
json_data["model"] = mc.name;
57+
json_data["system_prompt"] = mc.system_template;
58+
json_data["user_prompt"] = mc.user_template;
59+
json_data["ai_prompt"] = mc.ai_template;
60+
json_data["ctx_len"] = mc.ctx_len;
61+
json_data["stop"] = mc.stop;
62+
json_data["engine"] = mc.engine;
4763

4864
auto data_str = json_data.dump();
4965
cli.set_read_timeout(std::chrono::seconds(60));
@@ -52,13 +68,17 @@ bool ModelStartCmd::Exec() {
5268
if (res) {
5369
if (res->status == httplib::StatusCode::OK_200) {
5470
CLI_LOG("Model loaded!");
71+
return true;
72+
} else {
73+
CTL_ERR("Model failed to load with status code: " << res->status);
74+
return false;
5575
}
5676
} else {
5777
auto err = res.error();
5878
CTL_ERR("HTTP error: " << httplib::to_string(err));
5979
return false;
6080
}
61-
return true;
81+
return false;
6282
}
6383

6484
}; // namespace commands

engine/commands/model_start_cmd.h

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,8 @@ namespace commands {
66

77
class ModelStartCmd {
88
public:
9-
explicit ModelStartCmd(std::string host, int port,
10-
const config::ModelConfig& mc);
11-
bool Exec();
9+
bool Exec(const std::string& host, int port, const std::string& model_handle);
1210

13-
private:
14-
std::string host_;
15-
int port_;
16-
const config::ModelConfig& mc_;
11+
bool Exec(const std::string& host, int port, const config::ModelConfig& mc);
1712
};
1813
} // namespace commands

engine/commands/model_status_cmd.cc

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,25 @@
33
#include "httplib.h"
44
#include "nlohmann/json.hpp"
55
#include "utils/logging_utils.h"
6+
#include "utils/modellist_utils.h"
67

78
namespace commands {
9+
bool ModelStatusCmd::IsLoaded(const std::string& host, int port,
10+
const std::string& model_handle) {
11+
modellist_utils::ModelListUtils modellist_handler;
12+
config::YamlHandler yaml_handler;
13+
try {
14+
auto model_entry = modellist_handler.GetModelInfo(model_handle);
15+
yaml_handler.ModelConfigFromFile(model_entry.path_to_model_yaml);
16+
auto mc = yaml_handler.GetModelConfig();
17+
return IsLoaded(host, port, mc);
18+
} catch (const std::exception& e) {
19+
CLI_LOG("Fail to get model status with ID '" + model_handle +
20+
"': " + e.what());
21+
return false;
22+
}
23+
}
24+
825
bool ModelStatusCmd::IsLoaded(const std::string& host, int port,
926
const config::ModelConfig& mc) {
1027
httplib::Client cli(host + ":" + std::to_string(port));

engine/commands/model_status_cmd.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@ namespace commands {
66

77
class ModelStatusCmd {
88
public:
9+
bool IsLoaded(const std::string& host, int port,
10+
const std::string& model_handle);
911
bool IsLoaded(const std::string& host, int port,
1012
const config::ModelConfig& mc);
1113
};

0 commit comments

Comments
 (0)