Andrey K wrote:> Hi
>
> when i try to update a document from 1 running DB to another writeable DB,
i
> got the follwoing error, because of the running DB has changed.
>
> The revision being read has been discarded - you should call
> Xapian::Database::reopen() and retry the operation
>
> This might be silly, but i wonder how to actually COPY an xapian.document
> (snap shot), so i can update it using the captured datas/terms..
> without raising an error coz the source doc has been changed during my
> updating procedures
Document objects are already "snapshots" of the items in the database
-
if the database is changed, the changes will never be visible in a
document object created from a readonly database opened before the
changes were made: the problem here isn't so much that the document
you've accessed has changed, but that the database has changed enough
that the document object can't access the values stored in the database.
The problem is that the Xapian::Document object lazily reads various
aspects of the Document from the database. When you add it to another
database, any data in the document which hasn't already been read from
the database will be looked up at that point. So, the easy solution to
your problem is to ensure that the Document object you're holding has
already loaded all its data from the Database before the database has a
chance to change. Something like the following (run immediately after
getting the document from your sample database) should fix this:
Document doc;
// get doc from a database
doc.get_value(0) // Causes all values in the document to be read from db
doc.get_data(0) // Get the document data string from the db
doc.termlist_count() // Get the list of terms in the document from the db
Unfortunately, this isn't a long-term fix. In particular, the document
object currently reads all values whenever a single value is read - we
plan to change this at some point, so that only the actual value asked
for is read. However, we also plan to change the database
implementation such that any object which needs to access data from the
database causes a read-lock to be kept on the database, preventing the
version of the database which that document refers to from being
discarded (whilst still allowing further modifications to be made).
It's reasonably likely that both these changes will be made at the same
time (in the next generation of database stuff; not in flint). So I
don't think you need to worry too much about this - just thought I
should flag it up.
--
Richard