1 /*
2  * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License").
5  * You may not use this file except in compliance with the License.
6  * A copy of the License is located at
7  *
8  *  http://aws.amazon.com/apache2.0
9  *
10  * or in the "license" file accompanying this file. This file is distributed
11  * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
12  * express or implied. See the License for the specific language governing
13  * permissions and limitations under the License.
14  */
15 
16 package software.amazon.awssdk.testutils;
17 
18 import java.io.BufferedOutputStream;
19 import java.io.File;
20 import java.io.FileOutputStream;
21 import java.io.IOException;
22 import java.io.InputStream;
23 import java.util.UUID;
24 import org.slf4j.Logger;
25 import org.slf4j.LoggerFactory;
26 import software.amazon.awssdk.utils.JavaSystemSetting;
27 
28 /**
29  * Extension of File that creates a temporary file with a specified name in
30  * Java's temporary directory, as declared in the JRE's system properties. The
31  * file is immediately filled with a specified amount of random ASCII data.
32  *
33  * @see RandomInputStream
34  */
35 public class RandomTempFile extends File {
36 
37     private static final Logger log = LoggerFactory.getLogger(RandomTempFile.class);
38     private static final long serialVersionUID = -8232143353692832238L;
39 
40     /** Java temp dir where all temp files will be created. */
41     private static final String TEMP_DIR = JavaSystemSetting.TEMP_DIRECTORY.getStringValueOrThrow();
42 
43     /** Flag controlling whether binary or character data is used. */
44     private final boolean binaryData;
45 
46     /**
47      * Creates, and fills, a temp file with a randomly generated name and specified size of random ASCII data.
48      *
49      * @param sizeInBytes The amount of random ASCII data, in bytes, for the new temp
50      *                    file.
51      * @throws IOException If any problems were encountered creating the new temp file.
52      */
RandomTempFile(long sizeInBytes)53     public RandomTempFile(long sizeInBytes) throws IOException {
54         this(UUID.randomUUID().toString(), sizeInBytes, false);
55     }
56 
57     /**
58      * Creates, and fills, a temp file with the specified name and specified
59      * size of random ASCII data.
60      *
61      * @param filename
62      *            The name for the new temporary file, within the Java temp
63      *            directory as declared in the JRE's system properties.
64      * @param sizeInBytes
65      *            The amount of random ASCII data, in bytes, for the new temp
66      *            file.
67      *
68      * @throws IOException
69      *             If any problems were encountered creating the new temp file.
70      */
RandomTempFile(String filename, int sizeInBytes)71     public RandomTempFile(String filename, int sizeInBytes) throws IOException {
72         this(filename, sizeInBytes, false);
73     }
74 
75 
76     /**
77      * Creates, and fills, a temp file with the specified name and specified
78      * size of random ASCII data.
79      *
80      * @param filename
81      *            The name for the new temporary file, within the Java temp
82      *            directory as declared in the JRE's system properties.
83      * @param sizeInBytes
84      *            The amount of random ASCII data, in bytes, for the new temp
85      *            file.
86      *
87      * @throws IOException
88      *             If any problems were encountered creating the new temp file.
89      */
RandomTempFile(String filename, long sizeInBytes)90     public RandomTempFile(String filename, long sizeInBytes) throws IOException {
91         this(filename, sizeInBytes, false);
92     }
93 
94     /**
95      * Creates, and fills, a temp file with the specified name and specified
96      * size of random binary or character data.
97      *
98      * @param filename
99      *            The name for the new temporary file, within the Java temp
100      *            directory as declared in the JRE's system properties.
101      * @param sizeInBytes
102      *            The amount of random ASCII data, in bytes, for the new temp
103      *            file.
104      * @param binaryData Whether to fill the file with binary or character data.
105      *
106      * @throws IOException
107      *             If any problems were encountered creating the new temp file.
108      */
RandomTempFile(String filename, long sizeInBytes, boolean binaryData)109     public RandomTempFile(String filename, long sizeInBytes, boolean binaryData)
110             throws IOException {
111         super(TEMP_DIR + File.separator + System.currentTimeMillis() + "-"
112               + filename);
113         this.binaryData = binaryData;
114         createFile(sizeInBytes);
115         log.debug("RandomTempFile {} created", this);
116     }
117 
RandomTempFile(File root, String filename, long sizeInBytes)118     public RandomTempFile(File root, String filename, long sizeInBytes) throws IOException {
119         super(root, filename);
120         this.binaryData = false;
121         createFile(sizeInBytes);
122     }
123 
124 
createFile(long sizeInBytes)125     public void createFile(long sizeInBytes) throws IOException {
126         deleteOnExit();
127 
128         try (FileOutputStream outputStream = new FileOutputStream(this);
129              BufferedOutputStream bufferedOutputStream = new BufferedOutputStream(outputStream);
130              InputStream inputStream = new RandomInputStream(sizeInBytes, binaryData)) {
131             byte[] buffer = new byte[1024];
132             int bytesRead;
133             while ((bytesRead = inputStream.read(buffer)) > -1) {
134                 bufferedOutputStream.write(buffer, 0, bytesRead);
135             }
136         }
137     }
138 
139     @Override
delete()140     public boolean delete() {
141         if (!super.delete()) {
142             throw new RuntimeException("Could not delete: " + getAbsolutePath());
143         }
144         return true;
145     }
146 
randomUncreatedFile()147     public static File randomUncreatedFile() {
148         File random = new File(TEMP_DIR, UUID.randomUUID().toString());
149         random.deleteOnExit();
150         return random;
151     }
152 
153     @Override
equals(Object obj)154     public boolean equals(Object obj) {
155         return this == obj;
156     }
157 }
158