Skip to content

Commit 43258db

Browse files
committed
Resolve upload URL relative to redirected upload creation URL
Fixes an issue mentioned in #10 (comment) which prevented tus-java-client to be able to interact with tus-node-server.
1 parent 865975d commit 43258db

File tree

2 files changed

+42
-1
lines changed

2 files changed

+42
-1
lines changed

src/main/java/io/tus/java/client/TusClient.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,10 @@ public TusUploader createUpload(@NotNull TusUpload upload) throws ProtocolExcept
156156
throw new ProtocolException("missing upload URL in response for creating upload", connection);
157157
}
158158

159-
URL uploadURL = new URL(urlStr);
159+
// The upload URL must be relative to the URL of the request by which is was returned,
160+
// not the upload creation URL. In most cases, there is no difference between those two
161+
// but there may be cases in which the POST request is redirected.
162+
URL uploadURL = new URL(connection.getURL(), urlStr);
160163

161164
if(resumingEnabled) {
162165
urlStore.set(upload.getFingerprint(), uploadURL);

src/test/java/io/tus/java/client/TestTusClient.java

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,44 @@ public void testCreateUploadWithMissingLocationHeader() throws IOException, Exce
102102
}
103103
}
104104

105+
@Test
106+
public void testCreateUplaodWithRelativeLocation() throws Exception {
107+
// We need to enable strict following for POST requests first
108+
System.setProperty("http.strictPostRedirect", "true");
109+
110+
// Attempt a real redirect
111+
mockServer.when(new HttpRequest()
112+
.withMethod("POST")
113+
.withPath("/filesRedirect")
114+
.withHeader("Tus-Resumable", TusClient.TUS_VERSION)
115+
.withHeader("Upload-Length", "10"))
116+
.respond(new HttpResponse()
117+
.withStatusCode(301)
118+
.withHeader("Location", mockServerURL + "Redirected/"));
119+
120+
mockServer.when(new HttpRequest()
121+
.withMethod("POST")
122+
.withPath("/filesRedirected/")
123+
.withHeader("Tus-Resumable", TusClient.TUS_VERSION)
124+
.withHeader("Upload-Length", "10"))
125+
.respond(new HttpResponse()
126+
.withStatusCode(201)
127+
.withHeader("Tus-Resumable", TusClient.TUS_VERSION)
128+
.withHeader("Location", "foo"));
129+
130+
TusClient client = new TusClient();
131+
client.setUploadCreationURL(new URL(mockServerURL + "Redirect"));
132+
TusUpload upload = new TusUpload();
133+
upload.setSize(10);
134+
upload.setInputStream(new ByteArrayInputStream(new byte[10]));
135+
TusUploader uploader = client.createUpload(upload);
136+
137+
// The upload URL must be relative to the URL of the request by which is was returned,
138+
// not the upload creation URL. In most cases, there is no difference between those two
139+
// but it's still important to be correct here.
140+
assertEquals(uploader.getUploadURL(), new URL(mockServerURL + "Redirected/foo"));
141+
}
142+
105143
@Test
106144
public void testResumeUpload() throws ResumingNotEnabledException, FingerprintNotFoundException, IOException, ProtocolException {
107145
mockServer.when(new HttpRequest()

0 commit comments

Comments
 (0)