View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements. See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache license, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License. You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the license for the specific language governing permissions and
15   * limitations under the license.
16   */
17  package org.apache.logging.log4j.core.appender.rolling.action;
18  
19  import java.io.File;
20  import java.io.FileInputStream;
21  import java.io.FileOutputStream;
22  import java.io.IOException;
23  import java.util.zip.ZipEntry;
24  import java.util.zip.ZipOutputStream;
25  
26  
27  /**
28   * Compresses a file using Zip compression.
29   */
30  public final class ZipCompressAction extends AbstractAction {
31  
32      private static final int BUF_SIZE = 8102;
33  
34      /**
35       * Source file.
36       */
37      private final File source;
38  
39      /**
40       * Destination file.
41       */
42      private final File destination;
43  
44      /**
45       * If true, attempt to delete file on completion.
46       */
47      private final boolean deleteSource;
48  
49      /**
50       * Compression level.
51       */
52      private final int level;
53  
54      /**
55       * Create new instance of GzCompressAction.
56       *
57       * @param source       file to compress, may not be null.
58       * @param destination  compressed file, may not be null.
59       * @param deleteSource if true, attempt to delete file on completion.  Failure to delete
60       *                     does not cause an exception to be thrown or affect return value.
61       * @param level TODO
62       */
63      public ZipCompressAction(final File source, final File destination, final boolean deleteSource, final int level) {
64          if (source == null) {
65              throw new NullPointerException("source");
66          }
67  
68          if (destination == null) {
69              throw new NullPointerException("destination");
70          }
71  
72          this.source = source;
73          this.destination = destination;
74          this.deleteSource = deleteSource;
75          this.level = level;
76      }
77  
78      /**
79       * Compress.
80       *
81       * @return true if successfully compressed.
82       * @throws IOException on IO exception.
83       */
84      @Override
85      public boolean execute() throws IOException {
86          return execute(source, destination, deleteSource, level);
87      }
88  
89      /**
90       * Compress a file.
91       *
92       * @param source       file to compress, may not be null.
93       * @param destination  compressed file, may not be null.
94       * @param deleteSource if true, attempt to delete file on completion.  Failure to delete
95       *                     does not cause an exception to be thrown or affect return value.
96       * @param level the compression level
97       * @return true if source file compressed.
98       * @throws IOException on IO exception.
99       */
100     public static boolean execute(final File source, final File destination, final boolean deleteSource, final int level)
101         throws IOException {
102         if (source.exists()) {
103             final FileInputStream fis = new FileInputStream(source);
104             final FileOutputStream fos = new FileOutputStream(destination);
105             final ZipOutputStream zos = new ZipOutputStream(fos);
106             zos.setLevel(level);
107 
108             final ZipEntry zipEntry = new ZipEntry(source.getName());
109             zos.putNextEntry(zipEntry);
110 
111             final byte[] inbuf = new byte[BUF_SIZE];
112             int n;
113 
114             while ((n = fis.read(inbuf)) != -1) {
115                 zos.write(inbuf, 0, n);
116             }
117 
118             zos.close();
119             fis.close();
120 
121             if (deleteSource && !source.delete()) {
122                 LOGGER.warn("Unable to delete " + source.toString() + '.');
123             }
124 
125             return true;
126         }
127 
128         return false;
129     }
130 
131     /**
132      * Capture exception.
133      *
134      * @param ex exception.
135      */
136     @Override
137     protected void reportException(final Exception ex) {
138         LOGGER.warn("Exception during compression of '" + source.toString() + "'.", ex);
139     }
140 
141     @Override
142     public String toString() {
143         return ZipCompressAction.class.getSimpleName() + '[' + source + " to " + destination //
144                 + ", level=" + level + ", deleteSource=" + deleteSource + ']';
145     }
146 }