pull/105/head
ApexLiu 2017-10-30 09:42:02 +08:00
parent 3d2754799f
commit a49590705d
13 changed files with 146 additions and 66 deletions

View File

@ -51,6 +51,11 @@
#define TP_SESS_STAT_ERR_RESET 7 // 会话结束因为teleport核心服务重置了
#define TP_SESS_STAT_ERR_IO 8 // 会话结束,因为网络中断
#define TP_SESS_STAT_ERR_SESSION 9 // 会话结束因为无效的会话ID
#define TP_SESS_STAT_STARTED 100 // 已经连接成功了,开始记录录像了
#define TP_SESS_STAT_ERR_START_INTERNAL 104 // 会话结束,因为内部错误
#define TP_SESS_STAT_ERR_START_BAD_PKG 106 // 会话结束,因为收到错误的报文
#define TP_SESS_STAT_ERR_START_RESET 107 // 会话结束因为teleport核心服务重置了
#define TP_SESS_STAT_ERR_START_IO 108 // 会话结束,因为网络中断
//=======================================================

View File

@ -22,8 +22,10 @@
<file url="file://$PROJECT_DIR$/tp_core/core/ts_http_rpc.cpp" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_http_rpc.h" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_main.cpp" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_session.cpp" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_session.h" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_web_rpc.cpp" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/core/ts_web_rpc.h" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/protocol/rdp/rdp_recorder.h" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/protocol/rdp/rdp_session.h" charset="GBK" />
<file url="file://$PROJECT_DIR$/tp_core/protocol/ssh/ssh_proxy.cpp" charset="GBK" />

View File

@ -23,9 +23,10 @@ bool TppEnvBase::init(TPP_INIT_ARGS* args)
get_connect_info = args->func_get_connect_info;
free_connect_info = args->func_free_connect_info;
session_begin = args->func_session_begin;
session_update = args->func_session_update;
session_end = args->func_session_end;
if (NULL == get_connect_info || NULL == free_connect_info || NULL == session_begin || NULL == session_end)
if (NULL == get_connect_info || NULL == free_connect_info || NULL == session_begin || NULL == session_update || NULL == session_end)
{
EXLOGE("invalid init args(2).\n");
return false;

View File

@ -19,6 +19,7 @@ public:
TPP_GET_CONNNECT_INFO_FUNC get_connect_info;
TPP_FREE_CONNECT_INFO_FUNC free_connect_info;
TPP_SESSION_BEGIN_FUNC session_begin;
TPP_SESSION_UPDATE_FUNC session_update;
TPP_SESSION_END_FUNC session_end;
protected:

View File

@ -44,6 +44,7 @@ typedef struct TPP_CONNECT_INFO
typedef TPP_CONNECT_INFO* (*TPP_GET_CONNNECT_INFO_FUNC)(const char* sid);
typedef void(*TPP_FREE_CONNECT_INFO_FUNC)(TPP_CONNECT_INFO* info);
typedef bool(*TPP_SESSION_BEGIN_FUNC)(const TPP_CONNECT_INFO* info, int* db_id);
typedef bool(*TPP_SESSION_UPDATE_FUNC)(int db_id, int state);
typedef bool(*TPP_SESSION_END_FUNC)(const char* sid, int db_id, int ret);
@ -58,6 +59,7 @@ typedef struct TPP_INIT_ARGS
TPP_GET_CONNNECT_INFO_FUNC func_get_connect_info;
TPP_FREE_CONNECT_INFO_FUNC func_free_connect_info;
TPP_SESSION_BEGIN_FUNC func_session_begin;
TPP_SESSION_UPDATE_FUNC func_session_update;
TPP_SESSION_END_FUNC func_session_end;
}TPP_INIT_ARGS;

View File

@ -91,6 +91,10 @@ bool tpp_session_begin(const TPP_CONNECT_INFO* info, int* db_id)
return ts_web_rpc_session_begin(sinfo, *db_id);
}
bool tpp_session_update(int db_id, int state) {
return ts_web_rpc_session_update(db_id, state);
}
bool tpp_session_end(const char* sid, int db_id, int ret)
{
return ts_web_rpc_session_end(sid, db_id, ret);
@ -204,6 +208,7 @@ bool TppManager::load_tpp(const ex_wstr& libname)
init_args.func_get_connect_info = tpp_get_connect_info;
init_args.func_free_connect_info = tpp_free_connect_info;
init_args.func_session_begin = tpp_session_begin;
init_args.func_session_update = tpp_session_update;
init_args.func_session_end = tpp_session_end;
if (EXRV_OK != lib->init(&init_args))

View File

@ -1,6 +1,6 @@
#include "ts_web_rpc.h"
#include "ts_env.h"
#include "ts_crypto.h"
#include "ts_crypto.h"
#include "ts_http_client.h"
#include "../common/ts_const.h"
@ -67,6 +67,41 @@ int ts_web_rpc_get_conn_info(int conn_id, TS_CONNECT_INFO& info)
Json::Value& _jret = jret["data"];
if(!_jret["user_id"].isInt())
EXLOGE("connection info: need `user_id`.\n");
if(!_jret["host_id"].isInt())
EXLOGE("connection info: need `host_id`.\n");
if(!_jret["acc_id"].isInt())
EXLOGE("connection info: need `acc_id`.\n");
if(!_jret["conn_port"].isInt())
EXLOGE("connection info: need `conn_port`.\n");
if(!_jret["protocol_type"].isInt())
EXLOGE("connection info: need `protocol_type`.\n");
if(!_jret["protocol_sub_type"].isInt())
EXLOGE("connection info: need `protocol_sub_type`.\n");
if(!_jret["auth_type"].isInt())
EXLOGE("connection info: need `auth_type`.\n");
if(!_jret["protocol_flag"].isInt())
EXLOGE("connection info: need `protocol_flag`.\n");
if(!_jret["_enc"].isInt())
EXLOGE("connection info: need `_enc`.\n");
if(!_jret["user_username"].isString())
EXLOGE("connection info: need `user_username`.\n");
if(!_jret["host_ip"].isString())
EXLOGE("connection info: need `host_ip`.\n");
if(!_jret["conn_ip"].isString())
EXLOGE("connection info: need `conn_ip`.\n");
if(!_jret["client_ip"].isString())
EXLOGE("connection info: need `client_ip`.\n");
if(!_jret["acc_username"].isString())
EXLOGE("connection info: need `acc_username`.\n");
if(!_jret["acc_secret"].isString())
EXLOGE("connection info: need `acc_secret`.\n");
if(!_jret["username_prompt"].isString())
EXLOGE("connection info: need `username_prompt`.\n");
if(!_jret["password_prompt"].isString())
EXLOGE("connection info: need `password_prompt`.\n");
if (
!_jret["user_id"].isInt()
|| !_jret["host_id"].isInt()
@ -110,63 +145,63 @@ int ts_web_rpc_get_conn_info(int conn_id, TS_CONNECT_INFO& info)
int protocol_flag = 0;
bool _enc;
user_id = _jret["user_id"].asInt();
host_id = _jret["host_id"].asInt();
acc_id = _jret["acc_id"].asInt();
user_username = _jret["user_username"].asString();
host_ip = _jret["host_ip"].asString();
conn_ip = _jret["conn_ip"].asString();
conn_port = _jret["conn_port"].asInt();
client_ip = _jret["client_ip"].asString();
acc_username = _jret["acc_username"].asString();
acc_secret = _jret["acc_secret"].asString();
username_prompt = _jret["username_prompt"].asString();
password_prompt = _jret["password_prompt"].asString();
protocol_type = _jret["protocol_type"].asInt();
protocol_sub_type = _jret["protocol_sub_type"].asInt();
protocol_flag = _jret["protocol_flag"].asInt();
auth_type = _jret["auth_type"].asInt();
_enc = _jret["_enc"].asBool();
// 进一步判断参数是否合法
// 注意account_id可以为-1表示这是一次测试连接。
if (user_id <= 0 || host_id <= 0
|| user_username.length() == 0
|| host_ip.length() == 0 || conn_ip.length() == 0 || client_ip.length() == 0
|| conn_port <= 0 || conn_port >= 65535
|| acc_username.length() == 0 || acc_secret.length() == 0
|| !(protocol_type == TP_PROTOCOL_TYPE_RDP || protocol_type == TP_PROTOCOL_TYPE_SSH || protocol_type == TP_PROTOCOL_TYPE_TELNET)
|| !(auth_type == TP_AUTH_TYPE_NONE || auth_type == TP_AUTH_TYPE_PASSWORD || auth_type == TP_AUTH_TYPE_PRIVATE_KEY)
)
{
return TPE_PARAM;
}
if (_enc) {
ex_astr _auth;
if (!ts_db_field_decrypt(acc_secret, _auth))
return TPE_FAILED;
acc_secret = _auth;
}
user_id = _jret["user_id"].asInt();
host_id = _jret["host_id"].asInt();
acc_id = _jret["acc_id"].asInt();
user_username = _jret["user_username"].asString();
host_ip = _jret["host_ip"].asString();
conn_ip = _jret["conn_ip"].asString();
conn_port = _jret["conn_port"].asInt();
client_ip = _jret["client_ip"].asString();
acc_username = _jret["acc_username"].asString();
acc_secret = _jret["acc_secret"].asString();
username_prompt = _jret["username_prompt"].asString();
password_prompt = _jret["password_prompt"].asString();
protocol_type = _jret["protocol_type"].asInt();
protocol_sub_type = _jret["protocol_sub_type"].asInt();
protocol_flag = _jret["protocol_flag"].asInt();
auth_type = _jret["auth_type"].asInt();
_enc = _jret["_enc"].asBool();
info.user_id = user_id;
info.host_id = host_id;
info.acc_id = acc_id;
info.user_username = user_username;
info.host_ip = host_ip;
info.conn_ip = conn_ip;
info.conn_port = conn_port;
info.client_ip = client_ip;
info.acc_username = acc_username;
info.acc_secret = acc_secret;
info.username_prompt = username_prompt;
info.password_prompt = password_prompt;
info.protocol_type = protocol_type;
info.protocol_sub_type = protocol_sub_type;
info.auth_type = auth_type;
info.protocol_flag = protocol_flag;
// 进一步判断参数是否合法
// 注意account_id可以为-1表示这是一次测试连接。
if (user_id <= 0 || host_id <= 0
|| user_username.length() == 0
|| host_ip.length() == 0 || conn_ip.length() == 0 || client_ip.length() == 0
|| conn_port <= 0 || conn_port >= 65535
|| acc_username.length() == 0 || acc_secret.length() == 0
|| !(protocol_type == TP_PROTOCOL_TYPE_RDP || protocol_type == TP_PROTOCOL_TYPE_SSH || protocol_type == TP_PROTOCOL_TYPE_TELNET)
|| !(auth_type == TP_AUTH_TYPE_NONE || auth_type == TP_AUTH_TYPE_PASSWORD || auth_type == TP_AUTH_TYPE_PRIVATE_KEY)
)
{
return TPE_PARAM;
}
if (_enc) {
ex_astr _auth;
if (!ts_db_field_decrypt(acc_secret, _auth))
return TPE_FAILED;
acc_secret = _auth;
}
info.user_id = user_id;
info.host_id = host_id;
info.acc_id = acc_id;
info.user_username = user_username;
info.host_ip = host_ip;
info.conn_ip = conn_ip;
info.conn_port = conn_port;
info.client_ip = client_ip;
info.acc_username = acc_username;
info.acc_secret = acc_secret;
info.username_prompt = username_prompt;
info.password_prompt = password_prompt;
info.protocol_type = protocol_type;
info.protocol_sub_type = protocol_sub_type;
info.auth_type = auth_type;
info.protocol_flag = protocol_flag;
return TPE_OK;
}
@ -228,11 +263,32 @@ bool ts_web_rpc_session_begin(TS_CONNECT_INFO& info, int& record_id)
return true;
}
bool ts_web_rpc_session_update(int record_id, int state) {
Json::FastWriter json_writer;
Json::Value jreq;
jreq["method"] = "session_update";
jreq["param"]["rid"] = record_id;
jreq["param"]["code"] = state;
ex_astr json_param;
json_param = json_writer.write(jreq);
ex_astr param;
ts_url_encode(json_param.c_str(), param);
ex_astr url = g_env.web_server_rpc;
url += "?";
url += param;
ex_astr body;
return ts_http_get(url, body);
}
//session ½áÊø
bool ts_web_rpc_session_end(const char* sid, int record_id, int ret_code)
{
// TODO: 对指定的sid相关的会话的引用计数减一但减到0时销毁
// TODO: 对指定的sid相关的会话的引用计数减一但减到0时销毁
Json::FastWriter json_writer;
Json::Value jreq;

View File

@ -13,6 +13,8 @@ int ts_web_rpc_get_conn_info(int conn_id, TS_CONNECT_INFO& info);
// 记录会话的开始
bool ts_web_rpc_session_begin(TS_CONNECT_INFO& info, int& record_id);
// update session state
bool ts_web_rpc_session_update(int id, int state);
//session 结束
bool ts_web_rpc_session_end(const char* sid, int id, int ret_code);

View File

@ -82,7 +82,7 @@ void SshProxy::timer(void) {
ts_ssh_sessions::iterator it;
for(it = m_sessions.begin(); it != m_sessions.end(); ++it) {
it->first->flush_record();
it->first->save_record();
}
}

View File

@ -78,7 +78,7 @@ bool TppSshRec::_on_end()
return true;
}
void TppSshRec::flush_record() {
void TppSshRec::save_record() {
if (m_cache.size() > 0)
_save_to_data_file();
if (m_cmd_cache.size() > 0)

View File

@ -56,7 +56,7 @@ public:
void record_win_size_change(int width, int height);
void record_command(const ex_astr& cmd);
void flush_record();
void save_record();
protected:
bool _on_begin(const TPP_CONNECT_INFO* info);

View File

@ -220,8 +220,8 @@ void SshSession::_run(void) {
ssh_event_free(event_loop);
}
void SshSession::flush_record() {
m_rec.flush_record();
void SshSession::save_record() {
m_rec.save_record();
}
@ -314,6 +314,12 @@ int SshSession::_on_auth_password_request(ssh_session session, const char *user,
return SSH_AUTH_ERROR;
}
if (!g_ssh_env.session_update(_this->m_db_id, TP_SESS_STAT_STARTED))
{
EXLOGD("[ssh] session_update error. %d\n", _this->m_db_id);
return false;
}
// // 检查服务端支持的认证协议
// rc = ssh_userauth_none(_this->m_srv_session, NULL);
// if (rc == SSH_AUTH_ERROR) {

View File

@ -53,7 +53,7 @@ public:
void client_port(ex_u16 port) { m_client_port = port; }
ex_u16 client_port(void) const { return m_client_port; }
void flush_record();
void save_record();
protected:
// ¼Ì³Ð×Ô TppSessionBase