Issue #1027 - Adding jetty-http version of newer MultiPartParsingTest

Signed-off-by: Joakim Erdfelt <joakim.erdfelt@gmail.com>
This commit is contained in:
Joakim Erdfelt 2018-03-22 10:21:57 -05:00
parent c0dcf9a0a2
commit 2004f0eb78
33 changed files with 1971 additions and 0 deletions

View File

@ -0,0 +1,284 @@
//
// ========================================================================
// Copyright (c) 1995-2018 Mort Bay Consulting Pty. Ltd.
// ------------------------------------------------------------------------
// All rights reserved. This program and the accompanying materials
// are made available under the terms of the Eclipse Public License v1.0
// and Apache License v2.0 which accompanies this distribution.
//
// The Eclipse Public License is available at
// http://www.eclipse.org/legal/epl-v10.html
//
// The Apache License v2.0 is available at
// http://www.opensource.org/licenses/apache2.0.php
//
// You may elect to redistribute this code under either of these licenses.
// ========================================================================
//
package org.eclipse.jetty.http;
import static java.nio.charset.StandardCharsets.UTF_8;
import static org.hamcrest.Matchers.containsString;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.notNullValue;
import static org.junit.Assert.assertThat;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.nio.file.Path;
import java.security.DigestOutputStream;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import javax.servlet.MultipartConfigElement;
import javax.servlet.http.Part;
import org.eclipse.jetty.toolchain.test.Hex;
import org.eclipse.jetty.toolchain.test.MavenTestingUtils;
import org.eclipse.jetty.toolchain.test.TestingDir;
import org.eclipse.jetty.util.IO;
import org.eclipse.jetty.util.QuotedStringTokenizer;
import org.eclipse.jetty.util.StringUtil;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
@RunWith(Parameterized.class)
public class MultiPartParsingTest
{
public static final int MAX_FILE_SIZE = 60 * 1024;
public static final int MAX_REQUEST_SIZE = 1024 * 1024;
public static final int FILE_SIZE_THRESHOLD = 50;
@Parameterized.Parameters(name = "{0}")
public static List<Object[]> data()
{
List<Object[]> ret = new ArrayList<>();
ret.add(new String[]{"multipart-text-files"});
ret.add(new String[]{"multipart-base64"});
ret.add(new String[]{"multipart-base64-long"});
ret.add(new String[]{"multipart-complex"});
ret.add(new String[]{"multipart-duplicate-names-1"});
ret.add(new String[]{"multipart-encoding-mess"});
ret.add(new String[]{"multipart-inside-itself"});
ret.add(new String[]{"multipart-inside-itself-binary"});
ret.add(new String[]{"multipart-number-browser"});
ret.add(new String[]{"multipart-number-strict"});
ret.add(new String[]{"multipart-sjis"});
ret.add(new String[]{"multipart-strange-quoting"});
ret.add(new String[]{"multipart-unicode-names"});
ret.add(new String[]{"multipart-uppercase"});
ret.add(new String[]{"multipart-x-www-form-urlencoded"});
ret.add(new String[]{"multipart-zencoding"});
return ret;
}
@Rule
public TestingDir testingDir = new TestingDir();
private final Path multipartRawFile;
private final MultipartExpectations multipartExpectations;
public MultiPartParsingTest(String rawPrefix) throws IOException
{
multipartRawFile = MavenTestingUtils.getTestResourcePathFile("multipart/" + rawPrefix + ".raw");
Path expectationPath = MavenTestingUtils.getTestResourcePathFile("multipart/" + rawPrefix + ".expected.txt");
multipartExpectations = new MultipartExpectations(expectationPath);
}
@Test
public void testParse() throws IOException, NoSuchAlgorithmException
{
Path outputDir = testingDir.getEmptyPathDir();
MultipartConfigElement config = newMultipartConfigElement(outputDir);
try (InputStream in = Files.newInputStream(multipartRawFile))
{
MultiPartInputStreamParser parser = new MultiPartInputStreamParser(in, multipartExpectations.contentType, config, outputDir.toFile());
parser.parse();
// Evaluate Count
if (multipartExpectations.partCount >= 0)
{
assertThat("Mulitpart.parts.size", parser.getParts().size(), is(multipartExpectations.partCount));
}
// Evaluate expected Contents
for (NameValue expected : multipartExpectations.partContainsContents)
{
Part part = parser.getPart(expected.name);
assertThat("Part[" + expected.name + "]", part, is(notNullValue()));
try (InputStream partInputStream = part.getInputStream())
{
String charset = getCharsetFromContentType(part.getContentType(), UTF_8);
String contents = IO.toString(partInputStream, charset);
assertThat("Part[" + expected.name + "].contents", contents, containsString(expected.value));
}
}
// Evaluate expected filenames
for (NameValue expected : multipartExpectations.partFilenames)
{
Part part = parser.getPart(expected.name);
assertThat("Part[" + expected.name + "]", part, is(notNullValue()));
assertThat("Part[" + expected.name + "]", part.getSubmittedFileName(), is(expected.value));
}
// Evaluate expected contents checksums
for (NameValue expected : multipartExpectations.partSha1sums)
{
Part part = parser.getPart(expected.name);
assertThat("Part[" + expected.name + "]", part, is(notNullValue()));
MessageDigest digest = MessageDigest.getInstance("SHA1");
try (InputStream partInputStream = part.getInputStream();
NoOpOutputStream noop = new NoOpOutputStream();
DigestOutputStream digester = new DigestOutputStream(noop, digest))
{
IO.copy(partInputStream, digester);
String actualSha1sum = Hex.asHex(digest.digest());
assertThat("Part[" + expected.name + "].sha1sum", actualSha1sum, containsString(expected.value));
}
}
}
}
private MultipartConfigElement newMultipartConfigElement(Path path)
{
return new MultipartConfigElement(path.toString(), MAX_FILE_SIZE, MAX_REQUEST_SIZE, FILE_SIZE_THRESHOLD);
}
private String getCharsetFromContentType(String contentType, Charset defaultCharset)
{
if(StringUtil.isBlank(contentType))
{
return defaultCharset.toString();
}
QuotedStringTokenizer tok = new QuotedStringTokenizer(contentType, ";", false, false);
while(tok.hasMoreTokens())
{
String str = tok.nextToken().trim();
if(str.startsWith("charset="))
{
return str.substring("charset=".length());
}
}
return defaultCharset.toString();
}
public static class NameValue
{
public String name;
public String value;
}
public static class MultipartExpectations
{
public final String contentType;
public final int partCount;
public final List<NameValue> partFilenames = new ArrayList<>();
public final List<NameValue> partSha1sums = new ArrayList<>();
public final List<NameValue> partContainsContents = new ArrayList<>();
public MultipartExpectations(Path expectationsPath) throws IOException
{
String parsedContentType = null;
String parsedPartCount = "-1";
try (BufferedReader reader = Files.newBufferedReader(expectationsPath))
{
String line;
while ((line = reader.readLine()) != null)
{
line = line.trim();
if (StringUtil.isBlank(line) || line.startsWith("#"))
{
// skip blanks and comments
continue;
}
String split[] = line.split("\\|");
switch (split[0])
{
case "Content-Type":
parsedContentType = split[1];
break;
case "Parts-Count":
parsedPartCount = split[1];
break;
case "Part-ContainsContents":
{
NameValue pair = new NameValue();
pair.name = split[1];
pair.value = split[2];
partContainsContents.add(pair);
break;
}
case "Part-Filename":
{
NameValue pair = new NameValue();
pair.name = split[1];
pair.value = split[2];
partFilenames.add(pair);
break;
}
case "Part-Sha1sum":
{
NameValue pair = new NameValue();
pair.name = split[1];
pair.value = split[2];
partSha1sums.add(pair);
break;
}
default:
throw new IOException("Bad Line in " + expectationsPath + ": " + line);
}
}
}
Objects.requireNonNull(parsedContentType, "Missing required 'Content-Type' declaration: " + expectationsPath);
this.contentType = parsedContentType;
this.partCount = Integer.parseInt(parsedPartCount);
}
}
class NoOpOutputStream extends OutputStream
{
@Override
public void write(byte[] b) throws IOException
{
}
@Override
public void write(byte[] b, int off, int len) throws IOException
{
}
@Override
public void flush() throws IOException
{
}
@Override
public void close() throws IOException
{
}
@Override
public void write(int b) throws IOException
{
}
}
}

View File

@ -0,0 +1,4 @@
Content-Type|multipart/form-data; boundary="JuH4rALGPJfmAquncS_U1du8s59GjKKiG9a8"
Parts-Count|1
Part-Filename|png|jetty-avatar-256.png
Part-Sha1sum|png|e75b73644afe9b234d70da9ff225229de68cdff8

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,4 @@
Content-Type|multipart/form-data; boundary="8GbcZNTauFWYMt7GeM9BxFMdlNBJ6aLJhGdXp"
Parts-Count|1
Part-Filename|png|jetty-avatar-256.png
Part-Sha1sum|png|e75b73644afe9b234d70da9ff225229de68cdff8

View File

@ -0,0 +1,389 @@
--8GbcZNTauFWYMt7GeM9BxFMdlNBJ6aLJhGdXp
Content-ID: <junk@company.com>
Content-Disposition: form-data; name="png"; filename="jetty-avatar-256.png"
Content-Type: image/png; name=jetty-avatar-256.png
Content-Transfer-Encoding: base64
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
--8GbcZNTauFWYMt7GeM9BxFMdlNBJ6aLJhGdXp--

View File

@ -0,0 +1,9 @@
Content-Type|multipart/form-data; boundary="PMyKOsh8JrSZm-rUF8EJej42yqbh-UWw9FG-"
Parts-Count|6
Part-ContainsContents|pi|3.14159265358979323846264338327950288419716939937510
Part-ContainsContents|company|bob & frank's shoe repair
Part-ContainsContents|power|о𝗋𝖾
Part-ContainsContents|japanese|健治
Part-ContainsContents|hello|ャユ戆タ
Part-Filename|upload_file|filename
Part-Sha1sum|upload_file|e75b73644afe9b234d70da9ff225229de68cdff8

View File

@ -0,0 +1,2 @@
Content-Type|multipart/form-data; boundary="mToTaXZk2RQZb6TrQRLOgqW-44MPpVbs5wyJTlyl"
Parts-Count|10

View File

@ -0,0 +1,4 @@
Content-Type|multipart/form-data; boundary="CVnTR46ddexmZjsh1ORHg9QbCOiLhUYl"
Parts-Count|168
Part-ContainsContents|persian-UTF-8|برج بابل
Part-ContainsContents|persian-CESU-8|برج بابل

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,6 @@
Content-Type|multipart/form-data; boundary="94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-"
Parts-Count|4
Part-ContainsContents|reporter|<user@company.com>
Part-ContainsContents|timestamp|2018-03-21T19:00:18+00:00
Part-ContainsContents|comments|this also couldn't be parsed
Part-ContainsContents|attachment|cherry

View File

@ -0,0 +1,50 @@
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-
Content-Disposition: form-data; name="reporter"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
<user@company.com>
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-
Content-Disposition: form-data; name="timestamp"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
2018-03-21T19:00:18+00:00
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-
Content-Disposition: form-data; name="comments"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
this also couldn't be parsed
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-
Content-Disposition: form-data; name="attachment"
Content-Type: application/octet-stream
Content-Transfer-Encoding: binary
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0v
Content-Disposition: form-data; name="fruit"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
cherry
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0v
Content-Disposition: form-data; name="color"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
red
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0v
Content-Disposition: form-data; name="cost"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
$1.20 USG
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0v
Content-Disposition: form-data; name="comments"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8-
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0v--
--94GJ2MW4vpjh92qj-CHjUUIwb9X8Y2LqkU2Yxn0vTU2oHy5jk6_Kpxn2aE9EokEiRGox4eWfAYP8---

View File

@ -0,0 +1,6 @@
Content-Type|multipart/form-data; boundary="kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x"
Parts-Count|4
Part-ContainsContents|reporter|<user@company.com>
Part-ContainsContents|timestamp|2018-03-21T18:52:18+00:00
Part-ContainsContents|comments|this couldn't be parsed
Part-ContainsContents|attachment|banana

View File

@ -0,0 +1,42 @@
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x
Content-Disposition: form-data; name="reporter"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
<user@company.com>
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x
Content-Disposition: form-data; name="timestamp"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
2018-03-21T18:52:18+00:00
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x
Content-Disposition: form-data; name="comments"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
this couldn't be parsed
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x
Content-Disposition: form-data; name="attachment"
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGj
Content-Disposition: form-data; name="fruit"
banana
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGj
Content-Disposition: form-data; name="color"
yellow
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGj
Content-Disposition: form-data; name="cost"
$0.12 USG
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGj
Content-Disposition: form-data; name="comments"
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGj--
--kCFSwstIsIZkZtQ5JM7193kJYcK5WkyvoxsGjx5eCuVFbaeUZ9oK57JCp_p5wP86S5nY4re5x--

View File

@ -0,0 +1,3 @@
Content-Type|multipart/form-data; boundary="RjYiyHVV9Phv7tYylzT1f94fvTC-s7oNKwB9_Y"
Parts-Count|1
Part-ContainsContents|pi|3.14159265358979323846264338327950288419716939937510

View File

@ -0,0 +1,5 @@
--RjYiyHVV9Phv7tYylzT1f94fvTC-s7oNKwB9_Y
Content-Disposition: form-data; name="pi"
3.14159265358979323846264338327950288419716939937510
--RjYiyHVV9Phv7tYylzT1f94fvTC-s7oNKwB9_Y--

View File

@ -0,0 +1,3 @@
Content-Type|multipart/form-data; boundary="P6Uyk-Vikfbk_NqTfVF4DwNXrIxpN451pD1"
Parts-Count|1
Part-ContainsContents|pi|3.14159265358979323846264338327950288419716939937510

View File

@ -0,0 +1,7 @@
--P6Uyk-Vikfbk_NqTfVF4DwNXrIxpN451pD1
Content-Disposition: form-data; name="pi"
Content-Type: text/plain
Content-Transfer-Encoding: 8bit
3.14159265358979323846264338327950288419716939937510
--P6Uyk-Vikfbk_NqTfVF4DwNXrIxpN451pD1--

View File

@ -0,0 +1,4 @@
Content-Type|multipart/form-data; boundary="VA2isIGmYNkgC3qrrGXnlQcWO17WB3a4npVQey"
Parts-Count|2
Part-ContainsContents|japanese|健治
Part-ContainsContents|hello|ャユ戆タ

View File

@ -0,0 +1,13 @@
--VA2isIGmYNkgC3qrrGXnlQcWO17WB3a4npVQey
Content-Disposition: form-data; name="japanese"
Content-Type: text/plain; charset=Shift_JIS
Content-Transfer-Encoding: 8bit
Œ’Ž¡
--VA2isIGmYNkgC3qrrGXnlQcWO17WB3a4npVQey
Content-Disposition: form-data; name="hello"
Content-Type: text/plain; charset=Shift_JIS
Content-Transfer-Encoding: 8bit
ƒƒƒ†?ƒ^
--VA2isIGmYNkgC3qrrGXnlQcWO17WB3a4npVQey--

View File

@ -0,0 +1,5 @@
Content-Type|multipart/form-data; boundary="tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA"
Parts-Count|4
Part-ContainsContents|and "I" quote|Value 1
Part-ContainsContents|and+%22I%22+quote|Value 2
Part-ContainsContents|value"; what="whoa"|Value 3

View File

@ -0,0 +1,26 @@
--tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA
Content-Disposition: form-data; name="and \"I\" quote"
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Value 1
--tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA
Content-Disposition: form-data; name="and+%22I%22+quote"
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Value 2
--tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA
Content-Disposition: form-data; name="value\"; what=\"whoa\""
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Value 3
--tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA
Content-Disposition: form-data; name="other\";
what=\"Something\""
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Value 4
--tR61vgdxSzzv2FDycET2lt-OUZ1IW1GqA--

View File

@ -0,0 +1,9 @@
Content-Type|multipart/form-data; boundary="ny9C5eIZL7fsfPY9ONPy8Lxb6tkgEv1"
Parts-Count|3
Part-ContainsContents|text|text default
Part-ContainsContents|file1|Content of a.txt
Part-ContainsContents|file2|<!DOCTYPE html><title>Content of a.html
Part-Filename|file1|a.txt
Part-Filename|file2|a.html
Part-Sha1sum|file1|588A0F273CB5AFE9C8D76DD081812E672F2061E2
Part-Sha1sum|file2|9A9005159AB90A6D2D9BACB5414EFE932F0CED85

View File

@ -0,0 +1,23 @@
--ny9C5eIZL7fsfPY9ONPy8Lxb6tkgEv1
Content-Disposition: form-data; name="text"
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
text default
--ny9C5eIZL7fsfPY9ONPy8Lxb6tkgEv1
Content-Type: text/plain; charset=UTF-8
X-SHA1: 588A0F273CB5AFE9C8D76DD081812E672F2061E2
Content-Disposition: form-data; name="file1"; filename="a.txt"
Content-Transfer-Encoding: binary
Content of a.txt
--ny9C5eIZL7fsfPY9ONPy8Lxb6tkgEv1
Content-Type: text/html; charset=UTF-8
X-SHA1: 9A9005159AB90A6D2D9BACB5414EFE932F0CED85
Content-Disposition: form-data; name="file2"; filename="a.html"
Content-Transfer-Encoding: binary
<!DOCTYPE html><title>Content of a.html.</title>
--ny9C5eIZL7fsfPY9ONPy8Lxb6tkgEv1--

View File

@ -0,0 +1,5 @@
Content-Type|multipart/form-data; boundary="1R40qTSaEjDJPcArQiccT7vdpp0l02248R"
Parts-Count|2
Part-ContainsContents|こんにちは世界|Greetings 1
Part-ContainsContents|%E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF%E4%B8%96%E7%95%8C|Greetings 2

View File

@ -0,0 +1,13 @@
--1R40qTSaEjDJPcArQiccT7vdpp0l02248R
Content-Disposition: form-data; name="こんにちは世界"
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Greetings 1
--1R40qTSaEjDJPcArQiccT7vdpp0l02248R
Content-Disposition: form-data; name="%E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF%E4%B8%96%E7%95%8C"
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Greetings 2
--1R40qTSaEjDJPcArQiccT7vdpp0l02248R--

View File

@ -0,0 +1,5 @@
Content-Type|multipart/form-data; boundary="8Q4MHJ3LWIQEQQ_OXYU5U9ZLYEH60_CFZQYANCZ"
Parts-Count|2
Part-ContainsContents|STATE|TEXAS
Part-ContainsContents|CITY|AUSTIN

View File

@ -0,0 +1,13 @@
--8Q4MHJ3LWIQEQQ_OXYU5U9ZLYEH60_CFZQYANCZ
CONTENT-DISPOSITION: FORM-DATA; NAME="STATE"
CONTENT-TYPE: TEXT/PLAIN; CHARSET=WINDOWS-1252
CONTENT-TRANSFER-ENCODING: 8BIT
TEXAS
--8Q4MHJ3LWIQEQQ_OXYU5U9ZLYEH60_CFZQYANCZ
CONTENT-DISPOSITION: FORM-DATA; NAME="CITY"
CONTENT-TYPE: TEXT/PLAIN; CHARSET=WINDOWS-1252
CONTENT-TRANSFER-ENCODING: 8BIT
AUSTIN
--8Q4MHJ3LWIQEQQ_OXYU5U9ZLYEH60_CFZQYANCZ--

View File

@ -0,0 +1,5 @@
Content-Type|multipart/form-data; boundary="qjIkwQOhaYfC2VEcL5j-9sjEK1FIsYMd5"
Parts-Count|1
Part-ContainsContents|company|bob & frank's shoe repair

View File

@ -0,0 +1,7 @@
--qjIkwQOhaYfC2VEcL5j-9sjEK1FIsYMd5
Content-Disposition: form-data; name="company"
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
Content-Transfer-Encoding: 8bit
bob+%26+frank%27s+shoe+repair
--qjIkwQOhaYfC2VEcL5j-9sjEK1FIsYMd5--

View File

@ -0,0 +1,8 @@
Content-Type|multipart/form-data; boundary="UuAU1liVuDVE7wfJUYE72PUF9DZafZ"
Parts-Count|4
Part-ContainsContents|zalgo-8|y͔͕͍o̪̞͎̥͇̤̕u'̛̰̫̳̰v̧̘̪̠̟̟e̥͈̱ ̥̠͇͎͕̜s̤e̺e̙ͅņ̜ ̲̟͝za̴͖̱̲͈̘l͖̖͓̙̮͔g͕̞͖͘o͕̤͈̗ ̯̲̹̲͓b͙͟e̞͎̜̗͈͉̭͞f̸or̰̩e̡̝̺,̸͕̙̥̼͇̜ ̪͇̹r̘̪ͅị͔̥͈ͅg̠̟̯͖̦͇ht͖̪͍͚̖͡?͙̝͖̞
Part-ContainsContents|zalgo-16|y͔͕͍o̪̞͎̥͇̤̕u'̛̰̫̳̰v̧̘̪̠̟̟e̥͈̱ ̥̠͇͎͕̜s̤e̺e̙ͅņ̜ ̲̟͝za̴͖̱̲͈̘l͖̖͓̙̮͔g͕̞͖͘o͕̤͈̗ ̯̲̹̲͓b͙͟e̞͎̜̗͈͉̭͞f̸or̰̩e̡̝̺,̸͕̙̥̼͇̜ ̪͇̹r̘̪ͅị͔̥͈ͅg̠̟̯͖̦͇ht͖̪͍͚̖͡?͙̝͖̞
Part-ContainsContents|zalgo-16-be|y͔͕͍o̪̞͎̥͇̤̕u'̛̰̫̳̰v̧̘̪̠̟̟e̥͈̱ ̥̠͇͎͕̜s̤e̺e̙ͅņ̜ ̲̟͝za̴͖̱̲͈̘l͖̖͓̙̮͔g͕̞͖͘o͕̤͈̗ ̯̲̹̲͓b͙͟e̞͎̜̗͈͉̭͞f̸or̰̩e̡̝̺,̸͕̙̥̼͇̜ ̪͇̹r̘̪ͅị͔̥͈ͅg̠̟̯͖̦͇ht͖̪͍͚̖͡?͙̝͖̞
Part-ContainsContents|zalgo-16-le|y͔͕͍o̪̞͎̥͇̤̕u'̛̰̫̳̰v̧̘̪̠̟̟e̥͈̱ ̥̠͇͎͕̜s̤e̺e̙ͅņ̜ ̲̟͝za̴͖̱̲͈̘l͖̖͓̙̮͔g͕̞͖͘o͕̤͈̗ ̯̲̹̲͓b͙͟e̞͎̜̗͈͉̭͞f̸or̰̩e̡̝̺,̸͕̙̥̼͇̜ ̪͇̹r̘̪ͅị͔̥͈ͅg̠̟̯͖̦͇ht͖̪͍͚̖͡?͙̝͖̞