]> git.lyx.org Git - lyx.git/commitdiff
Embedding: prepare to read/write manifest in .lyx file
authorBo Peng <bpeng@lyx.org>
Mon, 10 Sep 2007 03:54:02 +0000 (03:54 +0000)
committerBo Peng <bpeng@lyx.org>
Mon, 10 Sep 2007 03:54:02 +0000 (03:54 +0000)
git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@20186 a592a061-630c-0410-9148-cb99ea01b6c8

src/Buffer.cpp
src/EmbeddedFiles.cpp
src/EmbeddedFiles.h
src/insets/InsetGraphics.cpp

index 404efdf6fb438651832f1b669c062f2732af6bf4..76cce2c544b72210b4288115fcad4822816c5a75 100644 (file)
@@ -669,12 +669,6 @@ bool Buffer::readFile(FileName const & filename)
                        fs::exists(lyxfile.toFilesystemEncoding())) {
                        params().embedded = true;
                        fname = lyxfile;
-                       // read manifest file
-                       ifstream is(manifest.toFilesystemEncoding().c_str());
-                       is >> pimpl_->embedded_files;
-                       is.close();
-                       LYXERR(Debug::FILES) << filename << " is a embedded file. Its manifest is:\n"
-                                       << pimpl_->embedded_files;
                }
        }
        // The embedded lyx file can also be compressed, for backward compatibility
index 2680f4d56329aca3293e04a95c40b22f6db7ecdb..155ed86ac787c1b57f58d669b59c9bc71f0bf482 100644 (file)
@@ -20,6 +20,8 @@
 #include "debug.h"
 #include "gettext.h"
 #include "Format.h"
+#include "Lexer.h"
+#include "ErrorList.h"
 
 #include "frontends/alert.h"
 
@@ -244,7 +246,7 @@ bool EmbeddedFiles::enable(bool flag)
 
 
 void EmbeddedFiles::registerFile(string const & filename,
-       bool embed, Inset const * inset)
+       bool embed, Inset const * inset, string const & inzipName)
 {
        // filename can be relative or absolute, translate to absolute filename
        string abs_filename = makeAbsPath(filename, buffer_->filePath()).absFilename();
@@ -257,18 +259,12 @@ void EmbeddedFiles::registerFile(string const & filename,
        // find this filename, keep the original embedding status
        if (it != file_list_.end()) {
                it->addInset(inset);
-               // if the file is embedded, the embedded file should have exist
-               // check for this to ensure that our logic is correct
-               if (it->embedded())
-                       BOOST_ASSERT(fs::exists(it->embeddedFile(buffer_)));
                it->validate();
                return;
        }
        // try to be more careful
        file_list_.push_back(EmbeddedFile(abs_filename, 
-               getInzipName(abs_filename), embed, inset));
-       // validate if things are OK
-       BOOST_ASSERT(fs::exists(file_list_.back().availableFile(buffer_)));
+               getInzipName(abs_filename, inzipName), embed, inset));
 }
 
 
@@ -287,10 +283,6 @@ void EmbeddedFiles::update()
 
        for (InsetIterator it = inset_iterator_begin(buffer_->inset()); it; ++it)
                it->registerEmbeddedFiles(*buffer_, *this);
-
-       LYXERR(Debug::FILES) << "Manifest updated: " << endl
-               << *this
-               << "End Manifest" << endl;
 }
 
 
@@ -298,17 +290,11 @@ bool EmbeddedFiles::write(DocFileName const & filename)
 {
        // file in the temporary path has the content
        string const content = FileName(addName(buffer_->temppath(),
-               onlyFilename(filename.toFilesystemEncoding()))).toFilesystemEncoding();
+               "content.lyx")).toFilesystemEncoding();
 
-       // get a file list and write a manifest file
        vector<pair<string, string> > filenames;
-       string const manifest = FileName(
-               addName(buffer_->temppath(), "manifest.txt")).toFilesystemEncoding();
-
-       // write a manifest file
-       ofstream os(manifest.c_str());
-       os << *this;
-       os.close();
+       // add content.lyx to filenames
+       filenames.push_back(make_pair(content, "content.lyx"));
        // prepare list of embedded file
        EmbeddedFileList::iterator it = file_list_.begin();
        EmbeddedFileList::iterator it_end = file_list_.end();
@@ -321,9 +307,6 @@ bool EmbeddedFiles::write(DocFileName const & filename)
                                filenames.push_back(make_pair(file, it->inzipName()));
                }
        }
-       // add filename (.lyx) and manifest to filenames
-       filenames.push_back(make_pair(content, onlyFilename(filename.toFilesystemEncoding())));
-       filenames.push_back(make_pair(manifest, "manifest.txt"));
        // write a zip file with all these files. Write to a temp file first, to
        // avoid messing up the original file in case something goes terribly wrong.
        DocFileName zipfile(addName(buffer_->temppath(),
@@ -380,11 +363,13 @@ bool EmbeddedFiles::updateFromExternalFile() const
 }
 
 
-string const EmbeddedFiles::getInzipName(string const & abs_filename)
+string const EmbeddedFiles::getInzipName(string const & abs_filename, string const & name)
 {
        // register a new one, using relative file path as inzip_name
-       string inzip_name = to_utf8(makeRelPath(from_utf8(abs_filename),
-               from_utf8(buffer_->fileName())));
+       string inzip_name = name;
+       if (name.empty())
+               inzip_name = to_utf8(makeRelPath(from_utf8(abs_filename),
+                       from_utf8(buffer_->filePath())));
        // if inzip_name is an absolute path, use filename only to avoid
        // leaking of filesystem information in inzip_name
        // The second case covers cases '../path/file' and '.'
@@ -413,81 +398,74 @@ string const EmbeddedFiles::getInzipName(string const & abs_filename)
 }
 
 
-istream & operator>> (istream & is, EmbeddedFiles & files)
+bool EmbeddedFiles::readManifest(Lexer & lex, ErrorList & errorList)
 {
-       files.clear();
-       string tmp;
-       getline(is, tmp);
-       // get version
-       istringstream itmp(tmp);
-       int version;
-       itmp.ignore(string("# LyX manifest version ").size());
-       itmp >> version;
-
-       if (version != 1) {
-               lyxerr << "This version of LyX can only read LyX manifest version 1" << endl;
-               return is;
-       }
+       int line = -1;
+       int begin_manifest_line = -1;
 
-       getline(is, tmp);
-       if (tmp != "<manifest>") {
-               lyxerr << "Invalid manifest file, lacking <manifest>" << endl;
-               return is;
-       }
-       // manifest file may be messed up, be carefully
-       while (is.good()) {
-               getline(is, tmp);
-               if (tmp != "<file>")
-                       break;
+       file_list_.clear();
+       string filename = "";
+       string inzipName = "";
+       bool status = "";
+
+       while (lex.isOK()) {
+               lex.next();
+               string const token = lex.getString();
+
+               if (token.empty())
+                       continue;
 
-               string fname;
-               getline(is, fname);
-               string inzip_name;
-               getline(is, inzip_name);
-               getline(is, tmp);
-               istringstream itmp(tmp);
-               int embed;
-               itmp >> embed;
-
-               getline(is, tmp);
-               if (tmp != "</file>") {
-                       lyxerr << "Invalid manifest file, lacking </file>" << endl;
+               if (token == "\\end_manifest")
                        break;
-               }
 
-               files.registerFile(fname, embed);
-       };
-       // the last line must be </manifest>
-       if (tmp != "</manifest>") {
-               lyxerr << "Invalid manifest file, lacking </manifest>" << endl;
-               return is;
+               ++line;
+               if (token == "\\begin_manifest") {
+                       begin_manifest_line = line;
+                       continue;
+               }
+               
+               LYXERR(Debug::PARSER) << "Handling document manifest token: `"
+                                     << token << '\'' << endl;
+
+               if (token == "\\filename")
+                       lex >> filename;
+               else if (token == "\\inzipName")
+                       lex >> inzipName;
+               else if (token == "\\status") {
+                       lex >> status;
+                       registerFile(filename, status, NULL, inzipName);
+                       filename = "";
+                       inzipName = "";
+               } else {
+                       docstring const s = _("\\begin_file is missing");
+                       errorList.push_back(ErrorItem(_("Manifest error"),
+                               s, -1, 0, 0));
+               }
+       }
+       if (begin_manifest_line) {
+               docstring const s = _("\\begin_manifest is missing");
+               errorList.push_back(ErrorItem(_("Manifest error"),
+                       s, -1, 0, 0));
        }
-       return is;
+       return true;
 }
 
 
-ostream & operator<< (ostream & os, EmbeddedFiles const & files)
+void EmbeddedFiles::writeManifest(ostream & os) const
 {
-       // store a version so that operator >> can read later versions
-       // using version information.
-       os << "# lyx manifest version 1\n";
-       os << "<manifest>\n";
-       EmbeddedFiles::EmbeddedFileList::const_iterator it = files.begin();
-       EmbeddedFiles::EmbeddedFileList::const_iterator it_end = files.end();
+       EmbeddedFiles::EmbeddedFileList::const_iterator it = begin();
+       EmbeddedFiles::EmbeddedFileList::const_iterator it_end = end();
        for (; it != it_end; ++it) {
                if (!it->valid())
                        continue;
-               // use differnt lines to make reading easier.
-               os << "<file>\n"
-                       // save the relative path
+               // save the relative path
+               os << "\\filename "
                        << to_utf8(makeRelPath(from_utf8(it->absFilename()),
-                               from_utf8(files.buffer_->filePath()))) << '\n'
-                       << it->inzipName() << '\n'
-                       << it->embedded() << '\n'
-                       << "</file>\n";
+                               from_utf8(buffer_->filePath()))) << '\n'
+                       << "\\inzipName " << it->inzipName() << '\n'
+                       << "\\status " << (it->embedded() ? "true" : "false") << '\n';
        }
-       os << "</manifest>\n";
-       return os;
 }
 
+
 }
index df8915e6bb932acf78602f2928e493c2476160ad..58b1a08b1a9501264431267f153c077299e679f3 100644 (file)
@@ -107,6 +107,8 @@ embedded file (check path == temppath()), if so, save filename() instead.
 namespace lyx {
 
 class Buffer;
+class Lexer;
+class ErrorList;
 
 class EmbeddedFile : public support::DocFileName
 {
@@ -186,10 +188,12 @@ public:
        /* \param filename filename to add
         * \param embed embedding status. For a new file item, this is always true.
         *    If the file already exists, this parameter is ignored.
-        * \param pit paragraph id.
+        * \param inset Inset pointer
+        * \param inzipName suggested inzipname
         */
        void registerFile(std::string const & filename, bool embed = false,
-               Inset const * inset = NULL);
+               Inset const * inset = NULL,
+               std::string const & inzipName = std::string());
 
        /// scan the buffer and get a list of EmbeddedFile
        void update();
@@ -214,12 +218,11 @@ public:
        /// update all files from external, used when enable embedding
        bool updateFromExternalFile() const;
        ///
-       friend std::istream & operator>> (std::istream & is, EmbeddedFiles &);
-
-       friend std::ostream & operator<< (std::ostream & os, EmbeddedFiles const &);
+       bool readManifest(Lexer & lex, ErrorList & errorList);
+       void writeManifest(std::ostream & os) const;
 private:
-       /// get a unique inzip name
-       std::string const getInzipName(std::string const & name);
+       /// get a unique inzip name, a suggestion can be given.
+       std::string const getInzipName(std::string const & name, std::string const & inzipName);
        /// list of embedded files
        EmbeddedFileList file_list_;
        ///
@@ -227,9 +230,5 @@ private:
 };
 
 
-std::istream & operator>> (std::istream & is, EmbeddedFiles &);
-
-std::ostream & operator<< (std::ostream & os, EmbeddedFiles const &);
-
 }
 #endif
index a54de14c98aabbedb3d3d5791460a78457f4e45f..70cfe9767d719a3d35a8a24788fe9cca231b2310 100644 (file)
@@ -285,11 +285,14 @@ void InsetGraphics::read(Buffer const & buf, Lexer & lex)
 
        // InsetGraphics is read, with filename in params_. We do not know if this file actually
        // exists or is embedded so we need to get the 'availableFile' from buf.embeddedFiles()
-       EmbeddedFiles::EmbeddedFileList::const_iterator it = buf.embeddedFiles().find(params_.filename.toFilesystemEncoding());
-       if (it != buf.embeddedFiles().end())
-               // using available file, embedded or external, depending on file availability and
-               // embedding status.
-               params_.filename = DocFileName(it->availableFile(&buf));
+       if (buf.embeddedFiles().enabled()) {
+               EmbeddedFiles::EmbeddedFileList::const_iterator it = 
+                       buf.embeddedFiles().find(params_.filename.toFilesystemEncoding());
+               if (it != buf.embeddedFiles().end())
+                       // using available file, embedded or external, depending on file availability and
+                       // embedding status.
+                       params_.filename = DocFileName(it->availableFile(&buf));
+       }
        graphic_->update(params().as_grfxParams());
 }