📄 commit.c
字号:
svn_ra_serf__create_options_req(&opt_ctx, ctx->session, ctx->session->conns[0], ctx->session->repos_url.path, ctx->pool); SVN_ERR(svn_ra_serf__context_run_wait( svn_ra_serf__get_options_done_ptr(opt_ctx), ctx->session, ctx->pool)); activity_str = svn_ra_serf__options_get_activity_collection(opt_ctx); if (!activity_str) { abort(); } ctx->activity_url = svn_path_url_add_component(activity_str, ctx->uuid, ctx->pool); ctx->activity_url_len = strlen(ctx->activity_url); /* Create our activity URL now on the server. */ handler = apr_pcalloc(ctx->pool, sizeof(*handler)); handler->method = "MKACTIVITY"; handler->path = ctx->activity_url; handler->conn = ctx->session->conns[0]; handler->session = ctx->session; mkact_ctx = apr_pcalloc(ctx->pool, sizeof(*mkact_ctx)); handler->response_handler = svn_ra_serf__handle_status_only; handler->response_baton = mkact_ctx; svn_ra_serf__request_create(handler); SVN_ERR(svn_ra_serf__context_run_wait(&mkact_ctx->done, ctx->session, ctx->pool)); if (mkact_ctx->status != 201) { abort(); } SVN_ERR(svn_ra_serf__discover_root(&vcc_url, NULL, ctx->session, ctx->conn, ctx->session->repos_url.path, ctx->pool)); /* Now go fetch our VCC and baseline so we can do a CHECKOUT. */ props = apr_hash_make(ctx->pool); propfind_ctx = NULL; svn_ra_serf__deliver_props(&propfind_ctx, props, ctx->session, ctx->conn, vcc_url, SVN_INVALID_REVNUM, "0", checked_in_props, FALSE, NULL, ctx->pool); SVN_ERR(svn_ra_serf__wait_for_props(propfind_ctx, ctx->session, ctx->pool)); ctx->baseline_url = svn_ra_serf__get_ver_prop(props, vcc_url, SVN_INVALID_REVNUM, "DAV:", "checked-in"); if (!ctx->baseline_url) { abort(); } dir = apr_pcalloc(dir_pool, sizeof(*dir)); dir->pool = dir_pool; dir->commit = ctx; dir->base_revision = base_revision; dir->name = ""; dir->changed_props = apr_hash_make(dir->pool); dir->removed_props = apr_hash_make(dir->pool); SVN_ERR(get_version_url(dir)); ctx->checked_in_url = dir->checked_in_url; /* Checkout our root dir */ SVN_ERR(checkout_dir(dir)); /* PROPPATCH our log message and pass it along. */ proppatch_ctx = apr_pcalloc(ctx->pool, sizeof(*proppatch_ctx)); proppatch_ctx->pool = dir_pool; proppatch_ctx->commit = ctx; proppatch_ctx->path = ctx->baseline->resource_url; proppatch_ctx->changed_props = apr_hash_make(proppatch_ctx->pool); proppatch_ctx->removed_props = apr_hash_make(proppatch_ctx->pool); svn_ra_serf__set_prop(proppatch_ctx->changed_props, proppatch_ctx->path, SVN_DAV_PROP_NS_SVN, "log", dir->commit->log_msg, proppatch_ctx->pool); SVN_ERR(proppatch_resource(proppatch_ctx, dir->commit, ctx->pool)); *root_baton = dir; return SVN_NO_ERROR;}static svn_error_t *delete_entry(const char *path, svn_revnum_t revision, void *parent_baton, apr_pool_t *pool){ dir_context_t *dir = parent_baton; delete_context_t *delete_ctx; svn_ra_serf__handler_t *handler; svn_error_t *err; /* Ensure our directory has been checked out */ SVN_ERR(checkout_dir(dir)); /* DELETE our entry */ delete_ctx = apr_pcalloc(pool, sizeof(*delete_ctx)); delete_ctx->path = path; delete_ctx->revision = revision; delete_ctx->lock_token_hash = dir->commit->lock_tokens; delete_ctx->keep_locks = dir->commit->keep_locks; handler = apr_pcalloc(pool, sizeof(*handler)); handler->session = dir->commit->session; handler->conn = dir->commit->conn; handler->response_handler = svn_ra_serf__handle_status_only; handler->response_baton = &delete_ctx->progress; handler->header_delegate = setup_delete_headers; handler->header_delegate_baton = delete_ctx; handler->method = "DELETE"; handler->path = svn_path_url_add_component(dir->checkout->resource_url, svn_path_basename(path, pool), pool); svn_ra_serf__request_create(handler); err = svn_ra_serf__context_run_wait(&delete_ctx->progress.done, dir->commit->session, pool); if (err && (err->apr_err == SVN_ERR_FS_BAD_LOCK_TOKEN || err->apr_err == SVN_ERR_FS_NO_LOCK_TOKEN || err->apr_err == SVN_ERR_FS_LOCK_OWNER_MISMATCH || err->apr_err == SVN_ERR_FS_PATH_ALREADY_LOCKED)) { svn_error_clear(err); handler->body_delegate = create_delete_body; handler->body_delegate_baton = delete_ctx; handler->body_type = "text/xml"; svn_ra_serf__request_create(handler); delete_ctx->progress.done = 0; SVN_ERR(svn_ra_serf__context_run_wait(&delete_ctx->progress.done, dir->commit->session, pool)); } else if (err) { return err; } if (delete_ctx->progress.status != 204) { return return_response_err(handler, &delete_ctx->progress); } apr_hash_set(dir->commit->deleted_entries, apr_pstrdup(dir->commit->pool, path), APR_HASH_KEY_STRING, (void*)1); return SVN_NO_ERROR;}static svn_error_t *add_directory(const char *path, void *parent_baton, const char *copyfrom_path, svn_revnum_t copyfrom_revision, apr_pool_t *dir_pool, void **child_baton){ dir_context_t *parent = parent_baton; dir_context_t *dir; svn_ra_serf__handler_t *handler; svn_ra_serf__simple_request_context_t *add_dir_ctx; /* Ensure our parent is checked out. */ SVN_ERR(checkout_dir(parent)); dir = apr_pcalloc(dir_pool, sizeof(*dir)); dir->pool = dir_pool; dir->parent_dir = parent; dir->commit = parent->commit; dir->base_revision = SVN_INVALID_REVNUM; dir->copy_revision = copyfrom_revision; dir->copy_path = copyfrom_path; dir->name = path; dir->checked_in_url = svn_path_url_add_component(parent->commit->checked_in_url, path, dir->pool); dir->changed_props = apr_hash_make(dir->pool); dir->removed_props = apr_hash_make(dir->pool); handler = apr_pcalloc(dir->pool, sizeof(*handler)); handler->conn = dir->commit->conn; handler->session = dir->commit->session; add_dir_ctx = apr_pcalloc(dir->pool, sizeof(*add_dir_ctx)); handler->response_handler = svn_ra_serf__handle_status_only; handler->response_baton = add_dir_ctx; if (!dir->copy_path) { handler->method = "MKCOL"; handler->path = svn_path_url_add_component(parent->checkout->resource_url, svn_path_basename(path, dir->pool), dir->pool); } else { apr_uri_t uri; apr_hash_t *props; const char *vcc_url, *rel_copy_path, *basecoll_url, *req_url; props = apr_hash_make(dir->pool); apr_uri_parse(dir->pool, dir->copy_path, &uri); SVN_ERR(svn_ra_serf__discover_root(&vcc_url, &rel_copy_path, dir->commit->session, dir->commit->conn, uri.path, dir->pool)); SVN_ERR(svn_ra_serf__retrieve_props(props, dir->commit->session, dir->commit->conn, vcc_url, dir->copy_revision, "0", baseline_props, dir->pool)); basecoll_url = svn_ra_serf__get_ver_prop(props, vcc_url, dir->copy_revision, "DAV:", "baseline-collection"); if (!basecoll_url) { abort(); } req_url = svn_path_url_add_component(basecoll_url, rel_copy_path, dir->pool); handler->method = "COPY"; handler->path = req_url; handler->header_delegate = setup_copy_dir_headers; handler->header_delegate_baton = dir; } svn_ra_serf__request_create(handler); SVN_ERR(svn_ra_serf__context_run_wait(&add_dir_ctx->done, dir->commit->session, dir->pool)); if (add_dir_ctx->status != 201) { SVN_ERR(add_dir_ctx->server_error.error); return svn_error_createf(SVN_ERR_RA_DAV_REQUEST_FAILED, NULL, _("Add directory failed: %s on %s (%d)"), handler->method, handler->path, add_dir_ctx->status); } *child_baton = dir; return SVN_NO_ERROR;}static svn_error_t *open_directory(const char *path, void *parent_baton, svn_revnum_t base_revision, apr_pool_t *dir_pool, void **child_baton){ dir_context_t *parent = parent_baton; dir_context_t *dir; dir = apr_pcalloc(dir_pool, sizeof(*dir)); dir->pool = dir_pool; dir->parent_dir = parent; dir->commit = parent->commit; dir->base_revision = base_revision; dir->name = path; dir->changed_props = apr_hash_make(dir->pool); dir->removed_props = apr_hash_make(dir->pool); SVN_ERR(get_version_url(dir)); *child_baton = dir; return SVN_NO_ERROR;}static svn_error_t *change_dir_prop(void *dir_baton, const char *name, const svn_string_t *value, apr_pool_t *pool){ dir_context_t *dir = dir_baton; const char *ns; /* Ensure we have a checked out dir. */ SVN_ERR(checkout_dir(dir)); name = apr_pstrdup(dir->pool, name); if (strncmp(name, SVN_PROP_PREFIX, sizeof(SVN_PROP_PREFIX) - 1) == 0) { ns = SVN_DAV_PROP_NS_SVN; name += sizeof(SVN_PROP_PREFIX) - 1; } else { ns = SVN_DAV_PROP_NS_CUSTOM; } if (value) { value = svn_string_dup(value, dir->pool); svn_ra_serf__set_prop(dir->changed_props, dir->checkout->resource_url, ns, name, value, dir->pool); } else { value = svn_string_create("", dir->pool); svn_ra_serf__set_prop(dir->removed_props, dir->checkout->resource_url, ns, name, value, dir->pool); } return SVN_NO_ERROR;}static svn_error_t *close_directory(void *dir_baton, apr_pool_t *pool){ dir_context_t *dir = dir_baton; /* Huh? We're going to be called before the texts are sent. Ugh. * Therefore, just wave politely at our caller. */ /* PROPPATCH our prop change and pass it along. */ if (apr_hash_count(dir->changed_props) || apr_hash_count(dir->removed_props)) { proppatch_context_t *proppatch_ctx; proppatch_ctx = apr_pcalloc(pool, sizeof(*proppatch_ctx)); proppatch_ctx->pool = pool; proppatch_ctx->commit = dir->commit; proppatch_ctx->name = dir->name; proppatch_ctx->path = dir->checkout->resource_url; proppatch_ctx->changed_props = dir->changed_props; proppatch_ctx->removed_props = dir->removed_props; SVN_ERR(proppatch_resource(proppatch_ctx, dir->commit, dir->pool)); } return SVN_NO_ERROR;}static svn_error_t *absent_directory(const char *path, void *parent_baton, apr_pool_t *pool){#if 0 dir_context_t *ctx = parent_baton;#endif abort();}static svn_error_t *add_file(const char *path, void *parent_baton, const char *copy_path, svn_revnum_t copy_revision, apr_pool_t *file_pool, void **file_baton){ dir_context_t *dir = parent_baton; file_context_t *new_file; /* Ensure our directory has been checked out */ SVN_ERR(checkout_dir(dir)); new_file = apr_pcalloc(file_pool, sizeof(*new_file)); new_file->pool = file_pool; dir->ref_count++; new_file->parent_dir = dir; new_file->commit = dir->commit; new_file->name = path; new_file->base_revision = SVN_INVALID_REVNUM; new_file->copy_path = copy_path; new_file->copy_revision = copy_revision; new_file->changed_props = apr_hash_make(new_file->pool); new_file->removed_props = apr_hash_make(new_file->pool); /* Ensure that the file doesn't exist by doing a HEAD on the resource - * only if we haven't deleted it in this commit already. */ if (!apr_hash_get(dir->commit->deleted_entries, new_file->name, APR_HASH_KEY_STRING)) { svn_ra_serf__simple_request_context_t *head_ctx; svn_ra_serf__handler_t *handler; handler = apr_pcalloc(new_file->pool, sizeof(*handler)); handler->session = new_file->commit->session; handler->conn = new_file->commit->conn; handler->method = "HEAD"; handler->path = svn_path_url_add_component(new_file->commit->session->repos_url.path, path, new_file->pool); head_ctx = apr_pcalloc(new_file->pool, sizeof(*head_ctx)); handler->response_handler = svn_ra_serf__handle_status_only; handler->response_baton = head_ctx; svn_ra_serf__request_create(handler); SVN_ERR(svn_ra_serf__context_run_wait(&head_ctx->done, new_file->commit->session, new_file->pool)); if (head_ctx->status != 404) { return svn_error_createf(SVN_ERR_RA_DAV_ALREADY_EXISTS, NULL, _("File '%s' already exists"), path); } } new_file->put_url = svn_path_url_add_component(dir->checkout->resource_url, svn_path_basename(path, new_file->pool), new_file->pool); *file_baton = new_file;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -