View Javadoc
1   /*
2    * Copyright (c) 2002-2025 Gargoyle Software Inc.
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    * You may obtain a copy of the License at
7    * https://www.apache.org/licenses/LICENSE-2.0
8    *
9    * Unless required by applicable law or agreed to in writing, software
10   * distributed under the License is distributed on an "AS IS" BASIS,
11   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12   * See the License for the specific language governing permissions and
13   * limitations under the License.
14   */
15  package org.htmlunit.attachment;
16  
17  import java.io.File;
18  import java.net.URL;
19  import java.util.ArrayList;
20  import java.util.Collection;
21  import java.util.List;
22  
23  import org.apache.commons.io.FileUtils;
24  import org.htmlunit.MockWebConnection;
25  import org.htmlunit.Page;
26  import org.htmlunit.SimpleWebTestCase;
27  import org.htmlunit.WebClient;
28  import org.htmlunit.html.HtmlAnchor;
29  import org.htmlunit.html.HtmlPage;
30  import org.htmlunit.util.MimeType;
31  import org.htmlunit.util.NameValuePair;
32  import org.junit.jupiter.api.Test;
33  
34  /**
35   * Tests for {@link DownloadingAttachmentHandler}.
36   *
37   * @author Marek Andreansky
38   * @author Ronald Brill
39   */
40  public class DownloadingAttachmentHandlerTest extends SimpleWebTestCase {
41  
42      /**
43       * @throws Exception if an error occurs
44       */
45      @Test
46      public void basic() throws Exception {
47          final String content1 = DOCTYPE_HTML
48              + "<html><body>\n"
49              + "<form method='POST' name='form' action='" + URL_SECOND + "'>\n"
50              + "<input type='submit' value='ok'>\n"
51              + "</form>\n"
52              + "<a href='#' onclick='document.form.submit()'>click me</a>\n"
53              + "</body></html>";
54          final String content2 = "download file contents";
55  
56          final File tmpFolder = new File(System.getProperty("java.io.tmpdir"));
57          final File downloadFolder = new File(tmpFolder, "downloading-attachment-test");
58  
59          try {
60              FileUtils.forceMkdir(downloadFolder);
61  
62              assertEquals(0, FileUtils.listFiles(downloadFolder, null, false).size());
63  
64              final WebClient client = getWebClient();
65              client.setAttachmentHandler(new DownloadingAttachmentHandler(downloadFolder.toPath()));
66  
67              final List<NameValuePair> headers = new ArrayList<>();
68              headers.add(new NameValuePair("Content-Disposition", "attachment"));
69  
70              final MockWebConnection conn = new MockWebConnection();
71              conn.setResponse(URL_FIRST, content1);
72              conn.setResponse(URL_SECOND, content2, 200, "OK", MimeType.TEXT_HTML, headers);
73              client.setWebConnection(conn);
74  
75              final HtmlPage result = client.getPage(URL_FIRST);
76              final HtmlAnchor anchor = result.getAnchors().get(0);
77              final Page clickResult = anchor.click();
78              assertEquals(result, clickResult);
79  
80              Collection<File> files = FileUtils.listFiles(downloadFolder, null, false);
81              assertEquals(1, files.size());
82              assertEquals("download", files.iterator().next().getName());
83  
84              anchor.click();
85              files = FileUtils.listFiles(downloadFolder, null, false);
86              assertEquals(2, files.size());
87  
88              // be order agnostic
89              assertTrue(files.removeIf(f -> f.getName().equals("download")));
90              assertTrue(files.removeIf(f -> f.getName().equals("download(1)")));
91              assertEquals(0, files.size());
92          }
93          finally {
94              FileUtils.deleteDirectory(downloadFolder);
95          }
96      }
97  
98      /**
99       * @throws Exception if an error occurs
100      */
101     @Test
102     public void basicFileNameFromUrl() throws Exception {
103         final String content1 = DOCTYPE_HTML
104             + "<html><body>\n"
105             + "<form method='POST' name='form' action='" + URL_SECOND + "test.txt'>\n"
106             + "<input type='submit' value='ok'>\n"
107             + "</form>\n"
108             + "<a href='#' onclick='document.form.submit()'>click me</a>\n"
109             + "</body></html>";
110         final String content2 = "download file contents";
111 
112         final File tmpFolder = new File(System.getProperty("java.io.tmpdir"));
113         final File downloadFolder = new File(tmpFolder, "downloading-attachment-test");
114 
115         try {
116             FileUtils.forceMkdir(downloadFolder);
117 
118             assertEquals(0, FileUtils.listFiles(downloadFolder, null, false).size());
119 
120             final WebClient client = getWebClient();
121             client.setAttachmentHandler(new DownloadingAttachmentHandler(downloadFolder.toPath()));
122 
123             final List<NameValuePair> headers = new ArrayList<>();
124             headers.add(new NameValuePair("Content-Disposition", "attachment"));
125 
126             final MockWebConnection conn = new MockWebConnection();
127             conn.setResponse(URL_FIRST, content1);
128             conn.setResponse(new URL(URL_SECOND, "test.txt"), content2, 200, "OK", MimeType.TEXT_HTML, headers);
129             client.setWebConnection(conn);
130 
131             final HtmlPage result = client.getPage(URL_FIRST);
132             final HtmlAnchor anchor = result.getAnchors().get(0);
133             final Page clickResult = anchor.click();
134             assertEquals(result, clickResult);
135 
136             Collection<File> files = FileUtils.listFiles(downloadFolder, null, false);
137             assertEquals(1, files.size());
138             assertEquals("test.txt", files.iterator().next().getName());
139 
140             anchor.click();
141             files = FileUtils.listFiles(downloadFolder, null, false);
142             assertEquals(2, files.size());
143 
144             // be order agnostic
145             assertTrue(files.removeIf(f -> f.getName().equals("test.txt")));
146             assertTrue(files.removeIf(f -> f.getName().equals("test(1).txt")));
147             assertEquals(0, files.size());
148         }
149         finally {
150             FileUtils.deleteDirectory(downloadFolder);
151         }
152     }
153 
154     /**
155      * @throws Exception if an error occurs
156      */
157     @Test
158     public void basicFileNameFromHeader() throws Exception {
159         final String content1 = DOCTYPE_HTML
160             + "<html><body>\n"
161             + "<form method='POST' name='form' action='" + URL_SECOND + "test.txt'>\n"
162             + "<input type='submit' value='ok'>\n"
163             + "</form>\n"
164             + "<a href='#' onclick='document.form.submit()'>click me</a>\n"
165             + "</body></html>";
166         final String content2 = "download file contents";
167 
168         final File tmpFolder = new File(System.getProperty("java.io.tmpdir"));
169         final File downloadFolder = new File(tmpFolder, "downloading-attachment-test");
170         FileUtils.deleteDirectory(downloadFolder);
171 
172         try {
173             FileUtils.forceMkdir(downloadFolder);
174 
175             assertEquals(0, FileUtils.listFiles(downloadFolder, null, false).size());
176 
177             final WebClient client = getWebClient();
178             client.setAttachmentHandler(new DownloadingAttachmentHandler(downloadFolder.toPath()));
179 
180             final List<NameValuePair> headers = new ArrayList<>();
181             headers.add(new NameValuePair("Content-Disposition", "attachment; filename=sample.pdf"));
182 
183             final MockWebConnection conn = new MockWebConnection();
184             conn.setResponse(URL_FIRST, content1);
185             conn.setResponse(new URL(URL_SECOND, "test.txt"), content2, 200, "OK", MimeType.TEXT_HTML, headers);
186             client.setWebConnection(conn);
187 
188             final HtmlPage result = client.getPage(URL_FIRST);
189             final HtmlAnchor anchor = result.getAnchors().get(0);
190             final Page clickResult = anchor.click();
191             assertEquals(result, clickResult);
192 
193             Collection<File> files = FileUtils.listFiles(downloadFolder, null, false);
194             assertEquals(1, files.size());
195             assertEquals("sample.pdf", files.iterator().next().getName());
196 
197             anchor.click();
198             files = FileUtils.listFiles(downloadFolder, null, false);
199             assertEquals(2, files.size());
200 
201             // be order agnostic
202             assertTrue(files.removeIf(f -> f.getName().equals("sample.pdf")));
203             assertTrue(files.removeIf(f -> f.getName().equals("sample(1).pdf")));
204             assertEquals(0, files.size());
205         }
206         finally {
207             FileUtils.deleteDirectory(downloadFolder);
208         }
209     }
210 }