1 /** 2 * @copyright 3 * ==================================================================== 4 * Licensed to the Apache Software Foundation (ASF) under one 5 * or more contributor license agreements. See the NOTICE file 6 * distributed with this work for additional information 7 * regarding copyright ownership. The ASF licenses this file 8 * to you under the Apache License, Version 2.0 (the 9 * "License"); you may not use this file except in compliance 10 * with the License. You may obtain a copy of the License at 11 * 12 * http://www.apache.org/licenses/LICENSE-2.0 13 * 14 * Unless required by applicable law or agreed to in writing, 15 * software distributed under the License is distributed on an 16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 17 * KIND, either express or implied. See the License for the 18 * specific language governing permissions and limitations 19 * under the License. 20 * ==================================================================== 21 * @endcopyright 22 * 23 * @file svn_client_shelf.h 24 * @brief Subversion's client library: experimental shelving v3 25 */ 26 27 #ifndef SVN_CLIENT_SHELF_H 28 #define SVN_CLIENT_SHELF_H 29 30 #include <apr.h> 31 #include <apr_pools.h> 32 #include <apr_hash.h> 33 #include <apr_time.h> 34 35 #include "svn_client.h" 36 #include "svn_types.h" 37 #include "svn_string.h" 38 #include "svn_wc.h" 39 #include "svn_diff.h" 40 #include "private/svn_diff_tree.h" 41 42 #ifdef __cplusplus 43 extern "C" { 44 #endif /* __cplusplus */ 45 46 47 48 /** Shelving v3, with checkpoints 49 * 50 * @defgroup svn_client_shelves_checkpoints Shelves and checkpoints 51 * @{ 52 */ 53 54 /** A shelf. 55 * 56 * @warning EXPERIMENTAL. 57 */ 58 typedef struct svn_client__shelf_t 59 { 60 /* Public fields (read-only for public use) */ 61 const char *name; 62 int max_version; /**< @deprecated */ 63 64 /* Private fields */ 65 const char *wc_root_abspath; 66 const char *shelves_dir; 67 apr_hash_t *revprops; /**< non-null; allocated in POOL */ 68 svn_client_ctx_t *ctx; 69 apr_pool_t *pool; 70 } svn_client__shelf_t; 71 72 /** One version of a shelved change-set. 73 * 74 * @warning EXPERIMENTAL. 75 */ 76 typedef struct svn_client__shelf_version_t 77 { 78 /* Public fields (read-only for public use) */ 79 svn_client__shelf_t *shelf; 80 apr_time_t mtime; /**< time-stamp of this version */ 81 82 /* Private fields */ 83 const char *files_dir_abspath; /**< abspath of the storage area */ 84 int version_number; /**< version number starting from 1 */ 85 } svn_client__shelf_version_t; 86 87 /** Open an existing shelf or create a new shelf. 88 * 89 * Create a new shelf (containing no versions) if a shelf named @a name 90 * is not found. 91 * 92 * The shelf should be closed after use by calling svn_client_shelf_close(). 93 * 94 * @a local_abspath is any path in the WC and is used to find the WC root. 95 * 96 * @warning EXPERIMENTAL. 97 */ 98 SVN_EXPERIMENTAL 99 svn_error_t * 100 svn_client__shelf_open_or_create(svn_client__shelf_t **shelf_p, 101 const char *name, 102 const char *local_abspath, 103 svn_client_ctx_t *ctx, 104 apr_pool_t *result_pool); 105 106 /** Open an existing shelf named @a name, or error if it doesn't exist. 107 * 108 * The shelf should be closed after use by calling svn_client_shelf_close(). 109 * 110 * @a local_abspath is any path in the WC and is used to find the WC root. 111 * 112 * @warning EXPERIMENTAL. 113 */ 114 SVN_EXPERIMENTAL 115 svn_error_t * 116 svn_client__shelf_open_existing(svn_client__shelf_t **shelf_p, 117 const char *name, 118 const char *local_abspath, 119 svn_client_ctx_t *ctx, 120 apr_pool_t *result_pool); 121 122 /** Close @a shelf. 123 * 124 * If @a shelf is NULL, do nothing; otherwise @a shelf must be an open shelf. 125 * 126 * @warning EXPERIMENTAL. 127 */ 128 SVN_EXPERIMENTAL 129 svn_error_t * 130 svn_client__shelf_close(svn_client__shelf_t *shelf, 131 apr_pool_t *scratch_pool); 132 133 /** Delete the shelf named @a name, or error if it doesn't exist. 134 * 135 * @a local_abspath is any path in the WC and is used to find the WC root. 136 * 137 * @warning EXPERIMENTAL. 138 */ 139 SVN_EXPERIMENTAL 140 svn_error_t * 141 svn_client__shelf_delete(const char *name, 142 const char *local_abspath, 143 svn_boolean_t dry_run, 144 svn_client_ctx_t *ctx, 145 apr_pool_t *scratch_pool); 146 147 /** Get an editor that, when driven, will store changes in @a shelf_version. 148 * 149 * @warning EXPERIMENTAL. 150 */ 151 SVN_EXPERIMENTAL 152 svn_error_t * 153 svn_client__shelf_mods_editor(const svn_delta_editor_t **editor_p, 154 void **edit_baton_p, 155 svn_client__shelf_version_t *shelf_version, 156 svn_wc_notify_func2_t notify_func, 157 void *notify_baton, 158 svn_client_ctx_t *ctx, 159 apr_pool_t *result_pool); 160 161 /** Save the local modifications found by @a paths, @a depth, 162 * @a changelists as a new version of @a shelf. 163 * 164 * If any paths are shelved, create a new shelf-version and return the new 165 * shelf-version in @a *new_version_p, else set @a *new_version_p to null. 166 * @a new_version_p may be null if that output is not wanted; a new shelf- 167 * version is still saved and may be found through @a shelf. 168 * 169 * @a paths are relative to the CWD, or absolute. 170 * 171 * For each successfully shelved path: call @a shelved_func (if not null) 172 * with @a shelved_baton. 173 * 174 * If any paths cannot be shelved: if @a not_shelved_func is given, call 175 * it with @a not_shelved_baton for each such path, and still create a new 176 * shelf-version if any paths are shelved. 177 * 178 * This function does not revert the changes from the WC; use 179 * svn_client_shelf_unapply() for that. 180 * 181 * @warning EXPERIMENTAL. 182 */ 183 SVN_EXPERIMENTAL 184 svn_error_t * 185 svn_client__shelf_save_new_version3(svn_client__shelf_version_t **new_version_p, 186 svn_client__shelf_t *shelf, 187 const apr_array_header_t *paths, 188 svn_depth_t depth, 189 const apr_array_header_t *changelists, 190 svn_client_status_func_t shelved_func, 191 void *shelved_baton, 192 svn_client_status_func_t not_shelved_func, 193 void *not_shelved_baton, 194 apr_pool_t *scratch_pool); 195 196 /** Delete all newer versions of @a shelf newer than @a shelf_version. 197 * 198 * If @a shelf_version is null, delete all versions of @a shelf. (The 199 * shelf will still exist, with any log message and other revprops, but 200 * with no versions in it.) 201 * 202 * Leave the shelf's log message and other revprops unchanged. 203 * 204 * Any #svn_client__shelf_version_t object that refers to a deleted version 205 * will become invalid: attempting to use it will give undefined behaviour. 206 * The given @a shelf_version will remain valid. 207 * 208 * @warning EXPERIMENTAL. 209 */ 210 SVN_EXPERIMENTAL 211 svn_error_t * 212 svn_client__shelf_delete_newer_versions(svn_client__shelf_t *shelf, 213 svn_client__shelf_version_t *shelf_version, 214 apr_pool_t *scratch_pool); 215 216 /** Return in @a shelf_version an existing version of @a shelf, given its 217 * @a version_number (starting from 1). Error if that version doesn't exist. 218 * 219 * There is no need to "close" it after use. 220 * 221 * @warning EXPERIMENTAL. 222 */ 223 SVN_EXPERIMENTAL 224 svn_error_t * 225 svn_client__shelf_version_open(svn_client__shelf_version_t **shelf_version_p, 226 svn_client__shelf_t *shelf, 227 int version_number, 228 apr_pool_t *result_pool, 229 apr_pool_t *scratch_pool); 230 231 /** Return in @a shelf_version the newest version of @a shelf. 232 * 233 * Set @a shelf_version to null if no versions exist. 234 * 235 * @warning EXPERIMENTAL. 236 */ 237 SVN_EXPERIMENTAL 238 svn_error_t * 239 svn_client__shelf_get_newest_version(svn_client__shelf_version_t **shelf_version_p, 240 svn_client__shelf_t *shelf, 241 apr_pool_t *result_pool, 242 apr_pool_t *scratch_pool); 243 244 /** Return in @a versions_p an array of (#svn_client__shelf_version_t *) 245 * containing all versions of @a shelf. 246 * 247 * The versions will be in chronological order, oldest to newest. 248 * 249 * @warning EXPERIMENTAL. 250 */ 251 SVN_EXPERIMENTAL 252 svn_error_t * 253 svn_client__shelf_get_all_versions(apr_array_header_t **versions_p, 254 svn_client__shelf_t *shelf, 255 apr_pool_t *result_pool, 256 apr_pool_t *scratch_pool); 257 258 /** Apply @a shelf_version to the WC. 259 * 260 * If @a dry_run is true, try applying the shelf-version to the WC and 261 * report the full set of notifications about successes and conflicts, 262 * but leave the WC untouched. 263 * 264 * @warning EXPERIMENTAL. 265 */ 266 SVN_EXPERIMENTAL 267 svn_error_t * 268 svn_client__shelf_apply(svn_client__shelf_version_t *shelf_version, 269 svn_boolean_t dry_run, 270 apr_pool_t *scratch_pool); 271 272 /** Test whether we can successfully apply the changes for @a file_relpath 273 * in @a shelf_version to the WC. 274 * 275 * Set @a *conflict_p to true if the changes conflict with the WC state, 276 * else to false. 277 * 278 * If @a file_relpath is not found in @a shelf_version, set @a *conflict_p 279 * to FALSE. 280 * 281 * @a file_relpath is relative to the WC root. 282 * 283 * A conflict means the shelf cannot be applied successfully to the WC 284 * because the change to be applied is not compatible with the current 285 * working state of the WC file. Examples are a text conflict, or the 286 * file does not exist or is a directory, or the shelf is trying to add 287 * the file but it already exists, or trying to delete it but it does not 288 * exist. 289 * 290 * Return an error only if something is broken, e.g. unable to read data 291 * from the specified shelf-version. 292 * 293 * Leave the WC untouched. 294 * 295 * @warning EXPERIMENTAL. 296 */ 297 SVN_EXPERIMENTAL 298 svn_error_t * 299 svn_client__shelf_test_apply_file(svn_boolean_t *conflict_p, 300 svn_client__shelf_version_t *shelf_version, 301 const char *file_relpath, 302 apr_pool_t *scratch_pool); 303 304 /** Reverse-apply @a shelf_version to the WC. 305 * 306 * @warning EXPERIMENTAL. 307 */ 308 SVN_EXPERIMENTAL 309 svn_error_t * 310 svn_client__shelf_unapply(svn_client__shelf_version_t *shelf_version, 311 svn_boolean_t dry_run, 312 apr_pool_t *scratch_pool); 313 314 /** Send committable changes found in a shelf to a delta-editor. 315 * 316 * Push changes from the @a shelf_version subtree at @a top_relpath 317 * to @a editor : @a edit_baton. 318 * 319 * @warning EXPERIMENTAL. 320 */ 321 SVN_EXPERIMENTAL 322 svn_error_t * 323 svn_client__shelf_replay(svn_client__shelf_version_t *shelf_version, 324 const char *top_relpath, 325 const svn_delta_editor_t *editor, 326 void *edit_baton, 327 svn_wc_notify_func2_t notify_func, 328 void *notify_baton, 329 apr_pool_t *scratch_pool); 330 331 /** Set @a *affected_paths to a hash with one entry for each path affected 332 * by the @a shelf_version. 333 * 334 * The hash key is the path of the affected file, relative to the WC root. 335 * 336 * (Future possibility: When moves and copies are supported, the hash key 337 * is the old path and value is the new path.) 338 * 339 * @warning EXPERIMENTAL. 340 */ 341 SVN_EXPERIMENTAL 342 svn_error_t * 343 svn_client__shelf_paths_changed(apr_hash_t **affected_paths, 344 svn_client__shelf_version_t *shelf_version, 345 apr_pool_t *result_pool, 346 apr_pool_t *scratch_pool); 347 348 /** Set @a shelf's revprop @a prop_name to @a prop_val. 349 * 350 * This can be used to set or change the shelf's log message 351 * (property name "svn:log" or #SVN_PROP_REVISION_LOG). 352 * 353 * If @a prop_val is NULL, delete the property (if present). 354 * 355 * @warning EXPERIMENTAL. 356 */ 357 SVN_EXPERIMENTAL 358 svn_error_t * 359 svn_client__shelf_revprop_set(svn_client__shelf_t *shelf, 360 const char *prop_name, 361 const svn_string_t *prop_val, 362 apr_pool_t *scratch_pool); 363 364 /** Set @a shelf's revprops to @a revprop_table. 365 * 366 * This deletes all previous revprops. 367 * 368 * @warning EXPERIMENTAL. 369 */ 370 SVN_EXPERIMENTAL 371 svn_error_t * 372 svn_client__shelf_revprop_set_all(svn_client__shelf_t *shelf, 373 apr_hash_t *revprop_table, 374 apr_pool_t *scratch_pool); 375 376 /** Get @a shelf's revprop @a prop_name into @a *prop_val. 377 * 378 * If the property is not present, set @a *prop_val to NULL. 379 * 380 * This can be used to get the shelf's log message 381 * (property name "svn:log" or #SVN_PROP_REVISION_LOG). 382 * 383 * The lifetime of the result is limited to that of @a shelf and/or 384 * of @a result_pool. 385 * 386 * @warning EXPERIMENTAL. 387 */ 388 SVN_EXPERIMENTAL 389 svn_error_t * 390 svn_client__shelf_revprop_get(svn_string_t **prop_val, 391 svn_client__shelf_t *shelf, 392 const char *prop_name, 393 apr_pool_t *result_pool); 394 395 /** Get @a shelf's revprops into @a props. 396 * 397 * The lifetime of the result is limited to that of @a shelf and/or 398 * of @a result_pool. 399 * 400 * @warning EXPERIMENTAL. 401 */ 402 SVN_EXPERIMENTAL 403 svn_error_t * 404 svn_client__shelf_revprop_list(apr_hash_t **props, 405 svn_client__shelf_t *shelf, 406 apr_pool_t *result_pool); 407 408 /** Set the log message in @a shelf to @a log_message. 409 * 410 * If @a log_message is null, delete the log message. 411 * 412 * Similar to svn_client_shelf_revprop_set(... SVN_PROP_REVISION_LOG ...). 413 * 414 * @warning EXPERIMENTAL. 415 */ 416 SVN_EXPERIMENTAL 417 svn_error_t * 418 svn_client__shelf_set_log_message(svn_client__shelf_t *shelf, 419 const char *log_message, 420 apr_pool_t *scratch_pool); 421 422 /** Get the log message in @a shelf into @a *log_message. 423 * 424 * Set @a *log_message to NULL if there is no log message. 425 * 426 * Similar to svn_client_shelf_revprop_get(... SVN_PROP_REVISION_LOG ...). 427 * 428 * The result is allocated in @a result_pool. 429 * 430 * @warning EXPERIMENTAL. 431 */ 432 SVN_EXPERIMENTAL 433 svn_error_t * 434 svn_client__shelf_get_log_message(char **log_message, 435 svn_client__shelf_t *shelf, 436 apr_pool_t *result_pool); 437 438 /** Information about a shelf. 439 * 440 * @warning EXPERIMENTAL. 441 */ 442 typedef struct svn_client__shelf_info_t 443 { 444 apr_time_t mtime; /**< mtime of the latest change */ 445 } svn_client__shelf_info_t; 446 447 /** Set @a *shelf_infos to a hash, keyed by shelf name, of pointers to 448 * @c svn_client_shelf_info_t structures, one for each shelf in the 449 * given WC. 450 * 451 * @a local_abspath is any path in the WC and is used to find the WC root. 452 * 453 * @warning EXPERIMENTAL. 454 */ 455 SVN_EXPERIMENTAL 456 svn_error_t * 457 svn_client__shelf_list(apr_hash_t **shelf_infos, 458 const char *local_abspath, 459 svn_client_ctx_t *ctx, 460 apr_pool_t *result_pool, 461 apr_pool_t *scratch_pool); 462 463 /** Report the shelved status of all the shelved paths in @a shelf_version 464 * via @a walk_func(@a walk_baton, ...). 465 * 466 * @warning EXPERIMENTAL. 467 */ 468 SVN_EXPERIMENTAL 469 svn_error_t * 470 svn_client__shelf_version_status_walk(svn_client__shelf_version_t *shelf_version, 471 const char *wc_relpath, 472 svn_wc_status_func4_t walk_func, 473 void *walk_baton, 474 apr_pool_t *scratch_pool); 475 476 /** Output the subtree of @a shelf_version rooted at @a shelf_relpath 477 * as a diff to @a diff_processor. 478 * 479 * ### depth and ignore_ancestry are currently ignored. 480 * 481 * @warning EXPERIMENTAL. 482 */ 483 SVN_EXPERIMENTAL 484 svn_error_t * 485 svn_client__shelf_diff(svn_client__shelf_version_t *shelf_version, 486 const char *shelf_relpath, 487 svn_depth_t depth, 488 svn_boolean_t ignore_ancestry, 489 const svn_diff_tree_processor_t *diff_processor, 490 apr_pool_t *scratch_pool); 491 492 /** @} */ 493 494 #ifdef __cplusplus 495 } 496 #endif /* __cplusplus */ 497 498 #endif /* SVN_CLIENT_SHELF_H */ 499