mirror of
https://github.com/haiwen/seafile.git
synced 2025-01-09 04:17:30 +08:00
[client] Use http-sync exclusively for repos version > 0.
For repo version > 0, if requests to '/seafhttp/*' urls fail, and https is not used, fall back to send requests to 8082 port directly.
This commit is contained in:
parent
9d6482c034
commit
7a97fc055d
@ -278,8 +278,7 @@ check_head_commit_done (HttpHeadCommit *result, void *user_data)
|
||||
memcpy (task->server_head_id, result->head_commit, 40);
|
||||
start_clone_v2 (task);
|
||||
} else {
|
||||
task->http_sync = FALSE;
|
||||
connect_non_http_server (task);
|
||||
transition_to_error (task, CLONE_ERROR_CONNECT);
|
||||
}
|
||||
}
|
||||
|
||||
@ -289,12 +288,48 @@ http_check_head_commit (CloneTask *task)
|
||||
http_tx_manager_check_head_commit (seaf->http_tx_mgr,
|
||||
task->repo_id,
|
||||
task->repo_version,
|
||||
task->server_url,
|
||||
task->effective_url,
|
||||
task->token,
|
||||
task->use_fileserver_port,
|
||||
check_head_commit_done,
|
||||
task);
|
||||
}
|
||||
|
||||
static char *
|
||||
http_fileserver_url (const char *url)
|
||||
{
|
||||
char *colon;
|
||||
char *url_no_port;
|
||||
char *ret = NULL;
|
||||
|
||||
colon = strrchr (url, ':');
|
||||
if (colon) {
|
||||
url_no_port = g_strndup(url, colon - url);
|
||||
ret = g_strconcat(url_no_port, ":8082", NULL);
|
||||
} else {
|
||||
ret = g_strconcat(url, ":8082", NULL);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
check_http_fileserver_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
{
|
||||
CloneTask *task = user_data;
|
||||
|
||||
if (result->check_success && !result->not_supported) {
|
||||
task->http_protocol_version = result->version;
|
||||
task->effective_url = http_fileserver_url (task->server_url);
|
||||
task->use_fileserver_port = TRUE;
|
||||
task->http_sync = TRUE;
|
||||
http_check_head_commit (task);
|
||||
} else {
|
||||
/* Wait for periodic retry. */
|
||||
transition_state (task, CLONE_STATE_CONNECT);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
check_http_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
{
|
||||
@ -302,10 +337,21 @@ check_http_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
|
||||
if (result->check_success && !result->not_supported) {
|
||||
task->http_protocol_version = result->version;
|
||||
task->effective_url = g_strdup(task->server_url);
|
||||
task->http_sync = TRUE;
|
||||
http_check_head_commit (task);
|
||||
} else
|
||||
connect_non_http_server (task);
|
||||
} else if (strncmp(task->server_url, "https", 5) != 0) {
|
||||
char *host_fileserver = http_fileserver_url(task->server_url);
|
||||
http_tx_manager_check_protocol_version (seaf->http_tx_mgr,
|
||||
host_fileserver,
|
||||
TRUE,
|
||||
check_http_fileserver_protocol_done,
|
||||
task);
|
||||
g_free (host_fileserver);
|
||||
} else {
|
||||
/* Wait for periodic retry. */
|
||||
transition_state (task, CLONE_STATE_CONNECT);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
@ -313,6 +359,7 @@ check_http_protocol (CloneTask *task)
|
||||
{
|
||||
http_tx_manager_check_protocol_version (seaf->http_tx_mgr,
|
||||
task->server_url,
|
||||
FALSE,
|
||||
check_http_protocol_done,
|
||||
task);
|
||||
transition_state (task, CLONE_STATE_CHECK_HTTP);
|
||||
@ -359,6 +406,7 @@ clone_task_free (CloneTask *task)
|
||||
g_free (task->email);
|
||||
g_free (task->random_key);
|
||||
g_free (task->server_url);
|
||||
g_free (task->effective_url);
|
||||
|
||||
g_free (task);
|
||||
}
|
||||
@ -539,10 +587,18 @@ restart_task (sqlite3_stmt *stmt, void *data)
|
||||
if (repo != NULL && repo->head != NULL) {
|
||||
transition_state (task, CLONE_STATE_DONE);
|
||||
return TRUE;
|
||||
} else if (seaf->enable_http_sync && task->repo_version > 0 && task->server_url)
|
||||
check_http_protocol (task);
|
||||
else
|
||||
}
|
||||
|
||||
if (task->repo_version > 0) {
|
||||
if (seaf->enable_http_sync && task->server_url) {
|
||||
check_http_protocol (task);
|
||||
} else {
|
||||
transition_to_error (task, CLONE_ERROR_CONNECT);
|
||||
return TRUE;
|
||||
}
|
||||
} else {
|
||||
connect_non_http_server (task);
|
||||
}
|
||||
|
||||
g_hash_table_insert (mgr->tasks, g_strdup(task->repo_id), task);
|
||||
|
||||
@ -603,7 +659,10 @@ static int check_connect_pulse (void *vmanager)
|
||||
while (g_hash_table_iter_next (&iter, &key, &value)) {
|
||||
task = value;
|
||||
if (task->state == CLONE_STATE_CONNECT) {
|
||||
continue_task_when_peer_connected (task);
|
||||
if (task->repo_version == 0)
|
||||
continue_task_when_peer_connected (task);
|
||||
else
|
||||
check_http_protocol (task);
|
||||
}
|
||||
}
|
||||
|
||||
@ -790,7 +849,7 @@ add_transfer_task (CloneTask *task, GError **error)
|
||||
int ret = http_tx_manager_add_download (seaf->http_tx_mgr,
|
||||
task->repo_id,
|
||||
task->repo_version,
|
||||
task->server_url,
|
||||
task->effective_url,
|
||||
task->token,
|
||||
task->server_head_id,
|
||||
TRUE,
|
||||
@ -798,6 +857,7 @@ add_transfer_task (CloneTask *task, GError **error)
|
||||
task->worktree,
|
||||
task->http_protocol_version,
|
||||
task->email,
|
||||
task->use_fileserver_port,
|
||||
error);
|
||||
if (ret < 0)
|
||||
return -1;
|
||||
@ -1251,10 +1311,16 @@ add_task_common (SeafCloneManager *mgr,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (seaf->enable_http_sync && task->repo_version > 0 && task->server_url)
|
||||
check_http_protocol (task);
|
||||
else
|
||||
if (task->repo_version > 0) {
|
||||
if (seaf->enable_http_sync && task->server_url) {
|
||||
check_http_protocol (task);
|
||||
} else {
|
||||
clone_task_free (task);
|
||||
return NULL;
|
||||
}
|
||||
} else {
|
||||
connect_non_http_server (task);
|
||||
}
|
||||
|
||||
/* The old task for this repo will be freed. */
|
||||
g_hash_table_insert (mgr->tasks, g_strdup(task->repo_id), task);
|
||||
@ -2238,7 +2304,10 @@ on_repo_http_fetched (SeafileSession *seaf,
|
||||
transition_state (task, CLONE_STATE_CANCELED);
|
||||
return;
|
||||
} else if (tx_task->state == HTTP_TASK_STATE_ERROR) {
|
||||
transition_to_error (task, CLONE_ERROR_FETCH);
|
||||
if (add_transfer_task (task, NULL) == 0)
|
||||
transition_state (task, CLONE_STATE_FETCH);
|
||||
else
|
||||
transition_to_error (task, CLONE_ERROR_FETCH);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -2347,7 +2416,8 @@ check_folder_permissions (CloneTask *task)
|
||||
|
||||
/* The requests list will be freed in http tx manager. */
|
||||
http_tx_manager_get_folder_perms (seaf->http_tx_mgr,
|
||||
task->server_url,
|
||||
task->effective_url,
|
||||
task->use_fileserver_port,
|
||||
requests,
|
||||
check_folder_perms_done,
|
||||
task);
|
||||
|
@ -61,6 +61,8 @@ struct _CloneTask {
|
||||
|
||||
/* Http sync fields */
|
||||
char *server_url;
|
||||
char *effective_url;
|
||||
gboolean use_fileserver_port;
|
||||
int http_protocol_version;
|
||||
gboolean http_sync;
|
||||
char server_head_id[41];
|
||||
|
@ -692,6 +692,7 @@ transition_state (HttpTxTask *task, int state, int rt_state)
|
||||
|
||||
typedef struct {
|
||||
char *host;
|
||||
gboolean use_fileserver_port;
|
||||
HttpProtocolVersionCallback callback;
|
||||
void *user_data;
|
||||
|
||||
@ -753,7 +754,10 @@ check_protocol_version_thread (void *vdata)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/protocol-version", data->host);
|
||||
if (!data->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/protocol-version", data->host);
|
||||
else
|
||||
url = g_strdup_printf ("%s/protocol-version", data->host);
|
||||
|
||||
if (http_get (curl, url, NULL, &status, &rsp_content, &rsp_size, NULL, NULL, FALSE) < 0) {
|
||||
goto out;
|
||||
@ -799,12 +803,14 @@ check_protocol_version_done (void *vdata)
|
||||
int
|
||||
http_tx_manager_check_protocol_version (HttpTxManager *manager,
|
||||
const char *host,
|
||||
gboolean use_fileserver_port,
|
||||
HttpProtocolVersionCallback callback,
|
||||
void *user_data)
|
||||
{
|
||||
CheckProtocolData *data = g_new0 (CheckProtocolData, 1);
|
||||
|
||||
data->host = g_strdup(host);
|
||||
data->use_fileserver_port = use_fileserver_port;
|
||||
data->callback = callback;
|
||||
data->user_data = user_data;
|
||||
|
||||
@ -823,6 +829,7 @@ typedef struct {
|
||||
int repo_version;
|
||||
char *host;
|
||||
char *token;
|
||||
gboolean use_fileserver_port;
|
||||
HttpHeadCommitCallback callback;
|
||||
void *user_data;
|
||||
|
||||
@ -892,8 +899,12 @@ check_head_commit_thread (void *vdata)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/HEAD",
|
||||
data->host, data->repo_id);
|
||||
if (!data->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/HEAD",
|
||||
data->host, data->repo_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/commit/HEAD",
|
||||
data->host, data->repo_id);
|
||||
|
||||
if (http_get (curl, url, data->token, &status, &rsp_content, &rsp_size,
|
||||
NULL, NULL, FALSE) < 0)
|
||||
@ -942,6 +953,7 @@ http_tx_manager_check_head_commit (HttpTxManager *manager,
|
||||
int repo_version,
|
||||
const char *host,
|
||||
const char *token,
|
||||
gboolean use_fileserver_port,
|
||||
HttpHeadCommitCallback callback,
|
||||
void *user_data)
|
||||
{
|
||||
@ -953,6 +965,7 @@ http_tx_manager_check_head_commit (HttpTxManager *manager,
|
||||
data->token = g_strdup(token);
|
||||
data->callback = callback;
|
||||
data->user_data = user_data;
|
||||
data->use_fileserver_port = use_fileserver_port;
|
||||
|
||||
ccnet_job_manager_schedule_job (seaf->job_mgr,
|
||||
check_head_commit_thread,
|
||||
@ -989,6 +1002,7 @@ http_folder_perm_res_free (HttpFolderPermRes *res)
|
||||
|
||||
typedef struct {
|
||||
char *host;
|
||||
gboolean use_fileserver_port;
|
||||
GList *requests;
|
||||
HttpGetFolderPermsCallback callback;
|
||||
void *user_data;
|
||||
@ -1229,7 +1243,10 @@ get_folder_perms_thread (void *vdata)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/folder-perm", data->host);
|
||||
if (!data->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/folder-perm", data->host);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/folder-perm", data->host);
|
||||
|
||||
req_content = compose_get_folder_perms_request (data->requests);
|
||||
if (!req_content)
|
||||
@ -1283,6 +1300,7 @@ get_folder_perms_done (void *vdata)
|
||||
int
|
||||
http_tx_manager_get_folder_perms (HttpTxManager *manager,
|
||||
const char *host,
|
||||
gboolean use_fileserver_port,
|
||||
GList *folder_perm_requests,
|
||||
HttpGetFolderPermsCallback callback,
|
||||
void *user_data)
|
||||
@ -1293,6 +1311,7 @@ http_tx_manager_get_folder_perms (HttpTxManager *manager,
|
||||
data->requests = folder_perm_requests;
|
||||
data->callback = callback;
|
||||
data->user_data = user_data;
|
||||
data->use_fileserver_port = use_fileserver_port;
|
||||
|
||||
ccnet_job_manager_schedule_job (seaf->job_mgr,
|
||||
get_folder_perms_thread,
|
||||
@ -1335,17 +1354,18 @@ check_permission (HttpTxTask *task, Connection *conn)
|
||||
curl = conn->curl;
|
||||
|
||||
const char *type = (task->type == HTTP_TASK_TYPE_DOWNLOAD) ? "download" : "upload";
|
||||
const char *url_prefix = (task->use_fileserver_port) ? "" : "seafhttp/";
|
||||
if (seaf->session->base.name) {
|
||||
char *client_name = g_uri_escape_string (seaf->session->base.name,
|
||||
NULL, FALSE);
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/permission-check/?op=%s"
|
||||
url = g_strdup_printf ("%s/%srepo/%s/permission-check/?op=%s"
|
||||
"&client_id=%s&client_name=%s",
|
||||
task->host, task->repo_id, type,
|
||||
task->host, url_prefix, task->repo_id, type,
|
||||
seaf->session->base.id, client_name);
|
||||
g_free (client_name);
|
||||
} else {
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/permission-check/?op=%s",
|
||||
task->host, task->repo_id, type);
|
||||
url = g_strdup_printf ("%s/%srepo/%s/permission-check/?op=%s",
|
||||
task->host, url_prefix, task->repo_id, type);
|
||||
}
|
||||
|
||||
if (http_get (curl, url, task->token, &status, NULL, NULL, NULL, NULL, FALSE) < 0) {
|
||||
@ -1379,6 +1399,7 @@ http_tx_manager_add_upload (HttpTxManager *manager,
|
||||
const char *host,
|
||||
const char *token,
|
||||
int protocol_version,
|
||||
gboolean use_fileserver_port,
|
||||
GError **error)
|
||||
{
|
||||
HttpTxTask *task;
|
||||
@ -1405,6 +1426,8 @@ http_tx_manager_add_upload (HttpTxManager *manager,
|
||||
|
||||
task->state = TASK_STATE_NORMAL;
|
||||
|
||||
task->use_fileserver_port = use_fileserver_port;
|
||||
|
||||
g_hash_table_insert (manager->priv->upload_tasks,
|
||||
g_strdup(repo_id),
|
||||
task);
|
||||
@ -1541,8 +1564,12 @@ check_quota (HttpTxTask *task, Connection *conn)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/quota-check/?delta=%"G_GINT64_FORMAT"",
|
||||
task->host, task->repo_id, delta);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/quota-check/?delta=%"G_GINT64_FORMAT"",
|
||||
task->host, task->repo_id, delta);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/quota-check/?delta=%"G_GINT64_FORMAT"",
|
||||
task->host, task->repo_id, delta);
|
||||
|
||||
if (http_get (curl, url, task->token, &status, NULL, NULL, NULL, NULL, FALSE) < 0) {
|
||||
task->error = HTTP_TASK_ERR_NET;
|
||||
@ -1583,8 +1610,12 @@ send_commit_object (HttpTxTask *task, Connection *conn)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
|
||||
if (http_put (curl, url, task->token,
|
||||
data, len,
|
||||
@ -1903,8 +1934,12 @@ send_fs_objects (HttpTxTask *task, Connection *conn, GList **send_fs_list)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/recv-fs/",
|
||||
task->host, task->repo_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/recv-fs/",
|
||||
task->host, task->repo_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/recv-fs/",
|
||||
task->host, task->repo_id);
|
||||
|
||||
if (http_post (curl, url, task->token,
|
||||
package, evbuffer_get_length(buf),
|
||||
@ -2177,8 +2212,12 @@ send_block (HttpTxTask *task, Connection *conn, const char *block_id)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
|
||||
if (http_put (curl, url, task->token,
|
||||
NULL, bmd->size,
|
||||
@ -2219,8 +2258,12 @@ update_branch (HttpTxTask *task, Connection *conn)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/HEAD/?head=%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/HEAD/?head=%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/commit/HEAD/?head=%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
|
||||
if (http_put (curl, url, task->token,
|
||||
NULL, 0,
|
||||
@ -2338,8 +2381,12 @@ http_upload_thread (void *vdata)
|
||||
goto out;
|
||||
}
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/check-fs/",
|
||||
task->host, task->repo_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/check-fs/",
|
||||
task->host, task->repo_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/check-fs/",
|
||||
task->host, task->repo_id);
|
||||
|
||||
while (send_fs_list != NULL) {
|
||||
if (upload_check_id_list_segment (task, conn, url,
|
||||
@ -2373,8 +2420,12 @@ http_upload_thread (void *vdata)
|
||||
goto out;
|
||||
}
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/check-blocks/",
|
||||
task->host, task->repo_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/check-blocks/",
|
||||
task->host, task->repo_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/check-blocks/",
|
||||
task->host, task->repo_id);
|
||||
|
||||
while (block_list != NULL) {
|
||||
if (upload_check_id_list_segment (task, conn, url,
|
||||
@ -2466,6 +2517,7 @@ http_tx_manager_add_download (HttpTxManager *manager,
|
||||
const char *worktree,
|
||||
int protocol_version,
|
||||
const char *email,
|
||||
gboolean use_fileserver_port,
|
||||
GError **error)
|
||||
{
|
||||
HttpTxTask *task;
|
||||
@ -2496,6 +2548,8 @@ http_tx_manager_add_download (HttpTxManager *manager,
|
||||
|
||||
task->state = TASK_STATE_NORMAL;
|
||||
|
||||
task->use_fileserver_port = use_fileserver_port;
|
||||
|
||||
g_hash_table_insert (manager->priv->download_tasks,
|
||||
g_strdup(repo_id),
|
||||
task);
|
||||
@ -2520,8 +2574,12 @@ get_commit_object (HttpTxTask *task, Connection *conn)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/commit/%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
|
||||
if (http_get (curl, url, task->token, &status,
|
||||
&rsp_content, &rsp_size,
|
||||
@ -2573,6 +2631,8 @@ get_needed_fs_id_list (HttpTxTask *task, Connection *conn, GList **fs_id_list)
|
||||
json_error_t jerror;
|
||||
const char *obj_id;
|
||||
|
||||
const char *url_prefix = (task->use_fileserver_port) ? "" : "seafhttp/";
|
||||
|
||||
if (!task->is_clone) {
|
||||
master = seaf_branch_manager_get_branch (seaf->branch_mgr,
|
||||
task->repo_id,
|
||||
@ -2583,15 +2643,15 @@ get_needed_fs_id_list (HttpTxTask *task, Connection *conn, GList **fs_id_list)
|
||||
return -1;
|
||||
}
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/fs-id-list/"
|
||||
url = g_strdup_printf ("%s/%srepo/%s/fs-id-list/"
|
||||
"?server-head=%s&client-head=%s",
|
||||
task->host, task->repo_id,
|
||||
task->host, url_prefix, task->repo_id,
|
||||
task->head, master->commit_id);
|
||||
|
||||
seaf_branch_unref (master);
|
||||
} else {
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/fs-id-list/?server-head=%s",
|
||||
task->host, task->repo_id, task->head);
|
||||
url = g_strdup_printf ("%s/%srepo/%s/fs-id-list/?server-head=%s",
|
||||
task->host, url_prefix, task->repo_id, task->head);
|
||||
}
|
||||
|
||||
curl = conn->curl;
|
||||
@ -2720,7 +2780,10 @@ get_fs_objects (HttpTxTask *task, Connection *conn, GList **fs_list)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/pack-fs/", task->host, task->repo_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/pack-fs/", task->host, task->repo_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/pack-fs/", task->host, task->repo_id);
|
||||
|
||||
if (http_post (curl, url, task->token,
|
||||
data, len,
|
||||
@ -2877,8 +2940,12 @@ get_block (HttpTxTask *task, Connection *conn, const char *block_id)
|
||||
|
||||
curl = conn->curl;
|
||||
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
if (!task->use_fileserver_port)
|
||||
url = g_strdup_printf ("%s/seafhttp/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
else
|
||||
url = g_strdup_printf ("%s/repo/%s/block/%s",
|
||||
task->host, task->repo_id, block_id);
|
||||
|
||||
if (http_get (curl, url, task->token, &status, NULL, NULL,
|
||||
get_block_callback, &data, TRUE) < 0) {
|
||||
|
@ -69,6 +69,7 @@ struct _HttpTxTask {
|
||||
char *host;
|
||||
gboolean is_clone;
|
||||
char *email;
|
||||
gboolean use_fileserver_port;
|
||||
|
||||
char head[41];
|
||||
|
||||
@ -109,6 +110,7 @@ http_tx_manager_add_download (HttpTxManager *manager,
|
||||
const char *worktree,
|
||||
int protocol_version,
|
||||
const char *email,
|
||||
gboolean use_fileserver_port,
|
||||
GError **error);
|
||||
|
||||
int
|
||||
@ -118,6 +120,7 @@ http_tx_manager_add_upload (HttpTxManager *manager,
|
||||
const char *host,
|
||||
const char *token,
|
||||
int protocol_version,
|
||||
gboolean use_fileserver_port,
|
||||
GError **error);
|
||||
|
||||
struct _HttpProtocolVersion {
|
||||
@ -136,6 +139,7 @@ typedef void (*HttpProtocolVersionCallback) (HttpProtocolVersion *result,
|
||||
int
|
||||
http_tx_manager_check_protocol_version (HttpTxManager *manager,
|
||||
const char *host,
|
||||
gboolean use_fileserver_port,
|
||||
HttpProtocolVersionCallback callback,
|
||||
void *user_data);
|
||||
|
||||
@ -157,6 +161,7 @@ http_tx_manager_check_head_commit (HttpTxManager *manager,
|
||||
int repo_version,
|
||||
const char *host,
|
||||
const char *token,
|
||||
gboolean use_fileserver_port,
|
||||
HttpHeadCommitCallback callback,
|
||||
void *user_data);
|
||||
|
||||
@ -192,6 +197,7 @@ typedef void (*HttpGetFolderPermsCallback) (HttpFolderPerms *result,
|
||||
int
|
||||
http_tx_manager_get_folder_perms (HttpTxManager *manager,
|
||||
const char *host,
|
||||
gboolean use_fileserver_port,
|
||||
GList *folder_perm_requests, /* HttpFolderPermReq */
|
||||
HttpGetFolderPermsCallback callback,
|
||||
void *user_data);
|
||||
|
@ -89,6 +89,9 @@ struct _SeafRepo {
|
||||
|
||||
/* Used for http sync. */
|
||||
char *server_url;
|
||||
/* Can be server_url or server_url:8082, depends on which one works. */
|
||||
char *effective_host;
|
||||
gboolean use_fileserver_port;
|
||||
};
|
||||
|
||||
|
||||
|
@ -42,9 +42,13 @@ struct _ServerState {
|
||||
typedef struct _ServerState ServerState;
|
||||
|
||||
struct _HttpServerState {
|
||||
gboolean http_not_supported;
|
||||
int http_version;
|
||||
gboolean checking;
|
||||
gint64 last_http_check_time;
|
||||
char *testing_host;
|
||||
/* Can be server_url or server_url:8082, depends on which one works. */
|
||||
char *effective_host;
|
||||
gboolean use_fileserver_port;
|
||||
|
||||
gboolean folder_perms_not_supported;
|
||||
gint64 last_check_perms_time;
|
||||
@ -96,7 +100,7 @@ static int
|
||||
sync_repo_v2 (SeafSyncManager *manager, SeafRepo *repo, gboolean is_manual_sync);
|
||||
|
||||
static gboolean
|
||||
check_http_protocol (SeafSyncManager *mgr, SeafRepo *repo, gboolean *is_checking);
|
||||
check_http_protocol (SeafSyncManager *mgr, SeafRepo *repo);
|
||||
|
||||
SeafSyncManager*
|
||||
seaf_sync_manager_new (SeafileSession *seaf)
|
||||
@ -217,7 +221,10 @@ add_repo_relays ()
|
||||
|
||||
for (ptr = repo_list; ptr; ptr = ptr->next) {
|
||||
SeafRepo *repo = ptr->data;
|
||||
if (repo->relay_id) {
|
||||
/* Only use non-http sync protocol for old repos.
|
||||
* If no old repos exist, we don't need to connect to 10001 port.
|
||||
*/
|
||||
if (repo->version == 0 && repo->relay_id) {
|
||||
add_relay_if_needed (repo);
|
||||
}
|
||||
}
|
||||
@ -406,32 +413,25 @@ seaf_sync_manager_add_sync_task (SeafSyncManager *mgr,
|
||||
if (info->in_sync)
|
||||
return 0;
|
||||
|
||||
gboolean is_checking_http = FALSE;
|
||||
if (seaf->enable_http_sync && repo->version > 0) {
|
||||
if (check_http_protocol (mgr, repo, &is_checking_http)) {
|
||||
sync_repo_v2 (mgr, repo, TRUE);
|
||||
if (repo->version > 0) {
|
||||
if (seaf->enable_http_sync) {
|
||||
if (check_http_protocol (mgr, repo)) {
|
||||
sync_repo_v2 (mgr, repo, TRUE);
|
||||
return 0;
|
||||
}
|
||||
} else
|
||||
return 0;
|
||||
} else {
|
||||
/* If relay is not ready or protocol version is not determined,
|
||||
* need to wait.
|
||||
*/
|
||||
if (!check_relay_status (mgr, repo)) {
|
||||
seaf_warning ("Relay for repo %s(%.8s) is not ready or protocol version"
|
||||
"is not detected.\n", repo->name, repo->id);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* If relay is not ready or protocol version is not determined,
|
||||
* need to wait.
|
||||
*/
|
||||
if (!check_relay_status (mgr, repo)) {
|
||||
seaf_warning ("Relay for repo %s(%.8s) is not ready or protocol version"
|
||||
"is not detected.\n", repo->name, repo->id);
|
||||
return 0;
|
||||
}
|
||||
|
||||
ServerState *state = g_hash_table_lookup (mgr->server_states,
|
||||
repo->relay_id);
|
||||
|
||||
if (repo->version == 0 ||
|
||||
state->server_side_merge == SERVER_SIDE_MERGE_UNSUPPORTED ||
|
||||
has_old_commits_to_upload (repo))
|
||||
start_sync (mgr, repo, TRUE, TRUE, FALSE);
|
||||
else if (state->server_side_merge == SERVER_SIDE_MERGE_SUPPORTED)
|
||||
sync_repo_v2 (mgr, repo, TRUE);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -696,9 +696,10 @@ start_upload_if_necessary (SyncTask *task)
|
||||
if (http_tx_manager_add_upload (seaf->http_tx_mgr,
|
||||
repo->id,
|
||||
repo->version,
|
||||
repo->server_url,
|
||||
repo->effective_host,
|
||||
repo->token,
|
||||
task->http_version,
|
||||
repo->use_fileserver_port,
|
||||
&error) < 0) {
|
||||
seaf_warning ("Failed to start http upload: %s\n", error->message);
|
||||
seaf_sync_manager_set_task_error (task, SYNC_ERROR_START_UPLOAD);
|
||||
@ -743,13 +744,14 @@ start_fetch_if_necessary (SyncTask *task, const char *remote_head)
|
||||
if (http_tx_manager_add_download (seaf->http_tx_mgr,
|
||||
repo->id,
|
||||
repo->version,
|
||||
repo->server_url,
|
||||
repo->effective_host,
|
||||
repo->token,
|
||||
remote_head,
|
||||
FALSE,
|
||||
NULL, NULL,
|
||||
task->http_version,
|
||||
repo->email,
|
||||
repo->use_fileserver_port,
|
||||
&error) < 0) {
|
||||
seaf_warning ("Failed to start http download: %s.\n", error->message);
|
||||
seaf_sync_manager_set_task_error (task, SYNC_ERROR_START_FETCH);
|
||||
@ -1502,8 +1504,9 @@ check_head_commit_http (SyncTask *task)
|
||||
|
||||
int ret = http_tx_manager_check_head_commit (seaf->http_tx_mgr,
|
||||
repo->id, repo->version,
|
||||
repo->server_url,
|
||||
repo->effective_host,
|
||||
repo->token,
|
||||
repo->use_fileserver_port,
|
||||
check_head_commit_done,
|
||||
task);
|
||||
if (ret == 0)
|
||||
@ -1751,10 +1754,8 @@ create_sync_task_v2 (SeafSyncManager *manager, SeafRepo *repo,
|
||||
HttpServerState *state = g_hash_table_lookup (manager->http_server_states,
|
||||
repo->server_url);
|
||||
if (state) {
|
||||
if (!state->http_not_supported) {
|
||||
task->http_sync = TRUE;
|
||||
task->http_version = state->http_version;
|
||||
}
|
||||
task->http_sync = TRUE;
|
||||
task->http_version = state->http_version;
|
||||
}
|
||||
}
|
||||
|
||||
@ -1970,34 +1971,68 @@ check_relay_status (SeafSyncManager *mgr, SeafRepo *repo)
|
||||
}
|
||||
}
|
||||
|
||||
static char *
|
||||
http_fileserver_url (const char *url)
|
||||
{
|
||||
char *colon;
|
||||
char *url_no_port;
|
||||
char *ret = NULL;
|
||||
|
||||
colon = strrchr (url, ':');
|
||||
if (colon) {
|
||||
url_no_port = g_strndup(url, colon - url);
|
||||
ret = g_strconcat(url_no_port, ":8082", NULL);
|
||||
} else {
|
||||
ret = g_strconcat(url, ":8082", NULL);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
check_http_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
check_http_fileserver_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
{
|
||||
HttpServerState *state = user_data;
|
||||
|
||||
state->checking = FALSE;
|
||||
|
||||
if (result->check_success) {
|
||||
state->http_not_supported = result->not_supported;
|
||||
if (!result->not_supported)
|
||||
state->http_version = result->version;
|
||||
} else
|
||||
state->http_not_supported = TRUE;
|
||||
if (result->check_success && !result->not_supported) {
|
||||
state->http_version = result->version;
|
||||
state->effective_host = http_fileserver_url(state->testing_host);
|
||||
state->use_fileserver_port = TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
check_http_protocol_done (HttpProtocolVersion *result, void *user_data)
|
||||
{
|
||||
HttpServerState *state = user_data;
|
||||
|
||||
if (result->check_success && !result->not_supported) {
|
||||
state->http_version = result->version;
|
||||
state->effective_host = g_strdup(state->testing_host);
|
||||
state->checking = FALSE;
|
||||
} else if (strncmp(state->testing_host, "https", 5) != 0) {
|
||||
char *host_fileserver = http_fileserver_url(state->testing_host);
|
||||
http_tx_manager_check_protocol_version (seaf->http_tx_mgr,
|
||||
host_fileserver,
|
||||
TRUE,
|
||||
check_http_fileserver_protocol_done,
|
||||
state);
|
||||
g_free (host_fileserver);
|
||||
} else {
|
||||
state->checking = FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
#define CHECK_HTTP_INTERVAL 10
|
||||
|
||||
/*
|
||||
* Returns TRUE if we can use http-sync; otherwise FALSE.
|
||||
* If FALSE is returned, the caller should also check @is_checking value.
|
||||
* If @is_checking is set to TRUE, we're still determining whether the
|
||||
* server supports http-sync.
|
||||
* Returns TRUE if we're ready to use http-sync; otherwise FALSE.
|
||||
*/
|
||||
static gboolean
|
||||
check_http_protocol (SeafSyncManager *mgr, SeafRepo *repo, gboolean *is_checking)
|
||||
check_http_protocol (SeafSyncManager *mgr, SeafRepo *repo)
|
||||
{
|
||||
*is_checking = FALSE;
|
||||
|
||||
/* If a repo was cloned before 4.0, server-url is not set. */
|
||||
if (!repo->server_url)
|
||||
return FALSE;
|
||||
@ -2011,21 +2046,36 @@ check_http_protocol (SeafSyncManager *mgr, SeafRepo *repo, gboolean *is_checking
|
||||
}
|
||||
|
||||
if (state->checking) {
|
||||
*is_checking = TRUE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (state->http_not_supported)
|
||||
return FALSE;
|
||||
if (state->http_version > 0)
|
||||
if (state->http_version > 0) {
|
||||
if (!repo->effective_host) {
|
||||
repo->effective_host = g_strdup(state->effective_host);
|
||||
repo->use_fileserver_port = state->use_fileserver_port;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* If we haven't detected the server url successfully, retry every 10 seconds. */
|
||||
gint64 now = time(NULL);
|
||||
if (now - state->last_http_check_time < CHECK_HTTP_INTERVAL)
|
||||
return FALSE;
|
||||
|
||||
/* First try repo->server_url.
|
||||
* If it fails and https is not used, try server_url:8082 instead.
|
||||
*/
|
||||
g_free (state->testing_host);
|
||||
state->testing_host = g_strdup(repo->server_url);
|
||||
|
||||
state->last_http_check_time = (gint64)time(NULL);
|
||||
|
||||
http_tx_manager_check_protocol_version (seaf->http_tx_mgr,
|
||||
repo->server_url,
|
||||
FALSE,
|
||||
check_http_protocol_done,
|
||||
state);
|
||||
state->checking = TRUE;
|
||||
*is_checking = TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
@ -2381,7 +2431,8 @@ check_folder_permissions_one_server (SeafSyncManager *mgr,
|
||||
|
||||
/* The requests list will be freed in http tx manager. */
|
||||
http_tx_manager_get_folder_perms (seaf->http_tx_mgr,
|
||||
host,
|
||||
server_state->effective_host,
|
||||
server_state->use_fileserver_port,
|
||||
requests,
|
||||
check_folder_perms_done,
|
||||
server_state);
|
||||
@ -2494,32 +2545,20 @@ auto_sync_pulse (void *vmanager)
|
||||
if (info->in_sync)
|
||||
continue;
|
||||
|
||||
/* Try to use http sync first if enabled. */
|
||||
gboolean is_checking_http = FALSE;
|
||||
if (seaf->enable_http_sync && repo->version > 0) {
|
||||
if (check_http_protocol (manager, repo, &is_checking_http)) {
|
||||
sync_repo_v2 (manager, repo, FALSE);
|
||||
continue;
|
||||
} else if (is_checking_http)
|
||||
continue;
|
||||
/* Otherwise we've determined the server doesn't support http-sync. */
|
||||
if (repo->version > 0) {
|
||||
/* For repo version > 0, only use http sync. */
|
||||
if (seaf->enable_http_sync) {
|
||||
if (check_http_protocol (manager, repo)) {
|
||||
sync_repo_v2 (manager, repo, FALSE);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
/* If relay is not ready or protocol version is not determined,
|
||||
* need to wait.
|
||||
*/
|
||||
if (check_relay_status (manager, repo))
|
||||
sync_repo (manager, repo);
|
||||
}
|
||||
|
||||
/* If relay is not ready or protocol version is not determined,
|
||||
* need to wait.
|
||||
*/
|
||||
if (!check_relay_status (manager, repo))
|
||||
continue;
|
||||
|
||||
ServerState *state = g_hash_table_lookup (manager->server_states,
|
||||
repo->relay_id);
|
||||
|
||||
if (repo->version == 0 ||
|
||||
state->server_side_merge == SERVER_SIDE_MERGE_UNSUPPORTED ||
|
||||
has_old_commits_to_upload (repo))
|
||||
sync_repo (manager, repo);
|
||||
else if (state->server_side_merge == SERVER_SIDE_MERGE_SUPPORTED)
|
||||
sync_repo_v2 (manager, repo, FALSE);
|
||||
}
|
||||
|
||||
g_list_free (repos);
|
||||
|
Loading…
Reference in New Issue
Block a user