Bo Peng wrote:
It seems to me that it would be a good idea, in general, if we were to
do that after, say, InsetInclude's parameters were changed. I saw some
crashes with InsetBibtex that were related to my not updating this
structure. E.g., I changed the bibfiles and then tried to save, but they
hadn't been copied over yet. But I don't yet know the EmbeddedFiles code
well enough how best to do this. Here's one sort of idea.
void Buffer::updateEmbeddedFiles()
{
embeddedFiles().enable(*this);
}
Does that seem right?
No. The validity, i.e., the existence of external and/or embedded file
is difficult to control. I am handling it this way:
OK, that's helpful by way of explanation. But here's where I was getting
the crash: You have an existing InsetBibtex, embedded, and then you
change the bibfiles. Now you try to save. Boom, because the newly chosen
bibfiles haven't been copied and, when the exception is thrown, LyX
tries an emergency save which just throws another exception, for the
same reason. (That has to be wrong, independently.) There needs to be
some way in this situation to make sure that all the new files get
copied over and the global list is updated, and enable() looks to me
like it does exactly that. If not, then we need some other method.
rh
1. When a file is not in bundled format, every file is external and
there is no need to extract/update. Embedding a file merely sets a
flag (usually non-empty inzipname). In this case, EmbeddedFiles are
not 'enabled'.
2. When a file is in bundled format, all embedded files must have a
valid inzip file. EmbeddedFileList::validate is used to adjust inzip
files if they are not consistent with inzipname used in the current
os. In this case, EmbeddedFiles are 'enabled', meaning that they have
temp_path_ saved so that they know where the inzip file is.
3. Each inset maintains its own EmbeddedFile(s), but insets usually do
*not* enable/disable an embedded file. This is because embedded files
are enabled/disabled when a buffer is loaded or when embedded is
disabled/enabled, through buffer-level register/enable/update process.
An exception is when an inset does not 'keep' an EmbeddedFile, such as
InsetInclude, in which an EmbeddedFile is created on-the-fly.
4. When an inset is added, a temporary EmbeddedFile is created, and
its enable() function is called. Here, file extract/update may happen,
and the file will fail to embed if an exception is thrown. Only when
an embedded file is successfully enabled, can it be copied to an
inset. When an embedded file is updated (say, setEmbed), enable will
be called. Again, update will fail if an exception is called. This is
why I handle EmbeddedFile update in GuiBlah, not InsetBlah, because in
this way, all EmbeddedFile returned from GuiBlah will be valid, and
with files in place.
The problem you see is because you want to enable an EmbeddedFile at
the inset level. I am reading your patch and hopefully can make it
work.
Cheers,
Bo