You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@subversion.apache.org by Ramkumar Ramachandra <ar...@gmail.com> on 2010/07/07 00:14:42 UTC
[PATCH 02/13] Add skeleton SVN client and Makefile
Add a basic SVN command-line client along with a Makefile that does
just enough to establish a connection with the ASF subversion server;
it initializes a memory pool, sees that configuration files are in
order, builds up a context object, sets up an authentication baton,
and finally opens a session to the subversion server.
Signed-off-by: Ramkumar Ramachandra <ar...@gmail.com>
---
Makefile | 8 +++++++
svndumpr.c | 68 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 76 insertions(+), 0 deletions(-)
create mode 100644 Makefile
create mode 100644 svndumpr.c
diff --git a/Makefile b/Makefile
new file mode 100644
index 0000000..a6022f7
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,8 @@
+svndumpr: *.c *.h
+ $(CC) -Wall -Werror -DAPR_POOL_DEBUG -ggdb3 -O0 -o $@ svndumpr.c -lsvn_client-1 -I. -I/usr/include/subversion-1 -I/usr/include/apr-1.0
+
+svndumpr_bench: *.c *.h
+ $(CC) -O2 -o $@ svndumpr.c -lsvn_client-1 -I. -I/usr/include/subversion-1 -I/usr/include/apr-1.0
+
+clean:
+ $(RM) svndumpr svndumpr_bench
diff --git a/svndumpr.c b/svndumpr.c
new file mode 100644
index 0000000..737c4aa
--- /dev/null
+++ b/svndumpr.c
@@ -0,0 +1,68 @@
+/* Licensed under a two-clause BSD-style license.
+ * See LICENSE for details.
+ */
+
+#include "svn_pools.h"
+#include "svn_cmdline.h"
+#include "svn_client.h"
+#include "svn_ra.h"
+#include "svn_repos.h"
+
+static apr_pool_t *pool = NULL;
+static svn_client_ctx_t *ctx = NULL;
+static svn_ra_session_t *session = NULL;
+
+svn_error_t *populate_context()
+{
+ const char *http_library;
+
+ SVN_ERR(svn_config_get_config(&(ctx->config), NULL, pool));
+
+ http_library = getenv("SVN_HTTP_LIBRARY");
+ if (http_library)
+ svn_config_set(apr_hash_get(ctx->config, "servers", APR_HASH_KEY_STRING),
+ "global", "http-library", http_library);
+ return SVN_NO_ERROR;
+}
+
+svn_error_t *open_connection(const char *url)
+{
+ SVN_ERR(svn_config_ensure (NULL, pool));
+ SVN_ERR(svn_client_create_context (&ctx, pool));
+ SVN_ERR(svn_ra_initialize(pool));
+
+#if defined(WIN32) || defined(__CYGWIN__)
+ if (getenv("SVN_ASP_DOT_NET_HACK"))
+ SVN_ERR(svn_wc_set_adm_dir("_svn", pool));
+#endif
+
+ SVN_ERR(populate_context());
+ SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
+ NULL, NULL, NULL, FALSE,
+ FALSE, NULL, NULL, NULL,
+ pool));
+ SVN_ERR(svn_client_open_ra_session(&session, url, ctx, pool));
+ return SVN_NO_ERROR;
+}
+
+svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
+{
+ return SVN_NO_ERROR;
+}
+
+int main()
+{
+ const char url[] = "http://svn.apache.org/repos/asf";
+ svn_revnum_t start_revision = 1, end_revision = 500;
+ if (svn_cmdline_init ("svndumpr", stderr) != EXIT_SUCCESS)
+ return 1;
+
+ pool = svn_pool_create(NULL);
+
+ SVN_INT_ERR(open_connection(url));
+ SVN_INT_ERR(replay_range(start_revision, end_revision));
+
+ svn_pool_destroy(pool);
+
+ return 0;
+}
--
1.7.1
Re: [PATCH 02/13] Add skeleton SVN client and Makefile
Posted by Ramkumar Ramachandra <ar...@gmail.com>.
Hi,
Jonathan Nieder writes:
> Ramkumar Ramachandra wrote:
>
> > Here's a diff of the modifications I made after your review:
>
> That’s quite helpful.
>
> > +++ b/svndumpr.c
> > @@ -76,31 +76,19 @@ static svn_error_t *replay_revend(svn_revnum_t revision,
> [...]
> > + /* Populte ctx->auth_baton with the auth baton
> > + non-interactively. Arguments 3, 4 and 5 are for username,
> > + password and config_dir which is NULL in this case. Set
> > + no_auth_cache and trust_serv_cert to FALSE, don't provide a
> > + config, and omit cancel_func/ cancel_baton */
> > SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
> > NULL, NULL, NULL, FALSE,
> > FALSE, NULL, NULL, NULL,
>
> I think you took my suggestion too seriously here. Such a comment
> probably will not help people much; instead, maybe a more focused
> comment can help the curious avoid looking up
> svn_cmdline_create_auth_baton:
>
> /* Default authentication providers for noninteractive
> use. */
> SVN_ERR(svn_cmdline_create_auth_baton(...
Fixed.
> Looking this up, I notice that function was added in svn 1.6.
> Hopefully that is okay, since this code is destined for svn trunk.
I have a working 1.6 fork now that I intend to merge into
git.git. When there's a new release of Subversion that includes my
patch, I'll remove it from git.git.
> Reviewed-by: Jonathan Nieder <jr...@gmail.com>
Thanks.
-- Ram
Re: [PATCH 02/13] Add skeleton SVN client and Makefile
Posted by Jonathan Nieder <jr...@gmail.com>.
Ramkumar Ramachandra wrote:
> Here's a diff of the modifications I made after your review:
That’s quite helpful.
> +++ b/svndumpr.c
> @@ -76,31 +76,19 @@ static svn_error_t *replay_revend(svn_revnum_t revision,
[...]
> + /* Populte ctx->auth_baton with the auth baton
> + non-interactively. Arguments 3, 4 and 5 are for username,
> + password and config_dir which is NULL in this case. Set
> + no_auth_cache and trust_serv_cert to FALSE, don't provide a
> + config, and omit cancel_func/ cancel_baton */
> SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
> NULL, NULL, NULL, FALSE,
> FALSE, NULL, NULL, NULL,
I think you took my suggestion too seriously here. Such a comment
probably will not help people much; instead, maybe a more focused
comment can help the curious avoid looking up
svn_cmdline_create_auth_baton:
/* Default authentication providers for noninteractive
use. */
SVN_ERR(svn_cmdline_create_auth_baton(...
Looking this up, I notice that function was added in svn 1.6.
Hopefully that is okay, since this code is destined for svn trunk.
Except as noted above,
Reviewed-by: Jonathan Nieder <jr...@gmail.com>
Thanks.
Re: [PATCH 02/13] Add skeleton SVN client and Makefile
Posted by Ramkumar Ramachandra <ar...@gmail.com>.
Hi Jonathan,
Jonathan Nieder writes:
> Ramkumar Ramachandra wrote:
>
> > Add a basic SVN command-line client along with a Makefile that does
> > just enough to establish a connection with the ASF subversion server;
>
> Thanks for splitting this out.
Thanks for getting the review process started :)
> Let’s see what’s needed to set up a connection:
>
> > +++ b/Makefile
> > @@ -0,0 +1,8 @@
> > +svndumpr: *.c *.h
> > + $(CC) -Wall -Werror -DAPR_POOL_DEBUG -ggdb3 -O0 -o $@ svndumpr.c -lsvn_client-1 -I. -I/usr/include/subversion-1 -I/usr/include/apr-1.0
>
> Links against libsvnclient-1. Good.
>
> I assume the details of the Makefile are not important, since it is
> probably going to be revamped in the style of the svn build system
> anyway.
Right.
> > +++ b/svndumpr.c
> > @@ -0,0 +1,68 @@
> [...]
> > +svn_error_t *populate_context()
> [...]
> > +svn_error_t *open_connection(const char *url)
> [...]
> > +svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
>
> Why not static?
Changed (see end of email).
> > +svn_error_t *populate_context()
> > +{
> > + const char *http_library;
> > +
> > + SVN_ERR(svn_config_get_config(&(ctx->config), NULL, pool));
> > +
> > + http_library = getenv("SVN_HTTP_LIBRARY");
> > + if (http_library)
> > + svn_config_set(apr_hash_get(ctx->config, "servers", APR_HASH_KEY_STRING),
> > + "global", "http-library", http_library);
>
> I tried googling for this SVN_HTTP_LIBRARY setting, but no
> useful hints. I take it that this overrides the [global] http-library
> setting from ~/.subversion/servers? Do other commands honor this
> environment variable or just svndumpr?
I originally had this to switch between neon and serf libraries. It
seems that this is no more necessary.
> [...]
> > +svn_error_t *open_connection(const char *url)
> > +{
> > + SVN_ERR(svn_config_ensure (NULL, pool));
> > + SVN_ERR(svn_client_create_context (&ctx, pool));
> > + SVN_ERR(svn_ra_initialize(pool));
> > +
> > +#if defined(WIN32) || defined(__CYGWIN__)
> > + if (getenv("SVN_ASP_DOT_NET_HACK"))
> > + SVN_ERR(svn_wc_set_adm_dir("_svn", pool));
> > +#endif
>
> I guess it’s water under the bridge now (from 5 years ago), but why do
> clients have to do this themselves? It would not be so difficult for
> libsvnclient to automatically set the admin dir according to whether
> SVN_ASP_DOT_NET_HACK is set or not, or at least to provide a single
> function to call and do so.
Good question. I copied this out from some legacy code in the
Subversion trunk. Additionally, since I don't have a working copy,
this is completely unnecessary. Removed now.
> > +
> > + SVN_ERR(populate_context());
> > + SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
> > + NULL, NULL, NULL, FALSE,
> > + FALSE, NULL, NULL, NULL,
> > + pool));
>
> Maybe comments would help, for the boolean arguments.
Fixed.
> > + SVN_ERR(svn_client_open_ra_session(&session, url, ctx, pool));
> > + return SVN_NO_ERROR;
> > +}
> > +
> > +svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
> > +{
> > + return SVN_NO_ERROR;
> > +}
>
> Might be more self-explanatory without this function, but that
> is just nitpicking.
I've filled in the function in a future patch. It's just to say that
I'm "opening a connection and then calling replay_range, in that
order". Yes, replay_range does nothing in this patch.
> > +
> > +int main()
> > +{
> > + const char url[] = "http://svn.apache.org/repos/asf";
> > + svn_revnum_t start_revision = 1, end_revision = 500;
> > + if (svn_cmdline_init ("svndumpr", stderr) != EXIT_SUCCESS)
> > + return 1;
> > +
> > + pool = svn_pool_create(NULL);
> > +
> > + SVN_INT_ERR(open_connection(url));
> > + SVN_INT_ERR(replay_range(start_revision, end_revision));
> > +
> > + svn_pool_destroy(pool);
> > +
> > + return 0;
> > +}
>
> So: this is an expensive no-op.
Exactly. I built up the patches so that at every stage, the program
compiles and runs fine, implementing part of full functionality.
Here's a diff of the modifications I made after your review:
diff --git a/svndumpr.c b/svndumpr.c
index 011941f..f3117aa 100644
--- a/svndumpr.c
+++ b/svndumpr.c
@@ -76,31 +76,19 @@ static svn_error_t *replay_revend(svn_revnum_t revision,
return SVN_NO_ERROR;
}
-svn_error_t *populate_context()
-{
- const char *http_library;
-
- SVN_ERR(svn_config_get_config(&(ctx->config), NULL, pool));
-
- http_library = getenv("SVN_HTTP_LIBRARY");
- if (http_library)
- svn_config_set(apr_hash_get(ctx->config, "servers", APR_HASH_KEY_STRING),
- "global", "http-library", http_library);
- return SVN_NO_ERROR;
-}
-
-svn_error_t *open_connection(const char *url)
+static svn_error_t *open_connection(const char *url)
{
SVN_ERR(svn_config_ensure (NULL, pool));
SVN_ERR(svn_client_create_context (&ctx, pool));
SVN_ERR(svn_ra_initialize(pool));
-#if defined(WIN32) || defined(__CYGWIN__)
- if (getenv("SVN_ASP_DOT_NET_HACK"))
- SVN_ERR(svn_wc_set_adm_dir("_svn", pool));
-#endif
+ SVN_ERR(svn_config_get_config(&(ctx->config), NULL, pool));
- SVN_ERR(populate_context());
+ /* Populte ctx->auth_baton with the auth baton
+ non-interactively. Arguments 3, 4 and 5 are for username,
+ password and config_dir which is NULL in this case. Set
+ no_auth_cache and trust_serv_cert to FALSE, don't provide a
+ config, and omit cancel_func/ cancel_baton */
SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
NULL, NULL, NULL, FALSE,
FALSE, NULL, NULL, NULL,
@@ -109,7 +97,7 @@ svn_error_t *open_connection(const char *url)
return SVN_NO_ERROR;
}
-svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
+static svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
{
const svn_delta_editor_t *dump_editor, *debug_editor;
void *debug_baton, *dump_baton;
-- Ram
Re: [PATCH 02/13] Add skeleton SVN client and Makefile
Posted by Jonathan Nieder <jr...@gmail.com>.
Ramkumar Ramachandra wrote:
> Add a basic SVN command-line client along with a Makefile that does
> just enough to establish a connection with the ASF subversion server;
Thanks for splitting this out.
Let’s see what’s needed to set up a connection:
> +++ b/Makefile
> @@ -0,0 +1,8 @@
> +svndumpr: *.c *.h
> + $(CC) -Wall -Werror -DAPR_POOL_DEBUG -ggdb3 -O0 -o $@ svndumpr.c -lsvn_client-1 -I. -I/usr/include/subversion-1 -I/usr/include/apr-1.0
Links against libsvnclient-1. Good.
I assume the details of the Makefile are not important, since it is
probably going to be revamped in the style of the svn build system
anyway.
> +++ b/svndumpr.c
> @@ -0,0 +1,68 @@
[...]
> +svn_error_t *populate_context()
[...]
> +svn_error_t *open_connection(const char *url)
[...]
> +svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
Why not static?
> +svn_error_t *populate_context()
> +{
> + const char *http_library;
> +
> + SVN_ERR(svn_config_get_config(&(ctx->config), NULL, pool));
> +
> + http_library = getenv("SVN_HTTP_LIBRARY");
> + if (http_library)
> + svn_config_set(apr_hash_get(ctx->config, "servers", APR_HASH_KEY_STRING),
> + "global", "http-library", http_library);
I tried googling for this SVN_HTTP_LIBRARY setting, but no
useful hints. I take it that this overrides the [global] http-library
setting from ~/.subversion/servers? Do other commands honor this
environment variable or just svndumpr?
[...]
> +svn_error_t *open_connection(const char *url)
> +{
> + SVN_ERR(svn_config_ensure (NULL, pool));
> + SVN_ERR(svn_client_create_context (&ctx, pool));
> + SVN_ERR(svn_ra_initialize(pool));
> +
> +#if defined(WIN32) || defined(__CYGWIN__)
> + if (getenv("SVN_ASP_DOT_NET_HACK"))
> + SVN_ERR(svn_wc_set_adm_dir("_svn", pool));
> +#endif
I guess it’s water under the bridge now (from 5 years ago), but why do
clients have to do this themselves? It would not be so difficult for
libsvnclient to automatically set the admin dir according to whether
SVN_ASP_DOT_NET_HACK is set or not, or at least to provide a single
function to call and do so.
But that is not the topic for the moment. I am tempted to suggest
checking SVN_ASP_DOT_NET_HACK unconditionally (i.e., on Unix, too),
just so the function is easier to scan. Or there could be a separate
set_appropriate_adm_dir function in svndumpr.c:
#if defined(WIN32) || ...
static svn_error_t *set_appropriate_adm_dir(...)
{
if (getenv...
...
}
#else
static svn_error_t *set_appropriate_adm_dir(...
{
return SVN_NO_ERROR;
}
#endif
Feel free to ignore me here. :)
> +
> + SVN_ERR(populate_context());
> + SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), TRUE,
> + NULL, NULL, NULL, FALSE,
> + FALSE, NULL, NULL, NULL,
> + pool));
Maybe comments would help, for the boolean arguments.
> + SVN_ERR(svn_client_open_ra_session(&session, url, ctx, pool));
> + return SVN_NO_ERROR;
> +}
> +
> +svn_error_t *replay_range(svn_revnum_t start_revision, svn_revnum_t end_revision)
> +{
> + return SVN_NO_ERROR;
> +}
Might be more self-explanatory without this function, but that
is just nitpicking.
> +
> +int main()
> +{
> + const char url[] = "http://svn.apache.org/repos/asf";
> + svn_revnum_t start_revision = 1, end_revision = 500;
> + if (svn_cmdline_init ("svndumpr", stderr) != EXIT_SUCCESS)
> + return 1;
> +
> + pool = svn_pool_create(NULL);
> +
> + SVN_INT_ERR(open_connection(url));
> + SVN_INT_ERR(replay_range(start_revision, end_revision));
> +
> + svn_pool_destroy(pool);
> +
> + return 0;
> +}
So: this is an expensive no-op.
Thanks for the pleasant reading.
Jonathan