コード例 #1
0
        /// <summary>
        /// Extracts the specified zip file stream.
        /// </summary>
        /// <param name="fileStream">The zip file stream.</param>
        /// <returns></returns>
        public bool Extract(Stream fileStream) {
            if (null == fileStream) return false;

            CleanFromTemp();

            NewTempPath();

            _isValid = true;

            ZipFile zipFile = null;

            try {
                zipFile = new ZipFile(fileStream);

                var enumerator = zipFile.GetEnumerator();

                while (enumerator.MoveNext()) {
                    var entry = (ZipEntry)enumerator.Current;

                    ExtractZipEntry(zipFile, entry);
                }
            } catch (Exception ex) {
                _isValid = false;
                _exceptionMessage = ex.Message;

                CleanFromTemp();
            } finally {
                fileStream.Close();

                if (null != zipFile) zipFile.Close();
            }

            return _isValid ? CheckFolderTree() : false;
        }
コード例 #2
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		/// <summary>
		/// Create a new <see cref="ZipFile"/> whose data will be stored on a stream.
		/// </summary>
		/// <param name="outStream">The stream providing data storage.</param>
		/// <returns>Returns the newly created <see cref="ZipFile"/></returns>
		/// <exception cref="ArgumentNullException"><paramref name="outStream"> is null</paramref></exception>
		/// <exception cref="ArgumentException"><paramref name="outStream"> doesnt support writing.</paramref></exception>
		public static ZipFile Create(Stream outStream)
		{
			if ( outStream == null ) {
				throw new ArgumentNullException("outStream");
			}

			if ( !outStream.CanWrite ) {
				throw new ArgumentException("Stream is not writeable", "outStream");
			}

			if ( !outStream.CanSeek ) {
				throw new ArgumentException("Stream is not seekable", "outStream");
			}

			var result = new ZipFile();
			result.baseStream_ = outStream;
			return result;
		}
コード例 #3
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		/// <summary>
		/// Create a new <see cref="ZipFile"/> whose data will be stored in a file.
		/// </summary>
		/// <param name="fileName">The name of the archive to create.</param>
		/// <returns>Returns the newly created <see cref="ZipFile"/></returns>
		/// <exception cref="ArgumentNullException"><paramref name="fileName"></paramref> is null</exception>
		public static ZipFile Create(string fileName)
		{
			if ( fileName == null ) {
				throw new ArgumentNullException("fileName");
			}

			var fs = File.Create(fileName);
			
			var result = new ZipFile();
			result.name_ = fileName;
			result.baseStream_ = fs;
			result.isStreamOwner = true;
			return result;
		}
コード例 #4
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
	    /// <summary>
	    /// Initializes a new instance of the <see cref="DiskArchiveStorage"/> class.
	    /// </summary>
	    /// <param name="file">The file.</param>
	    public DiskArchiveStorage(ZipFile file)
	        : this(file, FileUpdateMode.Safe)
	    {
	    }
コード例 #5
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
	    /// <summary>
	    /// Initializes a new instance of the <see cref="DiskArchiveStorage"/> class.
	    /// </summary>
	    /// <param name="file">The file.</param>
	    /// <param name="updateMode">The update mode.</param>
	    public DiskArchiveStorage(ZipFile file, FileUpdateMode updateMode)
	        : base(updateMode)
	    {
	        if ( file.Name == null ) {
	            throw new ZipException("Cant handle non file archives");
	        }

	        fileName_ = file.Name;
	    }
コード例 #6
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
			/// <summary>
			/// Initialise a new instance of the <see cref="PartialInputStream"/> class.
			/// </summary>
			/// <param name="zipFile">The <see cref="ZipFile"/> containing the underlying stream to use for IO.</param>
			/// <param name="start">The start of the partial data.</param>
			/// <param name="length">The length of the partial data.</param>
			public PartialInputStream(ZipFile zipFile, long start, long length)
			{
				start_ = start;
				length_ = length;

				// Although this is the only time the zipfile is used
				// keeping a reference here prevents premature closure of
				// this zip file and thus the baseStream_.

				// Code like this will cause apparently random failures depending
				// on the size of the files and when garbage is collected.
				//
				// ZipFile z = new ZipFile (stream);
				// Stream reader = z.GetInputStream(0);
				// uses reader here....
				zipFile_ = zipFile;
				baseStream_ = zipFile_.baseStream_;
				readPos_ = start;
				end_ = start + length;
			}
コード例 #7
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		void CopyEntry(ZipFile workFile, ZipUpdate update)
		{
			workFile.WriteLocalEntryHeader(update);

			if ( update.Entry.CompressedSize > 0 ) {
				const int NameLengthOffset = 26;

				var entryDataOffset = update.Entry.Offset + NameLengthOffset;

				// TODO: This wont work for SFX files!
				baseStream_.Seek(entryDataOffset, SeekOrigin.Begin);

				uint nameLength = ReadLEUshort();
				uint extraLength = ReadLEUshort();

				baseStream_.Seek(nameLength + extraLength, SeekOrigin.Current);

				CopyBytes(update, workFile.baseStream_, baseStream_, update.Entry.CompressedSize, false);
			}
			CopyDescriptorBytes(update, workFile.baseStream_, baseStream_);
		}
コード例 #8
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		void CopyEntryDirect(ZipFile workFile, ZipUpdate update, ref long destinationPosition)
		{
			var skipOver = false;
			if ( update.Entry.Offset == destinationPosition ) {
				skipOver = true;
			}

			if ( !skipOver ) {
				baseStream_.Position = destinationPosition;
				workFile.WriteLocalEntryHeader(update);
				destinationPosition = baseStream_.Position;
			}

			long sourcePosition = 0;

			const int NameLengthOffset = 26;

			// TODO: Add base for SFX friendly handling
			var entryDataOffset = update.Entry.Offset + NameLengthOffset;

			baseStream_.Seek(entryDataOffset, SeekOrigin.Begin);

			// Clumsy way of handling retrieving the original name and extra data length for now.
			// TODO: Stop re-reading name and data length in CopyEntryDirect.
			uint nameLength = ReadLEUshort();
			uint extraLength = ReadLEUshort();

			sourcePosition = baseStream_.Position + nameLength + extraLength;

			if (skipOver) {
				if (update.OffsetBasedSize != -1)
					destinationPosition += update.OffsetBasedSize;
				else
					// TODO: Find out why this calculation comes up 4 bytes short on some entries in ODT (Office Document Text) archives.
					// WinZip produces a warning on these entries:
					// "caution: value of lrec.csize (compressed size) changed from ..."
					destinationPosition +=
						(sourcePosition - entryDataOffset) + NameLengthOffset +	// Header size
						update.Entry.CompressedSize + GetDescriptorSize(update);
			}
			else {
				if ( update.Entry.CompressedSize > 0 ) {
					CopyEntryDataDirect(update, baseStream_, false, ref destinationPosition, ref sourcePosition );
				}
				CopyDescriptorBytesDirect(update, baseStream_, ref destinationPosition, sourcePosition);
			}
		}
コード例 #9
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		void ModifyEntry(ZipFile workFile, ZipUpdate update)
		{
			workFile.WriteLocalEntryHeader(update);
			var dataStart = workFile.baseStream_.Position;

			// TODO: This is slow if the changes don't effect the data!!
			if ( update.Entry.IsFile && (update.Filename != null) ) {
				using ( var output = workFile.GetOutputStream(update.OutEntry) ) {
					using ( var source = GetInputStream(update.Entry) ) {
						CopyBytes(update, output, source, source.Length, true);
					}
				}
			}

			var dataEnd = workFile.baseStream_.Position;
			update.Entry.CompressedSize = dataEnd - dataStart;
		}
コード例 #10
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
		void AddEntry(ZipFile workFile, ZipUpdate update)
		{
			Stream source = null;

			if ( update.Entry.IsFile ) {
				source = update.GetSource();
				
				if ( source == null ) {
					source = updateDataSource_.GetSource(update.Entry, update.Filename);
				}
			}

			if ( source != null ) {
				using ( source ) {
					var sourceStreamLength = source.Length;
					if ( update.OutEntry.Size < 0 ) {
						update.OutEntry.Size = sourceStreamLength;
					}
					else {
						// Check for errant entries.
						if ( update.OutEntry.Size != sourceStreamLength ) {
							throw new ZipException("Entry size/stream size mismatch");
						}
					}

					workFile.WriteLocalEntryHeader(update);

					var dataStart = workFile.baseStream_.Position;

					using ( var output = workFile.GetOutputStream(update.OutEntry) ) {
						CopyBytes(update, output, source, sourceStreamLength, true);
					}

					var dataEnd = workFile.baseStream_.Position;
					update.OutEntry.CompressedSize = dataEnd - dataStart;

					if ((update.OutEntry.Flags & (int)GeneralBitFlags.Descriptor) == (int)GeneralBitFlags.Descriptor)
					{
						var helper = new ZipHelperStream(workFile.baseStream_);
						helper.WriteDataDescriptor(update.OutEntry);
					}
				}
			}
			else {
				workFile.WriteLocalEntryHeader(update);
				update.OutEntry.CompressedSize = 0;
			}

		}
コード例 #11
0
ファイル: ZipFile.cs プロジェクト: modulexcite/Transformalize
	    /// <summary>
	    /// Initialise a new instance of <see cref="TestStatus"/>
	    /// </summary>
	    /// <param name="file">The <see cref="ZipFile"/> this status applies to.</param>
	    public TestStatus(ZipFile file)
	    {
	        file_ = file;
	    }
コード例 #12
0
ファイル: FastZip.cs プロジェクト: modulexcite/Transformalize
		/// <summary>
		/// Extract the contents of a zip file held in a stream.
		/// </summary>
		/// <param name="inputStream">The seekable input stream containing the zip to extract from.</param>
		/// <param name="targetDirectory">The directory to save extracted information in.</param>
		/// <param name="overwrite">The style of <see cref="Overwrite">overwriting</see> to apply.</param>
		/// <param name="confirmDelegate">A delegate to invoke when confirming overwriting.</param>
		/// <param name="fileFilter">A filter to apply to files.</param>
		/// <param name="directoryFilter">A filter to apply to directories.</param>
		/// <param name="restoreDateTime">Flag indicating whether to restore the date and time for extracted files.</param>
		/// <param name="isStreamOwner">Flag indicating whether the inputStream will be closed by this method.</param>
		public void ExtractZip(Stream inputStream, string targetDirectory,
					   Overwrite overwrite, ConfirmOverwriteDelegate confirmDelegate,
					   string fileFilter, string directoryFilter, bool restoreDateTime,
					   bool isStreamOwner)
		{
			if ((overwrite == Overwrite.Prompt) && (confirmDelegate == null)) {
				throw new ArgumentNullException("confirmDelegate");
			}

			continueRunning_ = true;
			overwrite_ = overwrite;
			confirmDelegate_ = confirmDelegate;
			extractNameTransform_ = new WindowsNameTransform(targetDirectory);

			fileFilter_ = new NameFilter(fileFilter);
			directoryFilter_ = new NameFilter(directoryFilter);
			restoreDateTimeOnExtract_ = restoreDateTime;

			using (zipFile_ = new ZipFile(inputStream)) {

#if !NETCF_1_0
				if (password_ != null) {
					zipFile_.Password = password_;
				}
#endif
				zipFile_.IsStreamOwner = isStreamOwner;
				var enumerator = zipFile_.GetEnumerator();
				while (continueRunning_ && enumerator.MoveNext()) {
					var entry = (ZipEntry)enumerator.Current;
					if (entry.IsFile)
					{
						// TODO Path.GetDirectory can fail here on invalid characters.
						if (directoryFilter_.IsMatch(Path.GetDirectoryName(entry.Name)) && fileFilter_.IsMatch(entry.Name)) {
							ExtractEntry(entry);
						}
					}
					else if (entry.IsDirectory) {
						if (directoryFilter_.IsMatch(entry.Name) && CreateEmptyDirectories) {
							ExtractEntry(entry);
						}
					}
					else {
						// Do nothing for volume labels etc...
					}
				}
			}
		}
コード例 #13
0
        private void ExtractZipEntry(ZipFile zipFile, ZipEntry entry) {
            if (!entry.IsCompressionMethodSupported() || string.IsNullOrEmpty(entry.Name)) return;

            var tPath = Path.Combine(_tempPath, entry.Name);
            var path = entry.IsDirectory ? tPath : Path.GetDirectoryName(Path.GetFullPath(tPath));

            if (!Directory.Exists(path)) {
                Directory.CreateDirectory(path);
            }

            if (!entry.IsFile) return;

            try {
                using (var stream = File.Create(tPath)) {
                    if (buffer == null) {
                        buffer = new byte[0x1000];
                    }

                    var inputStream = zipFile.GetInputStream(entry);

                    int count;
                    while ((count = inputStream.Read(buffer, 0, buffer.Length)) > 0) {
                        stream.Write(buffer, 0, count);
                    }

                    stream.Flush();
                }
            } catch {
                throw;
            }
        }