In the command-line client, forbid
[svn.git] / subversion / libsvn_ra_neon / ra_neon.h
bloba1c8e06cc8958aa9d9cfaf95a28e4cb8360f837e
1 /*
2 * ra_neon.h : Private declarations for the Neon-based DAV RA module.
4 * ====================================================================
5 * Copyright (c) 2000-2007 CollabNet. All rights reserved.
7 * This software is licensed as described in the file COPYING, which
8 * you should have received as part of this distribution. The terms
9 * are also available at http://subversion.tigris.org/license-1.html.
10 * If newer versions of this license are posted there, you may use a
11 * newer version instead, at your option.
13 * This software consists of voluntary contributions made by many
14 * individuals. For exact contribution history, see the revision
15 * history and logs, available at http://subversion.tigris.org/.
16 * ====================================================================
21 #ifndef SVN_LIBSVN_RA_NEON_H
22 #define SVN_LIBSVN_RA_NEON_H
24 #include <apr_pools.h>
25 #include <apr_tables.h>
27 #include <ne_request.h>
28 #include <ne_uri.h>
29 #include <ne_207.h> /* for NE_ELM_207_UNUSED */
30 #include <ne_props.h> /* for ne_propname */
32 #include "svn_types.h"
33 #include "svn_string.h"
34 #include "svn_delta.h"
35 #include "svn_ra.h"
36 #include "svn_dav.h"
38 #include "private/svn_dav_protocol.h"
39 #include "svn_private_config.h"
41 #ifdef __cplusplus
42 extern "C" {
43 #endif /* __cplusplus */
47 /* Rename these types and constants to abstract from Neon */
49 #define SVN_RA_NEON__XML_DECLINE NE_XML_DECLINE
50 #define SVN_RA_NEON__XML_INVALID NE_XML_ABORT
52 #define SVN_RA_NEON__XML_CDATA (1<<1)
53 #define SVN_RA_NEON__XML_COLLECT ((1<<2) | SVN_RA_NEON__XML_CDATA)
55 typedef int svn_ra_neon__xml_elmid;
57 /** XML element */
58 typedef struct {
59 /** XML namespace. */
60 const char *nspace;
62 /** XML tag name. */
63 const char *name;
65 /** XML tag id to be passed to a handler. */
66 svn_ra_neon__xml_elmid id;
68 /** Processing flags for this namespace:tag.
70 * 0 (zero) - regular element, may have children,
71 * SVN_RA_NEON__XML_CDATA - child-less element,
72 * SVN_RA_NEON__XML_COLLECT - complete contents of such element must be
73 * collected as CDATA, includes *_CDATA flag. */
74 unsigned int flags;
76 } svn_ra_neon__xml_elm_t;
80 typedef struct {
81 apr_pool_t *pool;
82 svn_stringbuf_t *url; /* original, unparsed session url */
83 ne_uri root; /* parsed version of above */
84 const char *repos_root; /* URL for repository root */
86 ne_session *ne_sess; /* HTTP session to server */
87 ne_session *ne_sess2;
88 svn_boolean_t main_session_busy; /* TRUE when requests should be created
89 and issued on sess2; currently
90 only used by fetch.c */
92 const svn_ra_callbacks2_t *callbacks; /* callbacks to get auth data */
93 void *callback_baton;
95 svn_auth_iterstate_t *auth_iterstate; /* state of authentication retries */
96 const char *auth_username; /* last authenticated username used */
98 svn_boolean_t compression; /* should we use http compression? */
99 const char *uuid; /* repository UUID */
101 svn_ra_progress_notify_func_t progress_func;
102 void *progress_baton;
104 /* Maps SVN_RA_CAPABILITY_foo keys to "yes" or "no" values.
105 If a capability is not yet discovered, it is absent from the table.
106 The table itself is allocated in the svn_ra_neon__session_t's pool;
107 keys and values must have at least that lifetime. Most likely
108 the keys and values are constants anyway (and sufficiently
109 well-informed internal code may just compare against those
110 constants' addresses, therefore). */
111 apr_hash_t *capabilities;
112 } svn_ra_neon__session_t;
115 typedef struct {
116 ne_request *ne_req; /* neon request structure */
117 ne_session *ne_sess; /* neon session structure */
118 svn_ra_neon__session_t *sess; /* DAV session structure */
119 const char *method;
120 const char *url;
121 int rv; /* Return value from
122 ne_request_dispatch() or -1 if
123 not dispatched yet. */
124 int code; /* HTTP return code, or 0 if none */
125 const char *code_desc; /* Textual description of CODE */
126 svn_error_t *err; /* error encountered while executing
127 the request */
128 svn_boolean_t marshalled_error; /* TRUE if the error was server-side */
129 apr_pool_t *pool; /* where this struct is allocated */
130 apr_pool_t *iterpool; /* iteration pool
131 for use within callbacks */
132 } svn_ra_neon__request_t;
135 /* Statement macro to set the request error,
136 * making sure we don't leak any in case we encounter more than one error.
138 * Sets the 'err' field of REQ to the value obtained by evaluating NEW_ERR.
140 #define SVN_RA_NEON__REQ_ERR(req, new_err) \
141 do { \
142 svn_error_t *svn_err__tmp = (new_err); \
143 if ((req)->err && !(req)->marshalled_error) \
144 svn_error_clear(svn_err__tmp); \
145 else if (svn_err__tmp) \
147 svn_error_clear((req)->err); \
148 (req)->err = svn_err__tmp; \
149 (req)->marshalled_error = FALSE; \
151 } while (0)
154 /* Allocate an internal request structure allocated in a newly created
155 * subpool of POOL. Create an associated neon request with the parameters
156 * given.
158 * When a request is being dispatched on the primary Neon session,
159 * the request is allocated to the secondary neon session of SESS.
161 * Register a pool cleanup for any allocated Neon resources.
163 svn_ra_neon__request_t *
164 svn_ra_neon__request_create(svn_ra_neon__session_t *sess,
165 const char *method, const char *url,
166 apr_pool_t *pool);
169 /* Our version of ne_block_reader, which returns an
170 * svn_error_t * instead of an int. */
171 typedef svn_error_t *(*svn_ra_neon__block_reader)(void *baton,
172 const char *data,
173 size_t len);
175 /* Add a response body reader function to REQ.
177 * Use the associated session parameters to determine the use of
178 * compression.
180 * Register a pool cleanup on the pool of REQ to clean up any allocated
181 * Neon resources.
183 void
184 svn_ra_neon__add_response_body_reader(svn_ra_neon__request_t *req,
185 ne_accept_response accpt,
186 svn_ra_neon__block_reader reader,
187 void *userdata);
190 /* Destroy request REQ and any associated resources */
191 #define svn_ra_neon__request_destroy(req) svn_pool_destroy((req)->pool)
193 #ifdef SVN_DEBUG
194 #define DEBUG_CR "\n"
195 #else
196 #define DEBUG_CR ""
197 #endif
200 /** vtable function prototypes */
202 svn_error_t *svn_ra_neon__get_latest_revnum(svn_ra_session_t *session,
203 svn_revnum_t *latest_revnum,
204 apr_pool_t *pool);
206 svn_error_t *svn_ra_neon__get_dated_revision(svn_ra_session_t *session,
207 svn_revnum_t *revision,
208 apr_time_t timestamp,
209 apr_pool_t *pool);
211 svn_error_t *svn_ra_neon__change_rev_prop(svn_ra_session_t *session,
212 svn_revnum_t rev,
213 const char *name,
214 const svn_string_t *value,
215 apr_pool_t *pool);
217 svn_error_t *svn_ra_neon__rev_proplist(svn_ra_session_t *session,
218 svn_revnum_t rev,
219 apr_hash_t **props,
220 apr_pool_t *pool);
222 svn_error_t *svn_ra_neon__rev_prop(svn_ra_session_t *session,
223 svn_revnum_t rev,
224 const char *name,
225 svn_string_t **value,
226 apr_pool_t *pool);
228 svn_error_t * svn_ra_neon__get_commit_editor(svn_ra_session_t *session,
229 const svn_delta_editor_t **editor,
230 void **edit_baton,
231 apr_hash_t *revprop_table,
232 svn_commit_callback2_t callback,
233 void *callback_baton,
234 apr_hash_t *lock_tokens,
235 svn_boolean_t keep_locks,
236 apr_pool_t *pool);
238 svn_error_t * svn_ra_neon__get_file(svn_ra_session_t *session,
239 const char *path,
240 svn_revnum_t revision,
241 svn_stream_t *stream,
242 svn_revnum_t *fetched_rev,
243 apr_hash_t **props,
244 apr_pool_t *pool);
246 svn_error_t *svn_ra_neon__get_dir(svn_ra_session_t *session,
247 apr_hash_t **dirents,
248 svn_revnum_t *fetched_rev,
249 apr_hash_t **props,
250 const char *path,
251 svn_revnum_t revision,
252 apr_uint32_t dirent_fields,
253 apr_pool_t *pool);
255 svn_error_t * svn_ra_neon__abort_commit(void *session_baton,
256 void *edit_baton);
258 svn_error_t * svn_ra_neon__get_mergeinfo(svn_ra_session_t *session,
259 apr_hash_t **mergeinfo,
260 const apr_array_header_t *paths,
261 svn_revnum_t revision,
262 svn_mergeinfo_inheritance_t inherit,
263 apr_pool_t *pool);
265 svn_error_t * svn_ra_neon__do_update(svn_ra_session_t *session,
266 const svn_ra_reporter3_t **reporter,
267 void **report_baton,
268 svn_revnum_t revision_to_update_to,
269 const char *update_target,
270 svn_depth_t depth,
271 svn_boolean_t send_copyfrom_args,
272 const svn_delta_editor_t *wc_update,
273 void *wc_update_baton,
274 apr_pool_t *pool);
276 svn_error_t * svn_ra_neon__do_status(svn_ra_session_t *session,
277 const svn_ra_reporter3_t **reporter,
278 void **report_baton,
279 const char *status_target,
280 svn_revnum_t revision,
281 svn_depth_t depth,
282 const svn_delta_editor_t *wc_status,
283 void *wc_status_baton,
284 apr_pool_t *pool);
286 svn_error_t * svn_ra_neon__do_switch(svn_ra_session_t *session,
287 const svn_ra_reporter3_t **reporter,
288 void **report_baton,
289 svn_revnum_t revision_to_update_to,
290 const char *update_target,
291 svn_depth_t depth,
292 const char *switch_url,
293 const svn_delta_editor_t *wc_update,
294 void *wc_update_baton,
295 apr_pool_t *pool);
297 svn_error_t * svn_ra_neon__do_diff(svn_ra_session_t *session,
298 const svn_ra_reporter3_t **reporter,
299 void **report_baton,
300 svn_revnum_t revision,
301 const char *diff_target,
302 svn_depth_t depth,
303 svn_boolean_t ignore_ancestry,
304 svn_boolean_t text_deltas,
305 const char *versus_url,
306 const svn_delta_editor_t *wc_diff,
307 void *wc_diff_baton,
308 apr_pool_t *pool);
310 svn_error_t * svn_ra_neon__get_log(svn_ra_session_t *session,
311 const apr_array_header_t *paths,
312 svn_revnum_t start,
313 svn_revnum_t end,
314 int limit,
315 svn_boolean_t discover_changed_paths,
316 svn_boolean_t strict_node_history,
317 svn_boolean_t include_merged_revisions,
318 apr_array_header_t *revprops,
319 svn_log_entry_receiver_t receiver,
320 void *receiver_baton,
321 apr_pool_t *pool);
323 svn_error_t *svn_ra_neon__do_check_path(svn_ra_session_t *session,
324 const char *path,
325 svn_revnum_t revision,
326 svn_node_kind_t *kind,
327 apr_pool_t *pool);
329 svn_error_t *svn_ra_neon__do_stat(svn_ra_session_t *session,
330 const char *path,
331 svn_revnum_t revision,
332 svn_dirent_t **dirent,
333 apr_pool_t *pool);
335 svn_error_t *svn_ra_neon__get_file_revs(svn_ra_session_t *session,
336 const char *path,
337 svn_revnum_t start,
338 svn_revnum_t end,
339 svn_boolean_t include_merged_revisions,
340 svn_file_rev_handler_t handler,
341 void *handler_baton,
342 apr_pool_t *pool);
346 ** SVN_RA_NEON__LP_*: local properties for RA/DAV
348 ** ra_neon and ra_serf store properties on the client containing information needed
349 ** to operate against the SVN server. Some of this informations is strictly
350 ** necessary to store, and some is simply stored as a cached value.
353 #define SVN_RA_NEON__LP_NAMESPACE SVN_PROP_WC_PREFIX "ra_dav:"
355 /* store the URL where Activities can be created */
356 /* ### should fix the name to be "activity-coll" at some point */
357 #define SVN_RA_NEON__LP_ACTIVITY_COLL SVN_RA_NEON__LP_NAMESPACE "activity-url"
359 /* store the URL of the version resource (from the DAV:checked-in property) */
360 #define SVN_RA_NEON__LP_VSN_URL SVN_RA_NEON__LP_NAMESPACE "version-url"
364 ** SVN_RA_NEON__PROP_*: properties that we fetch from the server
366 ** These are simply symbolic names for some standard properties that we fetch.
368 #define SVN_RA_NEON__PROP_BASELINE_COLLECTION "DAV:baseline-collection"
369 #define SVN_RA_NEON__PROP_CHECKED_IN "DAV:checked-in"
370 #define SVN_RA_NEON__PROP_VCC "DAV:version-controlled-configuration"
371 #define SVN_RA_NEON__PROP_VERSION_NAME "DAV:" SVN_DAV__VERSION_NAME
372 #define SVN_RA_NEON__PROP_CREATIONDATE "DAV:creationdate"
373 #define SVN_RA_NEON__PROP_CREATOR_DISPLAYNAME "DAV:creator-displayname"
374 #define SVN_RA_NEON__PROP_GETCONTENTLENGTH "DAV:getcontentlength"
376 #define SVN_RA_NEON__PROP_BASELINE_RELPATH \
377 SVN_DAV_PROP_NS_DAV "baseline-relative-path"
379 #define SVN_RA_NEON__PROP_MD5_CHECKSUM SVN_DAV_PROP_NS_DAV "md5-checksum"
381 #define SVN_RA_NEON__PROP_REPOSITORY_UUID SVN_DAV_PROP_NS_DAV "repository-uuid"
383 #define SVN_RA_NEON__PROP_DEADPROP_COUNT SVN_DAV_PROP_NS_DAV "deadprop-count"
385 typedef struct {
386 /* what is the URL for this resource */
387 const char *url;
389 /* is this resource a collection? (from the DAV:resourcetype element) */
390 int is_collection;
392 /* PROPSET: NAME -> VALUE (const char * -> const svn_string_t *) */
393 apr_hash_t *propset;
395 /* --- only used during response processing --- */
396 /* when we see a DAV:href element, what element is the parent? */
397 int href_parent;
399 apr_pool_t *pool;
401 } svn_ra_neon__resource_t;
403 /* ### WARNING: which_props can only identify properties which props.c
404 ### knows about. see the elem_definitions[] array. */
406 /* fetch a bunch of properties from the server. */
407 svn_error_t * svn_ra_neon__get_props(apr_hash_t **results,
408 svn_ra_neon__session_t *sess,
409 const char *url,
410 int depth,
411 const char *label,
412 const ne_propname *which_props,
413 apr_pool_t *pool);
415 /* fetch a single resource's props from the server. */
416 svn_error_t * svn_ra_neon__get_props_resource(svn_ra_neon__resource_t **rsrc,
417 svn_ra_neon__session_t *sess,
418 const char *url,
419 const char *label,
420 const ne_propname *which_props,
421 apr_pool_t *pool);
423 /* fetch a single resource's starting props from the server. */
424 svn_error_t * svn_ra_neon__get_starting_props(svn_ra_neon__resource_t **rsrc,
425 svn_ra_neon__session_t *sess,
426 const char *url,
427 const char *label,
428 apr_pool_t *pool);
430 /* Shared helper func: given a public URL which may not exist in HEAD,
431 use SESS to search up parent directories until we can retrieve a
432 *RSRC (allocated in POOL) containing a standard set of "starting"
433 props: {VCC, resourcetype, baseline-relative-path}.
435 Also return *MISSING_PATH (allocated in POOL), which is the
436 trailing portion of the URL that did not exist. If an error
437 occurs, *MISSING_PATH isn't changed. */
438 svn_error_t *
439 svn_ra_neon__search_for_starting_props(svn_ra_neon__resource_t **rsrc,
440 const char **missing_path,
441 svn_ra_neon__session_t *sess,
442 const char *url,
443 apr_pool_t *pool);
445 /* fetch a single property from a single resource */
446 svn_error_t * svn_ra_neon__get_one_prop(const svn_string_t **propval,
447 svn_ra_neon__session_t *sess,
448 const char *url,
449 const char *label,
450 const ne_propname *propname,
451 apr_pool_t *pool);
453 /* Get various Baseline-related information for a given "public" URL.
455 Given a session SESS and a URL, return whether the URL is a
456 directory in *IS_DIR. IS_DIR may be NULL if this flag is unneeded.
458 REVISION may be SVN_INVALID_REVNUM to indicate that the operation
459 should work against the latest (HEAD) revision, or whether it should
460 return information about that specific revision.
462 If BC_URL is not NULL, then it will be filled in with the URL for
463 the Baseline Collection for the specified revision, or the HEAD.
465 If BC_RELATIVE is not NULL, then it will be filled in with a
466 relative pathname for the baselined resource corresponding to the
467 revision of the resource specified by URL.
469 If LATEST_REV is not NULL, then it will be filled in with the revision
470 that this information corresponds to. Generally, this will be the same
471 as the REVISION parameter, unless we are working against the HEAD. In
472 that case, the HEAD revision number is returned.
474 Allocation for BC_URL->data, BC_RELATIVE->data, and temporary data,
475 will occur in POOL.
477 Note: a Baseline Collection is a complete tree for a specified Baseline.
478 DeltaV baselines correspond one-to-one to Subversion revisions. Thus,
479 the entire state of a revision can be found in a Baseline Collection.
481 svn_error_t *svn_ra_neon__get_baseline_info(svn_boolean_t *is_dir,
482 svn_string_t *bc_url,
483 svn_string_t *bc_relative,
484 svn_revnum_t *latest_rev,
485 svn_ra_neon__session_t *sess,
486 const char *url,
487 svn_revnum_t revision,
488 apr_pool_t *pool);
490 /* Fetch a baseline resource populated with specific properties.
492 Given a session SESS and a URL, set *BLN_RSRC to a baseline of
493 REVISION, populated with whatever properties are specified by
494 WHICH_PROPS. To fetch all properties, pass NULL for WHICH_PROPS.
496 If BC_RELATIVE is not NULL, then it will be filled in with a
497 relative pathname for the baselined resource corresponding to the
498 revision of the resource specified by URL.
500 svn_error_t *svn_ra_neon__get_baseline_props(svn_string_t *bc_relative,
501 svn_ra_neon__resource_t **bln_rsrc,
502 svn_ra_neon__session_t *sess,
503 const char *url,
504 svn_revnum_t revision,
505 const ne_propname *which_props,
506 apr_pool_t *pool);
508 /* Fetch the repository's unique Version-Controlled-Configuration url.
510 Given a session SESS and a URL, set *VCC to the url of the
511 repository's version-controlled-configuration resource.
513 svn_error_t *svn_ra_neon__get_vcc(const char **vcc,
514 svn_ra_neon__session_t *sess,
515 const char *url,
516 apr_pool_t *pool);
518 /* Issue a PROPPATCH request on URL, transmitting PROP_CHANGES (a hash
519 of const svn_string_t * values keyed on Subversion user-visible
520 property names) and PROP_DELETES (an array of property names to
521 delete). Send any extra request headers in EXTRA_HEADERS. Use POOL
522 for all allocations. */
523 svn_error_t *svn_ra_neon__do_proppatch(svn_ra_neon__session_t *ras,
524 const char *url,
525 apr_hash_t *prop_changes,
526 apr_array_header_t *prop_deletes,
527 apr_hash_t *extra_headers,
528 apr_pool_t *pool);
530 extern const ne_propname svn_ra_neon__vcc_prop;
531 extern const ne_propname svn_ra_neon__checked_in_prop;
536 /* send an OPTIONS request to fetch the activity-collection-set */
537 svn_error_t * svn_ra_neon__get_activity_collection
538 (const svn_string_t **activity_coll,
539 svn_ra_neon__session_t *ras,
540 const char *url,
541 apr_pool_t *pool);
544 /* Call ne_set_request_body_pdovider on REQ with a provider function
545 * that pulls data from BODY_FILE.
547 svn_error_t *svn_ra_neon__set_neon_body_provider(svn_ra_neon__request_t *req,
548 apr_file_t *body_file);
551 #define SVN_RA_NEON__DEPTH_ZERO 0
552 #define SVN_RA_NEON__DEPTH_ONE 1
553 #define SVN_RA_NEON__DEPTH_INFINITE -1
554 /* Add a 'Depth' header to a hash of headers.
556 * DEPTH is one of the above defined SVN_RA_NEON__DEPTH_* values.
558 void
559 svn_ra_neon__add_depth_header(apr_hash_t *extra_headers, int depth);
561 /** Find a given element in the table of elements.
563 * The table of XML elements @a table is searched until element identified by
564 * namespace @a nspace and name @a name is found. If no elements are found,
565 * tries to find and return element identified by @c ELEM_unknown. If that is
566 * not found, returns NULL pointer. */
567 const svn_ra_neon__xml_elm_t *
568 svn_ra_neon__lookup_xml_elem(const svn_ra_neon__xml_elm_t *table,
569 const char *nspace,
570 const char *name);
574 /* Collect CDATA into a stringbuf.
576 * BATON points to a struct of which the first element is
577 * assumed to be an svn_stringbuf_t *.
579 svn_error_t *
580 svn_ra_neon__xml_collect_cdata(void *baton, int state,
581 const char *cdata, size_t len);
584 /* Our equivalent of ne_xml_startelm_cb, the difference being that it
585 * returns errors in a svn_error_t, and returns the element type via
586 * ELEM. To ignore the element *ELEM should be set to
587 * SVN_RA_NEON__XML_DECLINE and SVN_NO_ERROR should be returned.
588 * *ELEM can be set to SVN_RA_NEON__XML_INVALID to indicate invalid XML
589 * (and abort the parse).
591 typedef svn_error_t * (*svn_ra_neon__startelm_cb_t)(int *elem,
592 void *baton,
593 int parent,
594 const char *nspace,
595 const char *name,
596 const char **atts);
598 /* Our equivalent of ne_xml_cdata_cb, the difference being that it returns
599 * errors in a svn_error_t.
601 typedef svn_error_t * (*svn_ra_neon__cdata_cb_t)(void *baton,
602 int state,
603 const char *cdata,
604 size_t len);
606 /* Our equivalent of ne_xml_endelm_cb, the difference being that it returns
607 * errors in a svn_error_t.
609 typedef svn_error_t * (*svn_ra_neon__endelm_cb_t)(void *baton,
610 int state,
611 const char *nspace,
612 const char *name);
615 /* Create a Neon xml parser with callbacks STARTELM_CB, ENDELM_CB and
616 * CDATA_CB. The created parser wraps the Neon callbacks and marshals any
617 * errors returned by the callbacks through the Neon layer. Any errors
618 * raised will be returned by svn_ra_neon__request_dispatch() unless
619 * an earlier error occurred.
621 * Register a pool cleanup on the pool of REQ to clean up any allocated
622 * Neon resources.
624 * ACCPT indicates whether the parser wants read the response body
625 * or not. Pass NULL for ACCPT when you don't want the returned parser
626 * to be attached to REQ.
628 ne_xml_parser *
629 svn_ra_neon__xml_parser_create(svn_ra_neon__request_t *req,
630 ne_accept_response accpt,
631 svn_ra_neon__startelm_cb_t startelm_cb,
632 svn_ra_neon__cdata_cb_t cdata_cb,
633 svn_ra_neon__endelm_cb_t endelm_cb,
634 void *baton);
636 /* Send a METHOD request (e.g., "MERGE", "REPORT", "PROPFIND") to URL
637 * in session SESS, and parse the response. If BODY is non-null, it is
638 * the body of the request, else use the contents of file BODY_FILE
639 * as the body.
641 * STARTELM_CB, CDATA_CB and ENDELM_CB are start element, cdata and end
642 * element handlers, respectively. BATON is passed to each as userdata.
644 * SET_PARSER is a callback function which, if non-NULL, is called
645 * with the XML parser and BATON. This is useful for providers of
646 * validation and element handlers which require access to the parser.
648 * EXTRA_HEADERS is a hash of (const char *) key/value pairs to be
649 * inserted as extra headers in the request. Can be NULL.
651 * STATUS_CODE is an optional 'out' parameter; if non-NULL, then set
652 * *STATUS_CODE to the http status code returned by the server. This
653 * can be set to a useful value even when the function returns an error
654 * however it is not always set when an error is returned. So any caller
655 * wishing to check *STATUS_CODE when an error has been returned must
656 * initialise *STATUS_CODE before calling the function.
658 * If SPOOL_RESPONSE is set, the request response will be cached to
659 * disk in a tmpfile (in full), then read back and parsed.
661 * Use POOL for any temporary allocation.
663 svn_error_t *
664 svn_ra_neon__parsed_request(svn_ra_neon__session_t *sess,
665 const char *method,
666 const char *url,
667 const char *body,
668 apr_file_t *body_file,
669 void set_parser(ne_xml_parser *parser,
670 void *baton),
671 svn_ra_neon__startelm_cb_t startelm_cb,
672 svn_ra_neon__cdata_cb_t cdata_cb,
673 svn_ra_neon__endelm_cb_t endelm_cb,
674 void *baton,
675 apr_hash_t *extra_headers,
676 int *status_code,
677 svn_boolean_t spool_response,
678 apr_pool_t *pool);
681 /* ### add SVN_RA_NEON_ to these to prefix conflicts with (sys) headers? */
682 enum {
683 /* Redefine Neon elements */
684 /* With the new API, we need to be able to use element id also as a return
685 * value from the new `startelm' callback, hence all element ids must be
686 * positive. Root element id is the only id that is not positive, it's zero.
687 * `Root state' is never returned by a callback, it's only passed into it.
688 * Therefore, negative element ids are forbidden from now on. */
689 ELEM_unknown = 1, /* was (-1), see above why it's (1) now */
690 ELEM_root = NE_XML_STATEROOT, /* (0) */
691 ELEM_UNUSED = 100,
692 ELEM_207_first = ELEM_UNUSED,
693 ELEM_multistatus = ELEM_207_first,
694 ELEM_response = ELEM_207_first + 1,
695 ELEM_responsedescription = ELEM_207_first + 2,
696 ELEM_href = ELEM_207_first + 3,
697 ELEM_propstat = ELEM_207_first + 4,
698 ELEM_prop = ELEM_207_first + 5, /* `prop' tag in the DAV namespace */
699 ELEM_status = ELEM_207_first + 6,
700 ELEM_207_UNUSED = ELEM_UNUSED + 100,
701 ELEM_PROPS_UNUSED = ELEM_207_UNUSED + 100,
703 /* DAV elements */
704 ELEM_activity_coll_set = ELEM_207_UNUSED,
705 ELEM_baseline,
706 ELEM_baseline_coll,
707 ELEM_checked_in,
708 ELEM_collection,
709 ELEM_comment,
710 ELEM_revprop,
711 ELEM_creationdate,
712 ELEM_creator_displayname,
713 ELEM_ignored_set,
714 ELEM_merge_response,
715 ELEM_merged_set,
716 ELEM_options_response,
717 ELEM_set_prop,
718 ELEM_remove_prop,
719 ELEM_resourcetype,
720 ELEM_get_content_length,
721 ELEM_updated_set,
722 ELEM_vcc,
723 ELEM_version_name,
724 ELEM_post_commit_err,
725 ELEM_error,
727 /* SVN elements */
728 ELEM_absent_directory,
729 ELEM_absent_file,
730 ELEM_add_directory,
731 ELEM_add_file,
732 ELEM_baseline_relpath,
733 ELEM_md5_checksum,
734 ELEM_deleted_path, /* used in log reports */
735 ELEM_replaced_path, /* used in log reports */
736 ELEM_added_path, /* used in log reports */
737 ELEM_modified_path, /* used in log reports */
738 ELEM_delete_entry,
739 ELEM_fetch_file,
740 ELEM_fetch_props,
741 ELEM_txdelta,
742 ELEM_log_date,
743 ELEM_log_item,
744 ELEM_log_report,
745 ELEM_open_directory,
746 ELEM_open_file,
747 ELEM_target_revision,
748 ELEM_update_report,
749 ELEM_resource_walk,
750 ELEM_resource,
751 ELEM_SVN_prop, /* `prop' tag in the Subversion namespace */
752 ELEM_dated_rev_report,
753 ELEM_name_version_name,
754 ELEM_name_creationdate,
755 ELEM_name_creator_displayname,
756 ELEM_svn_error,
757 ELEM_human_readable,
758 ELEM_repository_uuid,
759 ELEM_get_locations_report,
760 ELEM_location,
761 ELEM_get_location_segments_report,
762 ELEM_location_segment,
763 ELEM_file_revs_report,
764 ELEM_file_rev,
765 ELEM_rev_prop,
766 ELEM_get_locks_report,
767 ELEM_lock,
768 ELEM_lock_path,
769 ELEM_lock_token,
770 ELEM_lock_owner,
771 ELEM_lock_comment,
772 ELEM_lock_creationdate,
773 ELEM_lock_expirationdate,
774 ELEM_lock_discovery,
775 ELEM_lock_activelock,
776 ELEM_lock_type,
777 ELEM_lock_scope,
778 ELEM_lock_depth,
779 ELEM_lock_timeout,
780 ELEM_editor_report,
781 ELEM_open_root,
782 ELEM_apply_textdelta,
783 ELEM_change_file_prop,
784 ELEM_change_dir_prop,
785 ELEM_close_file,
786 ELEM_close_directory,
787 ELEM_deadprop_count,
788 ELEM_mergeinfo_report,
789 ELEM_mergeinfo_item,
790 ELEM_mergeinfo_path,
791 ELEM_mergeinfo_info,
792 ELEM_has_children,
793 ELEM_merged_revision
796 /* ### docco */
797 svn_error_t * svn_ra_neon__merge_activity(svn_revnum_t *new_rev,
798 const char **committed_date,
799 const char **committed_author,
800 const char **post_commit_err,
801 svn_ra_neon__session_t *ras,
802 const char *repos_url,
803 const char *activity_url,
804 apr_hash_t *valid_targets,
805 apr_hash_t *lock_tokens,
806 svn_boolean_t keep_locks,
807 svn_boolean_t disable_merge_response,
808 apr_pool_t *pool);
811 /* Make a buffer for repeated use with svn_stringbuf_set().
812 ### it would be nice to start this buffer with N bytes, but there isn't
813 ### really a way to do that in the string interface (yet), short of
814 ### initializing it with a fake string (and copying it) */
815 #define MAKE_BUFFER(p) svn_stringbuf_ncreate("", 0, (p))
817 svn_error_t *
818 svn_ra_neon__copy_href(svn_stringbuf_t *dst, const char *src,
819 apr_pool_t *pool);
823 /* If RAS contains authentication info, attempt to store it via client
824 callbacks and using POOL for temporary allocations. */
825 svn_error_t *
826 svn_ra_neon__maybe_store_auth_info(svn_ra_neon__session_t *ras,
827 apr_pool_t *pool);
830 /* Like svn_ra_neon__maybe_store_auth_info(), but conditional on ERR.
832 Attempt to store auth info only if ERR is NULL or if ERR->apr_err
833 is not SVN_ERR_RA_NOT_AUTHORIZED. If ERR is not null, return it no
834 matter what, otherwise return the result of the attempt (if any) to
835 store auth info, else return SVN_NO_ERROR. */
836 svn_error_t *
837 svn_ra_neon__maybe_store_auth_info_after_result(svn_error_t *err,
838 svn_ra_neon__session_t *ras,
839 apr_pool_t *pool);
842 /* Create an error of type SVN_ERR_RA_DAV_MALFORMED_DATA for cases where
843 we recieve an element we didn't expect to see. */
844 #define UNEXPECTED_ELEMENT(ns, elem) \
845 (ns ? svn_error_createf(SVN_ERR_RA_DAV_MALFORMED_DATA, \
846 NULL, \
847 _("Got unexpected element %s:%s"), \
848 ns, \
849 elem) \
850 : svn_error_createf(SVN_ERR_RA_DAV_MALFORMED_DATA, \
851 NULL, \
852 _("Got unexpected element %s"), \
853 elem))
855 /* Create an error of type SVN_ERR_RA_DAV_MALFORMED_DATA for cases where
856 we don't receive a necessary attribute. */
857 #define MISSING_ATTR(ns, elem, attr) \
858 (ns ? svn_error_createf(SVN_ERR_RA_DAV_MALFORMED_DATA, \
859 NULL, \
860 _("Missing attribute '%s' on element %s:%s"), \
861 attr, \
862 ns, \
863 elem) \
864 : svn_error_createf(SVN_ERR_RA_DAV_MALFORMED_DATA, \
865 NULL, \
866 _("Missing attribute '%s' on element %s"), \
867 attr, \
868 elem))
870 /* Given a REQUEST, run it; if CODE_P is
871 non-null, return the http status code in *CODE_P. Return any
872 resulting error (from Neon, a <D:error> body response, or any
873 non-2XX status code) as an svn_error_t, otherwise return SVN_NO_ERROR.
875 EXTRA_HEADERS is a hash with (key -> value) of
876 (const char * -> const char *) where the key is the HTTP header name.
878 BODY is a null terminated string containing an in-memory request
879 body. Use svn_ra_neon__set_neon_body_provider() if you want the
880 request body to be read from a file. For requests which have no
881 body at all, consider passing the empty string ("") instead of
882 NULL, as this will cause Neon to generate a "Content-Length: 0"
883 header (which is important to some proxies).
885 OKAY_1 and OKAY_2 are the "acceptable" result codes. Anything other
886 than one of these will generate an error. OKAY_1 should always be
887 specified (e.g. as 200); use 0 for OKAY_2 if a second result code is
888 not allowed.
891 svn_error_t *
892 svn_ra_neon__request_dispatch(int *code_p,
893 svn_ra_neon__request_t *request,
894 apr_hash_t *extra_headers,
895 const char *body,
896 int okay_1,
897 int okay_2,
898 apr_pool_t *pool);
900 /* A layer over SVN_RA_NEON__REQUEST_DISPATCH() adding a
901 207 response parser to extract relevant (error) information.
903 Don't use this function if you're expecting 207 as a valid response.
905 BODY may be NULL if the request doesn't have a body. */
906 svn_error_t *
907 svn_ra_neon__simple_request(int *code,
908 svn_ra_neon__session_t *ras,
909 const char *method,
910 const char *url,
911 apr_hash_t *extra_headers,
912 const char *body,
913 int okay_1, int okay_2, apr_pool_t *pool);
916 /* Convenience statement macro for setting headers in a hash */
917 #define svn_ra_neon__set_header(hash, hdr, val) \
918 apr_hash_set((hash), (hdr), APR_HASH_KEY_STRING, (val))
921 /* Helper function layered over SVN_RA_NEON__SIMPLE_REQUEST() to issue
922 a HTTP COPY request.
924 DEPTH is one of the SVN_RA_NEON__DEPTH_* constants. */
925 svn_error_t *
926 svn_ra_neon__copy(svn_ra_neon__session_t *ras,
927 svn_boolean_t overwrite,
928 int depth,
929 const char *src,
930 const char *dst,
931 apr_pool_t *pool);
933 /* Return the Location HTTP header or NULL if none was sent.
935 * Do allocations in POOL.
937 const char *
938 svn_ra_neon__request_get_location(svn_ra_neon__request_t *request,
939 apr_pool_t *pool);
943 * Implements the get_locations RA layer function. */
944 svn_error_t *
945 svn_ra_neon__get_locations(svn_ra_session_t *session,
946 apr_hash_t **locations,
947 const char *path,
948 svn_revnum_t peg_revision,
949 apr_array_header_t *location_revisions,
950 apr_pool_t *pool);
954 * Implements the get_location_segments RA layer function. */
955 svn_error_t *
956 svn_ra_neon__get_location_segments(svn_ra_session_t *session,
957 const char *path,
958 svn_revnum_t peg_revision,
959 svn_revnum_t start_rev,
960 svn_revnum_t end_rev,
961 svn_location_segment_receiver_t receiver,
962 void *receiver_baton,
963 apr_pool_t *pool);
966 * Implements the get_locks RA layer function. */
967 svn_error_t *
968 svn_ra_neon__get_locks(svn_ra_session_t *session,
969 apr_hash_t **locks,
970 const char *path,
971 apr_pool_t *pool);
974 * Implements the lock RA layer function. */
975 svn_error_t *
976 svn_ra_neon__lock(svn_ra_session_t *session,
977 apr_hash_t *path_revs,
978 const char *comment,
979 svn_boolean_t force,
980 svn_ra_lock_callback_t lock_func,
981 void *lock_baton,
982 apr_pool_t *pool);
985 * Implements the unlock RA layer function. */
986 svn_error_t *
987 svn_ra_neon__unlock(svn_ra_session_t *session,
988 apr_hash_t *path_tokens,
989 svn_boolean_t force,
990 svn_ra_lock_callback_t lock_func,
991 void *lock_baton,
992 apr_pool_t *pool);
995 * Implements the get_lock RA layer function. */
996 svn_error_t *
997 svn_ra_neon__get_lock(svn_ra_session_t *session,
998 svn_lock_t **lock,
999 const char *path,
1000 apr_pool_t *pool);
1003 * Implements the replay RA layer function. */
1004 svn_error_t *
1005 svn_ra_neon__replay(svn_ra_session_t *session,
1006 svn_revnum_t revision,
1007 svn_revnum_t low_water_mark,
1008 svn_boolean_t send_deltas,
1009 const svn_delta_editor_t *editor,
1010 void *edit_baton,
1011 apr_pool_t *pool);
1014 * Implements the replay_range RA layer function. */
1015 svn_error_t *
1016 svn_ra_neon__replay_range(svn_ra_session_t *session,
1017 svn_revnum_t start_revision,
1018 svn_revnum_t end_revision,
1019 svn_revnum_t low_water_mark,
1020 svn_boolean_t send_deltas,
1021 svn_ra_replay_revstart_callback_t revstart_func,
1022 svn_ra_replay_revfinish_callback_t revfinish_func,
1023 void *replay_baton,
1024 apr_pool_t *pool);
1027 * Implements the has_capability RA layer function. */
1028 svn_error_t *
1029 svn_ra_neon__has_capability(svn_ra_session_t *session,
1030 svn_boolean_t *has,
1031 const char *capability,
1032 apr_pool_t *pool);
1035 /* Helper function. Loop over LOCK_TOKENS and assemble all keys and
1036 values into a stringbuf allocated in POOL. The string will be of
1037 the form
1039 <S:lock-token-list xmlns:S="svn:">
1040 <S:lock>
1041 <S:lock-path>path</S:lock-path>
1042 <S:lock-token>token</S:lock-token>
1043 </S:lock>
1044 [...]
1045 </S:lock-token-list>
1047 Callers can then send this in the request bodies, as a way of
1048 reliably marshalling potentially unbounded lists of locks. (We do
1049 this because httpd has limits on how much data can be sent in 'If:'
1050 headers.)
1052 svn_error_t *
1053 svn_ra_neon__assemble_locktoken_body(svn_stringbuf_t **body,
1054 apr_hash_t *lock_tokens,
1055 apr_pool_t *pool);
1058 #ifdef __cplusplus
1060 #endif /* __cplusplus */
1062 #endif /* SVN_LIBSVN_RA_NEON_H */