diff OrthancFramework/Sources/Compression/ZipWriter.h @ 4670:b12faca76a52

support of output streams in ZipWriter
author Sebastien Jodogne <s.jodogne@gmail.com>
date Fri, 28 May 2021 18:26:40 +0200
parents d9473bd5ed43
children d9942d48fea7
line wrap: on
line diff
--- a/OrthancFramework/Sources/Compression/ZipWriter.h	Fri May 28 11:40:47 2021 +0200
+++ b/OrthancFramework/Sources/Compression/ZipWriter.h	Fri May 28 18:26:40 2021 +0200
@@ -32,6 +32,13 @@
 #  error ZLIB support must be enabled to include this file
 #endif
 
+#if ORTHANC_BUILD_UNIT_TESTS == 1
+#  include <gtest/gtest_prod.h>
+#endif
+
+#include "../ChunkedBuffer.h"
+#include "../Compatibility.h"
+
 
 #include <stdint.h>
 #include <string>
@@ -42,7 +49,75 @@
 {
   class ORTHANC_PUBLIC ZipWriter : public boost::noncopyable
   {
+#if ORTHANC_BUILD_UNIT_TESTS == 1
+    FRIEND_TEST(ZipWriter, BufferWithSeek);
+#endif
+
+  public:
+    // New in Orthanc 1.9.4
+    class ORTHANC_PUBLIC IOutputStream : public boost::noncopyable
+    {
+    public:
+      virtual ~IOutputStream()
+      {
+      }
+
+      virtual void Write(const std::string& chunk) = 0;
+
+      virtual void Close() = 0;
+    };
+
+
+    // The lifetime of the "target" buffer must be larger than that of ZipWriter
+    class ORTHANC_PUBLIC MemoryStream : public IOutputStream
+    {
+    private:
+      std::string&   target_;
+      ChunkedBuffer  chunked_;
+      
+    public:
+      MemoryStream(std::string& target);
+      
+      virtual void Write(const std::string& chunk) ORTHANC_OVERRIDE;
+      
+      virtual void Close() ORTHANC_OVERRIDE;
+    };
+
+
   private:
+    // This class is only public for unit tests
+    class ORTHANC_PUBLIC BufferWithSeek : public boost::noncopyable
+    {
+    private:
+      size_t         currentPosition_;
+      ChunkedBuffer  chunks_;
+      std::string    flattened_;
+
+      void CheckInvariants() const;
+  
+    public:
+      BufferWithSeek();
+
+      ~BufferWithSeek();
+
+      size_t GetPosition() const;
+  
+      size_t GetSize() const;
+
+      void Write(const void* data,
+                 size_t size);
+
+      void Write(const std::string& data);
+
+      void Seek(size_t position);
+
+      void Flush(std::string& target);
+    };
+
+    
+  private:
+    class StreamBuffer;
+    
     struct PImpl;
     boost::shared_ptr<PImpl> pimpl_;
 
@@ -52,6 +127,8 @@
     uint8_t compressionLevel_;
     std::string path_;
 
+    std::unique_ptr<IOutputStream> outputStream_;
+
   public:
     ZipWriter();
 
@@ -84,5 +161,10 @@
     void Write(const void* data, size_t length);
 
     void Write(const std::string& data);
+
+    void AcquireOutputStream(IOutputStream* stream);  // transfers ownership
+
+    // The lifetime of the "target" buffer must be larger than that of ZipWriter
+    void SetMemoryOutput(std::string& target);
   };
 }