Ben Reser <b...@reser.org> writes:

> I haven't dug in to the specifics of how we broke this particular use case.
> But I suspect you'll find that if you create a transaction, call
> svn_fs_change_node_prop() and commit the transaction that this call works just
> fine.  So I'd bet that the problem only happens when you try to do this from
> the pre-commit hook.

A post-commit should not change the versioned data because it confuses
the client.  However a script in general should be able to modify a
versioned property and it's perfectly possible to write a python script
that does it.  I think the problem here is that the process committing
the transaction has populated the fs_fs_data_t.txn_dir_cache and this
cache gets outdated when the post-commit runs in a separate process.

Consider the test I added in 1617263, it's one process and so doesn't
demonstrate the problem:

+  /* Create txn with changes. */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_name(&txn_name, txn, pool)); 
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_fs_make_dir(root, "X", pool));
+
+  /* Reopen, add more changes. */
+  SVN_ERR(svn_fs_open_txn(&reopen_txn, fs, txn_name, pool));
+  SVN_ERR(svn_fs_txn_root(&reopen_root, reopen_txn, pool));
+  SVN_ERR(svn_fs_change_node_prop(reopen_root, "A", "name",
+                                  svn_string_create("value", pool),
+                                  pool));
+
+  /* Reopen, commit */
+  SVN_ERR(svn_fs_open_txn(&reopen_txn, fs, txn_name, pool));
+  SVN_ERR(test_commit_txn(&head_rev, reopen_txn, NULL, pool));

If I remove the svn_fs_change_node_prop() line from the test, run the
test in gdb and stop at the commit I can then run a python script in
another process to make the equivalent property change.  Then I resume
the test and the commit includes the expected property change.

However if I also remove the svn_fs_txn_root() call that reopens the
transaction in addition to the svn_fs_change_node_prop() call then the
commit will lose the property change made externally.  In both cases the
property change is present in the transaction on disk but if the
txn_dir_cache is out-of-date the property change gets lost.

svn_fs_txn_root() calls svn_fs_fs__initialize_txn_caches() and if that
detects concurrent transactions it sets ffd->txn_dir_cache to NULL so
the out-of-date cache doesn't get used and the property change on disk
makes it into the revision.

-- 
Philip Martin | Subversion Committer
WANdisco // *Non-Stop Data*

Reply via email to