2 * ra_serf.h : Private declarations for the Serf-based DAV RA module.
4 * ====================================================================
5 * Licensed to the Apache Software Foundation (ASF) under one
6 * or more contributor license agreements. See the NOTICE file
7 * distributed with this work for additional information
8 * regarding copyright ownership. The ASF licenses this file
9 * to you under the Apache License, Version 2.0 (the
10 * "License"); you may not use this file except in compliance
11 * with the License. You may obtain a copy of the License at
13 * http://www.apache.org/licenses/LICENSE-2.0
15 * Unless required by applicable law or agreed to in writing,
16 * software distributed under the License is distributed on an
17 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
18 * KIND, either express or implied. See the License for the
19 * specific language governing permissions and limitations
21 * ====================================================================
24 #ifndef SVN_LIBSVN_RA_SERF_RA_SERF_H
25 #define SVN_LIBSVN_RA_SERF_RA_SERF_H
29 #include <expat.h> /* for XML_Parser */
32 #include "svn_types.h"
33 #include "svn_string.h"
34 #include "svn_pools.h"
36 #include "svn_delta.h"
37 #include "svn_version.h"
39 #include "svn_dirent_uri.h"
41 #include "private/svn_dav_protocol.h"
42 #include "private/svn_subr_private.h"
43 #include "private/svn_editor.h"
49 #endif /* __cplusplus */
52 /* Enforce the minimum version of serf. */
53 #if !SERF_VERSION_AT_LEAST(1, 2, 1)
54 #error Please update your version of serf to at least 1.2.1.
57 /** Use this to silence compiler warnings about unused parameters. */
58 #define UNUSED_CTX(x) ((void)(x))
60 /** Wait duration (in microseconds) used in calls to serf_context_run() */
61 #define SVN_RA_SERF__CONTEXT_RUN_DURATION 500000
65 /* Forward declarations. */
66 typedef struct svn_ra_serf__session_t svn_ra_serf__session_t;
68 /* A serf connection and optionally associated SSL context. */
69 typedef struct svn_ra_serf__connection_t {
70 /* Our connection to a server. */
71 serf_connection_t *conn;
73 /* Bucket allocator for this connection. */
74 serf_bucket_alloc_t *bkt_alloc;
76 /* Collected cert failures in chain. */
77 int server_cert_failures;
79 /* What was the last HTTP status code we got on this connection? */
82 /* Optional SSL context for this connection. */
83 serf_ssl_context_t *ssl_context;
84 svn_auth_iterstate_t *ssl_client_auth_state;
85 svn_auth_iterstate_t *ssl_client_pw_auth_state;
87 svn_ra_serf__session_t *session;
89 } svn_ra_serf__connection_t;
91 /** Maximum value we'll allow for the http-max-connections config option.
93 * Note: minimum 2 connections are required for ra_serf to function
96 #define SVN_RA_SERF__MAX_CONNECTIONS_LIMIT 8
99 * The master serf RA session.
101 * This is stored in the ra session ->priv field.
103 struct svn_ra_serf__session_t {
104 /* Pool for allocations during this session */
107 /* The current context */
108 serf_context_t *context;
110 /* The maximum number of connections we'll use for parallelized
111 fetch operations (updates, etc.) */
112 apr_int64_t max_connections;
114 /* Are we using ssl */
115 svn_boolean_t using_ssl;
117 /* Should we ask for compressed responses? */
118 svn_boolean_t using_compression;
120 /* The user agent string */
121 const char *useragent;
123 /* The current connection */
124 svn_ra_serf__connection_t *conns[SVN_RA_SERF__MAX_CONNECTIONS_LIMIT];
128 /* The URL that was passed into _open() */
129 apr_uri_t session_url;
130 const char *session_url_str;
132 /* The actual discovered root; may be NULL until we know it. */
133 apr_uri_t repos_root;
134 const char *repos_root_str;
136 /* The server is not Apache/mod_dav_svn (directly) and only supports
137 HTTP/1.0. Thus, we cannot send chunked requests. */
138 svn_boolean_t http10;
140 /* Should we use Transfer-Encoding: chunked for HTTP/1.1 servers. */
141 svn_boolean_t using_chunked_requests;
143 /* Do we need to detect whether the connection supports chunked requests?
144 i.e. is there a (reverse) proxy that does not support them? */
145 svn_boolean_t detect_chunking;
147 /* Our Version-Controlled-Configuration; may be NULL until we know it. */
150 /* Authentication related properties. */
151 svn_auth_iterstate_t *auth_state;
154 /* Callback functions to get info from WC */
155 const svn_ra_callbacks2_t *wc_callbacks;
156 void *wc_callback_baton;
158 /* Callback function to send progress info to the client */
159 svn_ra_progress_notify_func_t progress_func;
160 void *progress_baton;
162 /* Callback function to handle cancellation */
163 svn_cancel_func_t cancel_func;
166 /* Ev2 shim callbacks */
167 svn_delta_shim_callbacks_t *shim_callbacks;
169 /* Error that we've received but not yet returned upstream. */
170 svn_error_t *pending_error;
172 /* List of authn types supported by the client.*/
175 /* Maps SVN_RA_CAPABILITY_foo keys to "yes" or "no" values.
176 If a capability is not yet discovered, it is absent from the table.
177 The table itself is allocated in the svn_ra_serf__session_t's pool;
178 keys and values must have at least that lifetime. Most likely
179 the keys and values are constants anyway (and sufficiently
180 well-informed internal code may just compare against those
181 constants' addresses, therefore). */
182 apr_hash_t *capabilities;
184 /* Activity collection URL. (Cached from the initial OPTIONS
185 request when run against HTTPv1 servers.) */
186 const char *activity_collection_url;
188 /* Are we using a proxy? */
189 svn_boolean_t using_proxy;
191 const char *proxy_username;
192 const char *proxy_password;
193 int proxy_auth_attempts;
195 /* SSL server certificates */
196 svn_boolean_t trust_default_ca;
197 const char *ssl_authorities;
199 /* Repository UUID */
202 /* Connection timeout value */
203 apr_interval_time_t timeout;
206 svn_tristate_t supports_deadprop_count;
208 /*** HTTP v2 protocol stuff. ***
210 * We assume that if mod_dav_svn sends one of the special v2 OPTIONs
211 * response headers, it has sent all of them. Specifically, we'll
212 * be looking at the presence of the "me resource" as a flag that
213 * the server supports v2 of our HTTP protocol.
216 /* The "me resource". Typically used as a target for REPORTs that
217 are path-agnostic. If we have this, we can speak HTTP v2 to the
219 const char *me_resource;
221 /* Opaque URL "stubs". If the OPTIONS response returns these, then
222 we know we're using HTTP protocol v2. */
223 const char *rev_stub; /* for accessing revisions (i.e. revprops) */
224 const char *rev_root_stub; /* for accessing REV/PATH pairs */
225 const char *txn_stub; /* for accessing transactions (i.e. txnprops) */
226 const char *txn_root_stub; /* for accessing TXN/PATH pairs */
227 const char *vtxn_stub; /* for accessing transactions (i.e. txnprops) */
228 const char *vtxn_root_stub; /* for accessing TXN/PATH pairs */
230 /* Hash mapping const char * server-supported POST types to
231 disinteresting-but-non-null values. */
232 apr_hash_t *supported_posts;
234 /*** End HTTP v2 stuff ***/
236 svn_ra_serf__blncache_t *blncache;
238 /* Trisate flag that indicates user preference for using bulk updates
239 (svn_tristate_true) with all the properties and content in the
240 update-report response. If svn_tristate_false, request a skelta
241 update-report with inlined properties. If svn_tristate_unknown then use
242 server preference. */
243 svn_tristate_t bulk_updates;
245 /* Indicates if the server wants bulk update requests (Prefer) or only
246 accepts skelta requests (Off). If this value is On both options are
248 const char *server_allows_bulk;
250 /* Indicates if the server supports sending inlined props in update editor
251 * in skelta mode (send-all == 'false'). */
252 svn_boolean_t supports_inline_props;
254 /* Indicates whether the server supports issuing replay REPORTs
255 against rev resources (children of `rev_stub', elsestruct). */
256 svn_boolean_t supports_rev_rsrc_replay;
259 #define SVN_RA_SERF__HAVE_HTTPV2_SUPPORT(sess) ((sess)->me_resource != NULL)
262 * Structure which represents a DAV element with a NAMESPACE and NAME.
264 typedef struct svn_ra_serf__dav_props_t {
265 /* Element namespace */
266 const char *namespace;
269 } svn_ra_serf__dav_props_t;
272 * Structure which represents an XML namespace.
274 typedef struct ns_t {
275 /* The assigned name. */
276 const char *namespace;
277 /* The full URL for this namespace. */
279 /* The next namespace in our list. */
284 * An incredibly simple list.
286 typedef struct ra_serf_list_t {
288 struct ra_serf_list_t *next;
289 } svn_ra_serf__list_t;
291 /** DAV property sets **/
293 static const svn_ra_serf__dav_props_t base_props[] =
295 { "DAV:", "version-controlled-configuration" },
296 { "DAV:", "resourcetype" },
297 { SVN_DAV_PROP_NS_DAV, "baseline-relative-path" },
298 { SVN_DAV_PROP_NS_DAV, "repository-uuid" },
302 static const svn_ra_serf__dav_props_t checked_in_props[] =
304 { "DAV:", "checked-in" },
308 static const svn_ra_serf__dav_props_t baseline_props[] =
310 { "DAV:", "baseline-collection" },
311 { "DAV:", SVN_DAV__VERSION_NAME },
315 static const svn_ra_serf__dav_props_t all_props[] =
317 { "DAV:", "allprop" },
321 static const svn_ra_serf__dav_props_t check_path_props[] =
323 { "DAV:", "resourcetype" },
327 static const svn_ra_serf__dav_props_t type_and_checksum_props[] =
329 { "DAV:", "resourcetype" },
330 { SVN_DAV_PROP_NS_DAV, "sha1-checksum" },
334 /* WC props compatibility with ra_neon. */
335 #define SVN_RA_SERF__WC_CHECKED_IN_URL SVN_PROP_WC_PREFIX "ra_dav:version-url"
337 /** Serf utility functions **/
340 svn_ra_serf__conn_setup(apr_socket_t *sock,
341 serf_bucket_t **read_bkt,
342 serf_bucket_t **write_bkt,
347 svn_ra_serf__conn_closed(serf_connection_t *conn,
353 /* Helper function to provide SSL client certificates.
355 * NOTE: This function sets the session's 'pending_error' member when
356 * returning an non-success status.
359 svn_ra_serf__handle_client_cert(void *data,
360 const char **cert_path);
362 /* Helper function to provide SSL client certificate passwords.
364 * NOTE: This function sets the session's 'pending_error' member when
365 * returning an non-success status.
368 svn_ra_serf__handle_client_cert_pw(void *data,
369 const char *cert_path,
370 const char **password);
374 * This function will run the serf context in SESS until *DONE is TRUE.
377 svn_ra_serf__context_run_wait(svn_boolean_t *done,
378 svn_ra_serf__session_t *sess,
379 apr_pool_t *scratch_pool);
381 /* Callback for response handlers */
382 typedef svn_error_t *
383 (*svn_ra_serf__response_handler_t)(serf_request_t *request,
384 serf_bucket_t *response,
386 apr_pool_t *scratch_pool);
388 /* Callback for when a request body is needed. */
389 /* ### should pass a scratch_pool */
390 typedef svn_error_t *
391 (*svn_ra_serf__request_body_delegate_t)(serf_bucket_t **body_bkt,
393 serf_bucket_alloc_t *alloc,
394 apr_pool_t *request_pool);
396 /* Callback for when request headers are needed. */
397 /* ### should pass a scratch_pool */
398 typedef svn_error_t *
399 (*svn_ra_serf__request_header_delegate_t)(serf_bucket_t *headers,
401 apr_pool_t *request_pool);
403 /* Callback for when a response has an error. */
404 typedef svn_error_t *
405 (*svn_ra_serf__response_error_t)(serf_request_t *request,
406 serf_bucket_t *response,
410 /* ### we should reorder the types in this file. */
411 typedef struct svn_ra_serf__server_error_t svn_ra_serf__server_error_t;
414 * Structure that can be passed to our default handler to guide the
415 * execution of the request through its lifecycle.
417 typedef struct svn_ra_serf__handler_t {
418 /* The HTTP method string of the request */
421 /* The resource to the execute the method on. */
424 /* The content-type of the request body. */
425 const char *body_type;
427 /* If TRUE then default Accept-Encoding request header is not configured for
428 request. If FALSE then 'gzip' accept encoding will be used if compression
430 svn_boolean_t custom_accept_encoding;
432 /* Has the request/response been completed? */
435 /* If we captured an error from the server, then this will be non-NULL.
436 It will be allocated from HANDLER_POOL. */
437 svn_ra_serf__server_error_t *server_error;
439 /* The handler and baton pair for our handler. */
440 svn_ra_serf__response_handler_t response_handler;
441 void *response_baton;
443 /* When REPONSE_HANDLER is invoked, the following fields will be set
444 based on the response header. HANDLER_POOL must be non-NULL for these
445 values to be filled in. SLINE.REASON and LOCATION will be allocated
446 within HANDLER_POOL. */
447 serf_status_line sline; /* The parsed Status-Line */
448 const char *location; /* The Location: header, if any */
450 /* The handler and baton pair to be executed when a non-recoverable error
451 * is detected. If it is NULL in the presence of an error, an abort() may
454 svn_ra_serf__response_error_t response_error;
455 void *response_error_baton;
457 /* This function and baton pair allows for custom request headers to
460 * It will be executed after the request has been set up but before it is
463 svn_ra_serf__request_header_delegate_t header_delegate;
464 void *header_delegate_baton;
466 /* This function and baton pair allows a body to be created right before
469 * It will be executed after the request has been set up but before it is
472 * May be NULL if there is no body to send.
475 svn_ra_serf__request_body_delegate_t body_delegate;
476 void *body_delegate_baton;
478 /* The connection and session to be used for this request. */
479 svn_ra_serf__connection_t *conn;
480 svn_ra_serf__session_t *session;
482 /* Internal flag to indicate we've parsed the headers. */
483 svn_boolean_t reading_body;
485 /* When this flag will be set, the core handler will discard any unread
486 portion of the response body. The registered response handler will
487 no longer be called. */
488 svn_boolean_t discard_body;
490 /* Pool for allocating SLINE.REASON and LOCATION. If this pool is NULL,
491 then the requestor does not care about SLINE and LOCATION. */
492 apr_pool_t *handler_pool;
494 } svn_ra_serf__handler_t;
497 /* Run one request and process the response.
499 Similar to context_run_wait(), but this creates the request for HANDLER
500 and then waits for it to complete.
502 WARNING: context_run_wait() does NOT create a request, whereas this
503 function DOES. Avoid a double-create. */
505 svn_ra_serf__context_run_one(svn_ra_serf__handler_t *handler,
506 apr_pool_t *scratch_pool);
510 * Helper function to queue a request in the @a handler's connection.
512 void svn_ra_serf__request_create(svn_ra_serf__handler_t *handler);
514 /* XML helper callbacks. */
516 typedef struct svn_ra_serf__xml_state_t {
517 /* A numeric value that represents the current state in parsing.
519 * Value 0 is reserved for use as the default state.
523 /* Private pointer set by the parsing code. */
526 /* Allocations should be made in this pool to match the lifetime of the
531 /* The currently-declared namespace for this state. */
532 svn_ra_serf__ns_t *ns_list;
534 /* Our previous states. */
535 struct svn_ra_serf__xml_state_t *prev;
536 } svn_ra_serf__xml_state_t;
538 /* Forward declaration of the XML parser structure. */
539 typedef struct svn_ra_serf__xml_parser_t svn_ra_serf__xml_parser_t;
541 /* Callback invoked with @a baton by our XML @a parser when an element with
542 * the @a name containing @a attrs is opened.
544 typedef svn_error_t *
545 (*svn_ra_serf__xml_start_element_t)(svn_ra_serf__xml_parser_t *parser,
546 svn_ra_serf__dav_props_t name,
548 apr_pool_t *scratch_pool);
550 /* Callback invoked with @a baton by our XML @a parser when an element with
551 * the @a name is closed.
553 typedef svn_error_t *
554 (*svn_ra_serf__xml_end_element_t)(svn_ra_serf__xml_parser_t *parser,
555 svn_ra_serf__dav_props_t name,
556 apr_pool_t *scratch_pool);
558 /* Callback invoked with @a baton by our XML @a parser when a CDATA portion
559 * of @a data with size @a len is encountered.
561 * This may be invoked multiple times for the same tag.
563 typedef svn_error_t *
564 (*svn_ra_serf__xml_cdata_chunk_handler_t)(svn_ra_serf__xml_parser_t *parser,
567 apr_pool_t *scratch_pool);
570 * Helper structure associated with handle_xml_parser handler that will
571 * specify how an XML response will be processed.
573 struct svn_ra_serf__xml_parser_t {
574 /* Temporary allocations should be made in this pool. */
577 /* What kind of response are we parsing? If set, this should typically
578 define the report name. */
579 const char *response_type;
581 /* Caller-specific data passed to the start, end, cdata callbacks. */
584 /* Callback invoked when a tag is opened. */
585 svn_ra_serf__xml_start_element_t start;
587 /* Callback invoked when a tag is closed. */
588 svn_ra_serf__xml_end_element_t end;
590 /* Callback invoked when a cdata chunk is received. */
591 svn_ra_serf__xml_cdata_chunk_handler_t cdata;
593 /* Our associated expat-based XML parser. */
596 /* Our current state. */
597 svn_ra_serf__xml_state_t *state;
599 /* Our previously used states (will be reused). */
600 svn_ra_serf__xml_state_t *free_state;
602 /* If non-NULL, this value will be set to TRUE when the response is
607 /* If non-NULL, when this parser completes, it will add done_item to
610 svn_ra_serf__list_t **done_list;
612 /* A pointer to the item that will be inserted into the list upon
615 svn_ra_serf__list_t *done_item;
617 /* If this flag is TRUE, errors during parsing will be ignored.
619 * This is mainly used when we are processing an error XML response to
620 * avoid infinite loops.
622 svn_boolean_t ignore_errors;
624 /* If an error occurred, this value will be non-NULL. */
627 /* Deciding whether to pause, or not, is performed within the parsing
628 callbacks. If a callback decides to set this flag, then the loop
629 driving the parse (generally, a series of calls to serf_context_run())
630 is going to need to coordinate the un-pausing of the parser by
631 processing pending content. Thus, deciding to pause the parser is a
632 coordinate effort rather than merely setting this flag.
634 When an XML parsing callback sets this flag, note that additional
635 elements may be parsed (as the current buffer is consumed). At some
636 point, the flag will be recognized and arriving network content will
637 be stashed away in the PENDING structure (see below).
639 At some point, the controlling loop should clear this value. The
640 underlying network processing will note the change and begin passing
641 content into the XML callbacks.
643 Note that the controlling loop should also process pending content
644 since the arriving network content will typically finish first. */
645 svn_boolean_t paused;
647 /* While the XML parser is paused, content arriving from the server
648 must be saved locally. We cannot stop reading, or the server may
649 decide to drop the connection. The content will be stored in memory
650 up to a certain limit, and will then be spilled over to disk.
652 See libsvn_ra_serf/util.c */
653 struct svn_ra_serf__pending_t *pending;
657 /* v2 of the XML parsing functions */
659 /* The XML parsing context. */
660 typedef struct svn_ra_serf__xml_context_t svn_ra_serf__xml_context_t;
663 /* An opaque structure for the XML parse element/state. */
664 typedef struct svn_ra_serf__xml_estate_t svn_ra_serf__xml_estate_t;
666 /* Called just after the parser moves into ENTERED_STATE. The tag causing
667 the transition is passed in TAG.
669 This callback is applied to a parsing context by using the
670 svn_ra_serf__xml_context_customize() function.
672 NOTE: this callback, when set, will be invoked on *every* transition.
673 The callback must examine ENTERED_STATE to determine if any action
674 must be taken. The original state is not provided, but must be derived
675 from ENTERED_STATE and/or the TAG causing the transition (if needed). */
676 typedef svn_error_t *
677 (*svn_ra_serf__xml_opened_t)(svn_ra_serf__xml_estate_t *xes,
680 const svn_ra_serf__dav_props_t *tag,
681 apr_pool_t *scratch_pool);
684 /* Called just before the parser leaves LEAVING_STATE.
686 If cdata collection was enabled for this state, then CDATA will be
687 non-NULL and contain the collected cdata.
689 If attribute collection was enabled for this state, then ATTRS will
690 contain the attributes collected for this element only, along with
691 any values stored via svn_ra_serf__xml_note().
693 Use svn_ra_serf__xml_gather_since() to gather up data from outer states.
695 ATTRS is char* -> char*.
697 Temporary allocations may be made in SCRATCH_POOL. */
698 typedef svn_error_t *
699 (*svn_ra_serf__xml_closed_t)(svn_ra_serf__xml_estate_t *xes,
702 const svn_string_t *cdata,
704 apr_pool_t *scratch_pool);
707 /* Called for all states that are not using the builtin cdata collection.
708 This callback is (only) appropriate for unbounded-size cdata content.
710 CURRENT_STATE may be used to decide what to do with the data.
712 Temporary allocations may be made in SCRATCH_POOL. */
713 typedef svn_error_t *
714 (*svn_ra_serf__xml_cdata_t)(svn_ra_serf__xml_estate_t *xes,
719 apr_pool_t *scratch_pool);
722 /* State transition table.
724 When the XML Context is constructed, it is in state 0. User states are
727 In a list of transitions, use { 0 } to indicate the end. Specifically,
728 the code looks for NS == NULL.
732 typedef struct svn_ra_serf__xml_transition_t {
733 /* This transition applies when in this state */
736 /* And when this tag is observed */
740 /* Moving to this state */
743 /* Should the cdata of NAME be collected? Note that CUSTOM_CLOSE should
744 be TRUE in order to capture this cdata. */
745 svn_boolean_t collect_cdata;
747 /* Which attributes of NAME should be collected? Terminate with NULL.
748 Maximum of 10 attributes may be collected. Note that attribute
749 namespaces are ignored at this time.
751 Attribute names beginning with "?" are optional. Other names must
752 exist on the element, or SVN_ERR_XML_ATTRIB_NOT_FOUND will be raised. */
753 const char *collect_attrs[11];
755 /* When NAME is closed, should the callback be invoked? */
756 svn_boolean_t custom_close;
758 } svn_ra_serf__xml_transition_t;
761 /* Construct an XML parsing context, based on the TTABLE transition table.
762 As content is parsed, the CLOSED_CB callback will be invoked according
763 to the definition in the table.
765 If OPENED_CB is not NULL, then it will be invoked for *every* tag-open
766 event. The callback will need to use the ENTERED_STATE and TAG parameters
767 to decide what it would like to do.
769 If CDATA_CB is not NULL, then it will be called for all cdata that is
770 not be automatically collected (based on the transition table record's
771 COLLECT_CDATA flag). It will be called in every state, so the callback
772 must examine the CURRENT_STATE parameter to decide what to do.
774 The same BATON value will be passed to all three callbacks.
776 The context will be created within RESULT_POOL. */
777 svn_ra_serf__xml_context_t *
778 svn_ra_serf__xml_context_create(
779 const svn_ra_serf__xml_transition_t *ttable,
780 svn_ra_serf__xml_opened_t opened_cb,
781 svn_ra_serf__xml_closed_t closed_cb,
782 svn_ra_serf__xml_cdata_t cdata_cb,
784 apr_pool_t *result_pool);
786 /* Destroy all subpools for this structure. */
788 svn_ra_serf__xml_context_destroy(
789 svn_ra_serf__xml_context_t *xmlctx);
791 /* Construct a handler with the response function/baton set up to parse
792 a response body using the given XML context. The handler and its
793 internal structures are allocated in RESULT_POOL.
795 This also initializes HANDLER_POOL to the given RESULT_POOL. */
796 svn_ra_serf__handler_t *
797 svn_ra_serf__create_expat_handler(svn_ra_serf__xml_context_t *xmlctx,
798 apr_pool_t *result_pool);
801 /* Allocated within XES->STATE_POOL. Changes are not allowd (callers
802 should make a deep copy if they need to make changes).
804 The resulting hash maps char* names to char* values. */
806 svn_ra_serf__xml_gather_since(svn_ra_serf__xml_estate_t *xes,
810 /* Attach the NAME/VALUE pair onto this/parent state identified by STATE.
811 The name and value will be copied into the target state's pool.
813 These values will be available to the CLOSED_CB for the target state,
814 or part of the gathered state via xml_gather_since().
816 Typically, this function is used by a child state's close callback,
817 or within an opening callback to store additional data.
819 Note: if the state is not found, then a programmer error has occurred,
820 so the function will invoke SVN_ERR_MALFUNCTION(). */
822 svn_ra_serf__xml_note(svn_ra_serf__xml_estate_t *xes,
828 /* Returns XES->STATE_POOL for allocating structures that should live
829 as long as the state identified by XES.
831 Note: a state pool is created upon demand, so only use this function
832 when memory is required for a given state. */
834 svn_ra_serf__xml_state_pool(svn_ra_serf__xml_estate_t *xes);
837 /* Any XML parser may be used. When an opening tag is seen, call this
838 function to feed the information into XMLCTX. */
840 svn_ra_serf__xml_cb_start(svn_ra_serf__xml_context_t *xmlctx,
841 const char *raw_name,
842 const char *const *attrs);
845 /* When a close tag is seen, call this function to feed the information
848 svn_ra_serf__xml_cb_end(svn_ra_serf__xml_context_t *xmlctx,
849 const char *raw_name);
852 /* When cdata is parsed by the wrapping XML parser, call this function to
853 feed the cdata into the XMLCTX. */
855 svn_ra_serf__xml_cb_cdata(svn_ra_serf__xml_context_t *xmlctx,
861 * Parses a server-side error message into a local Subversion error.
863 struct svn_ra_serf__server_error_t {
864 /* Our local representation of the error. */
867 /* Are we done with the response? */
870 /* Have we seen an error tag? */
871 svn_boolean_t in_error;
873 /* Have we seen a HTTP "412 Precondition Failed" error? */
874 svn_boolean_t contains_precondition_error;
876 /* Should we be collecting the XML cdata? */
877 svn_boolean_t collect_cdata;
879 /* Collected cdata. NULL if cdata not needed. */
880 svn_stringbuf_t *cdata;
882 /* XML parser and namespace used to parse the remote response */
883 svn_ra_serf__xml_parser_t parser;
888 * Handler that discards the entire @a response body associated with a
889 * @a request. Implements svn_ra_serf__response_handler_t.
891 * If @a baton is a svn_ra_serf__server_error_t (i.e. non-NULL) and an
892 * error is detected, it will be populated for later detection.
894 * All temporary allocations will be made in a @a pool.
897 svn_ra_serf__handle_discard_body(serf_request_t *request,
898 serf_bucket_t *response,
904 * Handler that retrieves the embedded XML multistatus response from the
905 * the @a RESPONSE body associated with a @a REQUEST.
907 * Implements svn_ra_serf__response_handler_t.
909 * The @a BATON should be of type svn_ra_serf__handler_t. When the request
910 * is complete, the handler's DONE flag will be set to TRUE.
912 * All temporary allocations will be made in a @a scratch_pool.
915 svn_ra_serf__handle_multistatus_only(serf_request_t *request,
916 serf_bucket_t *response,
918 apr_pool_t *scratch_pool);
921 /* Handler that expects an empty body.
923 If a body IS present, and it is text/xml, then it will be parsed for
926 BATON should be the svn_ra_serf__handler_t running REQUEST.
928 Status line information will be in HANDLER->SLINE.
930 Any parsed errors will be left in HANDLER->SERVER_ERROR. That member
931 may be NULL if no body was present, or a problem occurred trying to
934 All temporary allocations will be made in SCRATCH_POOL. */
936 svn_ra_serf__expect_empty_body(serf_request_t *request,
937 serf_bucket_t *response,
939 apr_pool_t *scratch_pool);
943 * This function will feed the RESPONSE body into XMLP. When parsing is
944 * completed (i.e. an EOF is received), *DONE is set to TRUE.
945 * Implements svn_ra_serf__response_handler_t.
947 * If an error occurs during processing RESP_ERR is invoked with the
950 * Temporary allocations are made in POOL.
953 svn_ra_serf__handle_xml_parser(serf_request_t *request,
954 serf_bucket_t *response,
958 /* serf_response_handler_t implementation that completely discards
961 * All temporary allocations will be made in @a pool.
964 svn_ra_serf__response_discard_handler(serf_request_t *request,
965 serf_bucket_t *response,
970 /** XML helper functions. **/
973 * Advance the internal XML @a parser to the @a state.
976 svn_ra_serf__xml_push_state(svn_ra_serf__xml_parser_t *parser,
980 * Return to the previous internal XML @a parser state.
983 svn_ra_serf__xml_pop_state(svn_ra_serf__xml_parser_t *parser);
987 svn_ra_serf__process_pending(svn_ra_serf__xml_parser_t *parser,
988 svn_boolean_t *network_eof,
989 apr_pool_t *scratch_pool);
993 * Add the appropriate serf buckets to @a agg_bucket represented by
994 * the XML * @a tag and @a value.
996 * The bucket will be allocated from @a bkt_alloc.
999 svn_ra_serf__add_tag_buckets(serf_bucket_t *agg_bucket,
1002 serf_bucket_alloc_t *bkt_alloc);
1005 * Add the appropriate serf buckets to AGG_BUCKET with standard XML header:
1006 * <?xml version="1.0" encoding="utf-8"?>
1008 * The bucket will be allocated from BKT_ALLOC.
1011 svn_ra_serf__add_xml_header_buckets(serf_bucket_t *agg_bucket,
1012 serf_bucket_alloc_t *bkt_alloc);
1015 * Add the appropriate serf buckets to AGG_BUCKET representing the XML
1016 * open tag with name TAG.
1018 * Take the tag's attributes from varargs, a NULL-terminated list of
1019 * alternating <tt>char *</tt> key and <tt>char *</tt> val. Attribute
1020 * will be ignored if it's value is NULL.
1022 * NOTE: Callers are responsible for XML-escaping attribute values as
1025 * The bucket will be allocated from BKT_ALLOC.
1028 svn_ra_serf__add_open_tag_buckets(serf_bucket_t *agg_bucket,
1029 serf_bucket_alloc_t *bkt_alloc,
1034 * Add the appropriate serf buckets to AGG_BUCKET representing xml tag close
1037 * The bucket will be allocated from BKT_ALLOC.
1040 svn_ra_serf__add_close_tag_buckets(serf_bucket_t *agg_bucket,
1041 serf_bucket_alloc_t *bkt_alloc,
1045 * Add the appropriate serf buckets to AGG_BUCKET with xml-escaped
1048 * The bucket will be allocated from BKT_ALLOC.
1051 svn_ra_serf__add_cdata_len_buckets(serf_bucket_t *agg_bucket,
1052 serf_bucket_alloc_t *bkt_alloc,
1053 const char *data, apr_size_t len);
1055 * Look up the @a attrs array for namespace definitions and add each one
1056 * to the @a ns_list of namespaces.
1058 * New namespaces will be allocated in RESULT_POOL.
1061 svn_ra_serf__define_ns(svn_ra_serf__ns_t **ns_list,
1062 const char *const *attrs,
1063 apr_pool_t *result_pool);
1066 * Look up @a name in the @a ns_list list for previously declared namespace
1069 * Return (in @a *returned_prop_name) a #svn_ra_serf__dav_props_t tuple
1070 * representing the expanded name.
1073 svn_ra_serf__expand_ns(svn_ra_serf__dav_props_t *returned_prop_name,
1074 const svn_ra_serf__ns_t *ns_list,
1078 /** PROPFIND-related functions **/
1081 * This function will deliver a PROP_CTX PROPFIND request in the SESS
1082 * serf context for the properties listed in LOOKUP_PROPS at URL for
1083 * DEPTH ("0","1","infinity").
1085 * This function will not block waiting for the response. Callers are
1086 * expected to call svn_ra_serf__wait_for_props().
1089 svn_ra_serf__deliver_props(svn_ra_serf__handler_t **propfind_handler,
1090 apr_hash_t *prop_vals,
1091 svn_ra_serf__session_t *sess,
1092 svn_ra_serf__connection_t *conn,
1096 const svn_ra_serf__dav_props_t *lookup_props,
1097 svn_ra_serf__list_t **done_list,
1101 * This helper function will block until PROPFIND_HANDLER indicates that is
1102 * done or another error is returned.
1105 svn_ra_serf__wait_for_props(svn_ra_serf__handler_t *handler,
1106 apr_pool_t *scratch_pool);
1108 /* This is a blocking version of deliver_props.
1110 The properties are fetched and placed into RESULTS, allocated in
1113 ### more docco about the other params.
1115 Temporary allocations are made in SCRATCH_POOL.
1118 svn_ra_serf__retrieve_props(apr_hash_t **results,
1119 svn_ra_serf__session_t *sess,
1120 svn_ra_serf__connection_t *conn,
1124 const svn_ra_serf__dav_props_t *props,
1125 apr_pool_t *result_pool,
1126 apr_pool_t *scratch_pool);
1129 /* Using CONN, fetch the properties specified by WHICH_PROPS using CONN
1130 for URL at REVISION. The resulting properties are placed into a 2-level
1131 hash in RESULTS, mapping NAMESPACE -> hash<PROPNAME, PROPVALUE>, which
1132 is allocated in RESULT_POOL.
1134 If REVISION is SVN_INVALID_REVNUM, then the properties are fetched
1137 This function performs the request synchronously.
1139 Temporary allocations are made in SCRATCH_POOL. */
1141 svn_ra_serf__fetch_node_props(apr_hash_t **results,
1142 svn_ra_serf__connection_t *conn,
1144 svn_revnum_t revision,
1145 const svn_ra_serf__dav_props_t *which_props,
1146 apr_pool_t *result_pool,
1147 apr_pool_t *scratch_pool);
1150 /* Using CONN, fetch a DAV: property from the resource identified by URL
1151 within REVISION. The PROPNAME may be one of:
1156 The resulting value will be allocated in RESULT_POOL, and may be NULL
1157 if the property does not exist (note: "href" always exists).
1159 This function performs the request synchronously.
1161 Temporary allocations are made in SCRATCH_POOL. */
1163 svn_ra_serf__fetch_dav_prop(const char **value,
1164 svn_ra_serf__connection_t *conn,
1166 svn_revnum_t revision,
1167 const char *propname,
1168 apr_pool_t *result_pool,
1169 apr_pool_t *scratch_pool);
1172 /* Set PROPS for PATH at REV revision with a NS:NAME VAL.
1174 * The POOL governs allocation.
1177 svn_ra_serf__set_ver_prop(apr_hash_t *props,
1178 const char *path, svn_revnum_t rev,
1179 const char *ns, const char *name,
1180 const svn_string_t *val, apr_pool_t *pool);
1181 #define svn_ra_serf__set_rev_prop svn_ra_serf__set_ver_prop
1183 /** Property walker functions **/
1185 typedef svn_error_t *
1186 (*svn_ra_serf__walker_visitor_t)(void *baton,
1189 const svn_string_t *val,
1193 svn_ra_serf__walk_all_props(apr_hash_t *props,
1196 svn_ra_serf__walker_visitor_t walker,
1201 /* Like walk_all_props(), but a 2-level hash. */
1203 svn_ra_serf__walk_node_props(apr_hash_t *props,
1204 svn_ra_serf__walker_visitor_t walker,
1206 apr_pool_t *scratch_pool);
1209 typedef svn_error_t *
1210 (*svn_ra_serf__path_rev_walker_t)(void *baton,
1211 const char *path, apr_ssize_t path_len,
1212 const char *ns, apr_ssize_t ns_len,
1213 const char *name, apr_ssize_t name_len,
1214 const svn_string_t *val,
1217 svn_ra_serf__walk_all_paths(apr_hash_t *props,
1219 svn_ra_serf__path_rev_walker_t walker,
1224 /* Map a property name, as passed over the wire, into its corresponding
1225 Subversion-internal name. The returned name will be a static value,
1226 or allocated within RESULT_POOL.
1228 If the property should be ignored (eg. some DAV properties), then NULL
1229 will be returned. */
1231 svn_ra_serf__svnname_from_wirename(const char *ns,
1233 apr_pool_t *result_pool);
1236 /* Select the basic revision properties from the set of "all" properties.
1237 Return these in *REVPROPS, allocated from RESULT_POOL. */
1239 svn_ra_serf__select_revprops(apr_hash_t **revprops,
1242 apr_hash_t *all_revprops,
1243 apr_pool_t *result_pool,
1244 apr_pool_t *scratch_pool);
1247 /* PROPS is nested hash tables mapping NS -> NAME -> VALUE.
1248 This function takes the NS:NAME:VALUE hashes and flattens them into a set of
1249 names to VALUE. The names are composed of NS:NAME, with specific
1250 rewrite from wire names (DAV) to SVN names. This mapping is managed
1251 by the svn_ra_serf__set_baton_props() function.
1253 FLAT_PROPS is allocated in RESULT_POOL.
1254 ### right now, we do a shallow copy from PROPS to FLAT_PROPS. therefore,
1255 ### the names and values in PROPS must be in the proper pool.
1257 Temporary allocations are made in SCRATCH_POOL. */
1259 svn_ra_serf__flatten_props(apr_hash_t **flat_props,
1261 apr_pool_t *result_pool,
1262 apr_pool_t *scratch_pool);
1265 /* Return the property value for PATH at REV revision with a NS:NAME.
1266 * PROPS is a four-level nested hash: (svn_revnum_t => char *path =>
1267 * char *ns => char *name => svn_string_t *). */
1268 const svn_string_t *
1269 svn_ra_serf__get_ver_prop_string(apr_hash_t *props,
1270 const char *path, svn_revnum_t rev,
1271 const char *ns, const char *name);
1273 /* Same as svn_ra_serf__get_ver_prop_string(), but returns a C string. */
1275 svn_ra_serf__get_ver_prop(apr_hash_t *props,
1276 const char *path, svn_revnum_t rev,
1277 const char *ns, const char *name);
1279 /* Same as svn_ra_serf__get_ver_prop_string(), but for the unknown revision. */
1280 const svn_string_t *
1281 svn_ra_serf__get_prop_string(apr_hash_t *props,
1286 /* Same as svn_ra_serf__get_ver_prop(), but for the unknown revision. */
1288 svn_ra_serf__get_prop(apr_hash_t *props,
1293 /* Same as svn_ra_serf__set_rev_prop(), but for the unknown revision. */
1295 svn_ra_serf__set_prop(apr_hash_t *props, const char *path,
1296 const char *ns, const char *name,
1297 const svn_string_t *val, apr_pool_t *pool);
1300 svn_ra_serf__get_resource_type(svn_node_kind_t *kind,
1304 /** MERGE-related functions **/
1307 svn_ra_serf__merge_lock_token_list(apr_hash_t *lock_tokens,
1309 serf_bucket_t *body,
1310 serf_bucket_alloc_t *alloc,
1313 /* Create an MERGE request aimed at the SESSION url, requesting the
1314 merge of the resource identified by MERGE_RESOURCE_URL.
1315 LOCK_TOKENS is a hash mapping paths to lock tokens owned by the
1316 client. If KEEP_LOCKS is set, instruct the server to not release
1317 locks set on the paths included in this commit. */
1319 svn_ra_serf__run_merge(const svn_commit_info_t **commit_info,
1321 svn_ra_serf__session_t *session,
1322 svn_ra_serf__connection_t *conn,
1323 const char *merge_resource_url,
1324 apr_hash_t *lock_tokens,
1325 svn_boolean_t keep_locks,
1326 apr_pool_t *result_pool,
1327 apr_pool_t *scratch_pool);
1330 /** OPTIONS-related functions **/
1332 /* When running with a proxy, we may need to detect and correct for problems.
1333 This probing function will send a simple OPTIONS request to detect problems
1334 with the connection. */
1336 svn_ra_serf__probe_proxy(svn_ra_serf__session_t *serf_sess,
1337 apr_pool_t *scratch_pool);
1340 /* On HTTPv2 connections, run an OPTIONS request over CONN to fetch the
1341 current youngest revnum, returning it in *YOUNGEST.
1343 (the revnum is headers of the OPTIONS response)
1345 This function performs the request synchronously.
1347 All temporary allocations will be made in SCRATCH_POOL. */
1349 svn_ra_serf__v2_get_youngest_revnum(svn_revnum_t *youngest,
1350 svn_ra_serf__connection_t *conn,
1351 apr_pool_t *scratch_pool);
1354 /* On HTTPv1 connections, run an OPTIONS request over CONN to fetch the
1355 activity collection set and return it in *ACTIVITY_URL, allocated
1358 (the activity-collection-set is in the body of the OPTIONS response)
1360 This function performs the request synchronously.
1362 All temporary allocations will be made in SCRATCH_POOL. */
1364 svn_ra_serf__v1_get_activity_collection(const char **activity_url,
1365 svn_ra_serf__connection_t *conn,
1366 apr_pool_t *result_pool,
1367 apr_pool_t *scratch_pool);
1370 /* Set @a VCC_URL to the default VCC for our repository based on @a
1371 * ORIG_PATH for the session @a SESSION, ensuring that the VCC URL and
1372 * repository root URLs are cached in @a SESSION. Use @a CONN for any
1373 * required network communications if it is non-NULL; otherwise use the
1374 * default connection.
1376 * All temporary allocations will be made in @a POOL. */
1378 svn_ra_serf__discover_vcc(const char **vcc_url,
1379 svn_ra_serf__session_t *session,
1380 svn_ra_serf__connection_t *conn,
1383 /* Set @a REPORT_TARGET to the URI of the resource at which generic
1384 * (path-agnostic) REPORTs should be aimed for @a SESSION. Use @a
1385 * CONN for any required network communications if it is non-NULL;
1386 * otherwise use the default connection.
1388 * All temporary allocations will be made in @a POOL.
1391 svn_ra_serf__report_resource(const char **report_target,
1392 svn_ra_serf__session_t *session,
1393 svn_ra_serf__connection_t *conn,
1396 /* Set @a REL_PATH to a path (not URI-encoded) relative to the root of
1397 * the repository pointed to by @a SESSION, based on original path
1398 * (URI-encoded) @a ORIG_PATH. Use @a CONN for any required network
1399 * communications if it is non-NULL; otherwise use the default
1400 * connection. Use POOL for allocations. */
1402 svn_ra_serf__get_relative_path(const char **rel_path,
1403 const char *orig_path,
1404 svn_ra_serf__session_t *session,
1405 svn_ra_serf__connection_t *conn,
1409 /* Using the default connection in SESSION (conns[0]), get the youngest
1410 revnum from the server, returning it in *YOUNGEST.
1412 This function operates synchronously.
1414 All temporary allocations are performed in SCRATCH_POOL. */
1416 svn_ra_serf__get_youngest_revnum(svn_revnum_t *youngest,
1417 svn_ra_serf__session_t *session,
1418 apr_pool_t *scratch_pool);
1421 /* Generate a revision-stable URL.
1423 The RA APIs all refer to user/public URLs that float along with the
1424 youngest revision. In many cases, we do NOT want to work with that URL
1425 since it can change from one moment to the next. Especially if we
1426 attempt to operation against multiple floating URLs -- we could end up
1427 referring to two separate revisions.
1429 The DAV RA provider(s) solve this by generating a URL that is specific
1430 to a revision by using a URL into a "baseline collection".
1432 For a specified SESSION, with an optional CONN (if NULL, then the
1433 session's default connection will be used; specifically SESSION->conns[0]),
1434 generate a revision-stable URL for URL at REVISION. If REVISION is
1435 SVN_INVALID_REVNUM, then the stable URL will refer to the youngest
1436 revision at the time this function was called.
1438 If URL is NULL, then the session root will be used.
1440 The stable URL will be placed into *STABLE_URL, allocated from RESULT_POOL.
1442 If LATEST_REVNUM is not NULL, then the revision used will be placed into
1443 *LATEST_REVNUM. That will be equal to youngest, or the given REVISION.
1445 This function operates synchronously, if any communication to the server
1446 is required. Communication is needed if REVISION is SVN_INVALID_REVNUM
1447 (to get the current youngest revnum), or if the specified REVISION is not
1448 (yet) in our cache of baseline collections.
1450 All temporary allocations are performed in SCRATCH_POOL. */
1452 svn_ra_serf__get_stable_url(const char **stable_url,
1453 svn_revnum_t *latest_revnum,
1454 svn_ra_serf__session_t *session,
1455 svn_ra_serf__connection_t *conn,
1457 svn_revnum_t revision,
1458 apr_pool_t *result_pool,
1459 apr_pool_t *scratch_pool);
1462 /** RA functions **/
1464 /* Implements svn_ra__vtable_t.get_log(). */
1466 svn_ra_serf__get_log(svn_ra_session_t *session,
1467 const apr_array_header_t *paths,
1471 svn_boolean_t discover_changed_paths,
1472 svn_boolean_t strict_node_history,
1473 svn_boolean_t include_merged_revisions,
1474 const apr_array_header_t *revprops,
1475 svn_log_entry_receiver_t receiver,
1476 void *receiver_baton,
1479 /* Implements svn_ra__vtable_t.get_locations(). */
1481 svn_ra_serf__get_locations(svn_ra_session_t *session,
1482 apr_hash_t **locations,
1484 svn_revnum_t peg_revision,
1485 const apr_array_header_t *location_revisions,
1488 /* Implements svn_ra__vtable_t.get_location_segments(). */
1490 svn_ra_serf__get_location_segments(svn_ra_session_t *session,
1492 svn_revnum_t peg_revision,
1493 svn_revnum_t start_rev,
1494 svn_revnum_t end_rev,
1495 svn_location_segment_receiver_t receiver,
1496 void *receiver_baton,
1499 /* Implements svn_ra__vtable_t.do_diff(). */
1501 svn_ra_serf__do_diff(svn_ra_session_t *session,
1502 const svn_ra_reporter3_t **reporter,
1503 void **report_baton,
1504 svn_revnum_t revision,
1505 const char *diff_target,
1507 svn_boolean_t ignore_ancestry,
1508 svn_boolean_t text_deltas,
1509 const char *versus_url,
1510 const svn_delta_editor_t *diff_editor,
1514 /* Implements svn_ra__vtable_t.do_status(). */
1516 svn_ra_serf__do_status(svn_ra_session_t *ra_session,
1517 const svn_ra_reporter3_t **reporter,
1518 void **report_baton,
1519 const char *status_target,
1520 svn_revnum_t revision,
1522 const svn_delta_editor_t *status_editor,
1526 /* Implements svn_ra__vtable_t.do_update(). */
1528 svn_ra_serf__do_update(svn_ra_session_t *ra_session,
1529 const svn_ra_reporter3_t **reporter,
1530 void **report_baton,
1531 svn_revnum_t revision_to_update_to,
1532 const char *update_target,
1534 svn_boolean_t send_copyfrom_args,
1535 svn_boolean_t ignore_ancestry,
1536 const svn_delta_editor_t *update_editor,
1538 apr_pool_t *result_pool,
1539 apr_pool_t *scratch_pool);
1541 /* Implements svn_ra__vtable_t.do_switch(). */
1543 svn_ra_serf__do_switch(svn_ra_session_t *ra_session,
1544 const svn_ra_reporter3_t **reporter,
1545 void **report_baton,
1546 svn_revnum_t revision_to_switch_to,
1547 const char *switch_target,
1549 const char *switch_url,
1550 svn_boolean_t send_copyfrom_args,
1551 svn_boolean_t ignore_ancestry,
1552 const svn_delta_editor_t *switch_editor,
1554 apr_pool_t *result_pool,
1555 apr_pool_t *scratch_pool);
1557 /* Implements svn_ra__vtable_t.get_file_revs(). */
1559 svn_ra_serf__get_file_revs(svn_ra_session_t *session,
1563 svn_boolean_t include_merged_revisions,
1564 svn_file_rev_handler_t handler,
1565 void *handler_baton,
1568 /* Implements svn_ra__vtable_t.get_dated_revision(). */
1570 svn_ra_serf__get_dated_revision(svn_ra_session_t *session,
1571 svn_revnum_t *revision,
1575 /* Implements svn_ra__vtable_t.get_commit_editor(). */
1577 svn_ra_serf__get_commit_editor(svn_ra_session_t *session,
1578 const svn_delta_editor_t **editor,
1580 apr_hash_t *revprop_table,
1581 svn_commit_callback2_t callback,
1582 void *callback_baton,
1583 apr_hash_t *lock_tokens,
1584 svn_boolean_t keep_locks,
1587 /* Implements svn_ra__vtable_t.get_file(). */
1589 svn_ra_serf__get_file(svn_ra_session_t *session,
1591 svn_revnum_t revision,
1592 svn_stream_t *stream,
1593 svn_revnum_t *fetched_rev,
1597 /* Implements svn_ra__vtable_t.change_rev_prop(). */
1599 svn_ra_serf__change_rev_prop(svn_ra_session_t *session,
1602 const svn_string_t *const *old_value_p,
1603 const svn_string_t *value,
1606 /* Implements svn_ra__vtable_t.replay(). */
1608 svn_ra_serf__replay(svn_ra_session_t *ra_session,
1609 svn_revnum_t revision,
1610 svn_revnum_t low_water_mark,
1611 svn_boolean_t text_deltas,
1612 const svn_delta_editor_t *editor,
1616 /* Implements svn_ra__vtable_t.replay_range(). */
1618 svn_ra_serf__replay_range(svn_ra_session_t *ra_session,
1619 svn_revnum_t start_revision,
1620 svn_revnum_t end_revision,
1621 svn_revnum_t low_water_mark,
1622 svn_boolean_t send_deltas,
1623 svn_ra_replay_revstart_callback_t revstart_func,
1624 svn_ra_replay_revfinish_callback_t revfinish_func,
1628 /* Implements svn_ra__vtable_t.lock(). */
1630 svn_ra_serf__lock(svn_ra_session_t *ra_session,
1631 apr_hash_t *path_revs,
1632 const char *comment,
1633 svn_boolean_t force,
1634 svn_ra_lock_callback_t lock_func,
1638 /* Implements svn_ra__vtable_t.unlock(). */
1640 svn_ra_serf__unlock(svn_ra_session_t *ra_session,
1641 apr_hash_t *path_tokens,
1642 svn_boolean_t force,
1643 svn_ra_lock_callback_t lock_func,
1647 /* Implements svn_ra__vtable_t.get_lock(). */
1649 svn_ra_serf__get_lock(svn_ra_session_t *ra_session,
1654 /* Implements svn_ra__vtable_t.get_locks(). */
1656 svn_ra_serf__get_locks(svn_ra_session_t *ra_session,
1662 /* Request a mergeinfo-report from the URL attached to SESSION,
1663 and fill in the MERGEINFO hash with the results.
1665 Implements svn_ra__vtable_t.get_mergeinfo().
1668 svn_ra_serf__get_mergeinfo(svn_ra_session_t *ra_session,
1669 apr_hash_t **mergeinfo,
1670 const apr_array_header_t *paths,
1671 svn_revnum_t revision,
1672 svn_mergeinfo_inheritance_t inherit,
1673 svn_boolean_t include_descendants,
1676 /* Exchange capabilities with the server, by sending an OPTIONS
1677 * request announcing the client's capabilities, and by filling
1678 * SERF_SESS->capabilities with the server's capabilities as read from
1679 * the response headers. Use POOL only for temporary allocation.
1681 * If the CORRECTED_URL is non-NULL, allow the OPTIONS response to
1682 * report a server-dictated redirect or relocation (HTTP 301 or 302
1683 * error codes), setting *CORRECTED_URL to the value of the corrected
1684 * repository URL. Otherwise, such responses from the server will
1685 * generate an error. (In either case, no capabilities are exchanged
1686 * if there is, in fact, such a response from the server.)
1689 svn_ra_serf__exchange_capabilities(svn_ra_serf__session_t *serf_sess,
1690 const char **corrected_url,
1693 /* Implements svn_ra__vtable_t.has_capability(). */
1695 svn_ra_serf__has_capability(svn_ra_session_t *ra_session,
1697 const char *capability,
1700 /* Implements svn_ra__vtable_t.get_deleted_rev(). */
1702 svn_ra_serf__get_deleted_rev(svn_ra_session_t *session,
1704 svn_revnum_t peg_revision,
1705 svn_revnum_t end_revision,
1706 svn_revnum_t *revision_deleted,
1709 /* Implements the get_inherited_props RA layer function. */
1710 svn_error_t * svn_ra_serf__get_inherited_props(svn_ra_session_t *session,
1711 apr_array_header_t **iprops,
1713 svn_revnum_t revision,
1714 apr_pool_t *result_pool,
1715 apr_pool_t *scratch_pool);
1717 /* Implements svn_ra__vtable_t.get_repos_root(). */
1719 svn_ra_serf__get_repos_root(svn_ra_session_t *ra_session,
1723 /* Implements svn_ra__vtable_t.register_editor_shim_callbacks(). */
1725 svn_ra_serf__register_editor_shim_callbacks(svn_ra_session_t *session,
1726 svn_delta_shim_callbacks_t *callbacks);
1728 /*** Authentication handler declarations ***/
1731 * Callback function that loads the credentials for Basic and Digest
1732 * authentications, both for server and proxy authentication.
1735 svn_ra_serf__credentials_callback(char **username, char **password,
1736 serf_request_t *request, void *baton,
1737 int code, const char *authn_type,
1742 /*** General utility functions ***/
1745 * Convert an HTTP STATUS_CODE resulting from a WebDAV request against
1746 * PATH to the relevant error code. Use the response-supplied LOCATION
1747 * where it necessary.
1750 svn_ra_serf__error_on_status(serf_status_line sline,
1752 const char *location);
1756 svn_ra_serf__copy_into_spillbuf(svn_spillbuf_t **spillbuf,
1758 apr_pool_t *result_pool,
1759 apr_pool_t *scratch_pool);
1763 svn_ra_serf__create_sb_bucket(svn_spillbuf_t *spillbuf,
1764 serf_bucket_alloc_t *allocator,
1765 apr_pool_t *result_pool,
1766 apr_pool_t *scratch_pool);
1768 /** Wrap STATUS from an serf function. If STATUS is not serf error code,
1769 * this is equivalent to svn_error_wrap_apr().
1772 svn_ra_serf__wrap_err(apr_status_t status,
1777 #if defined(SVN_DEBUG)
1778 /* Wrapper macros to collect file and line information */
1779 #define svn_ra_serf__wrap_err \
1780 (svn_error__locate(__FILE__,__LINE__), (svn_ra_serf__wrap_err))
1786 #endif /* __cplusplus */
1788 #endif /* SVN_LIBSVN_RA_SERF_RA_SERF_H */